Malleus' Tutorials:
Web Forms 2.0

Version: 0.7 ( 14.07.2006 )

© Frank Hammerschmidt

Forum  - Javascript Spiele - Javascript FAQ -  Impressum


Die Zukunft des Web-Formulars hat begonnen!

Die "WHATWG" ( Web Hypertext Application Technology Working Group ) Spezifikation

Web Forms 2.0

befindet sich kurz vor der Fertigstellung.

Sie befaßt sich mit Neuerungen bezüglich der Web-Formulare und wurde unter anderem von Entwicklern von Opera, Mozilla und Safari festgelegt.

"Opera 9" hat bereits einen Großteil dieser Spezifikation implementiert. Wenn Du ihn installiert hat, kannst Du Dir jetzt schon ansehen, was "bald" standardmäßig von allen Browsern unterstützt wird.

Viel Spaß damit!

Inhaltsangabe


 

1. Neue "INPUT"-Types

In "Web Forms 2.0" werden "getypte" "INPUT"-Controls eingeführt, die beim "Abschicken" des Formulars automatisch validiert werden. Gib' doch einfach mal etwas Falsches ein und wundere Dich:
<input type="email" name="myEmail">
<input type="url" name="myUrl">

email: 
url: 
Zur einfacheren Bedienbarkeit werden zahlreiche Eingabehilfen eingeführt:
<input type="datetime" name="myDateTime">
<input type="datetime-local" name="myLocalDateTime">
<input type="date" name="myDate">
<input type="month" name="myMonth">
<input type="week" name="myWeek">
<input type="time" name="myTime">
<input type="number" name="myNumber">

datetime
datetime-local
date
month
week
time
number
<input type="range" name="myRange1" min="0" max="100" step="10" value="50"
           style="height:20px;width:100px">
<input type="range" name="myRange2" min="0" max="100" step="20" value="40"
           style="height:100px;width:20px">

"Pflichtfelder" können durch das neue Attribute "required" gekennzeichnet werden. Ist eines der Pflichtfelder beim "Senden" leer, wird eine browserspezifische Fehlermeldung ausgegeben und das Verschicken des Formulars wird abgebrochen.
<input type="number" name="myNumber" required="required">

 

2. Wertbereiche

Des Weiteren ist es möglich, Wertbereiche zu definieren: "Min", "Max" und die Schrittweite "step". Der dazugehörige Wert wird dann mit Hilfe der Pfeiltasten entsprechend umgestellt. Wird nun ein Wert "von Hand" eingeben, der nicht in den Wertebereich passt, wird beim Senden der Fehler "rangeOverflow" bzw. "rangeUnderflow" angezeigt. Hierbei ist zu beachten, daß auch ein Fehler in der "Schrittweite" fehlerhaft ist, d.h. wenn als Schrittweite "10" spezifiziert wurde, liefert der Wert "111" einen "stepMismatch" Fehler. In diesem Fall ist der "Working Draft" etwas "schwammig": "Anscheinend" darf der Browser den Wert auf einen gültigen Wert "runden". Im Falle des Opera 9 wird jedoch die Fehlermeldung ausgegeben.
<input type="number" name="myNumber" value="150" min="100" max="200" step="10">
<input type="date" name="myDate" value="2006-07-30" min="2005-01-01" max="2007-12-31" step="5">
<input type="month" name="myMonth" value="2006-06" min="2005-01" max="2007-12" step="2">
<input type="week" name="myWeek" value="2006-W26" min="2005-W01" max="2007-W52" step="4">
               
Man beachte hierbei, daß der Wert "step" für "datetime", "datetime-local" und "time" in Sekunden angegeben wird.
<input type="datetime" name="myDateTime6" value="2006-06-01T12:30Z"
                                                  min="2005-01-01T00:00Z" max="2007-12-31T23:59Z" step="3600">

<input type="datetime-local" name="myLocalDateTime6" value="2006-06-01T17:00"
                                                  min="2005-01-01T00:00" max="2007-12-31T23:59" step="1800">

<input type="time" name="myTime6" value="12:00" min="07:30" max="16:30" step="1800">
           
Eine weitere Möglichkeit, die Eingabe clientseitig zu validieren, besteht durch regulärer Ausdrücke, den sogenannten "Pattern": Im Falle einer nicht passenden Eingabe wird zusätzlich zum "normalen" Fehlertext noch der Wert des "title"-Attributes ( wenn vorhanden ) ausgegeben.
<input type="text" name="myRegExp" pattern="[A-Za-z]+\d+"
                                                      title="Mehrere Buchstaben, gefolgt von mindestens einer Zahl">

Achtung: Der reguläre Ausdruck beginnt "intern" mit einem "^" und endet "intern" mit einem "$", d.h. es wird immer das gesamte Wort verglichen. Es wird "nicht" nach einem Teilstring gesucht! Will man dies aber trotzdem tun, muß man nur den regulären Ausdruck durch zwei .* umschließen:
Zum Beispiel würde das Pattern ".*\d{3}\D.*" einen Fehler anzeigen, wenn der eingegebene Text nicht genau drei aufeinanderfolgenden Zahlen hat, d.h. "aa123aa"," 123aaa","aaa123a12" sind gültig. "a12b3" und "a1234" aber nicht.

Außerdem ist zu beachten, daß die Sonderzeichen "/", "^" und "$" nicht "escaped" werden müssen, da diese ja schon intern verwendet werden.

<input type="text" name="myRegExp" pattern="[A-Za-z]+\d+"
title="Mehrere Buchstaben, gefolgt von mindestens einer Zahl">

<input type="text" name="myRegExp2" pattern=".*\d{3}\D.*"
title="Genau drei aufeinanderfolgende Zahlen">






Zu guter Letzt wurde auch noch das "file"-Control erweitert: Es ist nun endlich möglich, mehrere Files gleichzeitig "upzuloaden". Sind "min" und "max" angegeben, wird auch dieser Bereich validiert und gegebenenfalls ein "RangeOverflow" bzw. "RangeUnderflow" beim "Submit" angezeigt. Hat man auch noch "accept" spezifiziert, wird bei einem fehlerhaften Dateityp ein "TypeMismatch" gemeldet. Um den User auch hier noch bei der Eingabe zu unterstützen, wird innerhalb des Dateibrowsers auf die "accept"-Mimetypen eingeschränkt, d.h. nur die Dateien erscheinen, die man auch "uploaden" könnte.

<input type="file" name="myFile" min="1" max="3" accept="image/jpg,text/*">
 
 
 

3. Neue Controls

In einem "Freitext"-Feld ist es nun möglich, Werte "vorzuschlagen". Zu diesem Zweck wurde das "DATALIST"-Tag eingeführt, das wie eine "SELECT"-Box mehrere "OPTION"-Elemente enthalten kann. Um die Verbindung zwischen "INPUT" und "DATALIST" herzustellen, muß man nur das neue Attribute "list" des "INPUT"-Controls auf die "ID" der "DATALIST" setzen.  
<input type="url" name="location" list="myGames">
<datalist id="myGames">
 <select>
 <option label="Mahjongg" value="http://www.javasscript-spielereien.de/mahjongg.js">
 <option label="Patiencen" value="http://www.javasscript-spielereien.de/solitaire.js">
 <option label="Jokoban" value="http://www.javasscript-spielereien.de/jokoban.js">
 </select>
</datalist>

Das "SELECT" Tag innerhalb der "DATALIST" ist nicht zwingend erforderlich. Man sollte es aber in den Code integrieren, um älteren Browsern, die das "DATALIST"-Element nicht kennen, eine Alternative anbieten zu können.

Auch "nicht schlecht" ist die Möglichkeit, eine "DATALIST" auf ein "range"-Controls anzuwenden: Die einzelnen Optionen kennzeichen hierbei die "Striche" des Sliders.
<input type="range" name="myRange" list="myRanges">
	min="-100" max="100" value="0"">
<select>
<datalist id="myRanges">
 <option value="0">
 <option value="-10">
 <option value="10">
</select>
</datalist>

Wie man hier aber leider sieht, funktioniert das ganze unter "Opera 9" noch nicht.

 
 

4. Neue Events

Um Daten eines Formulars clientseitig auszuwerten, wurden zwei neue Events eingeführt:
  • onforminput:
    Ein beliebiges Formularelement feuert ein "onkeypress" Event.

  • onformchange:
    Ein beliebiges Formularelement feuert ein "onchange" Event
Hierbei ist zu beachten, daß nur "FORM"-Elemente in der Lage sind, diese Events "einzufangen". Aus diesem Grunde wurde wahrscheinlich auch das neue "OUTPUT"-Element eingefügt, das sich wie ein "SPAN" verhält:
x: <input name="x" type="number" value="0">
y: <input name="y" type="number" value="1">
x * y = <output name="xy1" onforminput="value = x.value * y.value"></output>
x + y = <output name="xy2" onformchange="value = 1*x.value + 1*y.value"></output>

x:
y:
x * y =
x + y =

"OUTPUT" sollte man daher nur verwenden, wenn sich dessen Inhalt aus anderen FORM-Elementen "berechnen" läßt. Dieser Wert wird jedoch wie ein Wert eines disabelden Controls nicht "verschickt".

Hast Du eigentlich bemerkt, daß die "OUTPUT"-Werte initial berechnet wurden? "onformchange" und "onforminput" feuern doch nur, wenn sich etwas interaktiv verändert hat. Wie kommt das?

Ganz einfach: Das "FORM"-Objekt besitzt zwei neue Methoden dispatchFormChange und dispatchFormInput, die die entsprechenden Events manuell feuern. In unserem Fall wurden die beiden Methoden im "onload"-Event Handler der Seite aufgerufen:

<body onload="document.myForm.dispatchFormChange();document.myForm.dispatchFormInput()">

Ein weiteres neues Event ist oninvalid: Es "feuert" wenn beim "Submit" des Formulars "etwas" mit den eingegebenen Daten nicht stimmt ( siehe Beispiel )
 

5. Templates

Bisher mußte man immer schon im Vorfeld angeben, wieviele Datenzeilen ein Benutzer angegeben darf. Dies ist Vergangenheit: Es wurden "Templates" eingeführt, die eine Zeile mit "FORM"-Controls definieren. Beim Aufbau des Formulars werden dann "repeat-start" Zeilen anhand dieses Templates "generiert". Reicht diese Anzahl nicht aus, kann der Benutzer durch Klick auf einen Button vom Typ "add" weitere Zeilen hinzufügen. Auch ist es möglich, einzelne Zeilen zu löschen bzw. innerhalb des Formular nach oben oder unten zu verschieben. Sind die Attribute "repeat-min" und "repeat-max" auch angegeben, wird bei jeder "Add/Delete"-Funktion überprüft, ob die neue Zeilenanzahl innerhalb des Grenzen ist. Wenn nicht, wird die Aktion nicht durchgeführt.
<form name="myForm">
<table border="1">
<thead>
<tr>
<th>Produkt</th>
<th>Menge</th>
<th colspan="3">Aktionen</th>
</tr>
</thead>
<tbody>
<tr id="orderTemplate" repeat="template" repeat-start="3" repeat-min="2" repeat-max="10">
<td><input type="text" name="myProduct[orderTemplate]" value=""></td>
<td><input type="number" name="myQuantity[orderTemplate]" value="1"></td>
<td><button type="remove">Zeile löschen</td>
<td><button type="move-up">Nach Oben</td>
<td><button type="move-down">Nach Unten</td>
</tr>
</tbody>
</table>
<p><button type="add" template="orderTemplate">Neue Zeile hinzufügen</button></p>
<p><button type="submit"></button></p>
</form>
Produkt Menge Aktionen

Der Name eines Controls wird dynamisch angepaßt, d.h. in der ersten Zeile unseres Beispiels würden daher zwei Controls mit Namen "myProduct1" und "myQuantity1" bzw. in der zweiten Zeile "myProduct2" und "myQuantity2" stehen. Die eckige Klammer, die nicht zwingend am Ende stehen muß, wird also durch den entsprechenden Index ersetzt. Dieser Index, hier "orderTemplate", muß die "Id" des Templates sein. Um was für ein HTML-Element es sich dabei handelt, ist unwichtig. Es kann jedes beliebige TAG sein!

Vom Template "abweichende" Zeilen kann man "vor" dem eigentlichen Template" spezifizieren: Man definiert im "Parent"-Tag das Attribut "repeat" mit dem entsprechenden Index. Das nachfolgende Template generiert dann "repeat-start" neue Reihen.

<form name="myForm">
<table border="1">
<thead>
<tr>
<th>Produkt</th>
<th>Menge</th>
</tr>
</thead>
<tbody>
<tr repeat="1">
<td><input type="text" name="myProduct1" value="Das muß man haben!" readonly></td>
<td><input type="number" name="myQuantity1" value="1" min="1" required></td>
</tr>
<tr id="orderTemplate" repeat="template" repeat-start="3">
<td><input type="text" name="myProduct[orderTemplate]" value=""></td>
<td><input type="number" name="myQuantity[orderTemplate]" value="1"></td>
</tr>
</tbody>
</table>
<p><button type="add" template="orderTemplate">Neue Zeile hinzufügen</button></p>
<p><input type="submit">
</form>

Produkt Menge

Im nebenstehenden Beispiel ist "myProduct1" ein "Pflichtprodukt",d.h. das Attribute "min" stellt sicher, daß nur Bestellungen verschickt werden, die dieses Produkt mindestens einmal mitbestellen. Die nachfolgenden Produkte "myProduct2", "myProduct3" und "myProduct4" sind beliebig.
 
 

6. Formularverarbeitung

"Früher" konnten Formulardaten nur durch eine Seite verarbeitet werden. Dies wurde jetzt verbessert: Die eigentlichen "FORM"-Attribute "action", "method", "enctype" und "target" können jetzt auch an mehreren "SUBMIT"-Buttons eines Formulars notiert werden. Somit ist es möglich, verschiedene Auswertungsseiten - und methoden aufzurufen:
<form name="myFormC">
<input type="submit" name="submit1" action="file1.php" method="post" target="window1" >
<input type="submit" name="submit2" action="file2.php" method="get" target="window2" >
</FORM>

Das früher zwingend erforderliche "action"-Attribut des Formulars kann auch komplett "weggelassen" werden: Ein "Submit" ohne "action"-Attribut verschickt die Daten einfach an sich selbst.

Eine weitere Neuheit bezüglich Formulare ist das Attribute "form", das nun bei allen Formularelementen angegeben werden kann: Es spezifiziert das Formular, zu dem es "gehört". Es ist also nicht mehr so, daß alle Elemente, die sich innerhalb eines "FORM"-Tags befinden, auch automatisch beim "Submit" bzw. "Reset" dieses Formulars übertragen bzw. resettet werden. Auch ist es nun möglich, mehrere, durch Leerzeichen getrennte, "zuständige" Formulare anzugeben.

Beachte hierbei, daß mit "form" die "ID" des entsprechenden Formulars und nicht dessen Namen gemeint ist!

Beispiel: Das "INPUT"-Control mit dem Namen "myTextA1" gehört zu den Formularen "myFormB" und "myFormC", d.h. nur ein Submit eines dieser Formulare übermittelt dessen Wert. Das ganze funktioniert natürlich analog zum "Reset".

Form A:<form id="myFormA">
( B, C ) <input type="text" name="myTextA1" form="myFormB myFormC">
( A ) <input type="text" name="myTextA2"><br>
<input type="reset" value="reset Form A">
</form>

Form B:<form id="myFormB">
<input type="text" name="myTextB1">
<input type="reset" value="reset Form B">
</form>

Form C:<form id="myFormC">
<input type="text" name="myTextC2"><br>
<input type="reset" value="reset Form C">
</form>

Form A:
( B, C )
( A )
Form B:

Form C:

 
 

7. Sonstige Änderungen

<select name="mySelect" size=10 style="width:200px">
 <optgroup label="Deutsche Städte">
  <option>Berlin</option>
  <option disabled>München</option>
  <option>Homburg</option>
 </optgroup>
 <optgroup label="Europäische Städte">
  <option>Paris</option>
  <option>Rom</option>
  <option disabled>London</option>
 </optgroup>
 <optgroup label="Sonstige Städte">
  <option>Moskau</option>
  <option>Kairo</option>
  <option>Sydney</option>
 </optgroup>

Es besteht nun die Möglichkeit, einzelne "OPTION"-Elemente eines "SELECT"-Controls zu "disabeln":

 
<fieldset disabled>
<select name="mySelect">
<option>1</option>
<option>2</option>
</select>
<input type="checkbox" name="myCheckBox" checked>
<input type="text" name="myText" value="ÄNDERE MICH!">
</fieldset>

Des Weiteren werden durch "disabeln" eines "FIELDSET"s alle darin enthaltene Controls deaktiviert:


Klick' mich:
 


<input type="text" name="myText" autofocus>



Bisher war es nur durch Javascript möglich, ein "INPUT"-Control nach dem Laden der Seite zu "fokussieren". Damit das ganze nun einfacher geht, wurde ein neues Attribute autofocus eingeführt.
 

<input type="text" name="myText" autocomplete="off">



Will man die autocomplete-Funktionalität eines Controls deaktivieren, muß man nur das "entsprechende" Attribut auf "off" setzen.
"on" schaltet es wieder ein.
 
 

8. Scripting

"FORM"-Elemente werden beim "Submit" nur dann validiert, wenn folgende Kritierien erfüllt sind:
  • Das Control gehört zu einem Formular, d.h. "object.form != null"

  • Das Control hat ein "name" Attribut.

  • Das Control ist nicht disabled.

  • Das Control gehört nicht zu einem Template, d.h. es ist kein Kind eines HTML-Elementes mit "repeat='template'".

    Achtung: Die vom Template "generierten" Controls zählen hier natürlich nicht darunter.

  • Das Control ist kein Kind eines "DATALIST"-Tags, da diese Elemente ja nur angezeigt werden, wenn "DATALIST" vom Browser nicht unterstützt wird.

  • Das Control ist kein Button vom Typ "reset", "add", "remove", "move-up" bzw. "move-down".

  • Das Control ist kein "OUTPUT" Element.

Das dazugehörige Property des Formelementes willValidate wird dementsprechend auf "true" oder "false" gesetzt.

Das Ergebnis der Validierung wird in einem Attribut validity des Controls gespeichert. Dieses "Objekt" hat dabei die folgende Ausprägungen bzw. Fehlercodes:

  • typeMismatch

    Der eingebene Wert "paßt" nicht zum Typ, d.h. die Eingabe eines Textes in ein "number"-Feld.

  • rangeUnderflow

    Ein Minimalwert "min" wurde angegeben und vom Benutzer "unterschritten".

  • rangeOverflow

    Ein Maximalwert "max" wurde angegeben und vom Benutzer "überschritten".

  • stepMismatch

    Eine Schrittweite "step" wurde angegeben und der eingegebene Wert "paßt" nicht, d.h. "step = 5" und "value = 6"

  • tooLong

    Der eingegebene Text ist länger als in "maxlength" zugelassen.

  • patternMismatch

    Der eingegebene Text "matched" nicht mit dem spezifizierten regulären Ausdruck, d.h. "a3bcde" paßt nicht zu "[a-z]+"

  • valueMissing

    Ein Pflichtfeld wurde nicht angebenen.

  • customError

    Der Wert wurde "von Hand" mit Hilfe der Control-Methode setCustomValiditiy("myErrorMessage") als "invalid" gekennzeichnet. Beim Submit wird folgende Meldung ausgegeben:

    "Dieser Wert wird von einem Script dieser Seite nicht zugelassen!
    myErrorMessage

    Dieser Error kann nicht durch Eingabe eines neuen Wertes bzw. Reset des Formulars gelöscht werden! Man muß explicit die Methode "setCustomValiditiy" mit einem Leerstring als Parameter aufrufen!

  • valid

    Wenn kein anderes oben aufgeführtes Flag gesetzt ist, ist dieses Flag "true", d.h. der Wert ist "gültig" und kann übertragen werden.



Wird der "Submit"-Button gedrückt, werden alle zur Form gehörenden Elemente mit gesetzten "willValidate" Property gesucht und validiert. Ist ein Wert nicht valide, wird ein oninvalid Event gefeuert, das vom betreffenden Control abgefangen werden kann. Liefert dessen Eventhandler "false" zurück, wird die "Default"-Fehlermeldung des Browsers unterdrückt.

Treten mehrere Fehler gleichzeitig auf, wird der "Info"-Text nur beim ersten fehlerhaften Control angezeigt.

 

Beispiel:

function initPage()
{
document.myForm.myText2. // Zeilenumbruch!
setCustomValidity( "aua" );
};

function checkErrorCodes(obj)
{
with (obj.validity)
{
if ( valueMissing )
	alert( "valueMissing" );

if ( rangeUnderflow )
	alert( "rangeUnderflow" );

if ( rangeOverflow )
	alert( "rangeOverflow" );

if ( stepMismatch )
	alert( "stepMismatch" );

if ( patternMismatch )
	alert( "patternMismatch" );

if ( customError )
	alert( "customError" );

if ( typeMismatch )
	alert("typeMismatch");

if ( tooLong )
	alert( "tooLong" );

};
return true;
//return false unterdrückt Fehlermeldung!
}

function clearError()
{
document.myFormH.myText2.setCustomValidity("");
}

 
<body onload="initPage()">
<form name="myForm">
<input type="number" name="myNumber"
	oninvalid="return checkErrorCodes(this)"
	min="10" max="20" step="5">
<input type="text" name="myText"
	pattern="[a-z]+"
	oninvalid="return checkErrorCodes(this)">

<input type="text" name="myText2"
	oninvalid="return checkErrorCodes(this)">

<input type="text" name="myText3"
	maxlength="4" value="abcde"
	oninvalid="return checkErrorCodes(this)">

<input type="button" value="lösche customError"
	onclick="clearError()">
<input type="submit"/>

</form>
</body>
10 < x < 2 0 ( step = 5 )
Nur kleine Buchstaben:
"Nie gültig":
Maximal 4 Buchstaben:

Mit der neuen "FORM"-Methode checkValidity ist es möglich, das Formular ohne Drücken des "Submit"-Buttons zu validieren.

<input type="number" name="myNumber" min="3" max="7" oninput="check4TypeMismatch(this)" >
function check4TypeMismatch( myControl )
{
	if ( myControl.value == "" )
	{
		myControl.setCustomValidity( "...wahrscheinlich ein 'TypeMismatch'-Fehler in Opera 9" );
	}
	else
	{
		myControl.setCustomValidity( "" );
	};
	myControl.form.checkValidity();
}
Gib' bitte mal einen Text (z.B. "4a" ) ein:  ( 3 < x < 7 )

Was passiert hier? Wenn der eingegebene Text keine Zahl ist, setzt Opera 9 den Value des Controls auf "". Fälschlicherweise wird aber intern der "TypeMismatch"-Fehler nicht gesetzt! Aus diesem Grund setze ich das Control mit Hilfe von "setCustomValidity" manuell auf "customError" und aktiviere die Formvalidierung. Ist der neue Value eine Zahl, wird der "customError" wieder gelösct.


Zum Abschluß dieses Kapitels gibt's noch etwas kleines Feines: das "SELECT"-Property selectedOptions. Dieses Array enthält alle ausgewählten "OPTION"-Elemente eine MultiSelectBox, d.h. man muß nicht mehr alle "options" durchlaufen und überprüfen, ob das Attribut "selected" gesetzt ist.
function showSelectedOptions()
{
	var option = document.myForm.mySelect.selectedOptions;
	for ( var i = 0; i > option.length; i++ )
			alert( option[ i ].text );
};
Bitte mehrere Einträge mit "Strg"+Klick auswählen:


 

9. Externes Nachladen mit "DATA"

Jeder der schon einmal abhängige "SELECT"-Boxen mit Javascript gebaut hat, weiß um was für eine Arbeit es sich dabei handelt. Zum Glück ist das jetzt vorbei: Es wurde ein neues Attribut "DATA" für "SELECT"-Tags eingeführt, das diese Arbeit automatisiert. Man kann hierbei unterscheiden, ob die alten "OPTION"-Einträge gelöscht bzw. beibehalten ( type="incremental" ) werden. Auch ist es nun möglich, die Daten als externe Datei auszulagern:

<form name="myForm">
<select name="mySelect" data="data.xml"></select>
<input type="button" onclick="add456()" value=" + ( 4,5,6 )"/>
<input type="button" onclick="change2ABC()" value=" = ( A, B, C )"/>
<input type="button" onclick="loadAndAddDEF()" value=" lade und + ( D, E, F )"/>
</form>
function addOptions( obj, newOptions )
{
	obj.data = 'data:application/xml,' +
		'<select xmlns="http://www.w3.org/1999/xhtml" type="incremental">' +
		newOptions +
		'</select>';
};

function changeOptions( obj, newOptions )
{
	obj.data = 'data:application/xml,' +
		'<select xmlns="http://www.w3.org/1999/xhtml">' +
		newOptions +
		'</select>';
};

function add456()
{
	addOptions( document.myForm.mySelect,
		"<option>4</option><option>5</option><option>6</option>" );
};

function change2ABC()
{
	changeOptions( document.myForm.mySelect,
		"<option>A</option><option>B</option><option>C</option>" );
};

function loadAndAddDEF()
{
	document.myForm.mySelect.data = "data2.xml";
};
Datei: data.xml
<select xmlns="http://www.w3.org/1999/xhtml">
<option>1</option><option>2</option><option>3</option>
</select>
Datei: data2.xml
<select xmlns="http://www.w3.org/1999/xhtml" type="incremental">
<option>D</option><option>E</option><option>F</option>
</select>
 


...und hier kommt noch ein Beispiel, daß sich mit dreifach "abhängigen" Selectboxen befaßt:

A = "<option>Audi</option><option>BMW</option><option>Opel</option>";
A0 = "<option>A3</option><option>A4</option><option>A5</option>";
A1 = "<option>320i</option><option>535i</option><option>635 csi</option>";
A2 = "<option>Ascona</option><option>Signum</option><option>Vectra</option>";

C = "<option>Festplatte</option><option>Monitor</option><option>Grafikkarte</option>";
C0 = "<option>100 GB</option><option>200 GB</option><option>400 GB</option>";
C1 = "<option>17 Zoll</option><option>19 Zoll</option><option>21 Zoll</option>";
C2 = "<option>32 MB</option><option>64 MB</option><option>128 MB</option>";

K = "<option>Hörspiele</option><option>Märchen</option><option>Filme</option>";
K0 = "<option>Benjamin Blümchen</option><option>Bibi Blocksberg</option>";
K1 = "<option>Dornröschen</option><option>Schneewittchen</option><option>Rapunzel</option>";
K2 = "<option>Lars Eisbär</option><option>Lauras Stern</option><option>Ice Age</option>";


function initPage()
{
	oMyForm = document.myForm;
	oMySelect1 = oMyForm.mySelect1;
	oMySelect2 = oMyForm.mySelect2;
	oMySelect3 = oMyForm.mySelect3;

	createToggle2();
};

function changeSelect( obj, options )
{
obj.data = 'data:application/xml,<select xmlns="http://www.w3.org/1999/xhtml">'+options+"</select>";
}

function createToggle2()
{
	changeSelect( oMySelect2, eval( oMySelect1.value ) );
	window.setTimeout("createToggle3()",100);
};

function createToggle3()
{
	changeSelect( oMySelect3, eval( oMySelect1.value + oMySelect2.selectedIndex ) );
};
<body onload="initPage()">
<form name="myForm">
<select name="mySelect1" onchange="createToggle2()">
<option value="A">Autos</option>
<option value="C">Computer</option>
<option value="K">Kinder</option>
</select>
<select name="mySelect2" onchange="createToggle3()"></select>
<select name="mySelect3"></select>
</form>
</body>


"FORM"-Tags können "initial" auch mit Hilfe des "DATA"-Attributes befüllt werden. Leider wurde dieses Feature bisher noch nicht von Opera 9 implementiert. Ein "mögliches" Beispiel könnte so aussehen:

<form name="myForm" data="data.xml">
<input type="text" name="myText">
</form>
<formdata xmlns="http://n.whatwg.org/formdata">
<field name="myText">Hallo</field>
</formdata>
Datei: data.xml

Genaure Infos werden "zu gegebener Zeit" nachgereicht" ;-)

 

10. CSS

Der "Zustand" einzelner Controls kann nun durch neue "CSS3" Pseudo-Selektoren "gestylt" werden:
  • :disabled

    Controls bzw. "OPTIONS" oder "OPTIONGROUPS", die "disabled" sind

  • :enabled

    Formelemente, die nicht disabled sind

  • :read-only

    Controls mit gesetzten "readonly"-Attribut

  • :read-write

    Controls, die nicht readonly sind

  • :checked

    Markierte "Check / Radio"-Boxen bzw "SELECT"-Boxen mit ausgewählter "OPTION"

  • :indeterminate

    Eine Gruppe von "radio"-Buttons von denen noch keiner ausgewählt wurde

  • :default

    • der gerade "focusierte" Button
    • "Check / Radio"-Boxen, die initial "gechecked" wurden
    • der "OPTION"-Eintrag einer Selectbox, der voreingestellt war.

  • :valid

    Controls mit "gültigem" Wert

  • :in-range

    Controls mit einem Wert der in einem spezifizierten Bereich liegt

  • :out-of-range

    Controls mit einem nicht gültigen Bereichswert

  • :required

    Controls, die "ausgefüllt" werden müssen

  • :optional

    Controls, die keine Pflichtfelder sind

<style>
:enabled {
	background-color : green;
	color : white;
	font-weight : bold
}
:disabled {
	background-color : red;
}
:checked {
	color : yellow;
	background-color : yellow
}
:in-range {
	color : green;
	font-weight : bold
}
:out-of-range {
	color : red
}
:required {
	border : solid 4px red;
}
:indeterminate {
	background-color : blue
}
</style>
<input type="text" disabled value="disabled">
<input type="text"">
<input type="text" required="required" value="Pflichtfeld">

<input type="number" min="10" max="20" step="5" value="15">
<input type="number" min="10" max="20" step="5" value="5">
<input type="number" min="10" max="20" step="5" value="25">
<input type="number" min="10" max="20" step="5" value="6">

<input type="radio" name="myRadios" value="a">
<input type="radio" name="myRadios" value="b">
<input type="radio" name="myRadios" value="c">
  



A: B: C:


Mit Hilfe des Pseudo-Selektors :invalid ist es möglich, das Aussehen der browserspezifischen Fehlermeldung abzuändern. Deren Text ist meines Wissens leider noch nicht änderbar.

:invalid {
	background-color: yellow;
	color:red; }
<input type="number" name="myNumber" min="10" max="20" step="2">
<input type="email" name="myEmail">
<input type="url" name="myUrl">

Eine gerade Zahl zwischen 10 und 20 :
eMail :
url mit "http://" :
Dieser Style ändert nicht nur die beim Versenden angezeigte Fehlermeldung, sondern auch das entsprechende Control in Echtzeit.



Zum Abschluß noch etwas zum Thema "Unerwünschte Attribute": Das "INPUT"-Attribut "size" bzw. "cols" und "rows" bei "TEXTAREAS" sollte man von nun an nicht mehr verwenden, da der gleiche Effekt auch mit dem css-Style "width" erzielt werden kann.

 

11. Opera 9 Bugs

  • type: email | url

    Das Icon links erscheint nur, wenn man eine Hintergrundfarbe für das "INPUT"-Control angibt.

  • type: number

    Bei einer falschen Eingabe wird kein "Typemismatch" gemeldet! Man muß das Feld als "required" kennzeichnen um eine entsprechende Fehlermeldung zu bekommen.

  • Die beiden Pseudo-Selektoren :checked und :default funktionieren nicht bei einer "SELECT"-Box.

  • Die Kombination range-Control und DATALIST funktioniert nicht.

  • Ein "File"-Control meldet keinen "Typemismatch"-Fehler wenn eine nicht zum "accept"-Attribut passende Datei ausgewählt wurde.

  • Javascript: Der "repetitionIndex" eines generierten Templates ist immer "0".

  • onformchange feuert nicht bei "SELECT"