3
\$\begingroup\$

I have a page with a list of items. Items have several actions assigned to them. (see screenshot).

One may choose to directly click on an icon next to each row or check a checkbox on the left hand side and click action above the list.

The issue is that after clicking an item OR checking a checkbox of several items and then clicking an action there is a lag (a second or so). Imagine having 100 rows or more.

enter image description here

Script:

 $("a.action:not(.remove)").click(function (e) { // .remove => do not execute on download tasks page
            var selected = new Array(); // array to hold selections or clicks
            var obj = $(this), objData = obj.data();
            e.preventDefault();
            if (!obj.hasClass('disablelink')) {                
                if (objData.ajaxMachineid) {
                    selected.push(objData.ajaxMachineid);
                } else {
                    $("input.checkbox:checkbox:checked:not(.checkall)").each(function () {
                        var checkbox = $(this), machineId = checkbox.val(), packageId = objData.ajaxPackageid.removeSpecialChars().toUpperCase(), operation = objData.ajaxType;
                        var $row = $("#" + machineId + packageId.removeSpecialChars().toUpperCase());
                        if ($row.length) {
                            $row.has("a[data-ajax-type=" + operation + "]:not(.hide)").length ? selected.push(machineId) : $(this).attr('checked', false);
                        }
                    });
                }
                if (selected.length > 0) {
                    // do something more here blah blah blah
                };
            }
            $("input.checkall").attr("checked", false);
        });

Sample HTML of one row:

<tr id="1960AGISGIGAMEM22220204" class="">
<td class="checkbox"><input type="checkbox" value="1960" class="checkbox"></td>
<td class=""><p><a href="/Devices/View/1960">GD009000246</a></p></td>
<td class="platform">PCGames</td>
<td class="cat">Up</td>
<td class="platform"><div class="pbar"><span class="progresslabel"></span></div></td>
<td class="date">10.48.1.236</td>   
<td class="options clearfix">   
   <a title="View" class="iconMagnifier tip" href="/Packages/View/AGI-SGI-GAME-M222-2.0.2.0.4">View</a>
<a title="Install" href="/Packages/PackageActionInstallAsync" data-ajax-type="Install" data-ajax-packageid="AGI-SGI-GAME-M222-2.0.2.0.4" data-ajax-machineid="1960" class="iconDiskPlus action tip ">Install</a>
   <a title="" href="/Packages/PackageActionAsyncDeletePackage" data-ajax-type="DeletePackage" data-ajax-packageid="AGI-SGI-GAME-M222-2.0.2.0.4" data-ajax-machineid="1960" class="iconDelete action tip">Remove</a>                              
</td>       
</tr>
\$\endgroup\$
0

1 Answer 1

2
\$\begingroup\$

So pretty much everything will make a insignificant effect apart from the section where you are looping through each of the checkboxes. See my modifications and notes below.

$("a.action:not(.remove)").click(function (e) { // .remove => do not execute on download tasks page
     var selected = new Array(); // array to hold selections or clicks
     var obj = $(this),
         objData = obj.data(),

         // Moved these up here as they are not specific to the checkboxes
         packageId = objData.ajaxPackageid.removeSpecialChars().toUpperCase(),
         operation = objData.ajaxType;

     e.preventDefault();
     if (!obj.hasClass('disablelink')) {
         if (objData.ajaxMachineid) {
             selected.push(objData.ajaxMachineid);
         } else {

             // This seems a little convoluted to me, normally you would 
             // use [type=checkbox]
             $("input[type=checkbox]:checked:not(.checkall)").each(function () {

                 var checkbox = $(this),
                     machineId = checkbox.val();

                 // No need to call .removeSpecialChars().toUpperCase() on packageId
                 var $row = $("#" + machineId + packageId);

                 if ($row.length) {

                     // Not 100% whether you need .length here
                     // It could also be beneficial to add a class to the row instead
                     // of calling this complex selector
                     $row.has("a[data-ajax-type=" + operation + "]:not(.hide)").length 
                         ? selected.push(machineId) 
                         : $(this).attr('checked', false);

                 }
             });
         }
         if (selected.length > 0) {
             // do something more here blah blah blah
         };
     }
     $("input.checkall").attr("checked", false);
 });

The obvious thing to do on top of my suggestions above is to cache the checkbox list, this means that every time it enters that section, the app will no longer need to go through every element in the DOM looking for all the checkboxes. Doing this will probably have the most meaningful impact on performance.

// in document ready
var checkboxes = $('input[type=checkbox]');

// When you need to find the checked check boxes
var checked = checkboxes.find(':checked:not(.checkall)');
\$\endgroup\$
3
  • \$\begingroup\$ Thanks Tyriar!. the only issue i'm having is having this: var checkboxes = $('input[type=checkbox]'); and then doing this: alert(checkboxes.find(':checked:not(.checkall)').length); always returns 0. however when I have this: alert($('input[type=checkbox]:checked').length); returns the right number of checked checkboxes. ??? \$\endgroup\$
    – Bob
    Mar 6, 2013 at 10:34
  • \$\begingroup\$ I figured it out. I used "filter" instead and it works: var checked = checkboxes.filter(":checked:not(.checkall)"); checked.each(function () { \$\endgroup\$
    – Bob
    Mar 6, 2013 at 10:41
  • \$\begingroup\$ Yeah that's it. Apologies, working without testing :p \$\endgroup\$ Mar 6, 2013 at 20:44

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.