My overall problem is to lazy load images. I've gotten to the point where I'm loading the images only when they are on screen. I need to remove the images that are not on screen.
I thought
$(image).removeAttr("src")
would do it and it rightly removes src, but it does not clear the image from the screen, nor does it replace it with what is in alt.
How do I make it remove the image? Note, I do not want to remove the img tag (I need it for later), just clear the image from the screen.
Other code that may be relevant(although why I don't know)-
updateCarImages:=>
imagesOnScreen = $(#el).find(".carImageClass:onScreen")
imagesOffScreen = _.without(cachedImagesOnScreen,imagesOnScreen)
for image in imagesOnScreen
imgSrc = $(image).attr("src")
if (!imgSrc)
id = $(image).data("tooltip-id")
console.log(id)
result = resultsStore.get(id+"")
console.log(result)
$(image).attr("src", result.get("carImageUrl"))
console.log(imagesOffScreen)
for image in imagesOffScreen
$(image).removeAttr("src")
If you are trying to clear memory (which as I see it would be the only reason to remove images that are not visible) you are up for a ride.
There is no bullet proof way to force a browser to do that. The only way the browser will call the garbage collector is to reach a certain memory limit, and then hint the collector what it should take first.
Moving nodes to a bin and empty it is considered a good way:
var $trash = $('<div>').hide().appendTo('body');
var waste = function(node) {
$trash.append(node).html('');
}
You might get lucky with replacing the source with an empty GIF:
$(image).attr('src','data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw%3D%3D');
This will also keep the node in place and image width/height.
But I highly doubt that any of this will result in any performance gain in your case, the best thing is to not stress the browser with too much data at all.
iOS for iPad (especially version 4.x) is known for having a low memory limit and can easilly crash if you leave too many IMG nodes around.
To hide the image:
$(image).hide();
This will set style="display:none;" on the image and make it not appear
To delete the image:
$(image).remove();
This will Physically remove it from the DOM so it no longer exists
Hybrid approach (leaves the image in the DOM and allows you to change it later)
//Remove the SRC and hide the image
$(image).removeAttr("src").hide();
//Then when you want to change to a new image
$(image).attr("src", "iamge.gif").show();
If your issue is performance, then you can use a pre-existing lazy load jQuery plugin. There is no point re-inventing the wheel.
http://www.appelsiini.net/2012/lazyload-170
Alternatively if you don't wish to use this plugin you could store the src value in a data-* attribute and only attach it to src when you wish to display it.
When hiding:
$(image).data("src", $(image).attr("src"));
$(image).removeAttr("src");
$(image).hide();
When displaying:
$(image).attr("src", $(image).data("src"));
$(image).show();
You can simply hide the image. If you don't wat to go there , you can maybe create a 1px image and than :
$(image).attr('src', '1px.png');
If you want to hide the image, but keep it in place in terms of taking up its space and not affecting container's scrollbars, use visibility: hidden style:
$(image).css('visibility', 'hidden');
You can simply remove image from this code. I have tried it.
$('.img2').dblclick(function()
{
$(".img2").removeAttr('src');
});
This following code shows how I was able to remove the image source
var image_holder = $("#preview-image-holder");
image_holder.empty();
Related
I'm building a very simple Chrome extension that will put a clickable image on top of any youtube.com page.
The image shows up and has its intended click-functionality, but it is layered below any other elements that appear on the page. This is my code:
const linkItem = document.createElement("a");
linkItem.href="https://www.youtube.com/";
linkItem.innerHTML = "<img src='https://imgur.com/gBgwnSa.png' title='YouTube Home'>";
linkItem.setAttribute("style", "position:absolute;top:50px;left:200px;");
document.getElementsByTagName("body")[0].appendChild(linkItem);
The position is just a placeholder.
How can I set the image to always appear layered above any other elements of the page (preferably without having to create a CSS style sheet)? I know this is a beginner question, but any help would be greatly appreciated! :)
You can use the "z-index" property on CSS. You just have to set it to a value high enough, and it'll always be over everything else that have a smaller/null z-index set.
In this case:
linkItem.setAttribute("style", "position:absolute;top:50px;left:200px;z-index:99");
I need to change the color of any image that contains a particular x coordinate. However, the code I am using now only gives me the #scrollwrapper container, and not the individual image that is at that location.
var xHome = window.innerWidth/2;
var yHome = window.innerHeight/2;
var pElement = document.elementFromPoint(xHome, yHome);
alert (pElement.className);
This gets wrapper container on the images, but not the particular image that is there. The site is coolaidhouse.com/projectcaptured
You can see the scroller there. I want to dim the images on the side of the "active," item, which is basically the image closest to the middle.
If I could get the image based on its coordinates I could do the rest. However, I can't figure out how to get the image in lieu of the container.
Here is what the end result should look like:
Your code grabs the image when run from the console. Therefore, you need to wait for the image to load before running the code.
IMG elements have an onload event you can use for this purpose.
The answer was in Rick Hitchcock's comment. Don't know how to mark a comment as an answer though. The images were in fact not loaded yet.
I have a script that examines elements and makes all the elements equal the height of the tallest element of the set. This works fine except for when images take a while to load, because by then the heights have already been set.
To overcome this I added an onload listener to the img tag and after the image has completely loaded, it resets the height of everything correctly.
Now the problem is, if there is a particularly large image, or slow connection, things still look strange while the image is downloading. Is there a way JavaScript can know the ultimate display height of the image at the BEGINNING of the download, rather than the end?
Something like this should work.
var bigImage = new Image();
bigImage.src = "path/to/image";
bigImage.onload = function() {
//create image tag with dimensions and insert into dom
console.log(bigImage.width, bigImage.height);
}
How can I get the height at which an element was rendered, after I have changed it's height?
E.g. the text make a very long (high) div, then I shorten it to make it look neat and I use overflow:hidden to temporarily cut off excess text. Now, dynamically, I want to resize the div to be as high as it would have been if I never touched it.
How is this possible to do?
CSS & JQuery is welcome.
Thanks
Grab that value prior to the re-size.
You can then save it, and use it, in two different ways:
// grab it as a JS value and keep it stored somewhere
var originalHeight = element.height();
// grab and store the original value in the rel HTML attribute
el.attr("rel", el.height()
So I have this page here:
http://www.eminentmedia.com/development/powercity/
As you can see when you mouse over the images the div slides up and down to show more information. Unfortunately I have 2 problems that i can't figure out and I've searched but haven't found quite the right answer through google and was hoping someone could point me in the direction of a tutorial.
The first problem is that when you mouse over an image it changes to color (loads a new image), but there's a short delay when the image is loading for the first time so the user sees white. Do I have to preload the images or something in order to fix that?
My second problem is that when you move your mouse over the 'additional content area' it goes crazy and starts going up and down a bunch of times. I just don't have any idea what would cause this but i hope one of you will!
All my code is directly in the source of that page if you would like to view the source.
Thanks in advance for your help!
Yes, you have to preload the images. Thankfully, this is simple:
var images_to_preload = ['myimage.jpg', 'myimage2.jpg', ...];
$.each(images_to_preload, function(i) {
$('<img/>').attr({src: images_to_preload[i]});
});
The other thing you have to understand is that when you use jQuery you have to truly embrace it or you will end up doing things the wrong way. For example, as soon as you find yourself repeating the same piece of code in different places, you are probably doing something wrong. Right now you have this all over the place:
<div id="service" onmouseover="javascript:mouseEnter(this.id);" onmouseout="javascript:mouseLeave(this.id);">
Get that out of your head. Now. Forever. Always. Inline javascript events are not proper, especially when you have a library like jQuery at your disposal. The proper way to do what you want is this:
$(function() {
$('div.box').hover(function() {
$(this).addClass('active');
$(this).find('div.slideup').slideDown('slow');
}, function() {
$(this).removeClass('active');
$(this).find('div.slideup').slideUp('slow');
});
});
(You have to give all the #industrial, #sustainable, etc elements a class of 'box' for the above to work)
These changes will also fix your sliding problem.
I can see your images (the ones that are changing) are set in the background of a div. Here is a jquery script that preloads every image found in a css file. I have had the same problem in the past and this script solves it. It is also very easy to use:
http://www.filamentgroup.com/lab/update_automatically_preload_images_from_css_with_jquery/
I will take a look at your other problem...
1) You should be using the jquery events to drive your mouseovers. Give each div a class to indicate that its a category container and use the hover function to produce the mouseover/mouseout action you're after.
html
<div id="industrial" class="category"></div>
Javascript
$(".category").hover(
function () {
$(this).find('.container').show();
},
function () {
$(this).find('.container').hide();
}
);
I simplified the code to just do show and hide, you'll need to use your additional code to slide up and slide down.
2) Yes, you need to preload your images. Another option would be "sprite" the images. This would involve combining both the black and white and colour versions of each image into a single image. You then set it as the div's background image and simply use CSS to adjust the background-position offset. Essentially, sliding instantly from the black and white to colour images as you rollover. This technique guarentees that both images are fully loaded.