Gawel91
Gawel91

Reputation: 39

Add class to dynamically added elements

I have a function that parses a JSON string and generates a grid of tiles. The grid width and height is set in the JSON, as well as the coordinates of "special tiles" like obstacles.

Thing is, the function that parses the JSON generates the map but doesn't add the "obstacle" class on tiles because they are dynamically added.

My function to parse the JSON :

            $('#json-result textarea').change(function(){

                $.each($.parseJSON($(this).val()), function (item, value) {
                    if(item == 'name') { $('#name').val(value); }
                    if(item == 'width') { $('#width').val(value); }
                    if(item == 'height') { $('#height').val(value); }

                    generateMap();

                    if (item == 'obstacles') {
                        $.each(value, function (i, object) {

                            console.log('[data-x="' + object['x'] + '"][data-y="' + object['y'] + '"]');
                            var obs = $('#map-preview').find('[data-x="' + object['x'] + '"][data-y="' + object['y'] + '"]');

                            console.log(obs);
                            obs.addClass('obstacle');


                        });
                    }

                });

            });

The generateMap function is here and generates the grid. It gets values of height and width in input boxes because the process is also "reverse".

function generateMap(){
    $('#map-preview').html('');

    var height = $('#height').val();
    var width = $('#width').val();

    for(h = 0 ; h < height ; h++) 
    {
          for(w = 0 ; w < width ; w++)
          {
               $('#map-preview').append('<div class="tile" data-x="' + w + '" data-y="' + h + '"></div>');
          }

          $('#map-preview').append('<br />');
    }
}

The HTML generated is inside the map-preview div. The map-preview div is there at the beginning and is empty. The "tiles" are added dynamically.

<div id="map-preview">
    <div class="tile" data-x="0" data-y="0"></div>
    <div class="tile" data-x="1" data-y="0"></div>
    <div class="tile" data-x="2" data-y="0"></div>
    <div class="tile" data-x="3" data-y="0"></div>
    <br>
    <div class="tile" data-x="0" data-y="1"></div>
    <div class="tile" data-x="1" data-y="1"></div>
    <div class="tile" data-x="2" data-y="1"></div>
    <div class="tile" data-x="3" data-y="1"></div>
    <br>
    <div class="tile" data-x="0" data-y="2"></div>
    <div class="tile" data-x="1" data-y="2"></div>
    <div class="tile" data-x="2" data-y="2"></div>
    <div class="tile" data-x="3" data-y="2"></div>
    <br>
</div>

So, in the first snippet of code, I try to add a class to the obstacle tiles, but nothing is done. When I try to type the same code in the Chrome console it works but not in code.

I tried with and without .find(), but nothing works.

Upvotes: 1

Views: 138

Answers (1)

Gabriele Petrioli
Gabriele Petrioli

Reputation: 196306

Most likely the generateMap(); should be called outside of the .each() because now on each iteration of $.each($.parseJSON($(this).val()), function (item, value) { the map is regenerated and thus removes all previous alterations.

Upvotes: 1

Related Questions