Change the whole content of iFrame - javascript

I have a textarea in which I wan't to add HTML code that will compose a full webpage, and as I type this content will be rendered in an iframe
For example in the textarea I'll write the following code:
<!DOCTYPE html>
<html>
<head>
<title>Live generate</title>
<style></style>
</head>
<body>
</body>
</html>
My problem is that I don't know how to access the iFrame in order to change it's full content so that it matches the one above

you should be able to get the iframe by its id with document.getElementsById or through jquery and then get its document, open it and write to it.
Like:
var iframe = $("iframe"); // or by Id $("#myIframeId")
var doc = iframe.document;
doc.open();
doc.write($("#myTextArea").text());
doc.close();

Related

How to get reference to the iframe from which script html tag was generated?

I have small snippet that is inside iframe and generates script html tag and appends it to the window.top.document.head.
Now I want to know how do I check from within potato.js from which iframe it was generated from once it is already loaded?
<!DOCTYPE html>
<html lang="en">
<head>
</head>
<body>
<iframe>
<!DOCTYPE html>
<html>
<head>
</head>
<body>
<script>
(function() {
var s = document.createElement('script');
s.setAttribute('type','text/javascript');
s.setAttribute('src','https://test.com/potato.js');
window.top.document.head.appendChild(s);
})();
</script>
</body>
</html>
</iframe>
</body>
</html>
Edit: I can not change this code inside the iframe
That information isn't stored automatically.
The only way I can think of would be to add an expando-prop to the script with a reference to the current window (i.e. the frame's window)…
s.sourceWindow = window;
… then read that from within potato.js …
const sourceWindow = document.currentScript.sourceWindow;
… and then loop over all the frames (window.frames) looking for a match.
Since you are using window.top and not window.parent you might need to be recursive there.

How to access html elements in iframe inside html tag

I have a html file which contains iframe like below lines of code. Note that this iframe is displayed by one of tiny mce jquery and is rendered in browser as
below
<html>
<body>
<textarea id="texteditor"></textarea>
<div class="mceeditor">
<iframe>
<html>
<body>
<script type="text/javascript">
function mySubmit() {
var URL = "http://localhost:61222/14CommunityImages/hands.png";
window.document.getElementById("texteditor").value = URL;
}
</script>
</body>
</html>
</iframe>
</div>
</body>
</html>
Now my goal is to append var url inside text area which is in parent html tag.
Please help me !!!
The document in the iframe can access its parent window via parent, and its parent window's document via parent.document. So:
parent.document.getElementById("texteditor").value = URL;
Note: To access each-other's documents, the main document and the iframe must be on the same origin. If they're on different origins, they can still communicate, but only if they both do so expressly, via web messaging.
Side note: Your iframe, as shown in the question, won't work. Inline content in iframes is for display when the browser doesn't support iframes. You use a separate resource (e.g., page) identified by the src attribute (or you use the srcdoc attribute; I have no idea how well supported it is), for the iframe's content.
E.g.:
Main page:
<!doctype html>
<html>
<head>
<meta charset="UTF-8">
<title>Main Page</title>
<body>
<textarea id="texteditor"></textarea>
<div class="mceeditor">
<iframe src="theframe.html"></iframe>
</div>
</body>
</html>
theframe.html:
<!doctype html>
<html>
<body>
<input type="button" value="Click to set" onclick="mySubmit()">
<script type="text/javascript">
function mySubmit() {
var URL = "http://localhost:61222/14CommunityImages/hands.png";
parent.document.getElementById("texteditor").value = URL;
}
</script>
</body>
</html>

Add contents to an empty frame

I have an empty frame in my page, with src set to '' (empty).
I also have a string like this:
<html>
<head>
<base src="http://www.example.com">
<title>Blah</title>
</head>
<body>
<p>Fancy web page</p>
</body>
</html>
I would like to populate the iframe with the string, so that the exact content of it matches the string.
What's the best way to do this? I am going insane trying to do it.
You need to set an id on the iframe and then set the innerHTML of the iframe's document body and head to the head/body string values.
Here's a working fiddle: http://jsfiddle.net/theoutlander/dw3r7/1/
<iframe id=testframe></iframe>
var strHead = '<base src="http://www.example.com"><title>Blah</title>'
var strBody = '<p>Fancy web page</p>';
testframe.document.head.innerHTML = strHead;
testframe.document.body.innerHTML = strBody;

Replacing HTML source of an iframe document

I am working on a page that will display the contents of a database field. The contents are in HTML format and includes an entire webpage
<html>
<title>Some title</title>
<style type="text/css">
/* CSS content here */
</style>
<body>
<!-- body content here -->
</body>
</html>
I need to display all of this inside another webpage so I thought using an iframe would allow me to negate any css from the parent page. However, I cannot figure out how to overwrite the contents of the iframe document.
What I've done so far is retrieve the data and then use the following
$("#iframe_constainer")
.find('iframe:first').contents().find('html:first').html(myHTML);
My web page includes a div called iframe_container which contains an iframe.
<div id="iframe_container"><iframe/></div>
This is working okay, but the contents of myHTML are getting wrapped inside html tags. So the effect is like this
<html>
<html>
<title>Some title</title>
<style type="text/css">
/* CSS content here */
</style>
<body>
<!-- body content here -->
</body>
</html>
</html>
I know it's because I'm finding the html tag in the iframe and changing the HTML. Is there a way to overwrite the entire document using jQuery?
Opening the document and closing afterwards will fix the issue with appending the content
var iframe = document.getElementById('iframeID');
iframe.contentWindow.document.open();
iframe.contentWindow.document.write(htmlData);
iframe.contentWindow.document.close();
You don't really need jQuery for this, just use document.write to write content to the iframe to completely replace iframe's document.
E.g. (in plain vanilla JS)
document.getElementById("myIframeId").contentWindow.document.write(myHTML);

Nested iframes, AKA Iframe Inception

Using jQuery I am trying to access div id="element".
<body>
<iframe id="uploads">
<iframe>
<div id="element">...</div>
</iframe>
</iframe>
</body>
All iframes are on the same domain with no www / non-www issues.
I have successfully selected elements within the first iframe but not the second nested iframe.
I have tried a few things, this is the most recent (and a pretty desperate attempt).
var iframe = jQuery('#upload').contents();
var iframeInner = jQuery(iframe).find('iframe').contents();
var iframeContent = jQuery(iframeInner).contents().find('#element');
// iframeContent is null
Edit:
To rule out a timing issue I used a click event and waited a while.
jQuery().click(function(){
var iframe = jQuery('#upload').contents().find('iframe');
console.log(iframe.find('#element')); // [] null
});
Any ideas?
Thanks.
Update:
I can select the second iframe like so...
var iframe = jQuery('#upload').contents().find('iframe');
The problem now seems to be that the src is empty as the iframe is generated with javascript.
So the iframe is selected but the content length is 0.
Thing is, the code you provided won't work because the <iframe> element has to have a "src" property, like:
<iframe id="uploads" src="http://domain/page.html"></iframe>
It's ok to use .contents() to get the content:
$('#uploads).contents() will give you access to the second iframe, but if that iframe is "INSIDE" the http://domain/page.html document the #uploads iframe loaded.
To test I'm right about this, I created 3 html files named main.html, iframe.html and noframe.html and then selected the div#element just fine with:
$('#uploads').contents().find('iframe').contents().find('#element');
There WILL be a delay in which the element will not be available since you need to wait for the iframe to load the resource. Also, all iframes have to be on the same domain.
Hope this helps ...
Here goes the html for the 3 files I used (replace the "src" attributes with your domain and url):
main.html
<!DOCTYPE HTML>
<html>
<head>
<meta charset="utf-8">
<title>main.html example</title>
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script>
$(function () {
console.log( $('#uploads').contents().find('iframe').contents().find('#element') ); // nothing at first
setTimeout( function () {
console.log( $('#uploads').contents().find('iframe').contents().find('#element') ); // wait and you'll have it
}, 2000 );
});
</script>
</head>
<body>
<iframe id="uploads" src="http://192.168.1.70/test/iframe.html"></iframe>
</body>
iframe.html
<!DOCTYPE HTML>
<html>
<head>
<meta charset="utf-8">
<title>iframe.html example</title>
</head>
<body>
<iframe src="http://192.168.1.70/test/noframe.html"></iframe>
</body>
noframe.html
<!DOCTYPE HTML>
<html>
<head>
<meta charset="utf-8">
<title>noframe.html example</title>
</head>
<body>
<div id="element">some content</div>
</body>
var iframeInner = jQuery(iframe).find('iframe').contents();
var iframeContent = jQuery(iframeInner).contents().find('#element');
iframeInner contains elements from
<div id="element">other markup goes here</div>
and iframeContent will find for elements which are inside of
<div id="element">other markup goes here</div>
(find doesn't search on current element) that's why it is returning null.
Hey I got something that seems to be doing what you want a do. It involves some dirty copying but works. You can find the working code here
So here is the main html file :
<!DOCTYPE html>
<html>
<head>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script type="text/javascript">
$(document).ready(function(){
Iframe = $('#frame1');
Iframe.on('load', function(){
IframeInner = Iframe.contents().find('iframe');
IframeInnerClone = IframeInner.clone();
IframeInnerClone.insertAfter($('#insertIframeAfter')).css({display:'none'});
IframeInnerClone.on('load', function(){
IframeContents = IframeInner.contents();
YourNestedEl = IframeContents.find('div');
$('<div>Yeepi! I can even insert stuff!</div>').insertAfter(YourNestedEl)
});
});
});
</script>
</head>
<body>
<div id="insertIframeAfter">Hello!!!!</div>
<iframe id="frame1" src="Test_Iframe.html">
</iframe>
</body>
</html>
As you can see, once the first Iframe is loaded, I get the second one and clone it. I then reinsert it in the dom, so I can get access to the onload event. Once this one is loaded, I retrieve the content from non-cloned one (must have loaded as well, since they use the same src). You can then do wathever you want with the content.
Here is the Test_Iframe.html file :
<!DOCTYPE html>
<html>
<head>
</head>
<body>
<div>Test_Iframe</div>
<iframe src="Test_Iframe2.html">
</iframe>
</body>
</html>
and the Test_Iframe2.html file :
<!DOCTYPE html>
<html>
<head>
</head>
<body>
<div>I am the second nested iframe</div>
</body>
</html>
You probably have a timing issue. Your document.ready commend is probably firing before the the second iFrame is loaded. You dont have enough info to help much further- but let us know if that seems like the possible issue.
You should use live method for elements which are rendered later, like colorbox, hidden fields or iframe
$(".inverter-value").live("change",function() {
elem = this
$.ajax({
url: '/main/invertor_attribute/',
type: 'POST',
aysnc: false,
data: {id: $(this).val() },
success: function(data){
// code
},
dataType: 'html'
});
});
I think the best way to reach your div:
var your_element=$('iframe#uploads').children('iframe').children('div#element');
It should work well.
If browser supports iframe, then DOM inside iframe come from src attribute of respective tag. Contents that are inside iframe tag are used as a fall back mechanism where browser does not supports iframe tag.
Ref: http://www.w3schools.com/tags/tag_iframe.asp
I guess your problem is that jQuery is not loaded in your iframes.
The safest approach is to rely on pure DOM-based methods to parse your content.
Or else, start with jQuery, and then once inside your iframes, test once if typeof window.jQuery == 'undefined', if it's true, jQuery is not enabled inside it and fallback on DOM-based method.

Categories

Resources