attachEvent versus addEventListener

17,727

Solution 1

Here's how to make this work cross-browser, just for reference though.

var myFunction=function(){
  //do something here
}
var el=document.getElementById('myId');

if (el.addEventListener) {
  el.addEventListener('mouseover',myFunction,false);
  el.addEventListener('mouseout',myFunction,false);
} else if(el.attachEvent) {
  el.attachEvent('onmouseover',myFunction);
  el.attachEvent('onmouseout',myFunction);
} else {
  el.onmouseover = myFunction;
  el.onmouseout = myFunction;
}

ref: http://jquerydojo.blogspot.com/2012/12/javascript-dom-addeventlistener-and.html

Solution 2

The source of your problems is the KeyBoardHandler function. Specifically, in IE Event objects do not have a target property: the equivalent is srcElement. Also, the returnValue property of Event objects is IE-only. You want the preventDefault() method in other browsers.

function KeyBoardHandler(evt, keyEventArgs) {
    if (evt.keyCode == 13) {
        var target = evt.target || evt.srcElement;
        target.ownerDocument.execCommand("inserthtml",false,'<br />');
        if (typeof evt.preventDefault != "undefined") {
            evt.preventDefault();
        } else {
            evt.returnValue = false;
        }
    }

    /* more code */
}

Solution 3

Just use a framework like jQuery or prototype. That's what they are there for, this exact reason: being able to do this sort of thing w/out having to worry about cross-browser compatibility. It's super easy to install...just include a .js script and add a line of code...

(edited just for you Crescent Fresh)

With a framework, the code is as simple as...

<script type='text/javascript' src='jquery.js'></script>
$('element').keyup(function() { 
  // stuff to happen on event here
});

Solution 4

Here is a function I use for both browsers:

function eventListen(t, fn, o) {
    o = o || window;
    var e = t+Math.round(Math.random()*99999999);
    if ( o.attachEvent ) {
        o['e'+e] = fn;
        o[e] = function(){
            o['e'+e]( window.event );
        };
        o.attachEvent( 'on'+t, o[e] );
    }else{
        o.addEventListener( t, fn, false );
    }
}

And you can use it like:

eventListen('keyup', function(ev){
  if (ev.keyCode === 13){
    ...
  }
  ...
}, Editor)

Solution 5

Different browsers will process events differently. Some browsers have event bubble up throw the controls where as some go top down. For more information on that take a look at this W3C doc: http://www.w3.org/TR/DOM-Level-3-Events/#event-flow

As for this specific issue setting the "userCapture" parameter to false for the addEventListener will make events behave the same as Internet Explorer: https://developer.mozilla.org/en/DOM/element.addEventListener#Internet_Explorer

Share:
17,727
Léon
Author by

Léon

I can perform miracles in PHP, but I'm lousy at Javascript. ;-)

Updated on June 03, 2022

Comments

  • Léon
    Léon about 2 years

    I'm having troubles getting the attachEvent to work. In all browsers that support the addEventListener handler the code below works like a charm, but in IE is a complete disaster. They have their own (incomplete) variation of it called attachEvent.

    Now here's the deal. How do I get the attachEvent to work in the same way addEventListener does?

    Here's the code:

    function aFunction(idname)
    {
        document.writeln('<iframe id="'+idname+'"></iframe>');
        var Editor = document.getElementById(idname).contentWindow.document;
    
        /* Some other code */
    
        if (Editor.attachEvent)
        {
            document.writeln('<textarea id="'+this.idname+'" name="' + this.idname + '" style="display:none">'+this.html+'</textarea>');
            Editor.attachEvent("onkeyup", KeyBoardHandler);
        }
        else
        {
            document.writeln('<textarea id="hdn'+this.idname+'" name="' + this.idname + '" style="display:block">'+this.html+'</textarea>');
            Editor.addEventListener("keyup", KeyBoardHandler, true);
        }
    }
    

    This calls the function KeyBoardHandler that looks like this:

    function KeyBoardHandler(Event, keyEventArgs) {
        if (Event.keyCode == 13) {
            Event.target.ownerDocument.execCommand("inserthtml",false,'<br />');
            Event.returnValue = false;
        }
    
        /* more code */
    }
    

    I don't want to use any frameworks because A) I'm trying to learn and understand something, and B) any framework is just an overload of code I'm nog going to use.

    Any help is highly appreciated!

  • jdonley
    jdonley almost 14 years
    seriously though...go pickup jQuery or something...I used to resist it for the longest time...one day I was forced to learn it to the extent of fixing some code that utilized it...ever since then...I constantly kick myself in the arse for not using it sooner. Greatest invention since sliced bread.
  • Crescent Fresh
    Crescent Fresh almost 14 years
    Why don't you show the OP how crazy easy it is to do with jQuery or Prototype then! "Just use jQuery" ain't no kind of answer.
  • Crescent Fresh
    Crescent Fresh almost 14 years
    What would the converse detachEvent/removeEventListener look like? (you know, for symmetry's sake).
  • Léon
    Léon almost 14 years
    Thanks guys, but no thanks. ;-) First of all I'm trying to learn something here, secondly I don't want an overload of code that I'm not going to use. So please no external framework advice, although I understand the idea behind it.
  • jdonley
    jdonley almost 14 years
    happy? I didn't think something that "crazy easy" needed explaining but since you want to be an arse like you're some kind of interweb police person...p.s. - thanks for the downvote, glad I made your self-righteous day a little brighter.
  • Léon
    Léon almost 14 years
    So how would I use the code above in this case? Sorry, somewhat of a JS noob. :/
  • Mic
    Mic almost 14 years
    @user451513, I've updated the example to look like yours. Is it your question?
  • Pekka
    Pekka almost 14 years
    @Crayon you don't know whether Crescent Fresh actually cast that downvote. +1 because I agree though
  • Léon
    Léon almost 14 years
    @Mic; it doesn't work unfortunately. Can I e-mail you the entire code so you can see the purpose?
  • Mic
    Mic almost 14 years
    Yep. Post it somewhere like friendpaste.com, but quick it is near bedtime here ;)
  • Mic
    Mic almost 14 years
    Here's a small example that works on IE and others gist.github.com/586091 I'll check yours
  • Léon
    Léon almost 14 years
    Let's keep it friendly please, no need to fight over such a stupid little thing. ;-)
  • Mic
    Mic almost 14 years
    Inside the callback function there are differences with IE. eg: event.srcElement while all other browsers use event.target, you may need as well to abstract these like var target = ev.target || ev.srcElement Good Night!
  • lincolnk
    lincolnk almost 14 years
    useCapture only determines if the event fires during the capture sequence or bubble sequence. IE only does the bubble sequence, so false is used for compatibility. it won't change the process of the handler.
  • Léon
    Léon almost 14 years
    Thanks Mic, now I see what I've learned something and fixed the problem.
  • Mic
    Mic almost 14 years
    Good! Welcome to the client-side of the web! Keep PHP to read/generate JSON messages, and do the view with JS and HTML on the browser 8)
  • Mike_OBrien
    Mike_OBrien over 12 years
    In crescent Fresh's defense I'm fairly new to JS and I'm researching this as well and your answer wasn't an answer. even after you added the code snippet the lack of explanation made it no help at all. just saying.
  • iono
    iono almost 11 years
    I mean this with the best of intentions - maybe it would be better to learn not the quirks of the underlying browsers, but to instead spend your time learning higher-level concepts like callbacks, promises, the module pattern, currying, etc. As browsers become more standardised, your ROI on learning such specifics will diminish, whereas learning more abstract Javascript ideas is just as satisfying to learn while at the same time equipping you for other languages and different things down the track.