JavaScript-Beispiele: DHTML mit Drag & Drop
Mit DHTML lassen sich feine Dinge anstellen. Ob Aufklapplisten, Blitze oder Drag and Drop - der Fantasie sind keine Grenzen gesetzt.Drag and Drop
Eine der vielen Anwendungsmöglichkeiten für DHTML sind sogenannte Drag & Drop Funktionen. Drag & Drop bedeutet, der Benutzer kann ein Element mit der Maus anfassen, es beliebig durch die Gegen ziehen und dann wieder fallen lassen.
Wie bei allen DHTML-Dingen benötigen wir auch hierfür eine Browserunterscheidung. Das Prinzip des Drag & Drop ist dann folgendes: Greift der Besucher nach einem Layer (onmousedown-Ereignis), verankern wir es mit der Maus. Verankern bedeutet, sobald sich die Maus bewegt (onmousemove-Ereignis), muss sich auch der Layer bewegen. Derartiges haben wir im Grunde schon in einem vorhergehenden Abschnitt mit Bildern gemacht - nur eben so, dass das Bild immer der Maus folgt. Läßt der Benutzer die Maustaste dann wieder los (onmouseup-Ereignis), wird auch die Verankerung gelöst.
Schritt 1: Einen Layer greifen
Wir wollen uns erst mal die fertige Funktion zum Aufnehmen ansehen (Browserabfrage vorausgesetzt):var hatgenommen = false;
var posx = 0,posy = 0;
var ziel = new Object();
function Nimm(e)
{
if(hatgenommen == true){return false;}
if(browser == 'IE')
{x=window.event.x; y=window.event.y; t=window.event.srcElement;}
else if(browser == 'OP')
{ x = e.clientX; y = e.clientY; t = e.target;}
else if(browser == 'NN6')
{ x = e.clientX; y = e.clientY; t = e.currentTarget;}
else if(browser == 'NN4')
{
x = e.pageX; y = e.pageY;
//ziel suchen
gefunden = false;
for(i=0;i<document.layers.length;i++)
{
a = document.layers[i];
if(x <= (a.left+a.clip.width) && x >= (a.left) &&
y <= (a.top+a.clip.height) && y >= (a.top))
{
if(gefunden == false){t = a;}
else if(t.zIndex < a.zIndex){t = a;}
}
}
}
ziel = t;
if(browser == 'IE' || browser == 'NN6' || browser == 'OP')
{
posx = (x - parseInt(t.style.left));
posy = (y - parseInt(t.style.top));
}
else if(browser == 'NN4')
{ posx = (x - t.left); posy = (y - t.top); }
hatgenommen = true;
}
Schritt 2: Den Layer bewegen
Anschließen muss der Layer natürlich bewegt werden. Um alles allgemein zu halten, haben wir den Layer zuvor in der Variablen ziel gespeichert. Die Funktion zum Bewegen könnte dann so aussehen:function Bewege(e)
{
if(hatgenommen == false){return false;}
if(browser == 'IE'){ x = window.event.x; y = window.event.y;}
else if(browser == 'NN6') { x = e.clientX; y = e.clientY;}
else{ x = e.pageX; y = e.pageY; }
x = x-posx;
y = y-posy;
if(browser == 'OP')
{ziel.style.left = x; ziel.style.top = y;}
else if(browser == 'IE' || browser == 'NN6')
{ziel.style.left = x+'px'; ziel.style.top = y+'px';}
else if(browser == 'NN4')
{ziel.left = x; ziel.top = y;}
}
Schritt 3: Den Layer wieder los lassen
Um den Layer wieder los zu lassen braucht es nicht viel:function LassLos(){ hatgenommen = false; }
Ist die Variable hatgenommen gleich false wird automatisch die Funktion Bewege abgebrochen - der zuvor bewegte Layer also nicht weiter bewegt.Schritt 4: Alles Zusammenfügen
Um alles komplett zu machen müssen nun nur noch alle Layer mit Event-Handlern verknüpft werden. Auch hierfür schaffen wir uns eine allgemeine Funktion um bei vielen Layern Übersicht und Platz zu sparen. Die Funktion könnte z.B. so aussehen:function Verknuepfe(id)
{
if(browser == 'OP' || browser == 'NN6')
{
document.getElementById(id).onmousedown = Nimm;
document.getElementById(id).onmousemove = Bewege;
document.getElementById(id).onmouseup = LassLos;
}
else if(browser == 'IE')
{
document.all[id].onmousedown = Nimm;
document.all[id].onmousemove = Bewege;
document.all[id].onmouseup = LassLos;
}
else if(browser == 'NN4')
{
document[id].captureEvents(Event.MOUSEMOVE | Event.MOUSEDOWN
| Event.MOUSEUP);
document[id].onmousedown = Nimm;
document[id].onmousemove = Bewege;
document[id].onmouseup = LassLos;
}
}
<html>
<head>
<title>Drag & Drop</title>
<script type="text/javascript">
<!--
ua = navigator.userAgent.toLowerCase();
uv = parseInt(navigator.appVersion);
if(ua.indexOf('opera') != -1 && uv >= 4){browser = 'OP'}
else if(ua.indexOf('msie') != -1 && uv >= 4){browser = 'IE'}
else if(uv == 4){browser = 'NN4'}
else if(uv >= 5){browser = 'NN6'}
// ... gekürzt ...
//-->
</script>
</head>
<body onload="Verknuepfe('Layer1'); Verknuepfe('Layer2')">
<div id="Layer1" style="position:absolute; left:10px; top:10px;
width:100px; height:100px;"> Verschiebe mich!</div>
<div id="Layer2" style="position:absolute; left:200px; op:200px;
width:100px; height:100px;">Verschiebe mich!</div>
</body>
</html>
Ausklapplisten mit dem DOM
Das folgende Beispiel beschreibt Aufklapplisten nach dem DOM, d.h. nicht bzw. nur teilweise DOM-fähige Browser wie der Netscape 4.x oder Opera 4.x können damit leider nur wenig anfangen.Vorbereitung: Die Symbole anfertigen
Das Prinzip ist kurz erklärt: Klickt der User auf einen Listenknoten (ul-Element) der Unterknoten besitzt klappen dies Unterknoten auf bzw. zu. Letztlich ergibt sich eine Art Baumnavigation wie man sie z.B. vom Windows-Explorer kennt:
Darstellung: Das Listen-Menü des Windows-Explorers
Darstellung: Die ausgeschnittenen Listenbilder
<html>
<head>
<title>Ausklappliste</title>
<style type="text/css">
<!--
.liste1
{
list-style-image: url('knopf_normal.jpg');
padding-left: 0px; padding-top: 0px; padding-bottom: 0px;
margin-left: 9px; margin-top: 0px; margin-bottom: 0px;
font-size:12px; font-weight:normal;
}
.liste2
{
position:relative; left:0px; top:0px;
list-style-image: url('knopf_minus.jpg');
padding-left: 0px; padding-top: 0px; padding-bottom: 0px;
margin-left: 9px; margin-top: 0px; margin-bottom: 0px;
font-size:12px; font-weight:bold;
}
.liste3
{
position:relative; left:0px; top:0px;
list-style-image: url('knopf_normal.jpg');
padding-left: 10px; padding-top: 0px; padding-bottom: 0px;
margin-left: 30px; margin-top: 0px; margin-bottom: 0px;
font-size:12px; font-weight:bold;
}
-->
</style>
<script type="text/javascript">
<!--
//-->
</script>
</head>
<body>
<ul class="liste3">
<li class="liste1"> Home</li>
<li id="a1" class="liste2"> Angebote
<ul id="a2" class="liste2">
<li class="liste1"> Aktuelle Angebote</li>
<li id="aa1" class="liste2"> Pflanzen
<ul id="aa2" class="liste2">
<li class="liste1"> Blumen</li>
<li class="liste1"> Bäume</li>
</ul>
</li>
<li class="liste1"> Gartenbedarf</li>
</ul>
</li>
<li class="liste1"> Kontakt</li>
<li class="liste1"> Suche</li>
</ul>
</body>
</html>
Die Zweige mit JavaScript verbinden
Als erstes müssen alle Haupteinträge mit einem Ereignis verknüpft werden. Eine kleine Funktion hilft uns unnötige Schreibarbeit bei vielen Knoten zu sparen (die Browserabfrage muss natürlich mit rein - die sparen wir uns jetzt aber mal):function Verknuepfe(id)
{
if(browser == 'OP' || browser == 'NN6')
{ a = document.getElementById(id); }
else if(browser == 'IE')
{ a = document.all[id]; }
a.onmousedown = Click;
a.style.listStyleImage = 'url('knopf_minus.jpg')';
}
<body onload="Verknuepfe('a1'); Verknuepfe('aa1'); ">
Die Zweige auf und zu klappen
Nun fehlt also nur noch die Funktion Click mit der wir die Unterknoten auf und zu klappen. Wir wollen Sie uns erstmal fertig anschauen:var list = '';
function Click(e)
{
if(browser == 'IE'){ t = window.event.srcElement; }
else if(browser == 'OP'){ t = e.target; }
else if(browser == 'NN6'){ t = e.currentTarget; }
//kinder finden
n = t.id.substr(0,t.id.length-1);
verstecken = false;
if(list.indexOf(n+',') == -1){verstecken = true; list += n+',';}
else
{
list = list.substr(0,list.indexOf(n+','))+
list.substr(list.indexOf(n+',')+n.length+1,list.length);
}
if(browser == 'OP' || browser == 'NN6')
{a = document.getElementById(n+'2');
b = document.getElementById(n+'1');}
else if(browser == 'IE')
{a = document.all[n+'2']; b = document.all[n+'1'];}
if(verstecken == true)
{
a.style.visibility = 'hidden'; a.style.display = 'none';
b.style.listStyleImage = 'url('knopf_plus.jpg')';
}
else
{
a.style.visibility = 'visible'; a.style.display = 'block';
b.style.listStyleImage = 'url('knopf_minus.jpg')';
}
if(browser == 'NN6'){e.cancelBubble = true; e.bubbles = false;}
else if(browser == 'IE'){window.event.cancelBubble = true;}
return false;
}
Am Schluß müssen wir noch das Event-Bubbling verhindern, da sonst Fehler auftreten könnten. Das fertige Resultat sieht dann schon recht nett aus ...
Blitze auf der Seite
Das nun folgende Beispiel vereint die Techniken der zwei vorangegangenen Beispiele in einem: Positionieren von Layern und deren Sichtbarkeit bestimmen. Wir hier nämlich versuchen Blitze auf unsere Homepage zu zaubern. Die vier dafür notwendigen Grafiken haben wir recht schnell mit einem guten Grafikprogramm erstellt:
Darstellung: Die 4 Blitze als Grafiken
Das HTML-Grundgerüst
Jeder dieser vier Grafiken binden wir als Layer in das Dokument ein. Da die Blitze am besten bei Nacht wirken, entscheiden wir uns hier für einen schwarzen Seitenhintergrund. Das HTML-Gerüst:<html>
<head>
<title>Blitze auf der Seite</title>
<script language="JavaScript">
<!--
ua = navigator.userAgent.toLowerCase();
uv = parseInt(navigator.appVersion);
if(ua.indexOf('opera') != -1 && uv >= 4){browser = 'OP'}
else if(ua.indexOf('msie') != -1 && uv >= 4){browser = 'IE'}
else if(uv == 4){browser = 'NN4'}
else if(uv >= 5){browser = 'NN6'}
// ... hier weiter ...
//-->
</script>
<style type="text/css">
<!--
.blitz{position:absolute; left:0px; top:0px; visibility:hidden;}
-->
</style>
</head>
<body text="white" bgcolor="black" onload="StartBlitze()" >
<div id="blitz1" class="blitz">
<img border="0" src="blitz1.gif" >
</div>
<div id="blitz2" class="blitz">
<img border="0" src="blitz2.gif" >
</div>
<div id="blitz3" class="blitz">
<img border="0" src="blitz3.gif" >
</div>
<div id="blitz4" class="blitz">
<img border="0" src="blitz4.gif" >
</div>
<h1>Blitze</h1>
... Seiteninhalt ...
</body>
</html>
Die Blitze erzeugen - Zufallsreihenfolgen festlegen
Als nächstes machen wir uns an das eigentliche Skript und vor allem an die Funktion, die die Blitze positionieren und anzeigen soll. Um die Blitze nicht einfach irgendwo zu positionieren sondern im Hauptteil der Seite, wird der ungefähre Anzeigebereich berechnet. Die Eigenschaften screen.availHeight und screen.availWidth geben uns darüber Aufschluß, wie breit das Browserfenster maximal sein dürfte. Daraus lassen wir eine zufällige Position ermitteln - wie zuvor auch schon benutzt, hilft hier die Methode Math.random weiter. Außerdem wählen wir ebenso zufällig einen der vier Layer aus. Der Rest ist einfach und sollte soweit bekannt sein: Der ausgewählte Layer wird auf die errechnete Position gesetzt und angezeigt. Hier der Code dazu:var blitze_timer = false;
var blitzIDs = new Array('blitz1','blitz2','blitz3','blitz4');
function DoBlitz()
{
i = Math.round(Math.random()*(blitzIDs.length-1));
h = screen.availHeight-100;
w = screen.availWidth-100;
l = Math.round(Math.random()*(w));
t = Math.round(Math.random()*(h));
if(browser == 'NN4')
{
a = document[blitzIDs[i]];
a.visibility = 'show'; a.left = l; a.top = t;
}
else if(browser == 'NN6' || browser == 'OP')
{
a = document.getElementById(blitzIDs[i]);
a.style.visibility = 'visible'; a.style.display = 'block';
if(browser == 'NN6'){a.style.left=l+'px'; a.style.top=t+'px';}
else if(browser == 'OP'){a.style.left=l; a.style.top=t;}
}
else if(browser == 'IE')
{
a = document.all[blitzIDs[i]];
a.style.visibility = 'visible'; a.style.display = 'block';
a.style.left = l+'px'; a.style.top = t+'px';
}
window.setTimeout('ClearBlitze()',200);
}
Die Blitze entfernen
Nun fehlt eigentlich nicht mehr viel. Die obige Funktion DoBlitz ruft nun ja zum Entfernen der Blitze die Funktion ClearBlitze auf. Sie braucht eigentlich nicht viel zu machen als alle Layer durch zu gehen und diese verschwinden zu lassen. Sind alle Blitze wieder unsichtbar wird einfach mit einem zufälligen Timeout ein neuer Blitz gestartet:function ClearBlitze()
{
for(i=0;i<blitzIDs.length;i++)
{
if(browser == 'NN4')
{ document[blitzIDs[i]].visibility = 'hide'; }
else if(browser == 'NN6' || browser == 'OP')
{
a = document.getElementById(blitzIDs[i]);
a.style.visibility = 'hidden';
a.style.display = 'none';
}
else if(browser == 'IE')
{
document.all[blitzIDs[i]].style.visibility = 'hidden';
document.all[blitzIDs[i]].style.display = 'none';
}
}
if(blitze_timer == true)
{
s = Math.round(Math.random()*(20));
window.setTimeout('DoBlitz()',s*100)
}
}
function StartBlitze(){ blitze_timer = true; DoBlitz(); }
function StopBlitze(){ blitze_timer = false; }
Du arbeitest in einer Agentur oder als Freelancer?
Dann wirf doch mal einen Blick auf unsere Software FeatValue.
Über uns

Wir entwickeln Webanwendungen mit viel Leidenschaft. Unser Wissen geben wir dabei gerne weiter. Mehr über a coding project