C# Ich kriegs nicht hin - Problem mit Stack

Atreju93

Lieutenant
Registriert
Nov. 2010
Beiträge
596
Hallo zusammen

Ich düftle nun mehr schon seit 3 Tagen an diesem Problem und komme nicht weiter.

Ich habe einen kleinen Browser programmiert mit einem Vor und Zurückbutton. Immer wenn ich eine Adresse eingebe und auf "go" klicke wird die im Adressfeld eingegebene Adresse geladen und die Adresse auf den einen Stack (für Zurück) gelegt.

Der Code zum Button "Go"
Code:
 // Funktion zum Navigieren - wurde hier in einem Click - Event verpackt. 
        private void button_go_Click(object sender, EventArgs e)
        {
            webBrowser1.Navigate(new Uri(textBox_url.Text));
            BackHistory.Push(webBrowser1.Url);
        }

Jetzt wenn man auf zurück klickt sollte es immer ein Objekt vom Stack nehmen (BackHistory.Peek() ) - diese Seite laden und dann auf den Anderen Stack laden (ForHistory.Push(BackHistory.Pop()), damit mann wider "vorwärts" kann.

Leider habe ich ganz komische Phänomene - ich komme auch nicht dahinter was nicht stimmt. Wenn ich auf zurück klicke sagt es mir z.b. dass ich schon am Anfang bin - obwohl dies nicht stimmt - vorwärts geht es gar nicht (lädt nur die aktuelle Seite) usw. Ich kann keine Systematik herausfinden.

hier der Code zu den beiden Buttons:

Code:
        private void button_zurueck_Click(object sender, EventArgs e)
        {
            BackHistory.Pop();
            MessageBox.Show(Convert.ToString(BackHistory.Count));
            MessageBox.Show(Convert.ToString(BackHistory.Peek()));
            try
            {
                webBrowser1.Navigate(BackHistory.Peek());
                ForHistory.Push(BackHistory.Peek());
            }
            catch (System.InvalidOperationException)
            {
                MessageBox.Show("Anfang Erreicht");
                BackHistory.Push(webBrowser1.Url);
                webBrowser1.Navigate(BackHistory.Peek());
            }
            catch (System.UriFormatException)
            {
                MessageBox.Show("Anfang Erreicht");
                BackHistory.Push(webBrowser1.Url);
                webBrowser1.Navigate(BackHistory.Peek());
            }
        }

        private void button_vor_Click(object sender, EventArgs e)
        {
            MessageBox.Show(Convert.ToString(ForHistory.Count));
            MessageBox.Show(Convert.ToString(ForHistory.Peek()));
            try
            {
                ForHistory.Pop();
                webBrowser1.Navigate(ForHistory.Peek());
                ForHistory.Push(BackHistory.Peek());
            }
            catch (System.InvalidOperationException)
            {
                MessageBox.Show("Anfang Erreicht");
                ForHistory.Push(webBrowser1.Url);
                webBrowser1.Navigate(ForHistory.Peek());
            }
            catch (System.UriFormatException)
            {
                MessageBox.Show("Anfang Erreicht");
                ForHistory.Push(webBrowser1.Url);
                webBrowser1.Navigate(ForHistory.Peek());
            }
        }

Sieht jemand von euch an was es hapert?

EDIT:

Ganz genau genommen Funktioniert der Zurückbutton jetzt einigermassen.
wenn ich jedoch von der Startseite (www.google.ch) eine andere Adrese eingebe und lade, kann ich zwar wider zurück, jedoch nicht mehr vorwärts - es legt mir immer nur www.google.ch in den Stack für Vorwärts (ForHistory). Somit bleibe ich bei Google hängen.
 
Zuletzt bearbeitet:
Code:
 // Funktion zum Navigieren - wurde hier in einem Click - Event verpackt. 
        private void button_go_Click(object sender, EventArgs e)
        {
            webBrowser1.Navigate(new Uri(textBox_url.Text));
            BackHistory.Push(webBrowser1.Url);
        }
Ist die Reihenfolge der beiden Befehle hier nicht falschrum? So legst du ja die neue URL auf den Stack und nicht die alte.


Code:
        private void button_zurueck_Click(object sender, EventArgs e)
        {
            BackHistory.Pop();
            MessageBox.Show(Convert.ToString(BackHistory.Count));
            MessageBox.Show(Convert.ToString(BackHistory.Peek()));
            try
            {
                webBrowser1.Navigate(BackHistory.Peek());
                ForHistory.Push(BackHistory.Peek());
            }
            catch (System.InvalidOperationException)
            {
                MessageBox.Show("Anfang Erreicht");
                BackHistory.Push(webBrowser1.Url);
                webBrowser1.Navigate(BackHistory.Peek());
            }
            catch (System.UriFormatException)
            {
                MessageBox.Show("Anfang Erreicht");
                BackHistory.Push(webBrowser1.Url);
                webBrowser1.Navigate(BackHistory.Peek());
            }
        }
Die Methode Pop() liefert das oberste Element zurück. Du brauchst hier also garnicht mit Peek() arbeiten.
 
pop holt ja ein element vom stack
wenn du danach "webBrowser1.Navigate(BackHistory.Peek());" aufrufst schaut er wieder auf das vorige... also zwei stufen in die vergangenheit.
du solltest mit Pop das letzte element holen und dir temporär speichern und dann damit weitermachen....
 
Was sind denn ForHistory und BackHistory für Klassen (bzw: welche Typen haben sie... wenn es keine Klassen sind, dann bitte mal die Schreibweise "korrigiere"...)

@the_nobs: So würde ich es auch sagen - pop holt das letzte Element und entfernt es...
 
BackHistory und ForHistory sind beide Stacks

So Definiert:
Code:
        //Stack für History anlegen (Zurück)
        Stack<Uri> BackHistory = new Stack<Uri>(15);
        //Stack für History Vorwärts anlegen
        Stack<Uri> ForHistory = new Stack<Uri>(15);

Dass Pop entfernt und ausgibt, Peek nur ausgibt und Push eines darauf legt weiss ich.

Beim Zurück muss ich zuerst das oberste Element löschen - sonst lädt es die aktuelle Seite ja nochmals - da ich sie auf dem Stack abgelege, sobald ich dazu navigiere.
Theoretisch nur das erste mal - habe ich hier provisorisch etwas unglücklich implementiert - somit überspringt es immer eine Seite - ist jedoch unerheblich, dass vorwärts nicht geht..
 
Code:
webBrowser1.Navigate(new Uri(textBox_url.Text));
BackHistory.Push(webBrowser1.Url);

Obiger Code ist falsch, es sei denn, du hast die neue Lightspeed-Leitung der Telekom.
Navigate wird asynchron ausgeführt. Was du machst ist die aktuelle Url auf den Stack zu pushen. Nach dem der Browser fertig ist mit laden, kannst du über Url die aktuell angezeigte Seite abrufen.
 
Das die aktuelle Url im "Zurück"-Stack liegt, ist etwas verwirrend. Die aktuelle Url steht ja in webBrowser1 und sollte daher in keinem der beiden Stacks liegen. Erst wenn du z.B. zurück gehst, schiebst du die aktuelle URL ab den "Vor"-Stack und ziehst dir die oberste vom "Zurück"-Stack und lädst diese. So umgehst du auch das von holy geschilderte Problem.
 
Dennoch muss doch bei zurück die Seite auf den Vorwärts-Stack, die vom Zurück-Stack kommt...

Und bitte an Konventionen halten was Schreibweise von Elementen angeht, das hilfft...
 
Also ich würds mir ja einfach machen und die History nicht in 2 Stacks speichern, sondern in einer List<Uri> und mir einfach den Index des aktiven Elements merken. So muss man nicht 2 Stacks verwalten und Elemente nicht immer hin und her schieben.
 
Ich könnte mich manchmal erhängen...

Ich habs mittlerweile hingekriegt:

Webbrowser1.GoForward();

Sowie Webbrowser1.GoBack();

Haben völlig genügt...
 
Zurück
Oben