I am working on my portfolio page and I want to have my projects in a demo mode where the user can preview the sites in different viewports. I got the idea from here:
http://my.studiopress.com/themes/genesis/#demo-full
On mobile devices I would like to keep the iframes from loading, and instead have links to the projects open the sites in the new tab.
If I have the divs containing the iframes hidden at the very top of my CSS file with display:none, I can see the iframes still load in the background and the page takes a long time to load.
Is there any way to keep them from loading at all when on a certain device or viewport size?
You could achieve this by using JavaScript and the HTML Data-Attribut. By setting the src-Attribute to something like "#" it won't load anything. You can use the data-Attribute to store the URL for use with JavaScript.
<iframe src="#" data-src="https://placekitten.com/200/300" frameborder="0"></iframe>
Then you just check to screen size with window.matchMedia() and set the src-attribute at a specific screen size.
var $iframe = $('iframe'),
src = $iframe.data('src');
if (window.matchMedia("(min-width: 480px)").matches) {
$iframe.attr('src', src);
}
Here is a working example: https://jsfiddle.net/5LnjL3uc/
If you want to show the iframe after a user resizes the window you need to put your code into a function and bind it to a resize event:
var $iframe = $('iframe'),
src = $iframe.data('src');
function showIframe() {
if (window.matchMedia("(min-width: 480px)").matches) {
$iframe.attr('src', src);
}
}
$(window).on('resize', showIframe);
// Initialize it once on document ready
showIframe();
Working Example: https://jsfiddle.net/5LnjL3uc/1/
A better solution is to approach this in reverse.
IE do not load the src to begin with by placing your URL in a attribute like 'data-src' for example.
See my code for this below. You simply copy the data-src to your src when your device, or device width is not mobile/mobile size.
I believe this is the best solution because there are no uncertainties. With the previously mentioned solutions (which I tried) you are racing against the clock with the browser for when your code runs and it decides to load the iframe src.
if(device !== true) {
// add '#' to the href
let iframe = document.getElementById('3dExperience')
iframe.src = iframe.getAttribute('data-src')
}
Note: 'device' is the is-mobile npm package for detecting mobile.
Related
I have some swf embedded in iframe but only if the page is refreshed the iframe is resized, then if I select other one then will show as all swf not only the animation the background as well. This is what I am using
if ( 'resizeIframe' === $('#onPlayAction').val() ) {
var ifrEl = $('div.player-container iframe.page-iframe')[0];
$(ifrEl).show();
ifrEl.src = htmlPageBrowserUri;
ifrEl.onload = function() {
ifrEl.width = ifrEl.contentWindow.document.body.scrollWidth;
ifrEl.height = ifrEl.contentWindow.document.body.scrollHeight;
}
}
There are three ways to do this.
You can change the size on every window resize
$(window).on('resize', function (){
ifrEl.width = ... ;
ifrEl.height = ... ;
})
You can use some jQuery plugins like iFrame Resizer
You can use some nifty css tricks. Go search for responsive iframes using css and you will find a ton of good answers.
I hope this all helps you.
I suspect the issue with your code might be thses two lines :
ifrEl.src = htmlPageBrowserUri;
ifrEl.onload = function() {
The problem being that the first line set s the frame address, but second line sets the onload event immediately, probably before the page has loaded ? So when the page does load, the line setting onload event has already run & so doens't get set.
I don't quite understand the text in your question (sorry!) but the code below successfully resizes an iframe - it's run 'onload' in the frame's page:
<body onload="setParent()">
In case it's relevant, the iframe itself has attributes:
<iframe id="neckfinishframe" style="width:100%;overflow-x:hidden" src=".. etc">
In my case I'm only concerned about height. Width is 100%.
In the iFrame page, this code runs from the onload event to amend the iframe height to be whatever the height of the page is, plus a bit. This is intended to avoid showing a set of scroll bars within the iframe.
function setParent() {
// runs onload in iframe page
// in my case I have to run it from the frame page because I need to know the page rendered height in order to set the iframe height
var f;
try {f = parent.getElementById("neckfinishframe")} catch (e) {};
if (f != null) f.style.height=(this.document.body.scrollHeight+30)+"px";
}
Note - I haven't tried this cross- browser but I know it works in IE.
I have the following script which take a string with html information (containing also reference to images).
When I create a DOM element the content for the image is being downloaded by the browser. I would like to know if it is possible to stop this Beauvoir and temporary prevent loading.
I am targeting web-kit and presto browsers.
relativeToAbosluteImgUrls: function(html, absoluteUrl) {
var tempDom = document.createElement('div');
debugger
tempDom.innerHTML = html;
var imgs = tempDom.getElementsByTagName('img'), i = imgs.length;
while (i--) {
var srcRel = imgs[i].getAttribute('src');
imgs[i].setAttribute('src', absoluteUrl + srcRel);
}
return tempDom.innerHTML;
},
Store the src path into an HTML5 data-* attribute such as data-src. Without src being set, the browser will not download any images. When you are ready to download the image, simply get the URL from the data-src attribute and set it as the src attribute
$(function() {
// Only modify the images that have 'data-src' attribute
$('img[data-src]').each(function(){
var src = $(this).data('src');
// modify src however you need to, maybe make
// a function called 'getAbsoluteUrl'
$(this).prop('src', src);
});
});
The approach taken by popular image library, Slimmage, is to wrap your img tags in noscript tags:
<noscript class="img">
<img src="my-image.jpeg" />
</noscript>
Web scrapers and people with JS turned off will see the image as if the noscript wasn't there but other browsers will completely ignore the noscript and img tags.
You can then use JavaScript to do whatever you want with it, for example (using jQuery):
$('noscript.img').replaceWith(function(){
return $(this.innerText).removeAttr('src');
});
I think you should reverse the logic, don't load the images by default and at the moment the image is needed, update it's src attribute to tell browser to start loading.
Or even better way would be to use some jquery lazy image loading plugin like this one:
http://www.appelsiini.net/projects/lazyload
Hope this helps.
To prevent images from being show, you could use this.
$(window).loaded( function() {
$("img").removeAttr("src");
});
It might be tricky and give unexpected results, but it does it.
I am looking for a way to cancel image loading using javascript. I've looked at other questions and hiding them is not enough. Also, the rest of the page must load (window.stop() is out of the question).
The page that is being loaded is not under my control, only one thing is guaranteed - the first <script> on the page is my javascript (lightweight - no jquery).
I have tried setting all img sources to nothing, that did not help since the dom is created after the page is parsed, and all browsers have the same behavior - the img is loaded once it is parsed.
Not possible with modern browsers. Even if you alter the src attribute of image tag with JavaScript browsers still insist on loading the images. I know this from developing the Lazy Load plugin.
The only way I can see to stop images loading is to not have an src attribute present in the image itself, and using a custom data-* attribute to hold the location of the image:
<img data-src="http://path.to/image.png" />
Obviously this doesn't gracefully degrade for those (admittedly rare) JavaScript disabled browsers, and therefore requires a noscript fall-back:
<img data-src="http://path.to/image.png" />
<noscript><img src="http://path.to/image.png" /></noscript>
And couple this with a simple function to load the images when you, or your users, are ready for them:
/* simple demo */
function imagePopulate(within, attr) {
within = within && within.nodeType == 1 ? within : document;
attr = attr || 'data-src';
var images = within.getElementsByTagName('img');
for (var i = 0, len = images.length; i < len; i++) {
if (images[i].parentNode.tagName.toLowerCase() !== 'noscript') {
images[i].src = images[i].getAttribute(attr);
}
}
}
document.getElementById('addImages').onclick = function(){
imagePopulate();
};
JS Fiddle demo.
I can't be sure for all browsers, but this seems to work in Chrome (in that there's no attempt, from looking at the network tab of the developer tools, to load the noscript-contained img).
It can be done with webworkers. See the following example:
https://github.com/NathanWalker/ng2-image-lazy-load.
Stopping a web worker cancels the image loading in browser
Recalling the onload event:
window.onload=function(){
imgs = document.getElementsByTagName('img');
for(i = 0; i < imgs.length(); i++){
imgs[i].src = '#';
}
};
If you want to only cancel the loading of the image , you can use sємsєм's solution
but i do not think it will work by using an window onload event .
You will probably need to provide a button to cancel the image load. Also i suggest, instead of setting the src attribute to "#" , you can remove the src attribute itself using
removeAttribute()
[Make sure you disable the cache while testing]
You need a proxy.
Your script can redirect to another server using something like
location.replace('http://yourserver.com/rewrite/php?url='+escape(this.href));
perhaps you tell us why you want to cancel image loading and whose site you are loading on so we can come up with a better solution
If there is nothing on the page other than images, you could try
document.write('<base href="http://yourserver.com/" />');
which will mess with all non-absolute src and hrefs on the page.
UPDATE Horrible hack but perhaps this almost pseudo code (I am off to bed) will do someting
document.write('<script src="jquery.js"></script><div id="myDiv"></div><!-'+'-');
$(function() {
$.get(location.href,function(data) {
$("#myDiv").html(data.replace(/src=/g,'xsrc='));
});
})
The closest you can get to what you maybe want is to have a quickly loaded placeholder image (ie. low resolution version of your image) and a hidden image (eg. {display:none}) in which the large image gets loaded but not displayed. Then in the onload event for the large image swap the images over (eg. display:block for the large image display:none for the smaller). I also use an array (with their url), to reuse any images that have already been opened.
BTW if you open an image in a new webpage when it gets closed then the image loading will be cancelled. So maybe you can do something similar in a webpage using an iframe to display the image.
To close the iframe and therefore unload the image, remove the frame from the DOM
(another advantage is that browsers spawn another process to deal with iframes, so the page won't lock up while the image loads)
I'm running a Javascript replace function to replace standard images with class="replace-2x"on my jQuery Mobile site with Retina-quality images if the user is on a mobile device with Retina display. For example, on a Retina device, logo.png will be replaced with logo#2x.png. The JS function is here:
function highdpi_init() {
$(".replace-2x").each(function () {
var src = $(this).attr("src");
$(this).attr("src", src.replace(".png", "#2x.png").replace(".jpg", "#2x.jpg"));
});
}
$(".page").live('pageinit',function(event){
highdpi_init();
});
I'm now running into an issue where the replace function is running more than once. So for example, it replaces logo.png with logo#2x.png as the page is loading, but then as the page continues to load, it KEEPS replacing .png with #2x.png in the img src over and over so that the image tag ends up looking like this:
<img src="mobile/images/logo#2x#2x#2x#2x#2x#2x#2x#2x#2x#2x#2x.png" class="replace-2x" alt="logo" width="200">
How can I prevent this from replacing on a single img element more than once? Keep in mind, I will have multiple images on the same page, so the function will need to apply to all images, but only one time each.
The problem is surely that your 'pageinit' event is being called more than once. You can either follow MДΓΓ БДLL's idea (which won't work if images are dynamically added) or you can make your handler smarter so that it doesn't replace the src if it already was replaced
function highdpi_init() {
$(".replace-2x").each(function () {
var $this = $(this);
var src = $this.attr("src");
$this.attr("src", src.replace(".png", "#2x.png").replace(".jpg", "#2x.jpg"));
// Remove the class so it doesn't replace it again
$this.removeClass('replace-2x')
});
}
You don't need JS for this, you could do it in CSS only.
<link rel="stylesheet" media="only screen and (-webkit-min-device-pixel-ratio: 2)" href="/css/highdpi.css"/>
You could make your images look like
<img src="transparent.gif" class="logo-a" alt="logo" width="200" />
And in highdpi.css you could do
img.logo-a {
background-image: url('file#2x.png')
}
And in lowdpi.css
img.logo-a {
background-image: url('file.png')
}
Using .one() should work since it is just a binding and if you are using Jquery Mobile the way that is suggested it will be just fine. That is unless you are passing back the html from the server. In which case it would be a good idea to add an extra condition to make sure that the src doesn't already have #2x.png before replacing.
There is disappointingly little documentation on pageinit on the offical jQuery Mobile docs. So I'm going to speculate here. It looks like pageinit is used to fire events for when a specific DOM element has finished loading, since it may not have been loaded on the initial page load (deferred until needed). That being said, it may be that adding/altering images to the DOM element in question fires the pageinit again. Could you tag each updated image with something that says, 'hey, I've already been updated to 2x'? Something such as
$.data(targetimg, 'retinafied', true);
And then check for that value before replacing the src?
I managed to change an iframe's src with javascript
var path='images/tattoo/fullsize/';
var h=$('#borderlessFrame').height();
var bigFrame=$('#borderlessFrame');
function loadGallery(num)
{
bigFrame=$('#borderlessFrame');
var galPath=path + num; // path to the image
h=$('#borderlessFrame').height();
var source=bigFrame.attr('src');
source='i load some address here';
}
But for now i see the old content of the iframe , is there a way to reload the iframe ( only iframe not the whole page)
The thing i am trying to achieve is a simple gallery , thumb pictures on the bottom and a large picture on the top ( iframe ). On click on any of the thumbs , i change the content of the iframe without reloading the actual page.
Keep in mind that i am new to html/javascript/jquery.
So basically i need a way(function?) to reload the iframe.
To set attribute, you need to call .attr( attributeName, value )
Try this:
var source='i load some address here';
bigFrame.attr('src', source);
Reference:
jQuery .attr()
jQuery has the load method, which is useable like so (assuming borderlessFrame is the id of the <iframe>):
var iFrame = $('#borderlessFrame');
iFrame.load('http://theurltoload.com')
However, iframes seem like an unnecessary approach for your requirements, consider looking into CSS and the jQuery DOM manipulation methods a little more.