admin管理员组

文章数量:1022956

I noticed that in Webkit the <button> element does not fire the onclick event when the mouse is moved from/to child elements of the button during the click. With other words: when the mousedown and mouseup events do not happen on the same element - even if both are children of the button.

The same happens when clicking/releasing on/out of the pixels of the button text.

To clarify I made a testcase: /

It works fine in FireFox. Fails in Chrome 15 and QtWebkit 4.7.1

Is there a way around this? I need a solution specifically for Webkit because my project is targeted to this browser only.

Solution

I could solve this problem based on the method suggested by Jan Kuča (the solution I accepted). Some additional tweaks were necessary, especially introducing a timer to avoid double clicks. Have a look at my fully working solution at JSFiddle: /

I noticed that in Webkit the <button> element does not fire the onclick event when the mouse is moved from/to child elements of the button during the click. With other words: when the mousedown and mouseup events do not happen on the same element - even if both are children of the button.

The same happens when clicking/releasing on/out of the pixels of the button text.

To clarify I made a testcase: http://jsfiddle/gx9B3/

It works fine in FireFox. Fails in Chrome 15 and QtWebkit 4.7.1

Is there a way around this? I need a solution specifically for Webkit because my project is targeted to this browser only.

Solution

I could solve this problem based on the method suggested by Jan Kuča (the solution I accepted). Some additional tweaks were necessary, especially introducing a timer to avoid double clicks. Have a look at my fully working solution at JSFiddle: http://jsfiddle/mwFQq/

Share Improve this question edited Nov 2, 2011 at 17:09 Udo G asked Nov 2, 2011 at 14:41 Udo GUdo G 13.2k16 gold badges63 silver badges92 bronze badges 3
  • You're lucky to have a project targeted only for WebKit. – Alex Turpin Commented Nov 2, 2011 at 14:46
  • 1 wow, that was weird. Never noticed that before – OptimusCrime Commented Nov 2, 2011 at 14:46
  • This is a bug in WebKit, which was apparently recently fixed in Blink (for Chrome), though I'm not seeing it yet: bugs.webkit/show_bug.cgi?id=39620 – jackocnr Commented Nov 29, 2013 at 3:04
Add a ment  | 

3 Answers 3

Reset to default 4

You could set up a mousedown listener on document.body (to fix the problem on the whole page). You would check if the mousedown event originated from an HTMLButtonElement (or from any of its child elements) and if it did, you set up a mouseup listener (on the button so it does not have to bubble too much) that will check the target property of the mouseup event. If it is contained in the button and is different from the target of the mousedown event, you fire a click event like this:

var e = document.createEvent('Events');
e.initEvent('click', true, true);
button.dispatchEvent(e);

(Do this only for WebKit-based browsers so that you don't get multiple click events in other browsers. Or you could call the preventDefault method of the mousedown event as it should also prevent firing the click event.)

You could try adding this CSS style:

button * {
    pointer-events: none;
}

Child elements will then ignore mouse events and the click will e from the button element itself. Here's an example http://jsfiddle/Tetaxa/gx9B3/2/

You can also solve it by pure CSS trick. Just place pseudo element over <button> to cover text:

button {
    position:relative;
    }
button:after {
    position:absolute;
    top:0;
    left:0;
    right:0;
    bottom:0;
    content:'';
    }

I noticed that in Webkit the <button> element does not fire the onclick event when the mouse is moved from/to child elements of the button during the click. With other words: when the mousedown and mouseup events do not happen on the same element - even if both are children of the button.

The same happens when clicking/releasing on/out of the pixels of the button text.

To clarify I made a testcase: /

It works fine in FireFox. Fails in Chrome 15 and QtWebkit 4.7.1

Is there a way around this? I need a solution specifically for Webkit because my project is targeted to this browser only.

Solution

I could solve this problem based on the method suggested by Jan Kuča (the solution I accepted). Some additional tweaks were necessary, especially introducing a timer to avoid double clicks. Have a look at my fully working solution at JSFiddle: /

I noticed that in Webkit the <button> element does not fire the onclick event when the mouse is moved from/to child elements of the button during the click. With other words: when the mousedown and mouseup events do not happen on the same element - even if both are children of the button.

The same happens when clicking/releasing on/out of the pixels of the button text.

To clarify I made a testcase: http://jsfiddle/gx9B3/

It works fine in FireFox. Fails in Chrome 15 and QtWebkit 4.7.1

Is there a way around this? I need a solution specifically for Webkit because my project is targeted to this browser only.

Solution

I could solve this problem based on the method suggested by Jan Kuča (the solution I accepted). Some additional tweaks were necessary, especially introducing a timer to avoid double clicks. Have a look at my fully working solution at JSFiddle: http://jsfiddle/mwFQq/

Share Improve this question edited Nov 2, 2011 at 17:09 Udo G asked Nov 2, 2011 at 14:41 Udo GUdo G 13.2k16 gold badges63 silver badges92 bronze badges 3
  • You're lucky to have a project targeted only for WebKit. – Alex Turpin Commented Nov 2, 2011 at 14:46
  • 1 wow, that was weird. Never noticed that before – OptimusCrime Commented Nov 2, 2011 at 14:46
  • This is a bug in WebKit, which was apparently recently fixed in Blink (for Chrome), though I'm not seeing it yet: bugs.webkit/show_bug.cgi?id=39620 – jackocnr Commented Nov 29, 2013 at 3:04
Add a ment  | 

3 Answers 3

Reset to default 4

You could set up a mousedown listener on document.body (to fix the problem on the whole page). You would check if the mousedown event originated from an HTMLButtonElement (or from any of its child elements) and if it did, you set up a mouseup listener (on the button so it does not have to bubble too much) that will check the target property of the mouseup event. If it is contained in the button and is different from the target of the mousedown event, you fire a click event like this:

var e = document.createEvent('Events');
e.initEvent('click', true, true);
button.dispatchEvent(e);

(Do this only for WebKit-based browsers so that you don't get multiple click events in other browsers. Or you could call the preventDefault method of the mousedown event as it should also prevent firing the click event.)

You could try adding this CSS style:

button * {
    pointer-events: none;
}

Child elements will then ignore mouse events and the click will e from the button element itself. Here's an example http://jsfiddle/Tetaxa/gx9B3/2/

You can also solve it by pure CSS trick. Just place pseudo element over <button> to cover text:

button {
    position:relative;
    }
button:after {
    position:absolute;
    top:0;
    left:0;
    right:0;
    bottom:0;
    content:'';
    }

本文标签: javascriptWebkit ltbutton onclickgt does not fire in certain situationsStack Overflow