Events met een parameter...

Status
Niet open voor verdere reacties.

csshunter

Meubilair
Lid geworden
4 aug 2009
Berichten
6.465
Beste mensen,
Het streven is om een mouseover-event aan een link te koppelen, waarbij er een variabele aan de mouseover-functie wordt meegegeven.
Zou toch redelijk veelvoorkomend en eenvoudig moeten zijn, zou je zeggen.
Onder uitgebreid lurken aan koffie en de compatibility-tables van quirksmode.org ("Attributes: a bloody mess.") heb ik o.a. het volgende getest.

Fase 1: setAttribute
Dat was:
[JS]...
links.setAttribute('onmouseover','maakRood('+i+')');
...[/JS]
Werkt prima in Firefox, Chrome, ... maar ja: Internet Explorer 7 doet het niet. :confused:

Fase 2: createAttribute plus setAttributeNode
Dat was:
[JS]...
z = document.createAttribute('onmouseover');
z.value = 'maakRood('+i+')';
links.setAttributeNode(z);
...
[/JS]
Werkt prima in Firefox, Chrome, ... maar ja: bekende verhaal. :confused:

Fase 3: addEventListener plus attachEvent
Hieraan zal toch ook IE7 moeten gehoorzamen.
Dat gaat in principe zo:
[JS]function addEventSimple(obj,evt,fn) {
if (obj.addEventListener)
obj.addEventListener(evt,fn,false);
else if (obj.attachEvent)
obj.attachEvent('on'+evt,fn);
}[/JS]
Maar ... zo kan je niet rechtstreeks een parameter meegeven aan de functie.
Daarvoor moet op een of andere manier een extra functie als tussenstap ingemonteerd worden.
En hier loop ik stuk. Ik kwam bv. tegen:
[JS]someObj.addEventListener("click",
function(){
var newVar = someVar;
some_function(someVar);
},
false);[/JS]
En vele andere Google-suggesties. Maar die krijg ik niet aan de praat, ondanks tig uitgeprobeerde varianten met en zonder enkele en/of dubbele aanhalingstekens en/of escape-slashes.

Dus de vraag:
Weet iemand toevallig uit zijn blote hoofd de oplossing, of een online-pagina met (ook in IE7) werkende demo voor het meegeven van zo'n parameter aan een EventListener?

Mijn dank zal met geen pen te beschrijven zijn. :)

Met vriendelijke groet,
CSShunter
______
PS: Volgens de boekjes moet IE>7 het wel doen op de twee eerste manieren. IE7 laten vallen is echter voor mij geen optie. Dwz wel een optie, maar niet goedgekeurd! ;)

PS-2: In bovenstaande voorbeelden lijkt het misschien alsof ik met een koe een olifant wil vangen: een kleurwisseling bij een mouseover kan natuurlijk veel simpeler en doeltreffender met een css-hover gedaan worden. Maar als het goed gaat, wordt een vergelijkbaar stukje script onderdeel van een groter script, waarin heel andere dingen moeten gebeuren. Vandaar.
 
Dit is de functie die ik graag gebruik - heeft nog een useCapture optie :)
[JS]function addEvent(el, type, callback, useCapture) {
if (el.addEventListener) {
el.addEventListener(type, callback, useCapture);
}
else if (el.attachEvent) {
el.attachEvent("on" + type, callback);
}
else {
console.log(el);
}
}[/JS]

...en aan de context, je eerste twee fasen, te zien wil je 'm zo aanroepen. Ik neem hier aan dat je in een loop zit en de i een nummertje is dat iedere stap verandert. Je gebruikt hier een z.g.n. curry van maakRood met de waarde van i op het moment dat je de listener toevoegt.
[JS]addEvent(links, "mouseover", (function(val) {
return function() {
maakRood(val);
};
})(i), false);[/JS]

Als i een referentie naar de variabele moet blijven, of toch al een referentie naar een JS-object is (dus geen String, Number, Boolean), kun je dit gebruiken:
[JS]addEvent(links, "mouseover", function() {
maakRood(i);
}, false);[/JS]
Edit: Dat laatste is niet logisch, gezien i dan geen key van links zou kunnen zijn, maar 't gaat om het idee ^^
 
Laatst bewerkt:
Ha Robin S,
Deze (eerste optie inderdaad) werkt als een tierelier, en mijn dank is met geen pen te beschrijven! :)

Van de Curry/Schönfinkeling techniek had ik nog nooit gehoord, en ik begrijp er al iets van. Dwz heel in de verte hoor ik zachtjes belletjes rinkelen. ;)
Maar op dit moment geldt voor mij "Alleen het resultaat telt" (titel van het Amsterdams program-akkoord van enkele jaren geleden). Wellicht dat ik me later nog eens in deze materie ga verdiepen, want het is wel bijster interessant.

Nogmaals bedankt!

Met vriendelijke groet,
CSShunter
_________
PS: Ik zet de vraag op "opgelost", maar als ik m'n toepassing af heb (kan nog wel even duren), zal ik het hier melden en aanlinken.
 
Graag gedaan :)

Over currying kun je denken als het 'alvast invullen' van (één of meer) argumenten in een functie.
[JS]function add(x, y) {
return x + y;
}
var add3 = add.curry(3); //add3 is een functie
//Er geldt steeds: add3(y) = add(3, y)
console.log(add3(5)); //8[/JS]
In dit voorbeeld kun je de add-functie curryen om niet iedere keer die x = 3 in te hoeven vullen. In jouw vraag wilde je i 'alvast invullen' :) Zo'n curry-functionaliteit is niet standaard, maar veel JS-libraries hebben er één.
 
Juist, de klepel begint al dichter bij de klok te komen. :)
Ter illustratie van het bovenstaande heb ik 3 testpagina's gemaakt:
  1. Met setAttribute, werkt niet in IE7.

  2. Met createAttribute, werkt niet in IE7.

  3. Met addEventListener en curry, werkt ook in IE7.
De laatste moet het ook in IE8 en IE9 doen, dus dat is de oplossing.
curry.png


Met vriendelijke groet,
CSShunter
___________
PS: In IE8 en IE9 kan ik niet testen, en met Browsershots of Netrenderer kom ik in dit geval niet ver. ;)
Voor de compleetheid ben ik wel nieuwsgierig wat IE8 en IE9 met test 1 resp. test 2 doen. Wie 8 of 9 heeft mag het zeggen: werken die wel of niet?
 
Status
Niet open voor verdere reacties.
Terug
Bovenaan Onderaan