html() function with variables - javascript

I'm attempting to inject some html code with variables in it into a JQM UL Listview. The problem I am running into is it seems the variables are throwing off the code because when I remove them, it injects the HTML perfectly.
Here is the snippet:
$(document).on("pageinit", "#vendorMessages", function() {
var listView = "";
pubnub.subscribe(
{
channelGroup: getChannelGroup()
},
function (status, response) {
alert("test");
console.log(status, response);
}
);
pubnub.channelGroups.listChannels(
{
channelGroup: getChannelGroup()
},
function (status, response) {
response.channels.forEach( function (channel) {
var channelFormatted = String(channel).split("_");
var channelMember = channelFormatted[1];
var temp = "<li onClick='loadChannel("+channel+")'>"+channelMember+"</li>";
var temp = String(temp);
listView = listView.concat(temp);
})
alert(listView);
}
)
var elem = $("#channels");
elem.html(elem.text(listView));
$("#channels").listview("refresh");
})
The alert(listView) returns the correct string format but the code still will not get added to the <ul>. I've tried a few suggested things, even switching back to javascript innerHTML but no avail. Any thoughts?

Change
elem.html(elem.text(listView));
to
elem.html(listView);
elem.text cannot handle html..

Related

Returning from JQuery 'get' when all images have loaded

I am using jquery get to load html onto my content div. The HTML I am loading contains some images and I am finding that my custom height calculation I am doing in javascript isn't working too well because the images are fully loaded when the loadHTML has returned.
var loadHTML = function(){
return $.get("javascripts/templates/" + templateType + ".html", function(text) {
$("#content").html(text);
});
};
Is there a way I can only return from loadHTML once all images have loaded? I tried to call and return load but this doesn't work
var loadHTML = function() {
return $.get("javascripts/templates/" + templateType + ".html", function(text) {
var content = $("#content").html(text);
return $('img', content).load();
})
};
Also, I am using Q promises in other parts of my application so is it possible to fix my problem using that.
ie. loadHTML.then(loadImages).then(doOtherStuff);
You can try to use a custom deferred object like below
var loadHTML = function () {
var deferred = $.Deferred();
$.get("javascripts/templates/" + templateType + ".html", function (html) {
var $html = $(html),
$imgs = $html.find('img'),
len = $imgs.length,
counter = 0;
$imgs.load(function () {
if (++counter == len) {
deferred.resolve();
}
});
$("#content").html($html);
});
return deferred.promise();
};
TD
var list = [];
for (var i = 0; i < 5; i++) {
list.push('<span><img src="//placehold.it/64&text=' + (i + 1) + '" /></span>');
}
var html = '<div>' + list.join('') + '</div>';
var loadHTML = function() {
var deferred = $.Deferred();
//using a timer to simulate ajax request
setTimeout(function() {
var $html = $(html),
$imgs = $html.find('img'),
len = $imgs.length,
counter = 0;
$imgs.load(function() {
if (++counter == len) {
deferred.resolve();
}
});
$("#content").html($html);
}, 500);
return deferred.promise();
};
loadHTML().done(function() {
$("#content").find('img').each(function() {
$(this).after(this.complete)
})
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<div id="content"></div>
Demo: Fiddle
Demo: Problem(Change the size of the image to see the problem)
Deleted my other answer because it was too wordy.
The reason your code is not working is because you are making an ajax request to a server, then returning from the function immediately. The page ploughs on with its scripting and probably finishes most if its work before that request comes back with your images.
You need to move your return to a place in your function you know is not going to process until the data comes back. You can use promises to do this:
var jqxhr = $.get( "example.php", function() {
alert( "request sent, images are loading" );
// DON'T PUT YOUR RETURN HERE,
//YOU WANT TO CALL IT WHEN THE ABOVE IS DONE
})
.done(function() {
alert( "the info is loaded" );
//put your html insert here to make sure the
//data is fully loaded before you manipulate it
//you could also call htmlresize here but that would be nesting.
//That shit gets complicated. Just call it after this function returns on success.
return
})
.fail(function() {
alert( "error" );
// its good to handle errors
return
})
if you dont want to hold up your whole page load to load some images you can do facny stuff like put the html resize and other dependent code on the jqxhr.sucess callback, so that other code gets read while your images come through. But that's complicated.

jquery.each not working after jquery.load

I use jQuery.load to load the HTML template. After this I'm trying to get HTML content from each loaded HTML element. The HTML is loading but I can't get the HTML content.
Here is the code:
var _InterfaceBuilder = function() {
var k45 = new _K45Kit;
var _this = this;
this.build = function(element) {
var error = false;
switch(element) {
case 'loginPanel':
$('#content').load('template/loginPanel.html', _this.localize(element));
break;
//sth else
}
// sth else
};
this.localize = function(section) {
$(".loginPanel.localString").each(function(index) {
console.log($(this).html());
});
//sth else
});
When I put
$(".loginPanel.localString").each(function(index) {
console.log($(this).html());
});
into the firebug console it works correctly. Can someone help me?
The 2nd parameter for $.load() must be a function that will be called once completion. You are not providing a function, but the result of calling _this.localize(element). So basically, the localize function is called before adding the listener, and since it returns undefined you have no handler.
Try with:
$('#content').load('template/loginPanel.html',
function(){
_this.localize(element);
});

Define a javascript variable under conditions with jquery

Like the title says, I would like to fill a variable up under some conditions
I thought I could do like that but no :
var content = $(function() {
if ($('#content').length) {
return $('#content');
}
if ($('#content_no_decoration').length) {
return $('#contenu_no_decoration');
}
if ($('#full_content').length) {
return $('#full_content');
}
if ($('#full_content_no_decoration').length) {
return $('#full_content_no_decoration');
}
});
So I thought that the javascript variable 'content' would be one of the jquery object representing an element in the dom. But it seems that 'content' is the function.
I guess you imagine what i want to do.. What is the syntax with JQuery ?
Thank you
$(function() { }) is short-code for the DOMReady event. You need to explicitly define a function, and then assign the return value to your variable.
For example:
function getObj()
{
if($('#content').length)
{
return $('#content');
}
if($('#content_no_decoration').length)
{
return $('#contenu_no_decoration');
}
if($('#full_content').length)
{
return $('#full_content');
}
if($('#full_content_no_decoration').length)
{
return $('#full_content_no_decoration');
}
}
You can then assign the value as :
var content = getObj();
You will need to call the assignment when the DOM is ready though, otherwise the selectors will not trigger as expected. For example:
$(function() {
var content = getObj();
});
You are only declaring the function, so content contains a pointer to the function.
Execute it and you are fine:
var content = function() {
if ($('#content').length) {
return $('#content');
}
if ($('#content_no_decoration').length) {
return $('#contenu_no_decoration');
}
if ($('#full_content').length) {
return $('#full_content');
}
if ($('#full_content_no_decoration').length) {
return $('#full_content_no_decoration');
}
}();
But you don't really need a function here. If the script tag is at the bottom of the page (right before the closing </body>-tag), or the assignment is within a load handler you could use:
var content = $('#content').length
? $('#content')
: $('#content_no_decoration').length
? $('#content_no_decoration')
: $('#full_content').length
? $('#full_content')
: $('#full_content_no_decoration').length
? $('#full_content_no_decoration')
: undefined;
Or use jQuery to your advantage and keep things really short:
var content =
$('#content,#content_no_decoration,#full_content,#full_content_no_decoration')
.get(0);
// if none of the elements exist, content will be undefined, otherwise
// it will contain [a JQuery Object of] the first existing element
why you don't do like that ?
function thatsAGoodName() {
if ($('#content').length) {
return $('#content');
}
if ($('#content_no_decoration').length) {
return $('#contenu_no_decoration');
}
if ($('#full_content').length) {
return $('#full_content');
}
if ($('#full_content_no_decoration').length) {
return $('#full_content_no_decoration');
}
}
var content = thatsAGoodName();
The function
$(function() {
// DOM safe to use do stuff
})
Is shorthand for the document ready event. This tells you the coder that the dom is safe to use.
You would not really return anything from this event.
content is an object because you're setting it to a object here:
var content = $(function() {
What you probably intended was:
var content;
if ($('#content').length) {
content = $('#content');
}
if ($('#content_no_decoration').length) {
content = $('#contenu_no_decoration'); // Is #contenu a typo???
}
if ($('#full_content').length) {
content = $('#full_content');
}
if ($('#full_content_no_decoration').length) {
content = $('#full_content_no_decoration');
}
Note, that this will have a reference to an element now. If you want the actual content you'll need to pull it out with something like html() or val().
You are using the shorthand for the jQuery ready event ($(function() {. What I believe you want is a self invoking function:
// remove the call to jQuery
var content = (function() {
if ($('#content').length) {
return $('#content');
}
// ... more
})(); // invoke the function, which should return a jQuery object
You may need to wrap this in a document.ready, depending on where your script is executed.
Rearrange it a little bit and it should work:
$(function () {
var content = (function() {
var regularContent = $('#content');
if (regularContent.length !== 0) {
return regularContent;
}
var contentNoDecoration = $('#content_no_decoration');
if (contentNoDecoration.length !== 0) {
return contentNoDecoration;
}
var fullContent = $('#full_content');
if (fullContent.length !== 0) {
return fullContent;
}
var fullContentNoDecoration = $('#full_content_no_decoration');
if (fullContentNoDecoration.length !== 0) {
return fullContentNoDecoration;
}
}());
});
This code is basically saying once the DOM is ready (the $(function () { ... }); part), run this anonymous function (the (function () { ... }()); part) and assign its return value to content.
Edit: Also, you're losing efficiency by running each of your selectors twice instead of just once.
It's true that content is the function, but you can use that function. Like:
var result = content();
Edit:
Remove the $() around var content = $({/* code */}) and it works.

jQuery Mobile Load external HTML that contains an ajax call to servlet script and execute them only once

i have an iphone style menu for a web app POS, when i press the Clients Button it shows a page with all the clients, this is made making an ajax call to a java servlet, i use the load() function in the Main page to bring the GetCustomers.html file with a script containing the jquery code with ajax and the UL tag, when i call it (load it) in my main page it only format the UL and its respectively generated LI when i use firebug debugger with with a breakpoint in the trigger('create'); which is the last instruction inside the "pagebeforeshow" function. BUT! if i run it without debugging it does format and stylize it and show it 2 milisecons then it shows it without the jquery-mobile Listview style. im using $(this).trigger('create'); and that.listview('refresh'); and it still does not work well... any suggestions?
HERE IS THE MAIN PAGE CODE:
$(document).on("pagebeforeshow", "#pagewelcomeclientes", function(){
if( navigationInitialized == 'X'){
var newItems = '<li data-role="list-divider">Page Options</li>';
newItems += '<li>Time</li>';
newItems += '<li>Agregar Cliente</li>';
$(".pageOpts").empty();
$(".pageOpts").append(newItems).listview("refresh");
$.ajaxSetup ({
cache: false
});
var loadUrl = "GetCustomers.html";
$("#contentwelcomeclientes").load(loadUrl,function(){
BringClientes();
$(this).trigger('create');
});
var list = $('ul[data-autodividers="true"][data-sort="true"]');
list.each(function (i, item) {
var that = $(item);
// Gel all the list items into an array (excluding te dividers)
var lis = that.find('li').not('.ui-li-divider').get();
// Sort the list items alphabetically, descending
lis.sort(function (a, b) {
var valA = $(a).text(),
valB = $(b).text();
if (valA < valB) {
return -1;
}
if (valA > valB) {
return 1;
}
return 0;
});
// Remove all list items
that.empty();
// Rebuild the list with the ordered items
$.each(lis, function (i, li) {
that.append(li);
});
// Refresh/rebuild the listview
that.listview('refresh');
});
$(this).trigger('create');
}
});
HERE THE CALLED HTML:
<script type='text/javascript'>
BringClientes = function() {
$.ajax({
type: "POST",
url: "GetCustomers",
dataType: "json",
success: function (data) {
if (data.Customers.length) {
$.each(data.Customers, function (i, data) {
var temp = null;
var temp = "#cd-dropdown";
var temp = temp+data.msg_id;
var msg_data =
'<li>'+data.first_name+'</li>';
$(msg_data).appendTo("#juntar");
});
} else {
$("#content").html("No Results");
}
}
});
}
</script>
<ul data-role="listview"
data-inset="true"
data-filter="true"
data-autodividers="true"
data-sort="true"
data-theme="c"
data-divider-theme="c"
data-split-icon="grid"
data-split-theme="d"
id="juntar"
>
</ul>
i think it is executing twice the script in second page, what i try to do to fix it, is naming the function and then call it only once, but it still does not work... if you need sample images i can send it by mail, this is my first question here and stacky doesn't let me upload images...
thanks in advance!! =)
Lets change following line $(document).on("pagebeforeshow", "#pagewelcomeclientes", function(){}); into as below
$('#pagewelcomeclientes').on('pagebeforeshow',function(event){
// your code goes here
});
Also change $(this).trigger('create'); this into $('#pagewelcomeclientes').trigger('create'); and see what happens
If you suspect that the service is being called twice then better way to tackle is using .html() than using .append().
You may chagne your script as below
$.ajax({
type: "POST",
url: "GetCustomers",
dataType: "json",
success: function (data) {
if (data.Customers.length) {
var myListstring = "";
$.each(data.Customers, function (i, data) {
var temp = null;
var temp = "#cd-dropdown";
var temp = temp+data.msg_id;
myListstring += '<li>'+data.first_name+'</li>';
});
$("#juntar").html(myListstring);
$("#juntar").listview();
} else {
$("#content").html("No Results");
}
}
});
I would suggest that you should not complicate things using .load() instead u can call the service in the page itself and render the listview. Which will produce much readable code.
Hope this might get u somewhere closer to the fix.

How can I parse a HTML attribute value out of XMLHttpRequest.responseText?

The below JS function does Ajax request and retrieves HTML in obj.responseText. My issue is that I need to extract the value of id inside the span into notify_id var. I just don't know how to get that done.
This is the HTML to lookup:
HTML:
<span id="1034"></span><img src="./images/icons/post_icon.png">
JS:
function func()
{
obj = new XMLHttpRequest();
obj.onreadystatechange = function() {
if(obj.readyState == 4)
jQuery.jGrowl(obj.responseText, {
sticky:true,
close: function(e,m) {
notifyClosed(notify_id);
}
});
}
obj.open("GET", "notifications.php?n=1", true);
obj.send(null);
}
Since you're already using jQuery:
var responseText = '<span id="1034"></span><img src="./images/icons/post_icon.png">';
var spanId = $('<div>').html(responseText).find('span').attr('id');
alert(spanId); // 1034
The whole function in turn can also be rewritten as follows:
$.get('notifications.php?n=1', function(responseText) {
// Your code here.
});
See also the jQuery tutorials.

Categories

Resources