Monday, August 11, 2008

Одлична addEvent() функција

Можноста за додавање на случки (events) е една од клучните за да се постигне добар и функционален кориснички интерфејс.
Очигледно,еден од начините е случките да се „прилепат“ уште во самиот HTML код, но тоа одзема голем дел од прегледноста на кодот, бидејќи тие (случките) се обработуваат во JavaScript делот на апликацијата, освен кога се работи за тривијални случаи.
Натаму, сите прегледувачи не работат на ист начин во обработката на случките, а особено не ги дефинираат на ист начин. Не можам а да не го споменам Internet Explorer, особено верзиите 6 и подолу (но, и седумката е лоша), кој нема вградено добро „чистење“ на меморијата, па при поинтензивни апликации се зафаќа многу меморија која не можа да се добие назад.
После подолго експериментирање, ја пронајдов и (малку) ја прилагодив функцијата направена од Dustin Diaz, кој од своја страна се базирал на трудот на John Resig (да, тој Џон Ресиг, од jQuery).
Оваа функција е потполно компатибилна со сите прелистувачи, грациозно деградира на постарите верзии (без грешки), го одржува that клучниот збор недопрен и не предизвикува „протекување“ на меморијата кај IE (memory leaks).
Всушност, се состои од три функции од кои првата е за залепување на обработувачи на случки (event handlers), втората за откачување на обработувачите, а третата се повикува при гасење на прозорецот на прегледувачот за да се изврши чистење (flush) на обработувачите и со тоа да се избегнат непријатните течења на меморијата.
EventCache функцијата оригинално е напишана од Mark Wubben.
Внимание! Функцијата се повикува без 'on' во вториот параметар.
На пример: addEvent(tab1, 'click', tab1_click); //Не е 'onclick'
Значи, еве го кодот:

function addEvent( obj, type, fn ) {
if (obj.addEventListener) {
obj.addEventListener( type, fn, false );
EventCache.add(obj, type, fn);
}
else if (obj.attachEvent) {
obj["e"+type+fn] = fn;
obj[type+fn] = function() { obj["e"+type+fn]( window.event ); }
obj.attachEvent( "on"+type, obj[type+fn] );
EventCache.add(obj, type, fn);
}
else {
obj["on"+type] = obj["e"+type+fn];
}
}

function removeEvent( obj, type, fn ) {
if ( obj.detachEvent ) {
obj.detachEvent( 'on'+type, obj[type+fn] );
obj[type+fn] = null;
}
else {
obj.removeEventListener( type, fn, false );
}
}

var EventCache = function(){
var listEvents = [];
return {
listEvents : listEvents,
add : function(node, sEventName, fHandler){
listEvents.push(arguments);
},
flush : function(){
var i, item;
for(i = listEvents.length - 1; i >= 0; i = i - 1){
item = listEvents[i];
if(item[0].removeEventListener){
item[0].removeEventListener(item[1], item[2], item[3]);
};
if(item[1].substring(0, 2) != "on"){
item[1] = "on" + item[1];
};
if(item[0].detachEvent){
item[0].detachEvent(item[1], item[2]);
};
item[0][item[1]] = null;
};
}
};
}();
addEvent(window,'unload',EventCache.flush);

Кодот е со CC-GNU LPGL лиценца, според желбата на Дастин Дијаз.

1 comment:

  1. Thanks for the information, can, I too can help you something?

    ReplyDelete