0

how can i update the contents of a dynamically created div as i type into an input field that was also created dynamically.

First i have an input that requests the number of code blocks i want:

$("#count-trigger").click(function(){
    var count = $("#slide-count").val();
    if (count !== "" && $.isNumeric(count)) {
        var i = 1;
        while (i <= count) {
            $('.appendHere').append(

 // Div I want to write to.
 '<div 'id="slide-content_'+i+'">'Sample Title </div>'+

 // Input field used to populate above div
 ' <input                                            '+ 
 '   type    = "text"                                '+
 '   name    = "slide_name_'+i+'"                    '+
 '   data-target    = "slide_name_'+i+'"             '+
            ));
            i++;
        }
});

The above is pretty obvious, enter in a value press go and i get x number of divs/inputs.

Problem comes when trying to populate a created div as I type into created input.

Any help would be greatly appreciated.

kash101
  • 247
  • 2
  • 4
  • 11
  • instead of using `$("#count-trigger").click(function(){` use `$(document).on('click', '#count-trigger', function(){` -- This looks for a `live` click on the page .. conversly -- `.on()` is the new version of deprecated `.live()` – Zak Mar 03 '18 at 18:48
  • *Problem comes when trying to populate a created div as I type into created input.* Can you explain what's that problem? – Ele Mar 03 '18 at 18:48
  • @Zak why event delegation when you have the ID? – Ele Mar 03 '18 at 18:49
  • @Ele -- Because even with the ID -- The element isn't loaded into the DOM on page load .. So it's there .. But the `.click` is only looking for pre-loaded elements into the DOM – Zak Mar 03 '18 at 18:51
  • @Zak how do you know that's the problem? – Ele Mar 03 '18 at 18:51
  • making change now, brb – kash101 Mar 03 '18 at 18:51
  • @zak okay made the change, and it seems as though i can read the contents of the div and input, but i cant write to the div. Anyone have a snippet that might work? – kash101 Mar 03 '18 at 19:39
  • Possible duplicate of [Event binding on dynamically created elements?](https://stackoverflow.com/questions/203198/event-binding-on-dynamically-created-elements) – Heretic Monkey Mar 03 '18 at 21:47
  • @MikeMcCaughan This can either be solved with unique ids + delegation. Or it can be solved with closures as there is a problem of iteration + event binding + keeping a reference to sibling. Doesn't sound like exact duplicate as mere delegation won't solve this. – sabithpocker Mar 03 '18 at 21:50
  • I didn't say it was an *exact* duplicate, and that's not what duplicates need to be. They need to answer the main thrust of the question. Also multiple duplicates can be added. So once this is closed as a duplicate of the above, one could add [JavaScript closure inside loops – simple practical example](//stackoverflow.com/q/750486). – Heretic Monkey Mar 03 '18 at 21:55
  • @MikeMcCaughan My idea of closing on duplicates was always to close only if it is an *exact* duplicate, I guess I got that idea from a post in meta. Do you have any reference to any place where it is mentioned otherwise. I'm confused with SO closing policies now. – sabithpocker Mar 04 '18 at 08:32
  • @sabithpocker [Is there a benefit to closing a question as a duplicate of more than one question?](//meta.stackoverflow.com/a/294125) is where I got the idea. – Heretic Monkey Mar 04 '18 at 13:15

2 Answers2

1

You can use an IIFE to keep a scope for each iteration and use variables that are consumed later. In latest ECMA, you can even make use of block level scope for the same.

$("#count-trigger").click(function() {
  var count = $("#slide-count").val();
  var i = 1;
  while (i <= count) {
    (function() {
      var codeOutput, codeInput;
      codeOutput = $('<div class="code">');
      codeInput = $('<input type="text"/>');
      codeInput.on('input', function() {
        codeOutput.text($(this).val())
      })
      $('.appendHere').append(codeInput, codeOutput);
    })();
    i++;
  }
});
.code {
  border: 1px dashed #bc0000;
  min-height: 20px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<input id="slide-count" type="number" />
<button id="count-trigger">Create</button>

<div class="appendHere"></div>
sabithpocker
  • 14,235
  • 1
  • 36
  • 69
0

Okay, so the change suggested from @zak did the trick.

I added a onchange="liveUpdate(input_id)" to each input.

and then add this function

function liveUpdate(e_id) {
    var typed = $('#'+e_id).val();
    $('[data-target='+e_id+']').text(typed);
}

I imagine there is a better solution to this but considering how much I suck at js and the fact that it works perfectly --I am happy with.

kash101
  • 247
  • 2
  • 4
  • 11