tags:

views:

58

answers:

3

html

  <button>a</button>
  <div class="headerer">
     <p>visit <a href="http://reigel-codes.co.cc"&gt;reigel-codes.co.cc&lt;/a&gt;&lt;/p&gt;
  </div>

problem

how can I add checkbox after <button> by pressing and hold left click ?.. then stop adding when left click is release...

I have tried so far,

$(document).ready(function(){
   $('button').mousedown(function(){
    $(this).after('<input type="checkbox">')
  });
})
+2  A: 

Try this:

$(document).ready(function(){
   var checkInterval;
   $('button').mousedown(function(){
     var me=this;                              // store 'this' button
     checkInterval=setInterval(function() {
       $(me).after('<input type="checkbox">'); // add checkbox after button...
     }, 200);                                  // ...every 200ms on mousedown
   }).bind('mouseup mouseleave', function() {  // bind on mouseup or mouseleave
     clearInterval(checkInterval);             // stop adding checkboxes
   });
});
stagas
Close, but the `$(this)` in your interval handler function will be wrong. `this` in the interval callback will be `window`, not the button, using that code.
T.J. Crowder
@T.J. Crowder: Was correcting that now, it's fixed :)
stagas
+3  A: 

mousedown doesn't have an automatic repeat, but you could create one via setInterval and then turn it off on mouseup via clearInterval. E.g.:

$(document).ready(function(){
    var addHandle, addTarget;

    addHandle = 0;

    $('button')
        .mousedown(function(){
            if (!addHandle) {
                addTarget = $(this);
                addHandle = setInterval(doTheAdd, 250); // Or whatever interval you want
            }
        })
        .bind('mouseup mouseleave', (function(){
            if (addHandle) {
                clearInterval(addHandle);
                addHandle = 0;
                addTarget = undefined;
            }
        });

    function doTheAdd() {
        if (addTarget) {
            addTarget.after('<input type="checkbox">');
        }
    }
});

Be sure to test your target browsers, I wouldn't be 100% certain some of them don't eat mousedown and mouseup on buttons.

Edit Shout out to jAndy for the point about mouseleave, edited the above to use it.

T.J. Crowder
While this is certainly tidier code, you define 2 variables and 1 function on the parent scope which really makes things slower as every reference to them forces the interpreter to move up a step and scan for them. In JS you should be as local as possible.
stagas
@stagas: And in a million iterations, with the above code, it *might* add as much as a millisecond to the total time. :-) Looking for a variable one step out on the scope chain is not a problem. Whereas, using those variables, I've defended against a couple of failure conditions and helped keep the code clear and maintainable. Well worth the trade.
T.J. Crowder
@T.J. Crowder: I'm speaking in generally it is best to avoid variables or functions that move up the scope. In a larger app it makes a lot of a difference. Those milliseconds will eventually add up.
stagas
@stagas: Not in my experience (with some fairly large apps, even on IE, the slowest mainstream browser). Certainly you want to avoid doing silly things, but the above is not silly.
T.J. Crowder
A: 

This is just T.J. Crowders answer compressed:

$(document).ready(function(){
  $('button').mousedown(function(e){
    $(this).data('handle', setInterval($.proxy(function(){
      $(this).after('<input type="checkbox" id="cb' + e.target.id + '">')
    }, this), 50));
  }).mouseup(function(e){
    clearInterval($(this).data('handle'));
  });    
});​​

It has the same problem that, pressing the button and leaving it will keep the Interval alive, so you have to track that down also.

jAndy
Oops yeah just saw that too. It needs a `$('body').mouseup()` or a `mouseleave()` on that.
stagas
Actually, that removes some of my error checking and nearly all of the readability. :-) And I'd expect stagas to chime in here about the speed implications of unnecessary function calls. ;-) Good point about `mouseleave`, though.
T.J. Crowder