Was früher ein Diavortrag ( Referat, Vortrag ) mit einem ( Tageslichtprojektor ) genannt wurde, war gestern noch eine "Fach-Termini-Rede" mit dem Overhead-Projektor und kann heute schon zu einem Mitmachen am eingenständigen Erstellen eines Erstellungstoolchens für Präsentationen werden. Insbesondere soll das das erstellte Toolchen klein und robust sein und auch für Blinde leicht bedienbar sein und ästetische "HTML-Power-Slides" erstellten
Jean de La Fontaine ( 1910-1995 ) sagt es so: "Man läuft Gefahr, zu verlieren, wenn man zu viel gewinnen möchte."
Kurzfassung der Aufgabe:
Es soll ein kleines, robustes Präsentation-Erstellungs-Toolchen entwickelt werden. Hier ist ein Muster für ein solches Erstellungs-Toolchen. Diese Toolchen-Entwicklung braucht hinreichendes Wissen zu Regulären Ausdrücken, deshalb ...
Ausgangspunkt waren die Neurophysiologen Warren McCulloch und Walter Pitts, 1956 Stephen Kleene: "die Algebra regulärer Mengen", daher der Begriff: "regulärer Ausdruck". Ken Thompson (Unix) machte daraus die erste praktische Anwendung im Unix-Editor qed.
Reguläre Ausdrücke wurden zu einem unverzichtbaren Bestandteil von zeichenverarbeitenden Sytemen (z.B. textbasierten Editoren, Suchtools, XSLT, usw). Reguläre Ausdrücke können für Transformationen von Zeichenfolgen in modifizierte Zeichenfolgen (z.B.Suchen-und-Ersetzen) verwendet werden, siehe z.B. Reguläre Ausdrücke (Allgemeines, Spezielle Literalzeichen, Reguläre Ausdrücke und Funktionen bei ECMAScript, Referenz , Beispiele ).
Übung und Besprechung von "Suche/Ersetzen mit Regulären Ausdrücken bei einem Editor ( z.B. Notepad++ ) erfolgt in der Veranstaltung.
Mit Regulären Ausdrücken und ECMAScript wurde das ECMAScript-Toolchen erstellt, das dem Lernen und dem Umgang von Regulären Ausdrücken dienen kann. Hierzu bitte erst mit [bearbeiten] und dann [reguläre Audrücke] ein Zusatz-Menu einschalten.
Ein String habe einen typischen Aufbau als HTML-Tabelle. Diese Tabelle soll an den markierten {key}-Stellen mit den repl_obj-Werten von repl_obj.key gefüllt werden. Wie kan dies mit Regulären Ausdrücker gemacht werden? Der Funktion templ_repl(templ_str, repl_obj) wird der templ_str und das repl_obj übergeben. Die Funktion templ_repl() liefert den "eingefüllten" String zurück. Bei einem Fehler findet an der entsprechenden Stelle keine Ersetzung statt.
function templ_repl(templ_str, repl_obj) { return templ_str.replace(/\{([^{}]*)\}/g, function (a, b) { var r = repl_obj[b]; return typeof r === 'string' ? r : a; }); } var repl_obj = { vorname: "Hans Josef", nachname: "Weber" }; var templ_str = '<h2>Anzeige</h2>' + '<table><tr><th> Mein Nachname:</th><td>{nachname}' + '</td></tr><tr><th> Mein Vorname:</th><td>{vorname}' + '</td></tr></table>'; document.getElementById("MYDIV").innerHTML = templ_repl(templ_str, repl_obj);
Zum Erstellen eines Toolchen kann von einem Beispiel ausgegangen werden. Ziel ist es, die folgende Arbeitsansicht in eine HTML-Seite umzuwandel.
-titel; Meine Präsentation -dia; Menu-Item1 -h3; Erstellungstoolchen ( Wie ?) -p; Aus ASCII-Arbeitsansicht wird Praesentation ... -p.r; Den Text eines p-Tags umrandet - dia ; Menu-Item2 - h3 ; Ein weiteres Dia - ta ; // -ta; if ( a < b ) { ta = 15 > 2; } - p . r1 ; -p.r1; Tag - p . r1 blau ; <em class="rot">-p.r1 blau;</em> Tag mit 2 css-Klassen - pre . r ; Das -pre.r; Tag soll Blanks erhalten
Das Toolchen soll also eine HTML-Seite machen. Etwa:
{{ HTML-Header }} <h1 class="titel"> Meine Präsentation</h1> <form class="menu_form" action="#"> <a class="menu_item" href="javascript:show_dia(1)"> Menu-Item1</a> <a class="menu_item" href="javascript:show_dia(2)"> Menu-Item2</a> </form> <form action="#" class=" show_form"> <h3> Erstellungstoolchen ( Wie ?) </h3> <p> Aus ASCII-Arbeitsansicht wird Praesentation ...</p> <p class="r"> Den Text eines p-Tags umrandet </p> </form> <form action="#" class=" hide_form"> <h3> Ein weiteres Dia </h3> <textarea cols="90" rows="5" tabindex="0"> // -ta; if ( a < b ) { ta = 15 > 2; }</textarea> <p class=" r1"> -p.r1; Tag </p> <p class=" r1 blau"> <em class="rot">-p.r1 blau;</em> Tag mit 2 css-Klassen </p> <pre class=" r" tabindex="0"> Das -pre.r; Tag soll Blanks erhalten </pre> </form> {{ HTML-Ende }}
Warum werden form-Tags verwendet? Eine Textarea kann ohne Umwandlung direkt HTML-, JavaScript-, C-Code aufnehmen. Eine Textarea braucht ein umschließendes form-Tag.
Wie gehen wir vor? Hier ist ein Grundgerüst für das Toolchen Als Ausgangspunkt werden lediglich bekannte Funktionen verwendet. Es wird "seitenglobal" mit ECMAScript gearbeitet. Das Grundgerüst wird systematisch erweitert und jeder Schritt getestet.
Zum einfachen Testen kann die Fehlerkonsole des Browsers verwendet werden. Als Hilfsfunktion während der Entwicklung kann die debug_ausgabe(id_dst, arr, hinweis_zur_ausgabe) Array-Content in der Textarea anzeigen ( siehe /*1*/ ). Bei /*2*/ werden die verwendeten Array's deklariert und kommentiert.
Damit der reguläre Ausdruck
src = src.replace(/\r?\n\s*\-\s*([^\s]*)\s*(\.\s*[\S\s]*?)?\s*;/g, 'C_HLP$1$2C_HLP');
auch bereits die 0.src-Zeile (die keine \n haben muß) erfaßt, wurde vor den dem Anfang von src ein \n eingefügt, etwa
src = '\n' + src; // zusätzliches \n am Anfang der Arbeitsansicht src += '\n-ENDE_KENNUNG'; // zusätzlichen Leer-Token am Ende der Arbeitsansicht
Bitte bei /*3*/ das erste Element aus dem split-Array entfernen ( etwa mit split.shift(); ).
// Jetzt sollte der split-Array enthalten: // split[i] das tagName.className-Token enthalten // split[i+1] den Text-Content tagName.className-Token enthalten // Eine Testanzeige von slit-Array ist möglich mit: debug_ausgabe(id_dst, split, "Token-Kontrolle" );return;
Die Schleife bei [*4*] soll split[ ] in 2-er steps durchlaufen, weil
split[i] das cmd- und cls-Token enthält, d.h. jedes split[i] besteht aus t[0] = tagName und t[1] = className's und
split[i+1] den Text-Content zum cmd-Token enthält.
Die Zählvariable j sorgt dafür, daß cmd[ ], cls[ ], text[ ] in "Einer-Steps" geschrieben werden.
[*4*] j = -1; // Wandle split[ ] in cmd[ ], cls[ ], text[ ] for (i = 0; i < split.length - 1; i += 2) { j += 1; // t[i] = tagName, t[i+1] = className's text[j] = split[i + 1]; t = split[i].split('.'); cmd[j] = t[0]; cls[j] = ''; if (t[1]) { cls[j] = t[1]; } //' class="' + t[1]+'"'; } }
Wie wird die die Endekennung "-ENDE_KENNUNG" aus dem letzten text[ ] Element gelöscht?
Wie wird die Schleife bei [*4*] danach getestet?
// Teste cmd[ ], cls[ ], text[ ] nach [*4*] // Testanzeige vom cmd-Array: debug_ausgabe(id_dst, cmd, "cmd-Kontrolle" );return; // Testanzeige von cls-Array: // debug_ausgabe(id_dst, cls, "cls-Kontrolle" );return; // Testanzeige von text-Array: // debug_ausgabe(id_dst, text, "text-Kontrolle" );return;
Wie können nun die getesteten Array's cmd[ ], cls[ ], text[ ] zu einer HTML5-Seite zusammen gesetzt werden?
In einer cmd[ ]-Schleife werden alle "tagName"-Token durchlaufen. Jedes cmd[ ]-Token macht einen HTML5-push-Eintrag in den dia[ ]-Array. Speziell beim dia-Token wird zusätzlich ein a-Tag-Eintrag in den menu[ ]-Array gemacht. Alle Elemente von menu[ ] ergeben form[0]. Jedes dia[i] gehört zu form[i] mit i > 0.
switch (cmd[i]) { ... } behandelt die "tagName"-Token.
dia_nr = 0; // dia_nr wird bei einem -dia;-Token hochgezählt. for (i = 0; i < cmd.length; i += 1) { txt = text[i].replace(/^\s+|\s+$/g, ''); // txt = trim text[i] cls_str = ''; if (cls[i] !== '') { cls_str = ' class="' + cls[i] + '"'; } switch (cmd[i]) { case 'titel': titel = txt; break; /* case 'dia': dia_nr += 1; // -dia wird zu form-Tag // Jedes dia-Token macht einen zusätzlichen Eintrag in den form[0] menu-Array if (dia_nr === 1) { menu.push('\n<form class="menu_form" action="#"> '); } if (txt === '') { txt = 1 + dia_nr; } menu.push(' <a class="menu_item" href="javascript:show_dia(' + (dia_nr) + ')"> ' + txt + '</a>\n'); // bei onload nur erste html-form sichtbar mit 'show_form' sichtbar machen t = cls_str + ' hide_form'; if (dia_nr === 1) { t = cls_str + ' show_form'; } t = '<\/form>\n\n\n<form action="#" class="' + t + '">'; dias.push(t); break; case 'pre': // Das pre-Tag soll Blanks erhaltend sein //dias.push('<' + cmd[i] + cls_str + ... + '\n<\/' + cmd[i] + '>'); break; case 'ta': t = txt.split('\n').length + 1; //dias.push('<textarea cols="90" rows="' + t + '"' + ... + '<\/textarea>'); break; */ default: // hierher kommen alle cmd[i], die keine Sonderbehandlung haben: t = ''; if (cls[i] !== '') { t = ' class="' + cls[i] + '"'; } dias.push('\n<' + cmd[i] + cls_str + '>\n' + txt + '\n<\/' + cmd[i] + '>'); break; } // ende switch } // ende for
Nach "ende for" kommt ein schließender dias.push('<\/form>');
Wie sieht dann ein Test für menu[ ], dias[ ] und
titel + menu.join('\n') + dias.join('\n') aus?
// [*5*] Teste menu[ ], dia[ ] und menu.join('\n')+dias.join('\n') debug_ausgabe(id_dst, menu, "Menu-Kontrolle" );return; // debug_ausgabe(id_dst, dias, "Dias-Kontrolle" );return; // debug_ausgabe(id_dst, titel+menu.join('\n')+dias.join('\n'), "titel+nemu+dias-Kontrolle" );return;
Wenn alle Tests OK sind, so kann von Hand (am HTML-Anfang) ein Style und die ECMAScript-Funktion show_dia(dia_nr) eingefügt werden. Die Vorschau zeigt die Funktionalität.
<style> form.hide_form {position: absolute;top:auto;left:-9999px;overflow:hidden;} form.show_form {position:relative;top:auto;left:auto;overflow:auto;} </style> <script> function show_dia(dia_nr) { var i, f = document.forms; for (i = 1; i < f.length; i += 1) { f[i].className = 'hide_form'; } f[dia_nr].className='show_form'; } </script>
Ähnlich wie die vorhanden Variable html_end können auch der gesamte HTML-Head incl. Style und script ( aus 6 ) "escaped" und auf html_start = "..."; gesetzt werden. Im Code bereits vorhanden sind
// [*7a*] siehe ganz oben html_end = "%3C/body%3E%0A%3C/html%3E%0A", html_start = "...";
Die obige (einfache Funktion show_dia(dia_nr) {...} reicht. Der bisherige einfache Style der Präsentation kann perfektioniert werden (siehe etwa verbesserter Präsentationsstyle )
html_start enthalte den gesamten HTML5-head, incl.
<!DOCTYPE html> <html lang="de"> <head> <meta charset="UTF-8" /> <meta name="robots" content="noindex" /> <title> T_I_T_E_L </title> <style> ... </style> <script> ... </script> </head> <body>
und sei in einen escape-%-String gewandelt. Dann kann bei //[*7*] eingefügt werden:
//[*7*] t = window.unescape(html_start); t = t.replace("T_I_T_E_L", titel); t += '<h1 class="titel"> ' + titel + '</h1>\n'; src = menu.join('\n') + dias.join('\n') + window.unescape(html_end); src = src.replace(/oA_HLP/g, '-'); // zurück-ersetzen, falls in ta am Zeilenanfang \-g; set_string(id_dst, t + src);
Perfektion ist ein Ideal und als solches unerreichbar. Dennoch sollte ...
Der Funktionsrumpf von set_arbeitsansicht_aus_praesentation() geschrieben und getestet werden.
// Rückübersetzung ... function set_arbeitsansicht_aus_praesentation(id_dst, id_src) { alert('Dies ist erst noch zu machen ...aus .html mach ASCII-Arbeitsansicht'); }
Viel Freude bei der Ausarbeitung!
Letzter Abgabetermine So 12.00 Uhr