css Navigation, Linien setzen
Pit
- css
Hallo,
ich komme an einer Stelle mit meiner Formatierung nicht weiter und befürchte, dass mein Konzept bereits einen grundsätzlichen Fehler enthält.
Ich möchte die Navigation mit einer dünnen Linie umranden, die an den Enden abgerundete Ecken hat und die die einzelnen Navigationspunkte mit einer Trennlinie voneinander trennt. Das Menü soll rechtsbündig sein. Und es soll ein Formular sein, die einzelnen Menüpunkte sollen rahmenlose Buttons sein.
Nun geht aber der Rahmen über die komplette Seite und die Trennlinien zwischen den Menüpunkten schaff ich auch nicht.
Kann mir jemand dabei helfen?
Pit
Hallo Pit,
die Trennlinien bekommst Du mit
.navButton {
border: none;
border-left: 1px solid #cecece;
}
.navButton:first-of-type {
border: none;
}
Bei deinem Markup funktioniert auch das hier:
.navButton {
border: none;
}
.navButton+.navButton {
border-left: 1px solid #cecece;
Den Rahmen kannst Du z.B. verkleinern, indem Du das Form (also #navlinks) mit display:inline-block
darstellst, dann ist es nur so groß wie nötig.
Das nav Element geht dann aber immer noch (unsichtbar) über die ganze Breite; wenn das dein Layout nicht stört, ist es ok, andernfalls muss man nochmal überlegen.
Rolf
Hi Rolf,
vielen Dank für Deine Hilfe.
Den Rahmen kannst Du z.B. verkleinern, indem Du das Form (also #navlinks) mit
display:inline-block
darstellst, dann ist es nur so groß wie nötig.Das nav Element geht dann aber immer noch (unsichtbar) über die ganze Breite; wenn das dein Layout nicht stört, ist es ok, andernfalls muss man nochmal überlegen.
Doch, das stört leider durchaus. 😟 Ich hätte am liebesten 3 Bereiche dort. Und rechts wäre halt diese Navigation. Was kann ich denn da machen? Grid-Layout? Oder ist das "overdressed" hierfür?
Pit
Hallo Pit,
statt vertical-align und padding-right solltest Du vielleicht besser ein rundum-Padding verwenden, damit die Striche auch genau zwischen den Buttontexten stehen. Zum Beispiel padding: 2px 5px;
. Wenn Dir dann der Abstand zum Form-Rand zu klein ist, gib dem Form auch noch ein Padding (z.B. padding: 0 5px
).
Und border-radius an den Buttons führt dazu, dass die Trennlinien abgerundet sind, willst Du das? Wenn nicht, musst du diese Eigenschaft bei .navButton
wegnehmen.
Rolf
Hi Rolf,
Und border-radius an den Buttons führt dazu, dass die Trennlinien abgerundet sind, willst Du das? Wenn nicht, musst du diese Eigenschaft bei
.navButton
wegnehmen.
Eigentlich wollte ich Beides:
Am Rand abgerundet und die Trennlinien ohne Rundung.
Pit
Hallo Pit,
in der Fiddle-Version 4 hast Du aber was in den falschen Hals bekommen.
#navlinks:first-child {
border-top-left-radius: 6px;
border-bottom-left-radius: 6px;
}
#navlinks:last-child {
border-top-right-radius: 6px;
border-bottom-right-radius: 6px;
}
die Pseudoklassen :first-child und :last-child identifizieren Elemente, die in der children-Liste ihres Elternelementes an erster bzw. letzter Stelle stehen. Du wendest sie auf das form-Element #navlinks an, das einziges Kind des nav Element ist. D.h. beide Regeln treffen auf das form zu. Das kannst Du einfacher haben - und so hattest Du es ja auch ursprünglich:
#navlinks {
border-radius: 6px;
}
Was Du vermutlich WOLLTEST, war, am linken Link die linke Seite abzurunden und am rechten Link die rechte Seite. Dazu hättest Du eine Leerstelle zwischen #navlinks und :first-child bzw. :last-child machen müssen, eine Leerstelle ist der "ist Kind von" Selektor.
Aber das nützt Dir nichts. Wenn Du den Rand auf die Links verlegst, kommst Du mit der inline Logik in Konflikt, die Leerstellen nicht entfernt. Links und Buttons sind inline-Elemente (deswegen landen sie nebeneinander), und darum haben sie auch ohne Margin einen Abstand. Ein Rand auf den Links wäre deshalb nicht durchgehend.
Es ist daher sinnvoll (und auch logischer), den Rand und die Rand-Abrundung auf den Link-Container zu legen. Das hattest Du in deiner ersten Version völlig richtig.
Und wie du den Trennstrich zwischen die Buttons machst, hatte ich Dir doch erklärt. Du hättest nur den Buttons den border-radius wegnehmen müssen, damit der Trennstrich gerade ist.
Ich bastele aber nochmal etwas, um dir zu zeigen wie man mit flexbox gut um die Kurve kommt.
Rolf
Hallo Rolf,
Ich weiß gar nicht genau, wo ich ansetzen soll, aber ich fang mal hier an:
Was Du vermutlich WOLLTEST, war, am linken Link die linke Seite abzurunden und am rechten Link die rechte Seite. Dazu hättest Du eine Leerstelle zwischen #navlinks und :first-child bzw. :last-child machen müssen, eine Leerstelle ist der "ist Kind von" Selektor.
Das muß ich mir morgen mal genauer durchlesen, bzw. nähere Infos hierzu besorgen. Aber mal kurz nachgefragt: Das Ergebniss passte doch, oder?
Aber das nützt Dir nichts. Wenn Du den Rand auf die Links verlegst, kommst Du mit der inline Logik in Konflikt, die Leerstellen nicht entfernt. Links und Buttons sind inline-Elemente (deswegen landen sie nebeneinander), und darum haben sie auch ohne Margin einen Abstand. Ein Rand auf den Links wäre deshalb nicht durchgehend.
Ach herrje… Da blick ich nimmer durch, muß ich morgen drüber nachdenken.
Es ist daher sinnvoll (und auch logischer), den Rand und die Rand-Abrundung auf den Link-Container zu legen. Das hattest Du in deiner ersten Version völlig richtig.
Und wie du den Trennstrich zwischen die Buttons machst, hatte ich Dir doch erklärt. Du hättest nur den Buttons den border-radius wegnehmen müssen, damit der Trennstrich gerade ist.
Achso, ok. Jetzt versteh ich zumindest diesen Part.
Ich bastele aber nochmal etwas, um dir zu zeigen wie man mit flexbox gut um die Kurve kommt.
Sehr gerne, freu' ich mich drauf. Trotzdem muß ich ggf. morgen nochmal zu den anderen Punkten nachfrage, ich würde die gan z gerne verstehen...davon bin ich derzeit noch etwas entfernt… Danke! auf jeden Fall für die Erklärungen und die Mühe, die Du Dir machst.
Pit
Hallo Pit,
ja ok, ich hab mal wieder viele Dinge gleichzeitig erklärt 😀
Es ist tatsächlich ein Unterschied, ob man im CSS einen Selektor nav.foo
oder nav .foo
schreibt. Die blöde Leerstelle ändert die Bedeutung, sie ist in den CSS-Regeln als eigenes Syntax-Element aufgeführt: der Nachfahren-Selektor. Deswegen trifft der erste Selektor ein nav-Element mit class="foo", der zweite ein Element mit class="foo", das Kind eines nav-Elements ist.
Die Inline-Story habe ich Dir mal hier visualisiert: https://jsfiddle.net/38zur9kn/. span-Elemente sind inline-Elemente und folgen deshalb der inline-Logik: Wenn dazwischen Leerraum ist, bleibt er erhalten. Deswegen sind die spans der ersten Zeile bündig und die der zweiten Zeile nicht. Ist das div ein Flex-Container, sieht die Sache anders aus. Nun gelten die Regeln der Flexbox und die span-Elemente werden flex-Elemente. Der Leerraum wird ignoriert.
Deswegen schrieb ich, dass ein durchgehender Rand um die Navigation nur sinnvoll funktioniert, wenn Du den Rahmen auf das nav Element legst und nicht auf dessen Kind-Elemente.
Und zum Abschluss noch das Fiddle, das einen Header mit deiner Navigation drin zeigt, einmal mit Flexbox und einmal mit Grid gemacht. Die Grid-Lösung hängt den Internet-Explorer und ältere Edge-Browser ab, da musst Du noch ein paar -ms- Prefixeinträge nachlegen.
Rolf
Hi,
Es ist tatsächlich ein Unterschied, ob man im CSS einen Selektor
nav.foo
odernav .foo
schreibt. Die blöde Leerstelle ändert die Bedeutung, sie ist in den CSS-Regeln als eigenes Syntax-Element aufgeführt: der Nachfahren-Selektor. Deswegen trifft der erste Selektor ein nav-Element mit class="foo", der zweite ein Element mit class="foo", das Kind eines nav-Elements ist.
Nicht nur Kind, sondern beliebiger Nachfahre.
cu,
Andreas a/k/a MudGuard
Hallo Rolf,
diesmal den Dank gleich vorab, damit ichs nachher nicht vergesse. Find' ich wirklich einzigartig klasse, wieviel Mühe Du Dir gibst!
Ich hoffe, Du bist nicht allzu enttäuscht, wenn ichs immer noch nicht ganz gerafft habe - ich bin aber schon näher dran und bemühe mich weiter.
Das mit dem Nachfahrenselector verstehe ich inzwischen. An Block- und Inlineelementen arbeite ich gerade noch.
Und border-radius an den Buttons führt dazu, dass die Trennlinien abgerundet sind, willst Du das? Wenn nicht, musst du diese Eigenschaft bei
.navButton
wegnehmen.
Ich wolte gerade gegenteiliges berichten, so schlecht sieht man (oder zumindest ich ohne Lesebrille) das 😉, aber Du hast (wie sooft recht), wenn ich über strg+ das Bild vergrößere, erkenne auch ich, dass es immer noch abgerundete Linien sind.
Das nav Element geht dann aber immer noch (unsichtbar) über die ganze Breite; wenn das dein Layout nicht stört, ist es ok, andernfalls muss man nochmal überlegen.
Mein erster Versuch, dieses Problem zu lösen.
Die Inline-Story habe ich Dir mal hier visualisiert..
Habe ich studiert, danke dafür.
Und zum Abschluss noch das Fiddle, das einen Header mit deiner Navigation drin zeigt, einmal mit Flexbox und einmal mit Grid gemacht. Die Grid-Lösung hängt den Internet-Explorer und ältere Edge-Browser ab, da musst Du noch ein paar -ms- Prefixeinträge nachlegen.
Diesen Fiddle hätte ich mir gerne angesehen. Kann es sein, dass Du die Verlinkung vergessen hast?
Gruß, Pit
Hallo Pit,
ja, hab ich vergessen. War ein Wegwerf-Fiddle und nicht in meinem jsFiddle-Profil; aber mein Browserverlauf hat mich gerettet:
https://jsfiddle.net/kxmztnfb/1/
Rolf
@@Pit
ich komme an einer Stelle mit meiner Formatierung nicht weiter und befürchte, dass mein Konzept bereits einen grundsätzlichen Fehler enthält.
So ist es. Eine Navigation ist kein Formular. Du möchtest Links verwenden.
LLAP 🖖
Hi Gunnar,
So ist es. Eine Navigation ist kein Formular. Du möchtest Links verwenden.
Wenns das alleine ist, kann ich damit leben. Ich habe die Links durch Buttons ersetzt, weil ich die Parameter via POST übermitteln wollte.
Pit
Hallo Pit,
ob es ein Button oder ein Link ist, klärt sich anhand der Frage, ob du eine Operation auf der gleichen Seite ausführst (neuer Listeneintrag, Eintrag löschen) oder ob Du die Seite wechselst. Dabei ist auch der Aufruf der gleichen Serverressource, aber mit anderen Parametern, ein Seitenwechsel.
Die Frage, ob es ein POST oder GET ist, den Du machen musst, klärt sich mit der Überlegung, ob der Server-Request Daten verändert oder nur Daten abruft. Abruf=GET, Änderung=POST. Diese Semantik kannst Du Dir nicht aussuchen. Ergebnisse von GET-Requests dürfen gecached werden, die von POST-Requests nicht. Und ein „Zurück“ im Browser auf eine Seite, die das Ergebnis eines POST ist, löst eine Browserwarnung aus, dass man ggf. Daten erneut senden würde. Sowas tut man nicht ohne Not.
Da nur Du die genaue Funktion deiner Steuerelemente kennst, musst Du für Dich entscheiden, was angemessen ist. Es ist jedenfalls riskant für eine gute UX, wenn man Abfragen und Änderungsfunktionen nebeneinander in einer Liste hat, wenn 5 Knöpfe nebeneinander liegen und einer davon Daten löscht, kann das zu ungewollten Bedienungen führen. Deswegen trennt man das besser.
Du kannst übrigens Anker-Elemente zur gleichen Seite zeigen lassen, indem Du unter href sowas wie "?action=foo"
angibst. Tust Du das auf der Seite bar.php
, ruft der Browser bar.php?action=foo
auf.
Rolf