Get the width of an image getted by Ajax - javascript

I receive images using an Ajax fonction after clicking on a link, so I don't know their widths.. I want to change the css of the images if they are bigger than 650 px. All the images have the same class name .popup_pics so I did :
$(document).ready(function (e) {
$('a[class*="popup"]').click(function(){
showPics(current); //Ajax call
if ($(".popup_pics").clientWidth > 649) {
alert($("img.popup_pics").width());
}
else {
alert($("img.popup_pics").width());
}
}
}
But it gives me undefined so I think that's because the image isn't loaded yet.
How can I do this ?
Thank you

Wait for the image to load, and then get its width. Something like this should work:
$("img.popup_pics").each(function() {
var img = $(this),
src = img.attr('src'),
image = new Image();
image.onload = function() {
// detect width here
alert(img.width());
};
image.src = src;
});
Don't forget to execute this code only after the AJAX has returned successfully and changed the HTML.

.width (http://api.jquery.com/width/) and .height (http://api.jquery.com/height/) are no properties but jquery functions, so this code works:
http://jsfiddle.net/nQvK3/1/
$(".popup_pics").each(function(index, domElement) {
if (domElement.clientWidth > 649) {
alert(domElement.id + ' is bigger then 649: ' + $("img.popup_pics").width());
}
else {
alert(domElement.id + ' is smaller then 649: ' + $("img.popup_pics").width());
}
});
I have added some more code, here is the new fiddle: http://jsfiddle.net/nQvK3/4/
first do the ajax call to your images source (i commented it out in the fiddle as i can not do an ajax call to your source)
when the ajax call is a success we call the showImages function and pass the response object as first parameter
this function uses jquery each to go through the images array
for each image we create an image tag and then add the image to the dom
we finally measure its width and if it is bigger we apply a class to it to resize it
//-- updated code
$(document).ready(function() {
/*
var request = $.ajax({
url: "images.php?gallery_id=1",
type: "GET",
data: {id : menuId},
dataType: "json"
});
request.done(function(ajaxImagesResultObject) {*/
// this is what ajax returns to you, probably an array of objects
// to test it in your code uncomment the ajax call and comment out the following object
var ajaxImagesResultObject = { imagesArray:
[
{
name: 'stackoverflow small',
url: 'http://blog.stackoverflow.com/wp-content/uploads/stackoverflow-logo-300.png'
},
{
name: 'stackoverflow big',
url: 'http://cdn.sstatic.net/stackexchange/img/logos/careers/careers-logo.png'
}
]
};
console.log(ajaxImagesResultObject);
showPics(ajaxImagesResultObject);
/*});
request.fail(function(jqXHR, textStatus) {
alert( "Request failed: " + textStatus );
});
*/
});
var showPics = function(ajaxImagesResultObject) {
// foreach image that is contained in the result array
$.each(ajaxImagesResultObject.imagesArray, function(index, imageData) {
var imageElement = $('<img src="' + imageData.url + '" id="' + index+1 + '" title="' + imageData.name + '" />');
// now we add (append) the image inside of the imagesBox element
$('#imagesBox').append(imageElement);
// now we check its width and if it is bigger then 649 we add a resize class
// to save bandwidth images that are too big should get resized on the server not the client
if ($('#' + index+1).width() > 649) {
$('#' + index+1).addClass('imageResizer');
} else {
// do nothing
}
});
};

Related

Update div with new image only when user uploaded new image

I have two separate pages: one where user uploads new image, other where that images is loaded inside a div through ajax.
The script is looking at filenames inside a txt file and only the first filename is being fetched (file_name2.jpg|file_name1.jpg)
Here is the script:
$(function(){
var GALLERY = {
container: "#gallery",
url: "getImages.txt",
delay: 10000,
load: function(){
var _gallery = this;
var number = 1 + Math.floor(Math.random() * 9999999999);
$.ajax({
type: "get",
url: this.url + '?rand=' + number,
beforeSend: function(){
$(_gallery.container).find('img').remove();
},
success: function(data){
var images = data.split('|', 1);
$.each(images, function(){
_gallery.display(this);
});
},
complete: function(){
setTimeout(function(){
_gallery.load();
}, _gallery.delay);
}
});
},
display: function(image_url){
$('<img />').attr('src', 'images/' + image_url).load(function(){
$(this);
}).prependTo(this.container);
}
}
GALLERY.load();
});
The problem is: The script always executes and replaces the image, even when no new image was uploaded.
Ideal the image should only refresh when a new image was uploaded.
How can I achieve this behavior?
You need to store result data in a variable or like GALLERY.lastdata then the setTimeout will request another and see if new data is the same the image won't refresh.
$(function(){
var GALLERY = {
lastdata : "",
container: "#gallery",
url: "getImages.txt",
delay: 10000,
load: function(){
var _gallery = this;
var number = 1 + Math.floor(Math.random() * 9999999999);
$.ajax({
type: "get",
url: this.url + '?rand=' + number,
success: function(data){
//detect new images
if(_gallery.lastdata != data){
var images = data.split('|', 1);
$.each(images, function(){
_gallery.lastdata = data;
_gallery.display(this);
});
}
},
complete: function(data){
setTimeout(function(){
_gallery.load();
}, _gallery.delay);
}
});
},
display: function(image_url){
$('<img />').attr('src', 'images/' + image_url).load(function(){
$(this);
}).prependTo(this.container);
}
}
GALLERY.load();
});
In your success or display function, add code to check the image filenames received against the image filenames currently displayed and only update when they differ.

Images displaying with zero height & width after ajax load

I have a site in development which uses ajax page loading. This all works as expected except when it comes to images.
If you visit the link below, you will see a page title "Brands" which has an svg icon followed by an img.
Now if you click "Brands" in the sidebar the page will fade out, fetch the same page via the .load method and then fade in the content. However you will notice in Chrome that the svg is seemingly missing. If you check in safari the svg is visible but the img is missing. If you check it in Firefox then you get the alt attribute displayed.
After inspecting the page you will notice that they have a height of 0px and a width of 0px.
Why is happening and how can I resolve it?
http://kga.creativelittledevs.co.uk/consultant/brands/
I did try an create a reduced test case but it wasnt very easy to replicate.
Here's my full ajax code:
Object.defineProperty(String.prototype, "decodeHTML", {
value: function () {
return $('<div>', {html: '' + this}).html();
}
});
var init = function() {
$('select').selectric({
arrowButtonMarkup:'<svg class="selectric__button"><use xlink:href="/images/icons.svg#icon-right-chevron"></use></svg>'
}, 'refresh');
},
ajaxLoad = function(html) {
document.title = html.match(/<title>(.*?)<\/title>/)[1].trim().decodeHTML();
init();
},
loadPage = function(href, get, put) {
$(put).fadeOut(200, function(){
$(put).load(href + ' ' + get, function(){
ajaxLoad;
$(put).fadeIn(200);
});
});
};
init();
$(window).on('popstate', function(e) {
var state = e.originalEvent.state;
if (state !== null) {
loadPage(location.href, state.get, state.put);
} else {
history.pushState({get: '.app-main > *', put: '.app-main'}, '', location.href);
}
});
kga.doc.on('click', '.js-ajax', function() {
var $this = $(this),
href = $this.attr('href'),
get = $this.data('ajax-get') ? $this.data('ajax-get') + ' > *' : '.app-main > *',
put = $this.data('ajax-put') ? $this.data('ajax-put') : '.app-main';
if (href.indexOf(document.domain) > -1 || href.indexOf(':') === -1) {
history.pushState({get: get, put: put}, '', href);
loadPage(href, get, put);
return false;
}
});
Any help would be very much appreciated, thanks.

JavaScript local storage for pages

I have here a little script that I found and am using it to create a simple game of sorts...
/*
Here add:
'image_path': ['id_elm1', 'id_elm2']
"id_elm1" is the ID of the tag where the image is initially displayed
"id_elm2" is the ID of the second tag, where the image is moved, when click on the first tag
*/
var obimids = {
'http://www.notreble.com/buzz/wp-content/uploads/2011/12/les-claypool-200x200.jpg': ['lesto', 'les'],
'http://rs902.pbsrc.com/albums/ac223/walkingdeadheartbreaker/Muzak/Guitarists/LarryLalondePrimus.jpg~c200': ['lerto', 'ler'],
'http://www.noise11.com/wp/wp-content/uploads/2014/07/Primus-Alexander-200x200.jpg': ['timto', 'tim']
};
// function executed when click to move the image into the other tag
function whenAddImg() {
/* Here you can add a code to be executed when the images is added in the other tag */
return true;
}
/* From here no need to edit */
// create object that will contain functions to alternate image from a tag to another
var obaImg = new Object();
// http://coursesweb.net/javascript/
// put the image in element with ID from "ide"
obaImg.putImg = function(img, ide, stl) {
if(document.getElementById(ide)) {
document.getElementById(ide).innerHTML = '<img src="'+ img+ '" '+stl+' />';
}
}
// empty the element with ID from "elmid", add image in the other element associated to "img"
obaImg.alternateImg = function(elmid) {
var img = obaImg.storeim[elmid];
var addimg = (elmid == obimids[img][0]) ? obimids[img][1] : obimids[img][0];
$('#'+elmid+ ' img').hide(800, function(){
$('#'+elmid).html('');
obaImg.putImg(img, addimg, 'style="display:none;"');
$('#'+addimg+ ' img').fadeIn(500);
});
// function executed after the image is moved into "addimg"
whenAddImg();
}
obaImg.storeim = {}; // store /associate id_elm: image
// add 'image': 'id_elm1', and 'image': 'id_elm1' in "storeim"
// add the image in the first tag associated to image
// register 'onclick' to each element associated with images in "obimids"
obaImg.regOnclick = function() {
for(var im in obimids) {
obaImg.storeim[obimids[im][0]] = im;
obaImg.storeim[obimids[im][2]] = im;
obaImg.putImg(im, obimids[im][0], '');
document.getElementById(obimids[im][0]).onclick = function(){ obaImg.alternateImg(this.id); };
document.getElementById(obimids[im][3]).onclick = function(){ obaImg.alternateImg(this.id); };
}
}
obaImg.regOnclick(); // to execute regOnclick()
FIDDLE
When clicking the items it adds them to a container where I'd like them to be stored if the user navigates to another page. I have seen some local storage cookie code on another script
FIDDLE
var $chks = $('.compare').change(function () {
console.log('c', this)
if ($(this).is(':checked')) {
var img = $('<img>'),
findimg = $(this).closest('.box').find('img'),
data_term = findimg.data('term');
img.attr('src', findimg.attr('src'));
img.attr('data-term', data_term);
var input = '<input type="hidden" name="imagecompare" value="' + data_term + '">';
$('#area').find('div:empty:first').append(img).append(input);
} else {
var term = $(this).data('term'),
findboximage = $('#area > div > img[data-term=' + term + ']')
findboximage.parent('div').empty();
}
localStorage.setItem("imagecookie", $chks.filter(':checked').map(function () {
return $(this).data('term')
}).get().join(','));
});
$(document).on('click', '#area > div', function () {
$(this).empty();
localStorage.clear();
});
var cookie = localStorage.getItem("imagecookie");
if (cookie) {
var terms = cookie.split(',');
if (terms.length) {
$chks.filter($.map(terms, function (val) {
return '[data-term="' + val + '"]'
}).join()).prop('checked', true).change();
}
}
but can't figure how to apply something similar to this one. I would be grateful for any help or to be pointed to some useful places for help.

how to call functions of (function (f, h) after images loading?

This article taken from here. It is simple responsive cube with rotating. Normally images are from <div id="cs-slider">img1 img2... < /div>. Now here i wanted to load these from images folder automatically. Like all images from images folder.
Here, i tried for this like below code.
$.ajax({
url: "task.php",
data: {
'files': 'images'
},
success: function (datas) {
var res = datas.split(",");
var len = (res).length;var k=0;
res.forEach(function (entry) {
if (entry != '') {
$('#cs-slider').prepend('<img src="images/'+entry+'" />');
}
k++;
if(k==len)
{
alert("hai3");
}
});
// alert(filelist);
},
error: function (req) {
alert('Error: ' + req.status);
}
});
But these are appending after page loaded.
How to solve this?
Code is attached here fiddle
if I understand correctly, all you need is onload event.
Images will be shown after loading.
var img_ = new Image();
img_.onload = function() {
$('#cs-slider').prepend('<img src="images/'+entry+'" />');
}
img_.src = '/images/'+entry;

Page loading is gradually getting slower using jQuery script

I'm using this jQuery script to show search results. Everything works fine, but when search results have more than one page and I'm browsing pages via paging then every page loading is gradually getting slower. Usually first cca 10 pages loads I get quickly, but next are getting avoiding loading delay. Whole website get frozen for a little while (also loader image), but browser is not yet. What should be the problem?
function editResults(def) {
$('.searchResults').html('<p class=\'loader\'><img src=\'images/loader.gif\' /></p>');
var url = def;
var url = url + "&categories=";
// Parse Categories
$('input[name=chCat[]]').each(function() {
if (this.checked == true) {
url = url + this.value + ",";
}
});
url = url + "&sizes=";
// Parse Sizes
$('input[name=chSize[]]').each(function() {
if (this.checked == true) {
url = url + this.value + ",";
}
});
url = url + "&prices=";
// Parse Prices
$('input[name=chPrice[]]').each(function() {
if (this.checked == true) {
url = url + this.value + ",";
}
});
$('.searchResults').load('results.php'+url);
$('.pageLinks').live("click", function() {
var page = this.title;
editResults("?page="+page);
});
}
$(document).ready(function(){
editResults("?page=1");
// Check All Categories
$('input[name=chCat[0]]').click(function() {
check_status = $('input[name=chCat[0]]').attr("checked");
$('input[name=chCat[]]').each(function() {
this.checked = check_status;
});
});
// Check All Sizes
$('input[name=chSize[0]]').click(function() {
check_status = $('input[name=chSize[0]]').attr("checked");
$('input[name=chSize[]]').each(function() {
this.checked = check_status;
});
});
// Edit Results
$('.checkbox').change(function() {
editResults("?page=1");
});
// Change Type
$(".sort").change(function() {
editResults("?page=1&sort="+$(this).val());
});
});
$('.pageLinks').live("click", function() {
var page = this.title;
editResults("?page="+page);
});
just a wild guess but... wouldn't this piece of code add a new event handler to the click event instead reaplacing the old one with a new one? causing the click to call all the once registered handlers.
you should make the event binding just once
var global_var = '1';
function editResults(def) {
// all your code
global_var = 2; // what ever page goes next
};
$(document).ready(function() {
// all your code ...
$('.pageLinks').live("click", function() {
var page = global_var;
editResults("?page="+page);
});
});

Categories