I have a website that will fade out a section of my website, load new content in, and fadeIn. There's a feature I had where a picture would get big when you click on it (it's a jQuery event).
It works when I put it on the code when it loads up, however nothing happens when I click something in the area the AJAX loaded.
Here's how I load AJAX:
// If the user clicks the logo
$("#logo").click(function() {
$("#right_bar_wrapper").animate({ height: 'toggle', opacity: 'toggle' }, '200');
var thePostData = "username=c";
$.ajax({
type: "POST",
url: ".php",
data: thePostData,
success: function(theRetrievedData) {
document.getElementById('right_bar_wrapper').innerHTML = theRetrievedData;
$("#right_bar_wrapper").fadeIn("200");
}
});
});
Here's how I make a picture big:
// If the user makes a picture bigger
$(".makePictureBig").click(function() {
var theClassId = $(this).attr('id');
var theID = theClassId.substring(6)
var bigPictureComment = "#bigpicture_comment_" + theID;
var littlePictureComment = "#littlepicture_comment_" + theID;
var ddd = document.getElementById(theClassId);
var getBig = document.getElementById(bigPictureComment);
var getLittle = document.getElementById(littlePictureComment);
if (ddd.style.width == "180px") {
ddd.style.width="430px";
ddd.style.marginBottom='10px';
ddd.style.cssFloat="left";
$(littlePictureComment).hide();
$(bigPictureComment).show();
} else {
ddd.style.width="180px";
ddd.style.marginBottom='0px';
$(bigPictureComment).hide();
$(littlePictureComment).show();
}
});
Here's my code that loads when displayed:
<div class="sidebar_image_box_newsfeed">
<div class="sidebar_image_box_newsfeed_user_info makeProfileAppear"><img src=".php?short_string=uxpi&size=thumbnail" />Brandon Vento</div>
<img src=".php?short_string=o1sk&size=big" id="image_o1sk" class="makePictureBig" style="width: 180px; margin-bottom: 15px;" />
<div class="sidebar_image_box_newsfeed_user_info_comments" style="float: right; margin-top: -1px; margin-left: 20px; display: none;" id="bigpicture_comment_o1sk">9</div>
<div class="sidebar_image_box_newsfeed_caption">A cool caption will eventually go here.</div>
<div class="sidebar_image_box_newsfeed_user_info_comments" id="littlepicture_comment_o1sk">9</div>
<div style="clear: both;"></div>
</div>
Here's what doesn't load after loaded via AJAX:
<div class='sidebar_image_box_newsfeed'>
<div class='sidebar_image_box_newsfeed_user_info makeProfileAppear' id='user_coultonvento'><img src='.php?short_string=kmdp&size=thumbnail' />TheAmazingCoultoniusTheFourneeth...</div>
<img src='.php?short_string=6v9o&size=big' id='image_6v9o' class='makePictureBig' style='width: 180px;' />
<div class='sidebar_image_box_newsfeed_user_info_comments' style='float: right; margin-top: -1px; margin-left: 20px; display: none;' id='bigpicture_comment_6v9o'>9</div>
<div class='sidebar_image_box_newsfeed_caption'>Usama bin laden? I believe that's a typo, Fox. </div>
<div class='sidebar_image_box_newsfeed_user_info_comments' id='littlepicture_comment_6v9o'>9</div>
<div style='clear: both;'></div>
</div><div class='sidebar_image_box_newsfeed'>
<div class='sidebar_image_box_newsfeed_user_info makeProfileAppear' id='user_BrandonVento'><img src='.php?short_string=e4r7&size=thumbnail' />Brandon Vento</div>
<img src='.php?short_string=o1sk&size=big' id='image_o1sk' class='makePictureBig' style='width: 180px;' />
<div class='sidebar_image_box_newsfeed_user_info_comments' style='float: right; margin-top: -1px; margin-left: 20px; display: none;' id='bigpicture_comment_o1sk'>9</div>
<div class='sidebar_image_box_newsfeed_caption'></div>
<div class='sidebar_image_box_newsfeed_user_info_comments' id='littlepicture_comment_o1sk'>9</div>
<div style='clear: both;'></div>
</div>
Sorry for all the code. I find it all necessary!
Thanks in advance!
Coulton
I have a website that will fade out a section of my website, load new content in, and fadeIn. There's a feature I had where a picture would get big when you click on it (it's a jQuery event).
It works when I put it on the code when it loads up, however nothing happens when I click something in the area the AJAX loaded.
Here's how I load AJAX:
// If the user clicks the logo
$("#logo").click(function() {
$("#right_bar_wrapper").animate({ height: 'toggle', opacity: 'toggle' }, '200');
var thePostData = "username=c";
$.ajax({
type: "POST",
url: "http://myflashpics.com/v2/process_newsfeed.php",
data: thePostData,
success: function(theRetrievedData) {
document.getElementById('right_bar_wrapper').innerHTML = theRetrievedData;
$("#right_bar_wrapper").fadeIn("200");
}
});
});
Here's how I make a picture big:
// If the user makes a picture bigger
$(".makePictureBig").click(function() {
var theClassId = $(this).attr('id');
var theID = theClassId.substring(6)
var bigPictureComment = "#bigpicture_comment_" + theID;
var littlePictureComment = "#littlepicture_comment_" + theID;
var ddd = document.getElementById(theClassId);
var getBig = document.getElementById(bigPictureComment);
var getLittle = document.getElementById(littlePictureComment);
if (ddd.style.width == "180px") {
ddd.style.width="430px";
ddd.style.marginBottom='10px';
ddd.style.cssFloat="left";
$(littlePictureComment).hide();
$(bigPictureComment).show();
} else {
ddd.style.width="180px";
ddd.style.marginBottom='0px';
$(bigPictureComment).hide();
$(littlePictureComment).show();
}
});
Here's my code that loads when displayed:
<div class="sidebar_image_box_newsfeed">
<div class="sidebar_image_box_newsfeed_user_info makeProfileAppear"><img src="http://myflashpics.com/get_image.php?short_string=uxpi&size=thumbnail" />Brandon Vento</div>
<img src="http://myflashpics.com/get_image.php?short_string=o1sk&size=big" id="image_o1sk" class="makePictureBig" style="width: 180px; margin-bottom: 15px;" />
<div class="sidebar_image_box_newsfeed_user_info_comments" style="float: right; margin-top: -1px; margin-left: 20px; display: none;" id="bigpicture_comment_o1sk">9</div>
<div class="sidebar_image_box_newsfeed_caption">A cool caption will eventually go here.</div>
<div class="sidebar_image_box_newsfeed_user_info_comments" id="littlepicture_comment_o1sk">9</div>
<div style="clear: both;"></div>
</div>
Here's what doesn't load after loaded via AJAX:
<div class='sidebar_image_box_newsfeed'>
<div class='sidebar_image_box_newsfeed_user_info makeProfileAppear' id='user_coultonvento'><img src='http://myflashpics.com/get_image.php?short_string=kmdp&size=thumbnail' />TheAmazingCoultoniusTheFourneeth...</div>
<img src='http://myflashpics.com/get_image.php?short_string=6v9o&size=big' id='image_6v9o' class='makePictureBig' style='width: 180px;' />
<div class='sidebar_image_box_newsfeed_user_info_comments' style='float: right; margin-top: -1px; margin-left: 20px; display: none;' id='bigpicture_comment_6v9o'>9</div>
<div class='sidebar_image_box_newsfeed_caption'>Usama bin laden? I believe that's a typo, Fox. </div>
<div class='sidebar_image_box_newsfeed_user_info_comments' id='littlepicture_comment_6v9o'>9</div>
<div style='clear: both;'></div>
</div><div class='sidebar_image_box_newsfeed'>
<div class='sidebar_image_box_newsfeed_user_info makeProfileAppear' id='user_BrandonVento'><img src='http://myflashpics.com/get_image.php?short_string=e4r7&size=thumbnail' />Brandon Vento</div>
<img src='http://myflashpics.com/get_image.php?short_string=o1sk&size=big' id='image_o1sk' class='makePictureBig' style='width: 180px;' />
<div class='sidebar_image_box_newsfeed_user_info_comments' style='float: right; margin-top: -1px; margin-left: 20px; display: none;' id='bigpicture_comment_o1sk'>9</div>
<div class='sidebar_image_box_newsfeed_caption'></div>
<div class='sidebar_image_box_newsfeed_user_info_comments' id='littlepicture_comment_o1sk'>9</div>
<div style='clear: both;'></div>
</div>
Sorry for all the code. I find it all necessary!
Thanks in advance!
Coulton
8 Answers
Reset to default 13.click()
is a shorthand of .bind('click')
, which only binds to elements that are already in the page
To bind events to current and future elements, you must use .live()
// If the user makes a picture bigger
$(".makePictureBig").live('click',function() {
//code
});
Edit:
As of jQuery 1.7, live is deprecated. You can use jQuery on:
$(".makePictureBig").on('click', function() {
//code
});
Or, for delegated event handlers:
$("#wrapper").on('click', '.makePictureBig', function(){
//code
});
This is because all your events that you write inside document ready will get executed only for the elements that are available at the time of page load.
You will have to use .live()
to bind events for all current and dynamically generated elements.
Or you can bind the events once again in the success callback of your ajax function.
You need to re bind the events of the loaded elements.
something like:
document.getElementById('right_bar_wrapper').innerHTML = theRetrievedData;
$(".makePictureBig").click(picBigFunction);
You will have to rebind the ajax events on any new content that you have loaded.
Take your code that initializes the click event (ie the part that has the .click(...) in it) and put it in a seperate function.
For example:
function initImage() {
....click(function() {
}
}
Then call that function both on document.ready and on your ajax success event.
It might also be worth adding the following:
$(".makePictureBig").unbind("click");
just before:
$(".makePictureBig").click(function() { ...
To ensure you do not attach the same event twice on each ajax post.
Full example (this is done quickly and you might not need the logo to re-init, but it's safer to do it all in one place in case you change anything else with different ajax posts):
$(document).ready(function() {
initImages();
}
function initImages() {
$(".makePictureBig").unbind("click");
$(".makePictureBig").click(function() {
var theClassId = $(this).attr('id');
var theID = theClassId.substring(6)
var bigPictureComment = "#bigpicture_comment_" + theID;
var littlePictureComment = "#littlepicture_comment_" + theID;
var ddd = document.getElementById(theClassId);
var getBig = document.getElementById(bigPictureComment);
var getLittle = document.getElementById(littlePictureComment);
if (ddd.style.width == "180px") {
ddd.style.width="430px";
ddd.style.marginBottom='10px';
ddd.style.cssFloat="left";
$(littlePictureComment).hide();
$(bigPictureComment).show();
} else {
ddd.style.width="180px";
ddd.style.marginBottom='0px';
$(bigPictureComment).hide();
$(littlePictureComment).show();
}
});
$("#logo").unbind("click");
$("#logo").click(function() {
$("#right_bar_wrapper").animate({ height: 'toggle', opacity: 'toggle' }, '200');
var thePostData = "username=c";
$.ajax({
type: "POST",
url: "http://myflashpics.com/v2/process_newsfeed.php",
data: thePostData,
success: function(theRetrievedData) {
document.getElementById('right_bar_wrapper').innerHTML = theRetrievedData;
$("#right_bar_wrapper").fadeIn("200");
initImages();
}
});
});
}
i would suggest checking out a jquery plugin called livequery
with that you could replace:
$(".makePictureBig").click(function() {
//existing stuff
with
$(".makePictureBig").livequery(function() {
$(this).click(function() {
//existing stuff
With livequery, anytime an element is placed into the dom that matches the selector, the callback function will fire.
The other answers are correct, but I will expand. When you bind an event with jQuery.bind
(note that click
, etc. are macros for bind
) it only binds the event to DOM elements that exist at the current time. The jQuery selector scans the DOM for all elements that match the selector ($("#hoo").click()
binds an event handler to any existing element with id="hoo").
When elements are added to the DOM via ajax or other means, they do not automatically get all handlers bound to them. In order to do this, jQuery would have to scan the DOM for every event and apply the handler to any new element it found at any time. This is impractical.
The two solutions are to apply the handlers to any elements loaded to the DOM later. For instance, change the 'click' function you have above to an actual function:
function makePictureBig() {
var theClassId = this.id;
...
}
Then say $(".makePictureBig").click(makePictureBig);
...and in your Ajax: $("#right_bar_wrapper").html(theRetrievedData)
.find(".makePictureBig").click(makePictureBig);
The second option is to use .live()
, .delegate()
or a plugin like .livequery()
.
Delegate is a better option than Live. You can delegate to a higher level element. You can even do:
$('body').delegate('.makePictureBig', 'click', function() {
//code
});
use
$("****").live('click',function() {});