Why i can't append some html in to the desired element? - javascript

i hope someone can lend me a hand, i have been trying to insert some code via .post using jquery everything seem to works fine but the response data doesn't insert on the conhere div
html
<div class="ui-grid-a">
<div class="ui-block-a main">
<div data-role="fieldcontain">
<input type="checkbox" value="1##2##2##1080|2" name="pro1" id="pro1" class="checkpro">
<label for="pro1"> product description
</label>
</div>
</div>
<div class="ui-block-b side">
<div class="conhere">
</div>
</div>
</div>
javascript
$( document ).on( "change",".checkpro", function(event, ui) {
var checkedpro = $(this).is(':checked')?1:0;
if (checkedpro==1){
var variable=$(this).val().split("##");
$.post("product.php", h{row :contenedor[0],
mul : variable[1],
can : variable[2],
pri: variable[3],
id : variable[4]},
function(data){
$(this).parents(".ui-grid-a").find(".conhere").empty().append(data).trigger('create');
});
else{
$(this).parents(".ui-grid-a").find(".conhere").empty();
}

There are two issues, both with this code:
$(this).parents(".ui-block-a").find(".conhere")...
The first issue is that the .conhere element doesn't exist within .ui-block-a. It exists in .ui-block-b. (And both .ui-block-a and .ui-block-b are within .ui-grid-a.) find only looks at descendant elements of the elements in the set where it's called.
The second issue is that this is no longer what it was outside the call to $.post. So we want to capture it in a variable we close over.
Finally, in this case I would use closest, not parents:
$(this).closest(".ui-grid-a").find(".ui-block-b .conhere")...
// or
$(this).closest(".ui-grid-a").find(".conhere")...
Combining the above:
$(document).on("change", ".checkpro", function (event, ui) {
var $elm = $(this), // <== Remember $(this)
checkedpro = $elm.is(':checked') ? 1 : 0;
if (checkedpro == 1) {
var variable = $elm.val().split("##");
$.post("product.php", h {
row: contenedor[0],
mul: variable[1],
can: variable[2],
pri: variable[3],
id: variable[4]
},
function (data) {
// v-------------------------------- use it, and note 'closest'
$elm.closest(".ui-grid-a").find(".conhere").empty().append(data).trigger('create');
});
} // <== This } was also missing
else {
$elm.closest(".ui-grid-a").find(".conhere").empty();
}

Related

How to save using localStorage on each item and not for all

I have a problem with localStorage that will remember all saves even if one section is closed but the other is suppose to remain. Example: There's two banners on a page. If one person clicks to close a banner, it will close that banner but will also remember that the other banner has been closed as well.
Code:
<section class="alert-notice-contain status-alerts">
<div id ="1561524897" class="type-notice relative">
<div class="close-notice-alert"></div>
<div class="status-contain">
<div class="status-msg">
<p>This is a test. This is a long test.</p>
</div>
</div>
</div>
<div id ="1561524873" class="type-notice relative">
<div class="close-notice-alert"></div>
<div class="status-contain">
<div class="status-msg">
<p>This is notice 1</p>
</div>
</div>
</div>
<script> // JS code (inline to get the dynamic #ID
( function( $ ) {
'use strict';
$( document ).on( 'ready', function() {
// Status
if(localStorage.getItem('isHide'))
$('#1561524897').hide();
$('#1561524897 .close-notice-alert').click(function(){
$('#1561524897').hide();localStorage.setItem('isHide',true);
});
} );
} ( jQuery ) );
</script>
<script>
( function( $ ) {
'use strict';
$( document ).on( 'ready', function() {
// Status
if(localStorage.getItem('isHide'))
$('#1561524873').hide();
$('#1561524873 .close-notice-alert').click(function(){
$('#1561524873').hide(); localStorage.setItem('isHide',true);});
} );
} ( jQuery ) );
</script>
</section>
You should store with the id instead of simply set the same variable 'isHide' to true or not.
For example, set to store: localStorage.setItem('isHide-1561524897', true);
and read it: localStorage.getItem('isHide-1561524897');
Use an object to store in localstorage.
JSON.stringify() to convert your object to string form and JSON.parse() to convert string to object form after getting from localstorage.
For ex.
obj = { visibility : 'hidden' }
// set the localstorage
localstorage.setItem('isHide', JSON.stringify(obj));
// get the localstorage
let storageValue = JSON.parse(localstorage.getItem('isHide'));
// use storageValue accordingly

Get data of dynamically added elements using JQuery

Very similar problem to Dynamically added HTML elements can't be found using jQuery but, I want to access new element's data and not its event.
The element is added by JQuery through AJAX request. It is not missing to the DOM when I try to access it.
<button id="get-data">Get data</button>
<div id="container">
<!-- everything here is added through the first ajax call -->
<button id="update-data">Update</button>
<input type="hidden" id="elem" data-data="someData" />
</div>
So I tried :
$('#elem').data('data');
$(this).parents().find('#elem').data('data');
$(document).find('#elem').data('data');
...with no success.
And it's not going to work : JQuery doesn't find #elem in the DOM :
console.log($('input'));
// OR
console.log($(document).find('input'));
...output a list of the input items in the DOM, but #elem is not in this list.
I'm guessing that I can't use $().find() nor the direct $() to get dynamically added content, so how to I get it ?
Here is how my JS is organized :
$(function() {
$('#get-data').click(function() {
$.ajax({
url: "/"
}).done(function() {
$('#container').html(ajaxResult)
});
});
$(document).on('click', '#update-data', function() {
$.ajax({
url: "/new",
data: $('#elem').data('data')
});
//This ajax call doesn't work as expected because data is missing.
//#update-data is inserted by the first AJAX call, but the click even is catched without any problem here.
});
});
Edit after further research:
I tried to output the result of different JQuery selectors :
$('#container').find('#elem');
JQuery Object (length: 0) => prevObject : [ input#elem ]
$('#container').find('#elem').first();
JQuery Object (length: 0) => prevObject : JQuery Object (length: 0) => prevObject : [ input#elem ]
$('#elem');
//or
$(document).find('#elem');
//or
$('#container #elem');
JQueryObject (length: 0) => prevObject : [ HTMLDocument my_website.com ]
$('#elem').first();
//or
$(document).find('#elem').first();
//or
$('#container #elem').first();
JQuery Object (length: 0) => prevObject : JQuery Object (length: 0) => prevObject : [ HTMLDocument my_website.com ]
I have this working when I use the hidden selector. They both work below:
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js" type="text/javascript"></script>
<div class="row">
<div class="col">
<button id="get-data">Get data</button>
<div id="container">
<!-- everything here is added through the first ajax call -->
<button id="update-data">Update</button>
<button id="find-element">Find</button>
<input type="hidden" id="elem" data-data="someData" />
</div>
</div>
</div>
<script type="text/javascript">
$(document).ready(function () {
$('#find-element').bind("click", function () {
// your statements;
var boo = $('#elem').data('data');
var foo = $("#elem:hidden").data('data');
alert(boo + "\n" + foo);
});
});
</script>

Unable to remove css class and add a new one

I have this function that goes through each breadcrumb in a navbar and I want to change the styling of the breadcrumb depending what page they are on.
Here is the basic HTML of the breadcrumb navbar
<div id="WCBar">
<div class="bc_nav current span" id="bc_main">
<a class="bc_1" id="lnkCrumb" href="javascript:__doPostBack('ctl00$breadcrumbnav1$ctl00$lnkCrumb','')">
<li>Account Info</li></a>
<span class="step-arrow"></span>
<input name="ctl00$breadcrumbnav1$ctl00$hdnPageName" id="hdnPageName" type="hidden" value="WCQuoteMain2.aspx">
</div>
<div class="bc_nav a" id="bc_main">
<a class="aspNetDisabled bc_2" id="lnkCrumb"> <li>Rate</li></a>
<span class="step-arrow"></span>
<input name="ctl00$breadcrumbnav1$ctl01$hdnPageName" id="hdnPageName" type="hidden" value="WCQuoteRatingV4.aspx">
</div>
<div class="bc_nav a" id="bc_main">
<a class="aspNetDisabled bc_3" id="lnkCrumb"><li>Questions</li></a>
<span class="step-arrow"></span>
<input name="ctl00$breadcrumbnav1$ctl02$hdnPageName" id="hdnPageName" type="hidden" value="questions.aspx"></div>
<div class="bc_nav last" id="bc_main">
<a class="aspNetDisabled bc_4" id="lnkCrumb"><li>Final</li></a>
<span class="step-arrow" style="background-image: none;"></span>
<input name="ctl00$breadcrumbnav1$ctl03$hdnPageName" id="hdnPageName" type="hidden" value="managesubmission.aspx"></div>
I then call this function in Javascript:
function WCBar(pagename, iframepagename, currentSet) {
$('.bc_nav', $('#WCBar')).each(function () {
iframepagename = $(this).find('input[id*="hdnPageName"]').attr('value');
var bcMain = $(this).find('div[id*="bc_main"]');
var lnkCrumb = $(this).find('a[id*="lnkCrumb"]');
if (pagename == iframepagename) {
//bcMain.addClass("current span");
bcMain.attr("class", "current span");
currentSet = 1;
// notify server
$.ajax({
type: "POST",
url: window.location.pathname + "/UpdateIFrameBreadcrumb",
data: "{'pagename':'" + iframepagename + "'}",
contentType: "application/json; charset=utf-8",
dataType: "json",
success: function (msg) {
// alert(msg.d);
},
error: function (msg) {
// alert(msg.d);
}
});
}
else {
if (lnkCrumb[0].href.length > 1) { //&& currentSet == 0
//bcMain.attr("class", "bc_nav enabled span");
bcMain.removeClass("bc_nav");
bcMain.addClass("bc_nav enabled span");
}
else {
//bcMain.attr("class", "bc_nav a");
bcMain.removeClass();
bcMain.addClass("bc_nav a");
}
}
});
}
When I mouse over bc_Main during a debugging session, context > className shows the proper class but trying to determine if bc_main has a class results in
?bcMain.hasClass('bc_nav');
false
in Visual Studio's Immediate window.
Furthermore, trying to determine what the values are in class gets me an undefined error.
var x = bcMain.attr('class');
undefined
No class is ever removed from bc_main, no matter if I try .removeClass() and leave it empty or try .removeClass('bc_nav');
I have checked to make sure nothing is defaulting elsewhere and can't find anything.
Thanks for your help.
It looks like a scope issue. You are using THIS to perform your find which shouldn't find itself. Your .bc_nav elis actually your #bc_main el, so you might as well just treat $(this) as bcMain. I don't know why you are iterating on both .bc_nav and #WCBar, seems like you should only use .bc_nav.
$('.bc_nav', $('#WCBar')).each(function () {
...
var bcMain = $(this).find('div[id*="bc_main"]');
saying $(this) in this instance is the same as saying $('.bc_nav') so you are essentially doing $('.bc_nav').find('div[id*="bc_main"]'); which won't work since #bc_main isnt' a child of .bc_nav.
If you are trying to empty the class attribute use:
$('#myElementID').removeAttr('class');
or this
$('#myElementID').attr('class', '');
To remove a specific class, you have to use the class name:
$('#myElementID').removeClass('myClassName');
Also, FWIW, in the else statement, this line
bcMain.removeClass("bc_nav");
is pointless, being that it's followed by this one
bcMain.addClass("bc_nav enabled span");

How to use specific data from arrays - Example of click

I have the following JQuery code:
var test = new Array();
$(".quiz_list_row").each(function(index){
// Gets the data necessary to show game chosen
$quiz_list_id = $(this).data("quizlistId");
$quiz_level_reached = $(this).data("quizlevelReached");
test.push($quiz_list_id,$quiz_level_reached);
$(this).click(function(){
alert("test: "+test);
});
});
The divs (using html5 to send data):
<div class="quiz_list_row" data-quizlist-id="1" data-quizlevel-reached="5">
<div class="inline quiz_list_cell" id="quiz_list_cell_row0_id1">Quiz 1</div>
<div class="inline quiz_list_cell" id="quiz_list_cell_row0_id2">Current level: 5</div>
</div>
<div class="quiz_list_row" data-quizlist-id="2" data-quizlevel-reached="7">
<div class="inline quiz_list_cell" id="quiz_list_cell_row1_id1">Quiz 2</div>
<div class="inline quiz_list_cell" id="quiz_list_cell_row1_id2">Current level: 7</div>
</div>
The problem is that I need to find out how to use the data in the array test when the user clicks on a specific row (I want to use $quiz_list_id and $quiz_level_reached).
Unless there is a specific reason you're extracting the attributes and putting them into an array, I think you're taking some unecessary steps to achieving what you want. Take away the complexity from this, you have access to the data attributes with the .data() method at any time you have access to the elements jQuery object, one of those times is within the click handler itself.
var quizRows = $(".quiz_list_row");
quizRows.click(function(event) {
var self = $(this);
//As the element clicked on has it's data attributes defined
//You would just need to retrieve it when the element is clicked on
var id = self.data('quizlist-id'),
level = self.data('quizlevel-reached');
console.log("id is " + id);
console.log("level is " + level);
}

How do you apply an item, from a list of results, to the parent Div tag for the current object?

I am trying to build a function for inserting the number of Facebook Likes into a Div tag. So far, I have a script that can get the URL from a Div tag which is inside of another Div tag called 'entry' and then have the .getJSON() method retrieve the number of Facebook likes for each entry.However, I can't get each retrieved value of Facebook Likes to insert into a Div tag for each entry. Please note, I simplified my code to where it alerts each Facebook Like value. This is what I have so far:
<div class="entry">
<div class="fburl">https://graph.facebook.com/zombies</div>
<div class="facebook-likes"></div>
</div>
<div class="entry">
<div class="fburl">https://graph.facebook.com/starwars</div>
<div class="facebook-likes"></div>
</div>
And here's my jQuery:
$(document).ready(function(){
$(".entry").each(function() {
var fbURL = $(this).find(".fburl").html();
$.getJSON(fbURL, function(fbData) {
var fbArr = fbData['likes'];
alert(fbArr);
});
});
});
​So what I am trying to do is iterate through each entry, get the Open Graph URL for it, retrieve the Likes value, and then insert it into the appropriate Div tag, so the code should render as:
<div class="entry">
<div class="fburl">https://graph.facebook.com/zombies</div>
<div class="facebook-likes">2,586 Likes</div>
</div>
<div class="entry">
<div class="fburl">https://graph.facebook.com/starwars</div>
<div class="facebook-likes">8,905,721 Likes</div>
</div>
​
​
$(document).ready(function() {
$('.entry').each(function() {
var $this = $(this),
fbURL = $this.children('.fburl').html();
$.getJSON(fbURL, function(fbData) {
$this.children('.facebook-likes').html(fbData['likes'] + ' Likes')
});
});
});
See: http://api.jquery.com/children
Demo: http://jsfiddle.net/9EALz/2/
Note: Using children() is going to be marginally more efficient than using find() as it limits the DOM traversal to a single level ( http://jsperf.com/find-vs-children/13 ). Cashing the jQuery object $(this) via var $this = $(this) is also slightly more efficient as it prevents unnecessary selector interpretation ( http://jsperf.com/jquery-cache-vs-no-chace ).
You may want this
$(document).ready(function(){
$(".entry").each(function() {
var entry=$(this), fbURL=$(".fburl", entry).html(),
el=$('.facebook-likes', entry);
$.getJSON(fbURL, function(fbData) {
el.html(numberWithCommas(fbData['likes'])+" Likes");
});
});
});​
A thousand separator function from here
function numberWithCommas(x) {
return x.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
}
DEMO.
Update:
Alternatively you can use this too (using data-attribute) without an extra div for fburl, i.e.
<div class="entry">
<div data-fburl="https://graph.facebook.com/zombies" class="facebook-likes"></div>
</div>
JS
$(".entry").each(function() {
var entry=$(this), fbURL = $(".facebook-likes", entry).attr('data-fburl'),
el=$('.facebook-likes', entry);
$.getJSON(fbURL, function(fbData) {
el.html(numberWithCommas(fbData['likes'])+" Likes");
});
});

Categories

Resources