Hallo
Wie einige von euch sicherlich festgestellt haben, liegt in Bezug auf die Struktur der JavaScript-Sektion im Wiki immernoch vieles im Argen, sprich, die Trennung des Sprachkerns ECMAScript von den verschiedenen Schnittstellen einerseits, so wie andererseits auch die Abstraktion zwischen den diversen APIs selbst ist nach wie vor unzureichend, auch wenn es hier, dank des Engagements von Matthias Scharwies, gegenüber dem früheren Zustand bereits Fortschritte zu verzeichnen gibt.
Tatsächlich ist die korrekte Abbildung der diversen Schnittstellen, der built-in objects und ihrer Eigenschaften und Methoden keine ganz triviale Aufgabe, wobei die Arbeit hier unter anderem dadurch erschwert wird, dass im Wiki ja nicht bei null
angefangen wird, sondern eine bereits bestehende Struktur transformiert werden muss.
Zur Veranschaulichung des Themas sei vielleicht zunächst ein kleines Beispiel angeführt:
(function (param) {
var get = Object.getPrototypeOf;
var proto = get(param), con;
while (proto !== null) {
con = proto.constructor;
console.log(con.name || con);
proto = get(con.prototype);
}
}(document.body));
Hier haben wir zunächst einen anonymen IIFE (Immediately-Invoked Function Expression), welchem das Element Body als Argument übergeben wird, wobei dieses über die Eigenschaft gleichen Namens des Objektes document
referenziert wird. Diese Eigenschaft stellt eine HTML-spezifische Erweiterung der Schnittstelle Document
des DOM dar. In der Praxis bedeutet dies, dass die Eigenschaft mit dem Bezeichner body
je nach Implementierung entweder eine eigene Eigenschaft des Objektes ist, welches in der prototype
-Eigenschaft des Konstruktors HTMLDocument
hinterlegt ist, oder aber sie wird direkt von Document.prototype
an die Instanz document
vererbt, wobei ich Letzteres für keine gute Entscheidung der einschlägigen Browserhersteller halte, da hierbei eigentlich separate Schnittstellen vermischt werden.
Innerhalb der Funktion wird nun zunächst die Methode getPrototypeOf
des Konstruktors Object
der lokalen Variable mit dem Bezeichner get
als Wert zugewiesen. Wird dieser Methode bei ihrem Aufruf ein Objekt übergeben, dann gibt sie den Wert der internen Eigenschaft [[Prototype]]
dieses Objektes zurück, also gewissermaßen den nächsten Vorfahren innerhalb der jeweiligen Prototypenkette.
Diese Methode wird nun in einem nächsten Schritt für den mit Body initialisierten Parameter der Funktion aufgerufen und der Rückgabewert in der Variable mit dem Bezeichner proto
hinterlegt. Die folgende Schleife sorgt nun dafür, dass solange der Wert von proto
nicht null
ist, der Wert der prototype
-Eigenschaft constructor
in der Variable con
gespeichert wird. Der Wert dieser Eigenschaft ist wie der Name schon vermuten lässt immer eine Referenz auf den jeweiligen Konstruktor, dessen Name in einem nächsten Schritt in die Konsole geschrieben wird, sofern die Eigenschaft name
unterstützt wird. Dies geschieht freilich unter Verwendung des nicht standardisierten Console
-API, dessen Instanzobjekt im globalen Namensraum Eigenschaft des von Browser bereitgestellten window
-Objektes ist. Schließlich wird proto
für den nächsten Schleifendurchlauf mit dem Prototypen des Vorfahren initialisiert. Die Prüfung gegen null
erflogt hier, da dies der Wert der internen Eigenschaft [[Prototype]]
von Object.prototype
ist, welche das letzte Glied in der prototype chain darstellt. Im Ergebnis werden dann dem zur Folge durch die Funktion alle Namen der Konstrukoren eines Objektes in die Konsole geschrieben, was für Body im Firefox so aussehen würde:
HTMLBodyElement
HTMLElement
Element
Node
EventTarget
Object
Diese built-in objects repräsentieren hier also die verschiedenen Schnittstellen, die Eigenschaften und Methoden an das Objekt vererben, welches das Element Body repräsentiert, wobei sich die jeweiligen Implementierungen allerdings wie bereits gesehen in Details unterscheiden können.
Jedenfalls beginnt die Kette hier erwartungsgemäß mit Object
, welches bekanntermaßen Teil des Sprachkerns ECMAScript ist. Dann haben wir hier die Schnittstelle EventTarget
des DOM, welche unter anderem die Methode addEventListener
an unser Element vererbt. Weiterhin werden Eigenschaften und Methoden der Schnittstellen Node
und Element
des Document Object Models vererbt, wie etwa die Eigenschaft textContent
durch Node.prototype
oder die Eigenschaft tagName
durch Element.prototype
. Schließlich vererben die HTML-spezifischen Schnittstellen HTMLElement
und HTMLBodyElement
eigene Eigenschaften wie beispielsweise offsetTop
oder onhashchange
.
Es wird also deutlich, dass wenn es das Ziel des Wikis sein soll, eine halbwegs präzise Vorstellung vom Zusammenwirken der verschiedenen Schnittstellen zu vermitteln, der Aufbau der Sektion auch die tatsächlichen Strukturen entsprechend soweit wie möglich widerspiegeln sollte, womit wir dann beim derzeitigen Stand der Dinge angelangt wären.
Dem aufmerksamen Beobachter wird wie eingangs bereits erwähnt aufgefallen sein, dass sich in der letzten Zeit hier durchaus einiges getan hat. So wurde beispielsweise die Rubrik DOM aus der Rubrik Objekte herausgelöst und bestehende Artikel wurden neu gegliedert.
Nichtsdestotrotz ist die Aufteilung meiner Ansicht nach jedoch noch nicht ideal. Zwar sind nun innerhalb der Rubrik Objekte die built-in objects von ECMAScript, also etwa Object
, Function
oder Math
, von nicht zugehörigen Objekten optisch abgesetzt aufgelistet, jedoch sollten diese nicht zum Sprachkern gehörigen Objekte im Sinne einer strikten Trennung von Sprache und Schnittstellen dort eigentlich gar nicht stehen, sondern statt dessen unter APIs aufgeführt sein. – Also, nochmal zur Verdeutlichung, im Moment sieht es so aus:
Objekte
- navigator
- screen
- window
- document
- forms
- elements
- forms
- history
- location
- document
|und davon leicht abgesetzt|
- Object
- Array
- Boolean
- Date
- Function (usw.)
Hier fällt zunächst einmal auf, dass mindestens einmal der Artikel zu document
deplaziert ist. Das Instanzobjekt document
ist zwar wie alle eingebauten Objekte als Bestandteil des globalen Namensraums Eigenschaft des Objektes window
, aber im Sinne der inhaltlichen Zugehörigkeit sollte dieser Artikel neben node
unter der Rubrik DOM aufgeführt sein, dessen Schnittstelle Document
es repräsentiert, und bei den Eigenschaften von window
lediglich verlinkt werden. Was die forms
-Schnittstelle angeht, so handelt es sich hier ebenso wie bei der Dokumenteigenschaft body
aus dem Eingangsbeispiel um eine HTML-spezifische Erweiterung der Schnittstelle Document
des DOM. Dazu aber später noch etwas mehr.
Jedenfalls denke ich, dass die Punkte Window
, Screen
, Location
, Navigator
und History
am besten unter einer gemeinsamen Rubrik Browser zusammengefasst werden sollten, wobei die Objekte zwar auch als Eigenschaften von window
aufgeführt und entsprechend verlinkt sein sollten, sie jedoch wie ich meine davon abgesehen als separate Punkte aufgelistet gehören.
Browser
- Window
- document (link)
- innerHeight
- innerWidth
- navigator (link)
- Navigator
- History
- Location
- Screen
Die Auswahl an Unterpunkten zu Window
ist jetzt hier nur zu Demonstrationszwecken aufgelistet. Auf der Startseite der JavaScript-Sektion würde es wohl genügen wenn die entsprechenden Listenpunkte erst beim Klick auf die Überschrift Browser beziehungsweise auf Window
sichtbar werden. Darüber hinaus denke ich, dass diese gemeinsame Rubrik Browser ebenso wie zuvor schon die Rubrik DOM aus Objekte herausgelöst und auf die rechte Seite des Zwei-Spalten-Layouts verfrachtet werden sollte.
Es bietet sich in dieser Hinsicht wie ich meine gerade zu an, die beiden Spalten zur Trennung von Sprachkern und Schnittstellen zu verwenden und entsprechende Überschriften einzufügen. Denn momentan ist es ja noch so, dass von der Vermischung innerhalb von Objekte einmal abgesehen, auch die Überschriften auf der rechten Seite des Layouts etwas missverständlich sind:
- DOM
- Event
- APIs
Denn einerseits sind Event
und EventTarget
Schnittstellen des DOM, und andererseits ist das Document Object Model selbst natürlich auch eine Ansammlung von Schnittstellen, weshalb hier beim dritten Punkt wenn überhaupt die Überschrift andere APIs sinnvoll erschiene.
Jedenfalls habe ich mir über diesen Aspekt meine Gedanken gemacht und bin zu dem Ergebnis gekommen, dass es erstens, im Gegensatz etwa zur Handhabung im MDN, nicht sinnvoll ist, die „Web-APIs“ aus der JavaScript-Sektion vollkommen auszugliedern, zumindest nicht, solange JavaScript als Sprache der Browser keine ernsthafte Konkurrenz erwächst, und dass es zweitens notwendig ist, wenn man sich schon entscheidet, die Schnittstellen grundsätzlich in dieser Sektion des Wikis zu belassen, sowohl durch Überschriften als auch hinsichtlich der optischen Gliederung die Trennung von Sprachkern und APIs klar zu kommunizieren. Ich würde also dazu tendieren, die Überschrift APIs als globale Überschrift für die rechte Spalte einzusetzen, so dass diese Seite hernach etwa so auschauen würde:
APIs
-
DOM
- Document
- Node
- Event (usw.)
-
Browser
- Window
- History (usw.)
-
Console
-
Geolocation
-
File Upload
-
WebGL (usw.)
Dabei sollte man vielleicht auch darüber nachdenken, ob APIs als Überschrift allein aus Anfängersicht gesehen so aussagekräftig ist. Vielleicht wäre es doch besser hier von ‚Schnittstellen‘ zu sprechen!?
Um abschließend nocheinmal auf die Abgrenzung zwischen DOM und HTML zurückzukommen: Ich denke, hier muss nicht zwingend eine eigene Rubrik eingerichtet werden, schon allein weil die Implementierungen hier nicht immer einheitlich sind, aber es sollte sowohl bei der Beschreibung der DOM-Objekte als auch bei der Auflistung der Eigenschaften und Methoden so klar wie möglich abgegrenzt werden.
Soweit meine Ansicht zum Thema. Vielleicht hat ja noch jemand Ideen, wie die Sektion besser zu gliedern wäre? Das würde mich interessieren! Und ich möchte am Ende auch noch einmal darauf hinweisen, dass unabhängig von den geäußerten Erwägungen gerade in der DOM-Rubrik ein paar ausführlichere Beschreibungen von Nöten sind. – Es wäre toll, wenn sich da jemand einbringen würde! ;-)
Gruß,
Orlok
„Das Wesentliche einer Kerze ist nicht das Wachs, das seine Spuren hinterlässt, sondern das Licht.“ Antoine de Saint-Exupéry