简体   繁体   中英

Avoiding redundant code in Javascript(JQuery)

I have written a script for my project which allows the user to manage inventory using JS, PHP, and MySql. The user may select an inventory location and update the count of a product by clicking buttons. This process uses AJAX calls in order to update the front-end and back-end in real-time.

My code works, however, I am not satisfied with the execution due to the amount of code redundancy. I have the two add and remove AJAX functions in order to update the first inventory location displayed to the website. But in order to allow the user to continue to do this after they have selected a new location, I have to reuse the code of these two functions nested within the select location Ajax code. My JS skills are not that strong and I was wondering if JQuery allows better code cohesion. In PHP I would have created a class and functions to preform this task to avoid code reuse. Can I achieve something similar in JQuery?

 // This script is used update and display changes to inventory displayed on cp.php $(document).ready(function() { var this_item; var itemid; var count; // Store the first table from the MySQL Database and display it to the page var location = $('.location_select').attr('title'); $('.default_location').empty(); $('.default_location').append(location); // Add to the inventory count of the selected product $('.glyphicon-plus').click(function() { event.preventDefault(); // Store the selected product name and update its display count on the page this_item = $(this).attr('title'); itemid = this_item.substr(0, this_item.length - 1); count = parseInt($('#'+itemid).text()); count++; // Send the inventory count to modifyproduct.php and update new count to MySQL $.ajax ({ url: 'modifyproduct.php', type: 'GET', data: { location: location, itemid: itemid, count: count, }, success: function(serverResponse) { $('#'+itemid).hide(); $('#'+itemid).html(count).delay(170); $('#'+itemid).fadeIn(); } }); }); // Remove from the select inventory count $('.glyphicon-minus').click(function() { event.preventDefault(); // Store the selected product name and update its display count on the page this_item = $(this).attr('title'); itemid = this_item.substr(0, this_item.length - 1); count = parseInt($('#'+itemid).text()); count--; // Send the inventory count to modifyproduct.php and update new count to MySQL $.ajax ({ url: 'modifyproduct.php', type: 'GET', data: { location: location, itemid: itemid, count: count, }, success: function(serverResponse) { $('#'+itemid).hide(); $('#'+itemid).html(count).delay(170); $('#'+itemid).fadeIn(); } }); }); // Select inventory location to be displayed from .location_select menu $('.location_select').click(function(){ location = $(this).attr('title'); $('.default_location').empty(); $('.default_location').append(location); $.ajax ({ url: 'display.php', type: 'GET', data: { location: location, }, success: function(serverResponse) { $('#display_inventory').fadeOut('slow'); $('#display_inventory').empty(); $('#display_inventory').hide(); $('#display_inventory').append(serverResponse); $('#display_inventory').fadeIn('slow'); $('.glyphicon-plus').click(function() { event.preventDefault(); this_item = $(this).attr('title'); itemid = this_item.substr(0, this_item.length - 1); count = parseInt($('#'+itemid).text()); count++; $.ajax ({ url: 'modifyproduct.php', type: 'GET', data: { location: location, itemid: itemid, count: count, }, success: function(serverResponse) { $('#'+itemid).hide(); $('#'+itemid).html(count).delay(170); $('#'+itemid).fadeIn(); } }); }); $('.glyphicon-minus').click(function() { event.preventDefault(); this_item = $(this).attr('title'); itemid = this_item.substr(0, this_item.length - 1); count = parseInt($('#'+itemid).text()); count--; $.ajax ({ url: 'modifyproduct.php', type: 'GET', data: { location: location, itemid: itemid, count: count, }, success: function(serverResponse) { $('#'+itemid).hide(); $('#'+itemid).html(count).delay(170); $('#'+itemid).fadeIn(); } }); }); } }) }); }); 

Functions are first class citizens in JS therefore

var fn = function() { ... }

In your code I see that the only thing that changes is the value of count

I'd do the following

var modifyItem = function(quantity) {
  return function() {
    event.preventDefault();
    this_item = $(this).attr('title');
    itemid = this_item.substr(0, this_item.length - 1);
    count = parseInt($('#' + itemid).text());
    // note that quantity is added here
    count += quantity
    $.ajax({
      url: 'modifyproduct.php',
      type: 'GET',
      data: {
        location: location,
        itemid: itemid,
        count: count,
      },
      success: function(serverResponse) {
        $('#' + itemid).hide();
        $('#' + itemid).html(count).delay(170);
        $('#' + itemid).fadeIn();
      }
    });
  }
}

And then use the returning value (a function) as the action to be done

$('.glyphicon-plus').click(modifyItem(+1))
$('.glyphicon-minus').click(modifyItem(-1))

You don't have to have the second copy of your event handlers on '.glyphicon-plus' and '.glyphicon-minus'; you just need to change how you're attaching the handlers.

Use "on" rather than "click", and bind to a parent element that is always present, such as a table, a div, whatever wraps that section of your page.

"On" takes a selector: http://api.jquery.com/on/

$(".product-table").on("click", ".glyphicon-plus", function() {
    //your function body
});

This has the added benefit of the event handler being active for any .glyphicon-plus that you may create via the DOM at any time. Very handy for pages that do a lot of client-side updating.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM