public void Navigate(string uriString)
        {
            _isNavigating = true;

            bool cancelled = false;

            var uri = new Uri(uriString);

            var normalisedUri = UriTester.NormaliseUri(uri);

            var siteIdentity = new SiteIdentity(normalisedUri, Session.Instance);

            var fullQuery = normalisedUri.OriginalString;

            //sanity check we have a valid URL syntax at least
            if (normalisedUri.Scheme == null)
            {
                ToastNotify("Invalid URL: " + normalisedUri.OriginalString, ToastMessageStyles.Error);
                cancelled = true;
            }

            ToggleContainerControlsForBrowser(false);

            //these are the only ones we "navigate" to. We do this by downloading the GMI content
            //converting to HTML and then actually navigating to that.
            if (normalisedUri.Scheme == "gemini")
            {
                var geminiNavigator = new GeminiNavigator(this);
                cancelled = geminiNavigator.NavigateGeminiScheme(fullQuery, uri, siteIdentity);
            }
            else if (normalisedUri.Scheme == "gopher")
            {
                var gopherNavigator = new GopherNavigator(this);
                cancelled = gopherNavigator.NavigateGopherScheme(fullQuery, uri, siteIdentity);
            }
            else if (normalisedUri.Scheme == "about")
            {
                var aboutNavigator = new AboutNavigator(this);
                cancelled = aboutNavigator.NavigateAboutScheme(uri, siteIdentity);
            }
            else if (normalisedUri.Scheme.StartsWith("http"))       //both http and https
            {
                //detect ctrl click
                if (_settings.HandleWebLinks == "System web browser")
                {
                    //open in system web browser
                    var launcher = new ExternalNavigator(this);
                    launcher.LaunchExternalUri(uri.ToString());
                    ToggleContainerControlsForBrowser(true);
                    cancelled = true;
                }
                else if (_settings.HandleWebLinks == "Gemini HTTP proxy")
                {
                    // use a gemini proxy for http links
                    var geminiNavigator = new GeminiNavigator(this);
                    cancelled = geminiNavigator.NavigateGeminiScheme(fullQuery, uri, siteIdentity);
                }
                else
                {
                    //use internal navigator
                    var httpNavigator = new HttpNavigator(this);
                    cancelled = httpNavigator.NavigateHttpScheme(fullQuery, uri, siteIdentity, "web-launch-external");
                }
            }
            else if (normalisedUri.Scheme == "file")
            {
                //just load the converted html file
                //no further action.

                BrowserControl.Text = File.ReadAllText(normalisedUri.LocalPath);
            }
            else
            {
                //we don't care about any other protocols
                //so we open those in system web browser to deal with
                var launcher = new ExternalNavigator(this);
                launcher.LaunchExternalUri(uri.ToString());
                ToggleContainerControlsForBrowser(true);
                cancelled = true;
            }

            if (!cancelled)
            {
                uriString = uri.ToString();

                //look up the URL that this HTML page shows
                var regex = new Regex(@".*/([a-f0-9]+)\.(.*)");
                if (regex.IsMatch(uriString))
                {
                    var match = regex.Match(uriString);
                    var hash  = match.Groups[1].ToString();

                    string geminiUrl = _urlsByHash[hash];
                    if (geminiUrl != null)
                    {
                        //now show the actual gemini URL in the address bar
                        txtUrl.Text = geminiUrl;

                        ShowTitle(BrowserControl);

                        var originalUri = new UriBuilder(geminiUrl);

                        if (originalUri.Scheme == "http" || originalUri.Scheme == "https")
                        {
                            ShowLinkRenderMode(BrowserControl.Text);
                        }
                    }

                    //if a text file (i.e. view->source), explicitly set the charset
                    //to UTF-8 so ascii art looks correct etc.
                    if ("txt" == match.Groups[2].ToString().ToLower())
                    {
                        //set text files (GMI source) to be UTF-8 for now
                        HtmlPanelExtensions.SetCharsetUtf8(BrowserControl.Text);
                    }
                }

                BrowserControl.Focus();

                ShowTitle(BrowserControl);

                //we need to turn on/off other elements so focus doesnt move elsewhere
                //in that case the keyboard events go elsewhere and you have to click
                //into the browser to get it to work again
                //see https://stackoverflow.com/questions/8495857/webbrowser-steals-focus
                ToggleContainerControlsForBrowser(true);
            }

            _isNavigating = false;
        }
Example #2
0
        private void BrowserControl_Navigating(object sender, NavigatingCancelEventArgs e)
        {
            _isNavigating = true;

            var normalisedUri = UriTester.NormaliseUri(e.Uri);

            var siteIdentity = new SiteIdentity(normalisedUri, Session.Instance);

            var fullQuery = normalisedUri.OriginalString;

            //sanity check we have a valid URL syntax at least
            if (e.Uri.Scheme == null)
            {
                ToastNotify("Invalid URL: " + normalisedUri.OriginalString, ToastMessageStyles.Error);
                e.Cancel = true;
            }

            var settings = new UserSettings();

            ToggleContainerControlsForBrowser(false);

            //these are the only ones we "navigate" to. We do this by downloading the GMI content
            //converting to HTML and then actually navigating to that.
            if (normalisedUri.Scheme == "gemini")
            {
                var geminiNavigator = new GeminiNavigator(this, this.BrowserControl);
                geminiNavigator.NavigateGeminiScheme(fullQuery, e, siteIdentity);
            }
            else if (normalisedUri.Scheme == "nimigem")
            {
                var nimigemNavigator = new NimigemNavigator(this, this.BrowserControl);

                var document = (HTMLDocument)BrowserControl.Document;

                var firstTextarea = (IHTMLTextAreaElement)document.getElementsByTagName("textarea").item(0);

                string payload;
                if (firstTextarea != null)
                {
                    payload = firstTextarea.value;
                }
                else
                {
                    payload = "";
                }

                nimigemNavigator.NavigateNimigemScheme(fullQuery, e, payload);
            }
            else if (normalisedUri.Scheme == "gopher")
            {
                var gopherNavigator = new GopherNavigator(this, this.BrowserControl);
                gopherNavigator.NavigateGopherScheme(fullQuery, e, siteIdentity);
            }
            else if (normalisedUri.Scheme == "about")
            {
                var aboutNavigator = new AboutNavigator(this, this.BrowserControl);
                aboutNavigator.NavigateAboutScheme(e, siteIdentity);
            }
            else if (normalisedUri.Scheme.StartsWith("http"))       //both http and https
            {
                var linkId = "";
                ////doc might be null - you need to check when using!
                var doc = (HTMLDocument)BrowserControl.Document;
                ////this is how we could detect a click on a link to an image...
                if (doc?.activeElement != null)
                {
                    linkId = doc.activeElement.id;
                }

                //detect ctrl click
                if (
                    Keyboard.IsKeyDown(Key.LeftCtrl) ||
                    Keyboard.IsKeyDown(Key.RightCtrl) ||
                    settings.HandleWebLinks == "System web browser" ||
                    linkId == "web-launch-external"
                    )
                {
                    //open in system web browser
                    var launcher = new ExternalNavigator(this);
                    launcher.LaunchExternalUri(e.Uri.ToString());
                    ToggleContainerControlsForBrowser(true);
                    e.Cancel = true;
                }
                else if (settings.HandleWebLinks == "Gemini HTTP proxy")
                {
                    // use a gemini proxy for http links
                    var geminiNavigator = new GeminiNavigator(this, this.BrowserControl);
                    geminiNavigator.NavigateGeminiScheme(fullQuery, e, siteIdentity);
                }
                else
                {
                    //use internal navigator
                    var httpNavigator = new HttpNavigator(this, this.BrowserControl);
                    httpNavigator.NavigateHttpScheme(fullQuery, e, siteIdentity, linkId);
                }
            }
            else if (normalisedUri.Scheme == "file")
            {
                //just load the converted html file
                //no further action.
            }
            else
            {
                //we don't care about any other protocols
                //so we open those in system web browser to deal with
                var launcher = new ExternalNavigator(this);
                launcher.LaunchExternalUri(e.Uri.ToString());
                ToggleContainerControlsForBrowser(true);
                e.Cancel = true;
            }

            if (e.Cancel)
            {
                _isNavigating = false;
            }
        }