0

For some reason, I can only get my code to work with old school onclick events. I suspect the following attempt failed because I am actually building a string, inserting it into results div and hoping that these onclick bindings work and they don't.

This should be the right way to do it but nothing happens..

$( "a.collection-item" ).on("click", function(e) {
console.log('test click event fired.');
});

Here's a link for the LIVE DEMO so that you can visualize it better. It's a live search.

Here's the data.json file I am searching...

[
  {
    "name":"Sarah Connor",
    "client_id":"111"
  },
  {
    "name":"John Travolta",
    "client_id":"222"
  },
  {
    "name":"Tom Cruise",
    "client_id":"333"
  }
]

The complete JS code.

$(document).ready(function() {



$('#search').keyup(function(){

// the search input
var searchField = $('#search').val();

// if at least one char is typed...
if (searchField.length > 0) {

// A. Empty results div.
$('#results').empty();

// "i" = ignore case
var regex = new RegExp(searchField, 'i');

var output = '<ul class=\"collection\">';

// get JSON from PHP...
$.getJSON('data.json', function(data) {

// loop through JSON array of key/value pairs...
$.each(data, function(key, val){

// Returns a Number, representing the position of the first occurrence 
// of the specified searchvalue, or -1 if no match is found

// Here we search and compare against the -1 condition.
// Example... val.name.search(regex) different than NOT FOUND...

// If we got a match on name OR client_id....
if ((val.name.search(regex) != -1)) {

output += '<a href=\"/v94/client_select_distinct.php?client_id=' + val.client_id + '\" class=\"collection-item\" onclick=\"js_redirect(this, event)\">';
output += val.name;
output += '<span class=\"badge\">' + val.client_id + '</span>';
output += '</a>';
console.log('match!');

}
// end if

});
// end each

output += '</ul>';
// close ul tag

// output to results div
$('#results').html(output);

});
// end getJSON 

} else {

// clear results div
$('#results').empty();

}
// end search field length condition

});
// end keyup



});
// end document ready


function js_redirect(el, event) {

// Prevent the actual link redirect
event.preventDefault();

// Got to href location via Script instead.
window.location = el.href;

}
<!DOCTYPE html>
<html>
<head>
<!--Import Google Icon Font-->
<link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">
<!--Import materialize.css-->
<link href="https://cdnjs.cloudflare.com/ajax/libs/materialize/0.100.2/css/materialize.min.css" rel="stylesheet"/>
<!--Import Google JQuery-->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<!--Let browser know website is optimized for mobile-->
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>

</head>

<body>

<div class="container">

<div class="row">
<div class="input-field col s12">
<input id="search" type="text" class="validate" placeholder="at least 1 character...">
<label for="search">Search</label>
<div id="results" style="position: absolute; top:48px; background: white;"></div>
</div>

</div>

</div>
<!--JavaScript at end of body for optimized loading-->
<script src="https://cdnjs.cloudflare.com/ajax/libs/materialize/0.100.2/js/materialize.min.js"></script>
</body>
</html>
suchislife
  • 2,892
  • 8
  • 33
  • 63
  • 1
    Wait! Your answer was spot on! You've deleted it! Neil I believe was your name. I'm just going to assume you're reposting it. – suchislife Mar 08 '18 at 03:39
  • 2
    https://stackoverflow.com/questions/203198/event-binding-on-dynamically-created-elements – Tim Morton Mar 08 '18 at 03:45
  • Amazing resource! Event binding on dynamically created elements – suchislife Mar 08 '18 at 03:49
  • Beats self-inflicted baldness :) – Tim Morton Mar 08 '18 at 03:52
  • Man... That user had explained it in a way I actually understood. The idea behind some common misconception regarding what (e) refers to in the question's original scope. I'll settle for the solution. – suchislife Mar 08 '18 at 03:57
  • additional info: `$('a.collection-item').click()` is exactly same with `$('a.collection-item').on('click', function(){})` the right way is $( "#results" ).on("click", 'a.collection-item', function() {}); – plonknimbuzz Mar 08 '18 at 03:58

1 Answers1

0

I don't see in your code where you actually attach that set of listeners, but consider using event delegation instead. That is, don't attach to the 1,000 elements the same listener, attach to a containing element a single listener that only gets called when a matching event bubbles up. It's also easier to deal with than constantly adding it again when elements are added and removed (as you do with $('#results').empty()). Consider:

$('#results').on('click', 'a', function(e){
    console.log('test click event fired.');
    alert('Just so you see it, in case your console clears ...');
});
hunteke
  • 3,309
  • 1
  • 4
  • 15