I have some HTML:
<div class="post-container self">
<a href="/user/Wiz">
<img class="avatar" alt="Profile Picture" src="">
</a>
<div class="post-body">
<div class="post" style="margin-left:0px;">
<div class="post-timestamp" style="display:inline-block;float:right">
Oct 31
</div>
<div class="post-functions dropdown displaynone" style="float:right;margin-right:5px;">
<a class="dropdown-toggle" data-toggle="dropdown" href="javascript:void(0)">
<i class="icon-cog">
</i>
</a>
<ul class="dropdown-menu post-dropdown" role="menu" aria-labelledby="dLabel">
<a class="post-delete" href="javascript:void(0)"><i class="icon-trash"> </i>Delete</a>
</ul>
</div>
</div>
</div>
</div>
And with that, I have some Jquery:
$('.posts-content').on('click', '.post-delete', function(e) {
$('.post-dropdown').dropdown();
if (confirm('Are you sure you want to delete this post?')) {
var $this = $(this);
$.ajax({
url: '/a/delete_post',
type: 'POST',
dataType: 'json',
data: {'p' : post_id},
success: function() {
//...
return true;
}
});
}
return false;
});
Everything works perfectly the first click, but if I go to another post, and try to click .post-delete, the event never fires, and nothing shows up in the console. It also works if I use $.click(), but I need to dynamically create elements. Why does the $.on('click') not fire the second click?
My guess is that dropdown plugin you use change the DOM structure.
$('.post-dropdown').dropdown();
BTW,
$this.parent().parent().parent().parent().parent() this is really really bad practice.
You should use closest instead.
If you are dynamically creating elements try:
$(document).on('click', '.post-delete', function(e) { });
Related
With the following jQuery code.
$('#trade-offer form').on("submit", function(event) {
event.preventDefault();
var stock = $(this).closest('.allloopedover');
console.log(stock);
return;
$.ajax({
url: ajaxurl,
type: "POST",
dataType: 'json',
context: this,
data: $(this).serialize() + '&action=offer',
beforeSend: function() {
$('.alert-modal').remove();
$(this).closest('form').find('input').removeClass('form-error');
$(this).closest('form').find('.stm-ajax-loader').addClass('loading');
},
success: function(data) {
$(this).closest('form').find('.stm-ajax-loader').removeClass('loading');
$(this).closest('form').find('.modal-body').append('<div class="alert-modal alert alert-' + data.status + ' text-left">' + data.response + '</div>')
for (var key in data.errors) {
$('#request-trade-offer-form input[name="' + key + '"]').addClass('form-error');
}
}
});
$(this).closest('form').find('.form-error').live('hover', function() {
$(this).removeClass('form-error');
});
});
And the HTML code.
<div id="2012 FORD SUPER DUTY F-250 XLT" data-item="B01606" class="allloopedover listing-list-loop stm-listing-directory-list-loop stm-isotope-listing-item">
<div class="image">
<!--Video-->
<a href="http://x.com/listings/2012-ford-super-duty-f-250-xlt-2/" class="rmv_txt_drctn">
<div class="image-inner">
<!--Badge-->
<img width="300" height="225" src="http://x.com/blog/wp-content/uploads/2017/12/31-6-300x225.jpg" class="img-responsive wp-post-image" alt="" srcset="http://x.com/blog/wp-content/uploads/2017/12/31-6-300x225.jpg 300w, http://x.com/blog/wp-content/uploads/2017/12/31-6.jpg 640w" sizes="(max-width: 300px) 100vw, 300px"/>
</div>
</a>
</div>
<div class="content">
<div class="meta-top">
<!--Price-->
<div class="price offerc">
<div class="normal-price">
<span class="heading-font offercode">
<a class="rmv_txt_drctn" href="#trade-offer" data-toggle="modal" data-itemname="2012 FORD SUPER DUTY F-250 XLT" data-target="#trade-offer">Offer</a>
</span>
</div>
</div>
<!--Title-->
<div class="title heading-font mmbot">
<a href="http://x.com/listings/2012-ford-super-duty-f-250-xlt-2/" class="rmv_txt_drctn">
2012 FORD SUPER DUTY F-250 XLT
</a>
</div>
</div>
</div>
Now the div code it is not complete as it did not copied the whole code which is too big but it runs inside a loop and creates all the settings differently, notice the first div which have the
id="2012 FORD SUPER DUTY F-250 XLT" data-item="B01606"
and class as allloopedover.
now with jQuery, I want that when I click the submit button of a popup it should pass the id and data-item of that div, I tried using closest but that does not seems to be working, any idea?
When you attach a submit event handler to a form, the this inside your handler function will be the form itself, and not the button that you pressed to submit the form (which could be some div inside the form).
Therefore, $(this).closestwill traverse the parents of the form. If the div.allloopedover is inside the form that is being submitted, closest is not going to find it. If the div you're looking for is inside the form, you can get access to it with $(this).find(".alloopedover"). You should then be able to get the id and data-item value of that div from the jQuery object yielded by find.
In my view I have many tags with differents classed and ids like this:
<!-- html view -->
<div class="panel panel-default">
<ul class="" id="tablist" role="tablist">
<li class="getState active" id="proposed">
<b>Proposed</b>
</li>
<li class="getState" id="current">
<b>Current</b>
</li>
<li class="getState" id="incoming">
<b>Incoming</b>
</li>
<li class="getState" id="finished">
<b>Finished</b>
</li>
</ul>
</div>
<select class="form-control" id="isProduction">
<option value="" disabled selected>Type</option>
<option value="production">Production</option>
<option value="nonProduction">nonProduction</option>
</select>
<div>
<!-- some content here like <p></p> -->
<a href="#validity">
<button class="btn btn-default">Validity</button>
</a>
</div>
<div>
<!-- some content here like <p></p> -->
<a href="#rate">
<button class="btn btn-default">Rate</button>
</a>
</div>
<!-- content appear here -->
<div id="info">
<!-- put some content here following click and selected option change -->
</div>
Using jQuery, I would like to catch all clicks, changes of these tags, more precisely if user click on a <li></li> tag with class .getState, or if user have selected an option of the <select></select> tag which has the id #isProduction or if user have click on the other <button></button> tag wich have <a href="#validity"> or <a href="#rate">.
Like this example:
<script type="text/javascript" charset="utf-8" defer>
$('.getState').bind('click', function sortByState(){
var infoDiv = $('#info');
$.ajax({
type: "GET",
url: window.location.href,
data: {
state: $(this).attr("id"),
},
success: function(html){
infoDiv.empty();
var newinfoDiv = $(html).find('#info');
infoDiv.append(newinfoDiv);
infoDiv = newinfoDiv;
}
});
});
</script>
Here I could make a request (php server side) by recovering the state, then I could make a request with this argument.
How can I combine all these event in only one function in order to recover all the argument I need for my php server side using jQuery ?
I see on the doc here, that we could create a bind on multiple event like this:
$( "#foo" ).bind( "mouseenter mouseleave", function() {
$( this ).toggleClass( "entered" );
});
If I understand correctly you want to attach same event to multiple elements, if yes that could be done using comma separator ,:
$('body').on('click','#isProduction, .getState, button.my-btn',function(){
var infoDiv = $('#info');
$.ajax({
type: "GET",
url: window.location.href,
data: {
state: $(this).attr("id"),
},
success: function(html){
infoDiv.empty();
var newinfoDiv = $(html).find('#info');
infoDiv.append(newinfoDiv);
infoDiv = newinfoDiv;
}
});
})
NOTE : For the two buttons better if you could add a class to them so you will attach event just to them button.my-btn instead of attaching it to button so that will not infect other buttons click event.
<button class="btn btn-default my-btn">Validity</button>
<button class="btn btn-default my-btn">Rate</button>
Or also you could use separated function and attach events separately but trigger the same action :
$('body').on('click','.getState, button.my-btn',myAction);
$('body').on('change','#isProduction',myAction);
function myAction(){
var infoDiv = $('#info');
$.ajax({
type: "GET",
url: window.location.href,
data: {
state: $(this).attr("id"),
},
success: function(html){
infoDiv.empty();
var newinfoDiv = $(html).find('#info');
infoDiv.append(newinfoDiv);
infoDiv = newinfoDiv;
}
});
}
Hope this helps.
$('body').on('click','.getState, button.my-btn',myAction);
$('body').on('change','#isProduction',myAction);
function myAction(){
alert('myAction');
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<link href="https://netdna.bootstrapcdn.com/bootstrap/3.0.0/css/bootstrap.min.css" rel="stylesheet"/>
<script src="https://netdna.bootstrapcdn.com/bootstrap/3.0.0/js/bootstrap.min.js"></script>
<div class="panel panel-default">
<ul class="" id="tablist" role="tablist">
<li class="getState active" id="proposed">
<b>Proposed</b>
</li>
<li class="getState" id="current">
<b>Current</b>
</li>
<li class="getState" id="incoming">
<b>Incoming</b>
</li>
<li class="getState" id="finished">
<b>Finished</b>
</li>
</ul>
</div>
<select class="form-control" id="isProduction">
<option value="" disabled selected>Type</option>
<option value="production">Production</option>
<option value="nonProduction">nonProduction</option>
</select>
<div>
<!-- some content here like <p></p> -->
<a href="#validity">
<button class="btn btn-default my-btn">Validity</button>
</a>
</div>
<div>
<!-- some content here like <p></p> -->
<a href="#rate">
<button class="btn btn-default my-btn">Rate</button>
</a>
</div>
<!-- content appear here -->
<div id="info">
<!-- put some content here following click and selected option change -->
</div>
You can use below code to capture trigger click event on whole page and then you can write desired code to be executed:
$('body').bind('click',function(){
//your code here
});
I am really new to javascript and jquery, but I am trying to create a page that will allow the user to click on a Country name and information for that country will load in a div from a separate html file.
Else where I found this code which works nicely for this, using the .click(function) on the <a> tag:
var $j = jQuery.noConflict();
$j(document).ready(function(){
$j("a").click(function(){
$j.ajax({
url: $j(this).attr("href"),
success: function(response) {
$j("#partnerContent").html(response);
}
});
return false;
});
});
Here is the basic html:
<div id="contentcontain">
<div class="partnercol1">
<div class="container">
<div id="menu" class="btn-group">
<button type="button" class="btn btn-default dropdown-toggle" data- toggle="dropdown">International Sales <span class="caret"></span></button>
<ul class="dropdown-menu scrollable-menu" role="menu">
<li>Belgium</li>
<li>Brunei</li>
<li>Bulgaria</li>
</ul>
</div>
</div>
</div>
<div class="partnercol2">
<div id="partnerContent"></div>
</div>
However, now every <a> tag on the page (including top and bottom menus) loads their href into the div when clicked. How can I target just the div containing the state menu to work with this function?
Make the selector for the elements you're attaching the events to more restrictive:
// this selects all the anchors below the items with ID menu
$j("#menu a").click(function () {
...
});
in your html, put:
<ul class="dropdown-menu scrollable-menu" role="menu">
<li><a class="menu-item" href="partners/belgium.html">Belgium</a></li>
<li><a class="menu-item" href="partners/brunei.html">Brunei</a></li>
<li><a class="menu-item" href="partners/bulgaria.html">Bulgaria</a></li>
</ul>
And in your javascript
var $j = jQuery.noConflict();
$j(document).ready(function(){
$j(".menu-item").click(function(){
$j.ajax({
url: $j(this).attr("href"),
success: function(response) {
$j("#partnerContent").html(response);
}
});
return false;
});
});
You're loading an entire html page, which means you're loading
<html>...</html>
and then stuffing that in its entirety into your page, that means you'll eventually have
<html>
....
<html>...</html>
...
</html>
which is NOT valid. If you're trying to replace the contents of a single <div> in your page, then either you fetch that entire page into a var and slice out the chunk you want, or have jquery fetch/insert ONLY the part you want, e.g.
$('#div_to_replace').load('source_of_new.html #id_of_element_to_use_for_replacement');
Note the second #... argument in the .load() call. That tells jquery to ignore everything in the page EXCEPT for the specified element/ID. Only that ID's contents will be stuffed into #div_to_replace.
I want to load a JSON file that creates a list inside a Bootstrap Modal. I have it set where if you click on a person's picture, the modal pops up.
<li class="project span3" data-type="pfa">
<a data-toggle="modal" data-target="#myModal" class="thumbnail">
<img src="img/anon.jpg" alt="Kenneth Atkins" />
<h1>Kenneth Atkins</h1>
<p>[Description here]</p>
</a>
</li>
Here's an example of the JSON data:
var florida_exoneration = [
{
"last_name":"Atkins",
"first_name":"Kenneth",
"age":16,
"race":"Caucasian",
"state":"FL",
"crime":"Sexual Assault",
"sentence":"10 years",
"conviction":2004,
"exonerated":2008,
"dna":"",
"mistaken witness identification":"",
"false confession":"",
"perjury/false accusation":"Y",
"false evidence":"",
"official misconduct":"",
"inadequate legal defense":"",
"compensation":""
}
]
I'd like the modal to display something like this inside the box:
Title = "first_name + last_name"
Age = "age"
Race = "race"
State = "state"
""
""
I also want to make sure the data is tied to the picture so the modal doesn't get confused. I'm sorry if this is a bit confusing. I'll try and clarify if anyone has any questions.
Method 1: using Ajax
Every time a user clicks an image, you get the id from the clicked image and then you send an Ajax request to server in order to get the JSON object.
HTML
<ul>
<li class="project span3" data-type="pfa">
<a href="#" data-id="2" class="thumbnail">
<img src="img/anon.jpg" alt="Kenneth Atkins" />
<h1>Kenneth Atkins</h1>
<p>[Description here]</p>
</a>
</li>
</ul>
JavaScript
(function($) {
var infoModal = $('#myModal');
$('.thumbnail').on('click', function(){
$.ajax({
type: "GET",
url: 'getJson.php?id='+$(this).data('id'),
dataType: 'json',
success: function(data){
htmlData = '<ul><li>title: '+data.first_name+'</li><li>age: '+data.age+'</li></ul>';
infoModal.find('.modal-body').html(htmlData);
infoModal.modal('show');
}
});
return false;
});
})(jQuery);
Method 2: using hidden div
No need to any Ajax request, but you need to create a hidden div that contain all the information you want to display in the modal
HTML
<ul>
<li class="project span3" data-type="pfa">
<a href="#" class="thumbnail">
<img src="img/anon.jpg" alt="Kenneth Atkins" />
<h1>Kenneth Atkins</h1>
<p>[Description here]</p>
<div class="profile hide">
<ul>
<li>title: Atkins Kenneth</li>
<li>Age: 16</li>
</ul>
</div>
</a>
</li>
</ul>
JavaScript
(function($) {
var infoModal = $('#myModal');
$('.thumbnail').on('click', function(){
htmlData = $(this).find('.profile').html();
infoModal.find('.modal-body').html(htmlData);
infoModal.modal('show');
return false;
});
})(jQuery);
I have this button, and when clicked, it sends an ajax call which changes the value of score_up.
I dont see what the problem is. I tried firbug, but apparently it's not even detecting the javascript? :)) Thanks.
jquery:
$('.stats').delegate('.support', 'click', function(e) {
//stop event
e.preventDefault();
//get the id
var the_id = $(this).closest('.score').attr('id').split('_').pop();
//the main ajax request
$.ajax({
context:this,
type: "POST",
data: "action=support&id=" + the_id,
url: "ajax/sa.php",
success: function (msg) {
$(this).siblings("h2.score_up").html(msg).fadeIn();
//remove down button
// and remove support button
}
});
});
html:
<ul class="stats">
<li id="support_23"class="score">
<h2 class="score_up">12</h2>
<span style="text-align:center;">Supporters</span>
</li>
<li>
<button type="submit" value="Actions" class="support" title="support">
<i></i>
<span>Support</span>
</button>
</li>
//vote down button
<li id="down_23"class="score">
<h2 class="score_down">12</h2>
<span style="text-align:center;">down</span>
</li>
<li>
<button type="submit" value="Actions" class="down" title="down">
<i></i>
<span>down</span>
</button>
</li>
</ul>
It is not valid HTML for a <button> to be a direct child of a <ul>.
Children of <ul> should be <li>. I wouldn't expect things to work properly with invalid HTML.
HTML with <button> inside a <li>:
<ul class="stats">
<li id="topic_23" class="score">
<h2 class="score_up">12</h2>
<span style="text-align:center;">Supporters</span>
</li>
<li>
<button type="submit" value="Actions" class="support" title="support">
<i></i>
<span>Support</span>
</button>
</li>
</ul>
jQuery, fixing some of the traversal methods:
$('.stats').delegate('.support', 'click', function(e) {
//stop event
e.preventDefault();
// cache a reference to the previous <li> element
// since it is used more than once
var $prevLi = $(this).closest('li').prev('li');
//get the id
var the_id = $prevLi.attr('id').split('_').pop();
//the main ajax request
$.ajax({
context:this,
type: "POST",
data: "action=support&id=" + the_id,
url: "ajax/sa.php",
success: function (msg) {
$prevLi.find("h2.score_up").html(msg).fadeIn();
}
});
});
Your HTML is invalid, so I would do:
<form action="javascript:alert('form')";>
<ul class="stats">
<li id="topic_23"class="score">
<h2 class="score_up">12</h2>
<span style="text-align:center;">Supporters</span>
</li>
<li>
<button type="submit" value="Actions" class="support" title="support">
<i></i><span>Support</span></button>
</li>
</ul>
</form>
And then the jQuery (which in your original would not work, since you wanted .siblings() and not .closest() would now be:
var the_id = $(this).closest("li").siblings('.score').attr('id')
.split('_').pop();
and success:
$(this).closest("li").siblings("li.score").find("h2.score_up")
.html(msg).fadeIn();
I think you also run into troubles with prevent default, since you want to prevent default on the form, and in that case you might run into problems with delegate.
Here is what I would do with .live():
// Prevent form from submitting
$("form").live("submit", function(e) {
e.preventDefault(); });
// Run Ajax
$('button.support').live('click', function(e) {
//get the id
var $score = $(this).closest("li").siblings('.score'),
the_id = $score.attr('id').split('_').pop();
//the main ajax request
$.ajax({
context:this,
type: "POST",
data: "action=support&id=" + the_id,
url: "ajax/sa.php",
success: function (msg) {
$score.find("h2.score_up").html(msg).fadeIn();
}
});
});
Try it out on this jsFiddle