We all had this problem once: Including an iframe into a website and then – there were scroll bars which mess up everything. But have you ever heard of the JavaScript method Window.postMessage? We can use this method to communicate between the iframe and its parent and it is also widely supported.
At first, we need to register the message event to the listener on the parent:
<script type="text/javascript"> // browser compatibility: get method for event // addEventListener(FF, Webkit, Opera, IE9+) and attachEvent(IE5-8) var myEventMethod = window.addEventListener ? "addEventListener" : "attachEvent"; // create event listener var myEventListener = window[myEventMethod]; // browser compatibility: attach event uses onmessage var myEventMessage = myEventMethod == "attachEvent" ? "onmessage" : "message"; // register callback function on incoming message myEventListener(myEventMessage, function (e) { // we will get a string (better browser support) and validate // if it is an int - set the height of the iframe #my-iframe-id if (e.data === parseInt(e.data)) document.getElementById('my-iframe-id').height = e.data + "px"; }, false); </script>
Note: You can limit the source of the message for security by asking the event for its origin (e.origin).
Now we need to post the message, the height of its content, by the iframe:
<script type="text/javascript"> // all content including images has been loaded window.onload = function() { // post our message to the parent window.parent.postMessage( // get height of the content document.body.scrollHeight // set target domain ,"*" ) }; </script>
Thats it. Thats all.
Hi Michi,
A little set of instructions on how to set this up such as where to put what would be handy for the novice developer.
Thank you.
Hi Manjo,
the first part of the Javascript has to be put on the parent and the second part has to be put into the iframe loaded.
Hope this helps 🙂
I’ve been looking for solutions the whole day, I’ve found from jquery plugins to raw javascript tricks, but all I needed was this. I probed and It worked excelent. Thanks so much man, you have done a great contribution to the world publishing this.
Thank you!
I’m getting the following error, any idea?
Failed to execute ‘postMessage’ on ‘DOMWindow’: The target origin provided (‘http://www.iframe_url.es’) does not match the recipient window’s origin (‘http://myserver_url.com’).
Thank you
Hi Senén,
did you include
,"*"
for whitelabeling all domains as recipient in postMessage() ?
Hey! You have made my day! I was stuck on this particular issue since yesterday, didn’t find such a clear and workable explanation than your’s on the web and even on StackOverflow… Thanks!
Thank you for your comment! 🙂
Dude this is one kickass snippet but sadly its not working on my part because i have lack of javascript knowledge. I have a gut feeling im doing something wrong. I have a paypal iframe which already generates with javascript so somehow it doesn’t trigger. Can you please help me? The problem resides in the fact i have a button after which i choose payment option paypal it generates the paypal iframe and its content but it doesnt resize it. Im pulling my hair out. Anyway if you can help me it would be awesome if not still awsome piece of code thanks!!!!!
Hi Goran,
your iframe on the parent will be resized when the child sends the message. You can not get the childs size when you do not have control of the childs web application.
Michi
Hi.
I tried your script and it is working fine but I have a problem. I the one link in the iframe page get height 1700px and next one is 700px – the frame still have 1700px height. Does the script calculate the height back also?
http://reisiguru.ee/proov/seen.html – choose left “Kanaari Saared” than Choose Mehhiko and you’ll see.
Tahnks!
Hi Himot,
which each pageload in the child iframe, you have to post the message back to the parent to reseize.
Hope this helps
Hi
Like I understand I must do it in you second iframe? Can you give me a hint or code? I have not much skills in java or coding:)
Thanks!
Himot
I mean. I must add some lines in to this?
// all content including images has been loaded
window.onload = function() {
// post our message to the parent
window.parent.postMessage(
// get height of the content
document.body.scrollHeight
// set target domain
,”*”
)
};
my example is there: http://www.lennuleidja.ee/novatours
please help my i am getting e.data= undefined in IE
Do you have e in the anonym function parameter function(e) ?
Thanks for your replay sir, i just change my code to body level it’s working fine. by the way your code made my day
Hi Michi,
I included your code and it works. Thanks a lot. However I’m looking for something additional and I’m not sure if it requires tweaking this code or doing something else.
I have an iframe which loads contents dynamically into it from another domain. (I placed the above code at both the parent and child page). Now within this dynamically loaded content there’s a button which opens a new page (which is smaller in size). But when I put an alert, it shows the same height for both the pages loaded within the iframe. I need the real height of the shorter page to be reflected. How do I do this?
Thanks….
Hi Tas,
the new page has to send its height after loading.
Cheers Michi
Dear Sir,
Im working on a Joomla! 1.5 website, i made a CustomHTML module, then i insert the + the java code. Then i insert code in head.php.
Its working !!!!!
But instead of 3500 pixels that i need, it is resizing it to 950.
Any help ?
Thanks in advance !!
Hi Desperad0,
are you sure that you have no wrong css which leads to the wrong size?
Also see this questions and answers on Stackoverflow:
http://stackoverflow.com/questions/8857341/document-body-scrollheight-yielding-two-different-results-in-firefox-chrome
http://stackoverflow.com/questions/15932650/body-scrollheight-doesnt-work-in-firefox
Cheers Michi
Dear Sir, a few words can’t describe what im feeling about you rignt now !!
Thank you very much for this !!
We are working in a new website on WordPress and script worked just fine !!! You have saved me from a lot of trouble ! If u ever planning visiting Thessaloniki, Greece just drop me an e-mail =D
Hi Desperad0,
thank you – your comment really made me smile today. Glad that helped you.
Cheers Michi
Hello Desperado,
is it possible to send me an workaround to get this work in Joomla like you did?
Regards,
Richard
You still need help with Joomla ?
In my case i was trying to set a Booking Engine inside a iframe. I was able to put the second part of the code inside the of the Booking Engine. Then i just c/p the first part in my header.php right before .
Then i set iframe code on page
Best regards!
-desperad0
Tested in ie11,chrome,opera,firefox and all function thank you.
ie9 however does not.
I do not see any errors and need this to function back to ie7
Hi sconard,
IE9 should also work fine.
See this documentation: https://developer.mozilla.org/en-US/docs/Web/API/Window.postMessage
Cheers Michi
Its Working ..!!! Thank you so much!!!!
Thank you. I struggled to solve this problem, so happy to be a wonderful way to learn.
Hi MICHI,
document.body.scrollHeight send the scroll Height of Browser not the scroll Height of Iframe. can you please help me with this below is my plunker link
http://plnkr.co/edit/TZslZdR7q5okfUAiYfbo?p=preview
Hi Krishna,
the second JavaScript has to be included into the iframe and not on the parent.
Cheers Michi
I have a question that I want to add iFrame of other site on my site. Please check this link of my site https://unlockiphone.co.uk/unlock-iphone/ you can see a big scroll on this page with blank space. But when you select iPhone model and enter IMEI and select any network so you will see that it show reviews about this unlock and then blank scroll will fill with reviews.
Is it possible that when some one visit this page so he/she will see only iPhone selection section without long blank scroll but when he/she fill form so my site’s page scroll automatically as this officialiphoneunlock.co.uk/iphone_unlock.php original page do.
Regards.
Hi Ali,
you would have to send the height from the iframe (https://www.officialiphoneunlock.co.uk) to the parent.
Cheers Michi
Nice. One thing which would improve this solution — height will increase but not decrease if framed content changes.
David Bradshaw’s solution does this.
Cheers,
Skweekah
Hi Skweekah,
thank you!
David Bradshaw’s solution? Can you provide a link please 🙂
Cheers Michi
Here’s the iframe resizer by david bradshaw: https://github.com/davidjbradshaw/iframe-resizer
Hi Michi,
Was working on this since yesterday, looked around several ways to accomplish this but was not able to do. I never wondered this could be so easy. Thanks for this. I have a small question, how can I decrease the height of iframe if some link is clicked inside it.
Hi Tarun,
you can send postMessage to the parent from the new page which would be opened in the iframe to resize again.
Cheers Michi
u rock bro! Thanks. God bless.
Thank you 🙂
function resizeiframe()
{
// post our message to the parent
window.parent.postMessage(
// get height of the content
document.body.scrollHeight
// set target domain
,”*”
)
}
window.onload = function() {
resizeiframe();
};
window.onresize = function() {
resizeiframe();
};
window.onscroll = function () {
resizeiframe();
};
Thanks so much, you are really make my life beautiful today 🙂
Hey! Awesome code. It works really nice.
I tested it on IE version 9 yesterday but it is not working. Version 11 works great! I know that the percentage of people using old versions is a small percentage. Still, it’s a percentage I’d loose.
Any ideas on how you can make it work on older versions? I would really appreciate it.
Cheers
Hi Mantha,
it should work (http://caniuse.com/#search=postMessage).
Maybe this helps: http://stackoverflow.com/questions/13830480/ie8-9-window-postmessage-not-working-but-why
Cheers Michi
Thanks mate working great!!! 🙂
Hey Michi!
Thanx for the tip! Been looking for a script like this where on stackoverflow, they’d say it’s impossible!
Thanks again man!
Cheers!
Hi Guib,
post the link on the stackoverflow question 🙂
Glad this helps.
Also share your video with me!
Cheers Michi
It doesn’t decrease the height after loading another page inside the iframe, is there a way to fix this?
You will have to resend the postMessage again from the new page loaded.
I found this one: http://sly777.github.io/Iframe-Height-Jquery-Plugin/ , it really works in crossdomain iframes. It resizes all contents in iframes automatically.
Works exactly the same way 🙂
Thank you. Kick Ass!
Bei mir funktioniert es leider auch nur bei der zuerst aufgerufenen Seite. Wenn ich auf Links innerhalb des iFrames gehe, bleibt die Höhe vom Anfang.
Die iframe-Scripts stehen auf den jeweiligen Seiten ganz unten im body-Bereich.
Das parent-Script habe ich sowohl im head als auch im body getestet – funktioniert, leider aber nur auf der ersten iframe-seite…
Hallo Stephan,
das sollte auch für jede Unterseite, die die Post Message sendet funktionieren.
Viele Grüße
Michi
Dear Sir,
Been stuck for days on this and it looks like it works tyvm ^^ but a quastion is there a way to make it so if the browser resizes or lets say on the mobile some one tilt his screen back and forth it wil auto rezise to get the best possible size?
here is site i am working on: http://www.royaltextile.nl/nl/2/sleepace.aspx#0
tyvm again it works better thean i had at least if you ever come to amsterdam il buy you a bear ^^ just send me a email ^^
Hi Valerim
glad I could help you.
You can post the window size on “window.onresize” to your parent again.
Cheers Michi
I used this code, buy having problem on mobile devices – the height is not resizing properly. also how would i modify the code so when the person switches from landscape to portrait mode.
Hi,
you must add a resize listener.
Cheers
Michi
Thank you very much!!!
Hola Yo recibo este mensaje
Uncaught TypeError: Cannot set property ‘height’ of null
Me puedes ayudar?
Hi Antonio,
you have to check the iframe on the parent where you would like to set the height.
Hi Michi,
I have applied the code to my website but it is showing height=”{“event”:”ready”}px” when I inspect the element and when I use debugger it is calculating e.data=9710. Can you please help me to resolve this issue?
Thanks
Hi Sudhir,
I am very busy right now sorry. Do you have an example online?
Cheers Michi
This worked great in wordpress – thank you!
Hi Michi,
Can you please share both the codes again by putting some dummy code?
– Santy
Hi Santy,
both codes – one for the iframe and one for its parent were already in the blog post.
Cheers Michi
Thanks for your quick reply..!!
I have updated the below code in parent page where i am calling the iframe.
—————————————————————————
var myEventMethod =
window.addEventListener ? “addEventListener” : “attachEvent”;
var myEventListener = window[myEventMethod];
var myEventMessage =
myEventMethod == “attachEvent” ? “onmessage” : “message”;
myEventListener(myEventMessage, function (e) {
if (e.data === parseInt(e.data))
document.getElementById(‘myiframe’).height = e.data + “px”;
}, false);
—————————————————————————-
In Below code at iframe end
—————————————————————
window.onload = function() {
window.parent.postMessage(
document.body.scrollHeight
// set target domain
,”http://www.abc.com”
)
};
—————————————————————-
Above code is correct?
will you please confirm the code?
Hi Santy,
sorry – but I can’t give support for each person since this is my private blog.
Cheers Michi
Hey Michi..
You have any example where you have implemented this code?
Thanks in advance.
Jimmy
Hi Jimmy,
you can find a live example on https://michilehr.jimdo.com/
Cheers Michi
Hey Michii,
In Chrome browser, height is not coming properly.
Please suggest if have any fix?
cheers carlos
Along with chrome, also its having issue with Safari browser.
cheers carlos
Hi Carlos,
window.onload should be fired when the entire DOM is ready. When you have some lazy load stuff on the child, there could be errors.
Cheers Michi
hi sir, thanks for your code its really great.
i got a problem hope you can help me.
i have toggle on my iframe. script makes + px very well but i cant make -px work.
i to change iframe size on toggle.
is it possible with this code?
Hi Don,
yes – you will have to catch the resize event and fire the post on this event.
Cheers Michi
i have done that, i commented //document.getElementById(‘sizetracker2’).style.height = e.data + “px”;
this line and alerted e.data.
it works perfectly, alerts 900px when showing div and 150 px after hiding. but the problem is it when i uncomment style.height giving line it alerts 900 px and, continues alerting 900px doesnt change to 150px again.
what am i doing wrong ? i think i need some if else statement or anything else instead of style.height line.
i did it with setinterval on height sender function in iframe 🙂 everything is all right but i get one error.
Uncaught TypeError: e.data.split is not a function at handleMessage
what should i do ?
and one more question please 🙂
i have to iframe, how to catch height separately ?
these iframes come from different php files but from same domain.
when i write two of copy the code above they work on same height get from one php file. another iframe’s height sender works perfectly but i cant catch it becouse of duplicate code.
i tryed to change variable names and so but it doesn’t work
You will have to send and id to the iframe which sends the id back so that the script can apply the height to the correct iframe.
Nvm man, done everything 🙂 thanks again for your code.
I still got error in console, but the code works perfectly.
Here is the rrror:
Uncaught TypeError: e.data.split is not a function at handleMessage
No split in my code. Can you rebuild this on jsfiddle?
I can post code on jsfiddle but it willn’t work becouse of no cross-domains.
https://jsfiddle.net/0qjp3hxz/2/
Here is the parts of code.
finally a code that works! thanks for this brother.
Been searching for a few days and finally found a code that works. I’m using it to load a wordpress site within the iframe and it works. There’s just one thing which seems to happen to some here and I don’t think there has been a fix posted. When a really long page loads inside the iframe and a smaller page is loaded thereafter, the iframe stays at the height of the previous taller page and it won’t resize back to the smaller height. Is there any way get this fix? Thanks for any additional help Michi!
Hi JR,
since document.body.scrollHeight decreases when the document gets smaller, the iFrame should also decrease when the height of the next page is smaller. But you must also send the height of the new page to the parent.
Cheers Michi
Thanks for the quick reply. Would that require the current syntax to be modified or should it already be resizing from tallest to smallest? If no code modification is needed, the iframe does not currently get smaller, only taller.
It should work.
Change code in iframe content page of smaller page from document.body.scrollHeight
to
document.body.offsetHeight
Really helpful code but i am sorry its not working when content is dynamically loading into iframe.
Did you forget to fire ‘window.parent.postMessage’ from the iframe?
Thank you very much! Works like a charm … however i had to use method ‘document.getElementById(‘my-iframe-id’).style.height’ in my case.
I want to put multiple iframes on a page but all of the iframes are using the height of the last frame loaded.
Hi Dennis,
you have to assign a iframe id, pass it to the iframe and post it back.
Cheers Michi
This is the closest I’ve tried that works. Does indeed resize to each page, even long outputs from a database. However, each page is still short about 50px so still shows a scroll bar… not great at javascript myself so how/where would I add the extra 50px so the parent would think it’s an extra 50px in height?
Worked it out. Here for anyone else… Just add + 50 to the end of this line, like…
document.body.scrollHeight + 50