lukeseager
lukeseager

Reputation: 2615

Check for value in array, remove if true

I have a grid of images, each with a data-image attribute and value.

When a user selects an image, its data-image attributes's value is added to an array.

I want the code to work so that when the user clicks an item, if the item already is in the array (that is, if the user has clicked on it before), then it gets removed.

Like a select/de-select option.

HTML

<div class="fifth" data-image="1">
    <div class="full clearfix relative">
        <img src="image.png" />

        <div class="overlay"></div>

    </div>
    <div class="options">
        <h4 class="txt-white left">#0001</h4>
        <h4 class="right txt-gold select-image" data-image="1">Select</h4>
    </div>
</div>

jQuery

var images = [];
var price = $('.order').data('price');

    // select
    $('.select-image').on('click', function() {

        $(this).parent().parent().toggleClass('selected');
        $(this).toggleClass('selected');

        if( $(this).hasClass('selected') ) {
            $(this).html('&#10005;');
        } else {
            $(this).html('Select');
        }

        images = $.grep(images, function(value) {
            return value != $(this).data('image');
        });

        console.log(images);

        images.push($(this).data('image'));

        var items = images.length;

        $('.total-price').html(items*price);

    });

But, I can't seem to figure out how $.grep works. Any ideas?

[UPDATE]

Here's a JS Fiddle of what I have so far, you can see the issue here.

Upvotes: 1

Views: 852

Answers (3)

Koen.
Koen.

Reputation: 26999

No need to use $.grep here, a native indexOf and splice will suffice.

var images = [], image, index;
$('.select-image').on('click', function() {
    // ....
    image = $(this).data('image');
    // Lookup image in array
    index = images.indexOf(image);
    if(~index){ // ~ makes index evaluate as boolean (not really though)
         // If found, remove that entry from the array
         images.splice(index, 1);
    }else{
         // Otherwise, add it to the array
         images.push(image);
    }
    // ....
});

Upvotes: 1

Danny Nophut
Danny Nophut

Reputation: 60

Grep takes an array and performs a function for each element in this array. This function returns true or false, depending on a given criteria. Grep will then return every element for which the function returned true in an array.

$.grep( images, function($arrayElement, index) {
  return $arrayElement.attr("data-anything") == "yes i like fish";
});

I am not quite sure why you would need to use grep on a grid of images; How about giving a ".selected"-Class and use this in order to filter out the elements that have been selected?

Edit: You are basically asking for the not-case. You want to selected elements which do not have a certain value.

var a_preselected_value = 9;

var images_with_one_id_deselected = $.grep( images, function($arrayElement, index) {
  return $arrayElement.data("image") != a_preselected_value;
});

Upvotes: 0

JF it
JF it

Reputation: 2403

Grep loops through an array in pretty much the same way as $.each with one exception. If you return true from the callback, the element is retained. Otherwise, it is removed from the array.

Your code should look something like this:

items = $.grep(items, function (el, i) {
if (i === 5) { // or whatever
    return false;
}

// do your normal code on el

return true; // keep the element in the array
});

Upvotes: 0

Related Questions