51

After the user clicks on...."log in" button, and other events, I made a loading script -to let users know they have to wait (Until ajax replies back).

How can I DISABLE any MOUSE CLICKS (right click, left click, double click, middle click, x click), on div id="doc"?
I want to add that code to loading.js


HTML

<html>
...
<body>
<div id="doc">
   <div id="content">
   ...
   <input type="button" value="Login" id="login" />
   ...
   </div id="content">
</div id="doc">
</body>
</html>



loading.js

function load_bar(x)
{
    if (x==0)
    {
    $(document.body).css( {"cursor": "default"} );
    $("body").css( {"cursor": "default"} );
    $("#loading").css("visibility", "hidden"); //modal window
//  $("#doc").....ENABLE all clicks (left/right/etc)
    }

    else if (x==1)
    {
    $(document.body).css( {"cursor": "wait"} );
    $("body").css( {"cursor": "wait"} );
    $("#loading").css( {"visibility": "visible"} ); //modal window
//  $("#doc").....DISABLE all clicks (left/right/etc)
    }

    else
    {
    return alert("Wrong argument!");
    }
}



jQuery

$(document).ready(function()
{
//AJAX
$("#login").click(function()
{
    load_bar(1); //DISABLE clicks and show load_bar
    $(":input").attr("disabled", true);


$.post( 
    ...
    function(data)
    {
    ...
    load_bar(0); //ENABLE clicks and hide load_bar
    ...
    } //END: if:else
}); //END:$.post
    ...
}); //END:ajax
}); //END:jQuery
Omar
  • 11,783
  • 21
  • 84
  • 114
  • 1
    @alonisser I am using BOTH charles-ma and minitech solutions. Unfortunately I this website won't allow 2-votes >_ – Omar Jan 14 '12 at 02:15

5 Answers5

77

You can add a simple css3 rule in the body or in specific div, use pointer-events: none; property.

Brandon Durham
  • 7,096
  • 13
  • 64
  • 101
Leonardo Salles
  • 841
  • 6
  • 4
45

You can overlay a big, semi-transparent <div> that takes all the clicks. Just append a new <div> to <body> with this style:

.overlay {
    background-color: rgba(1, 1, 1, 0.7);
    bottom: 0;
    left: 0;
    position: fixed;
    right: 0;
    top: 0;
}
Ry-
  • 218,210
  • 55
  • 464
  • 476
  • how can I add `loading.jpg` ( `$("#loading")` )at the very center of this div (`.overlay`) -Center of the screen? – Omar Dec 21 '11 at 20:35
  • 4
    @Omar: `background-image: url('loading.jpg'); background-repeat: no-repeat; background-position: center center;` would be one way. Another would be to add `text-align: center;` on `.overlay`, then add a new image (`#loading`) in `.overlay` with the style `margin-top: 50%; position: relative; top: -(half-image's-height)px`. – Ry- Dec 21 '11 at 20:37
  • give `loading.jpg` a top and left equal to `parent.height()/2-loading.height()/2` and `parent.width()/2-loading.width()/2` respectively – Greg Guida Dec 21 '11 at 20:39
  • @minitech Is there any difference between `background-position: center center;` and `text-align: center...`? – Omar Dec 21 '11 at 20:44
  • @Omar: I think the latter is a bit more compatible, but it will degrade gracefully all the same. `background-*` is a little cleaner in syntax. – Ry- Dec 21 '11 at 20:49
  • @minitech I hope it's not too late. I tried this css on Firefox with no problems. However, I also need to make it compatible with IE. I tried several ways with no success. – Omar Jan 10 '12 at 00:44
  • @minitech This fiddle works fine on Firefox. With the exception that it does not center's properly. However, it does not work on IE8: http://jsfiddle.net/f7xFy/3/ – Omar Jan 10 '12 at 01:10
  • @minitech I am not sure what I am doing wrong. The fiddle works just fine on IE, but not when I load the very same code on my client's host [http://tiny.cc/7brtd](http://tiny.cc/7brtd) – Omar Jan 14 '12 at 00:36
  • @Omar: You're in quirks mode. Add a ` `. – Ry- Jan 14 '12 at 00:39
  • @minitech Great! Now to the next problem >_< Why is not centered? Right now is leaning tooooo much to the bottom – Omar Jan 14 '12 at 00:42
  • @Omar: Can you update your live web example to add that, please? – Ry- Jan 14 '12 at 00:46
  • @minitech You mean this link: http://tiny.cc/7brtd? I updated it already (Added ` `) – Omar Jan 14 '12 at 01:07
  • @Omar: No, the thing that isn't centering. – Ry- Jan 14 '12 at 01:19
  • @minitech ???...The div that is not centered is `
    – Omar Jan 14 '12 at 01:29
  • 1
    @minitech It auto-aligns with the window's resizing changes too...wicked!!! Here is the final Fiddle (I added some persona customization) http://jsfiddle.net/jJ85P/ – Omar Jan 14 '12 at 02:10
  • @minitech the div won't take a white border, but I can compromise =) ...`id="stretch'` on your fiddle http://jsfiddle.net/minitech/f7xFy/6/, or `id=loading_box` on my fiddle http://jsfiddle.net/jJ85P/ – Omar Jan 14 '12 at 02:26
  • @minitech why adding the jQuery from "Charles Ma"'s answer when your original answer works without it (hence making the code simpler). see http://jsbin.com/qixiwuqozive/1/edit?html,css,js,output – Adriano Sep 10 '14 at 11:50
  • @AdrienBe: I just updated the fiddle Omar linked above. I don’t really remember what this whole thing is about anymore… – Ry- Sep 10 '14 at 18:56
  • how can we make it work for IE8 as it doesnot take alpha property of background color in rgba ? – Tarun Mar 30 '15 at 07:11
  • @tarun_telang: Set it to an opaque background colour and use the `opacity` property. – Ry- Mar 30 '15 at 14:47
  • @minitech - opactity attribute is also not supported in IE 8. – Tarun Mar 31 '15 at 09:58
  • for IE 8 the following CSS code needs to be used. {filter: alpha(opacity=80); opacity: 0.8} – Tarun Mar 31 '15 at 10:52
22

To disable all mouse click

var event = $(document).click(function(e) {
    e.stopPropagation();
    e.preventDefault();
    e.stopImmediatePropagation();
    return false;
});

// disable right click
$(document).bind('contextmenu', function(e) {
    e.stopPropagation();
    e.preventDefault();
    e.stopImmediatePropagation();
    return false;
});

to enable it again:

$(document).unbind('click');
$(document).unbind('contextmenu');
Charles Ma
  • 47,141
  • 22
  • 87
  • 101
  • I did not know you could disable clicks on the whole document! I guess I do not need `
    ` after all =)
    – Omar Dec 21 '11 at 21:04
  • 5
    That won't disable middle-clicks. Also, an event handler set at the document level will be called _after_ the event bubbles up from the actual elements. (You're calling `stopPropagation()` after it has already propagated to the top.) http://jsfiddle.net/WWx9B/ – nnnnnn Dec 21 '11 at 21:22
  • 1
    You're right, JS handlers bound to elements below document will still fire, but it does stop html clickable events like link navigation and form submission. it also doesn't disable middle click, and I don't know a cross browser way to disable it. But the OP can probably achieve what he wants using a mix of my approach and a css overlay described by @minitec – Charles Ma Dec 22 '11 at 00:12
  • 1
    @charles-ma I guess you are right! A mixed approach is a better choice. – Omar Jan 03 '12 at 19:42
  • @charles-ma Even with this code, it is still clicking on IE8: http://jsfiddle.net/f7xFy/3/ – Omar Jan 10 '12 at 01:14
  • hm...try returning false from those functions. I don't have IE8 to test right now – Charles Ma Jan 13 '12 at 07:47
  • ??? I am a beginner...what do you mean by returning false? isn't it already returning false...`e.stopImmediatePropagation(); return false;`? – Omar Jan 14 '12 at 02:22
  • @Omar see http://stackoverflow.com/questions/5302903/jquery-event-stopimmediatepropagation-vs-return-false – Adriano Sep 10 '14 at 12:05
  • @CharlesMa although I like your solution (a jQuery approach), why would you use both your solution & the one of "minitec", when just using the one from "minitec" seems to work just fine for all clicks (right, left, middle...). see http://jsbin.com/nuzezayiliko/1/edit?html,css,js,output – Adriano Sep 10 '14 at 12:08
  • ooops, there was a small mistake in the live example I provided. See the correct one http://jsbin.com/picewamajufo/1/edit?html,css,js,output – Adriano Sep 10 '14 at 13:03
  • Uncaught ReferenceError: e is not defined – Vaibhav Ahalpara Mar 12 '18 at 15:19
8

something like:

    $('#doc').click(function(e){
       e.preventDefault()
       e.stopImmediatePropagation() //charles ma is right about that, but stopPropagation isn't also needed
});

should do the job you could also bind more mouse events with replacing for: edit: add this in the feezing part

    $('#doc').bind('click mousedown dblclick',function(e){
       e.preventDefault()
       e.stopImmediatePropagation()
});

and this in the unfreezing:

  $('#doc').unbind();
alonisser
  • 11,542
  • 21
  • 85
  • 139
1

The easiest way to freeze the UI would be to make the AJAX call synchronous.

Usually synchronous AJAX calls defeat the purpose of using AJAX because it freezes the UI, but if you want to prevent the user from interacting with the UI, then do it.

gilly3
  • 87,962
  • 25
  • 144
  • 176
  • 2
    +1 Good idea :) Although, if the user presses a bunch of keys in frustration, won't they all come back after it's done? – Ry- Dec 21 '11 at 20:40
  • 1
    @gilly3 I have noooo idea what you are talking about :,( It sounds gibberish to me (too advanced) – Omar Dec 22 '11 at 02:10