Mehrspaltiges Layout mit DIVs und CSS
Immer wieder wird die Frage gestellt, wie man ein mehrspaltiges Layout standardkonform mit CSS für moderne Browser erstellen kann. Ja, es gibt schon diverse Beispiele im Netz, aber ich möchte hier mal eine Variante vorstellen, die ich selber des öfteren Nutze.
Inspiriert wurde ich für diese Variante vom Dirk Jesses YAML Framework und seinem Buch "CSS Layouts - Praxislösungen mit YAML 3.0". Diese Varianten nutzt ein bestimmtes verhalten des CSS Floatings aus.
<div id="main">
</div id="col1">
</div id="col2">
</div id="col3">
</div>
Es soll zum Beispiel ein Layout mit drei Spalten erzeugt werden. Zwei schmale Spalten rechts und links und eine breite Content-Spalte in der Mitte. Alle Spalten sollen durch eine senkrechte Linie voneinander getrennt werden.
#col1
{
width: 150px;
float: left;
}
#col2
{
width: 150px;
float: right;
}
#col3
{
margin-left: 150px;
margin-right: 150px;
}
Dieser CSS Code richtet die erste Spalte nach links, die zweite Spalte nach rechts und die dritte Spalte mittig zwischen den beiden ersten aus.
Das Problem das sich jetzt schnell stellen wird ist, dass es nicht ganz einfach ist, alle Spalten auf gleiche Länge zu bringen, bzw. die senkrechten Linien bis ganz nach unten laufen zu lassen, wenn eine der drei Spalten mehr Inhalt hat als die anderen.
Schritt eins für die Senkrechten Trennlinien ist relativ einfach. Da die mittlere Spalte, unsere Inhaltsspalte, in der Regel den meisten Inhalt haben wird, bekommt diese rechts und Links einen Rand von 1px Breite:
#col3
{
margin-left: 150px;
margin-right: 150px;
border-left: solid 1px #000000;
border-right: solid 1px #000000;
}
Die Linien reichen also bis nach unten, wenn die dritte Spalte mehr Inhalt hat. Wenn jetzt allerdings eine der anderen beiden Spalten mehr Inhalt haben, hören die Senkrechten Linien mittendrin auf. Die mittlere Spalte wird nicht bis nach unten aufgedrückt. Eine oft verwendete Lösung ist es, die sogenannten Faux Columns (hier sehr schön von Peter beschrieben) zu verwenden. Die Linien mit einem Hintergrundbild zu erzeugen. In diesem Fall will ich aber die dritte Spalte dazu bringen, sich der Höhe eine der anderen Spalten anzupassen.
Wenn man das Verhalten von floatenden HTML Elementen kennt, ist es ganz einfach, sich dieses Verhalten zu Nutze zu machen: Alle drei Spalten sind floatende Spalten. Die erste nach links, die zweite nach rechts und die dritte (obwohl nicht explizit gesetzt) ebenfalls nach rechts, da sich das floating (entgegen allen anderen CSS Vererbungsregeln) auf allen folgenden Elementen fortsetzt, bis man irgendwo in die andere Richtung floatet oder mit clear:both das floating ganz aufhebt.
Ich könnte also am Ende der dritten Spalte ein Element einfügen, welches das floating aufhebt:
<div id="main">
</div id="col1">
</div id="col2">
<div id="col3">
</div id="clearing">
</div>
</div>
#clearing
{
clear: both;
}
Es passiert genau das erwartete: Das neue Element floatet nicht mehr und wird unterhalb des längsten floatenden Elements neu ausgerichtet. Da es sich innerhalb der dritten Spalte befindet, zieht es diese nach unten auf. Die dritte Spalte wird also so lang wie die längste der vorigen Spalten.
Aus irgend einem Grund gibt es im IE noch Darstellungsprobleme, wenn in der dritten Spalte Text markiert wird. Die rahmen werden während dem Markieren einfach entfernt, sie lösen sich auf. Das wird behoben, wenn man in dieser Spalten explizit eine Hintergrundfarbe (hier weiß) setzt und das clearing-DIV explizit auf eine Breite von 100% setzt.
#col3
{
margin-left: 150px;
margin-right: 150px;
border-left: solid 1px #000000;
border-right: solid 1px #000000;
background-color:#FFFFFF;
}
#clearing
{
clear: both;
width: 100%;
}
Auf ein weiteres Problem stößt man, wenn man die beiden seitlichen Spalten anders einfärben möchte. Die erste und zweite Spalte können nicht direkt eingefärbt werden, da in Wirklichkeit nicht alle Spalten gleich lang sind, sondern nur die dritte sich der längsten Spalte anpasst. Ist die dritte Spalte die längste, hören die anderen Beiden vorher auf. Die eingefärbten Bereiche würden also nicht bis nach unten durchgehen.
Auch hier helfen wieder die Faux Columns oder zwei weitere Tricks.
1) Man setzt die Hintergrundfarbe des übergeordneten Elements. Der Vorteil ist die Einfachheit, man muss die Farbe nur einmal setzen. Der Nachteil ist, dass nicht jede Spalte eine eigene Farbe haben kann.
2) Man nutzt wieder die dritte Spalte aus. Man entfernt einfach die margin-Angaben und setzt die Breite der rechten und Linken Rahmen auf die Breite der rechten und linken Spalte und gibt jedem Rahmen die gewünschte Farbe. Das ist alles:
#col1
{
width: 150px;
float: left;
}
#col2
{
width: 150px;
float: right;
}
#col3
{
border-left: solid 150px red;
border-right: solid 150px green;
background-color:#FFFFFF;
}
Diese Variante wird von IE7, Opera 9.51, FireFox 3.0.1 und Chrome 0.2 (*g*) unterstützt. Wer ganz sicher gehen möchte und Exoten, sowie ältere Browser unterstützen möchte, sollte auf das YAML Framework zurückgreifen, das noch viele weitere Tricks und Hacks beinhaltet.
Zwei Beispiele sind hier zu finden: floatingcolumsn.zip