如何使用 javascript 检查帧是否已加载? - 不是加载,不是 iframe
How to check if a frame is loaded using javascript? - not onload, not iframe
问题:较旧的知识库软件,无论出于何种原因,其链接已损坏。它是一系列嵌套的框架。有些指向正确的目标,有些则没有,而且很多都坏了。当它不能顺利工作时,它使使用知识库变得很麻烦
我要完成的工作:我想确定特定框架何时加载,然后解析框架的文档,用正确的 href 和目标替换锚标记。
资源和限制:我可以访问一些 .aspx 页面。我的目标现在包含一个加载知识库文档的框架集。然而,此框架的 src 似乎不是实际的 .aspx 页面(物理文件)——不确定它是如何生成的,也不确定文档是如何存储的。我看到列出了 src,但无法在我有权访问的网络服务器上找到它。
基本信息: 页面是使用 .aspx 加载的(我不太了解其中的部分内容,也无法访问更深入的内容)。 .aspx 页面有一个在加载页面时构建的框架集。
.aspx 文件中的示例 Framset 代码:
<FRAMESET id="FrameSetMainView" runat="server" border="0" framespacing="0" frameborder="0">
<!-- This frame set is defined and generated in the code -->
</FRAMESET>
我试过在 FRAMESET
标签中添加 onload(这会导致页面在尝试加载时出错)。框架集接管了正文,因此我无法将内联脚本添加到页面底部以使其在加载后成为 运行。
此外,b/c 产品的年龄 - 它被强制进入兼容模式。所以必须使用 IE7 等效支持。 (没有 addeventlistener
选项)
当前策略: 我认为我可以开始工作,但感觉很花哨 - 将脚本添加到 <head>
。大致如下:
<SCRIPT>
function load(){
var frameset = window.frames;
if(frameset.length > 0){ // frames have loaded - commence replacement
}else{ // frames not loaded
setTimeout(load,1000); // wait 1 sec, try again
}
}
load();
</SCRIPT>
其他解决方案?
使用 onreadystatechange 事件
是的,有可靠的方法可以解决这个问题,而无需诉诸计时器或其他滴答声。当页面加载时,为每个帧 "onreadystatechange" 事件分配一个处理程序。并且您还必须调用它一次以确保它应用于已加载的帧。下面的代码在 IE 兼容模式 5、7、8、9、10 中进行了测试,并按预期工作(在 IE11 中失败)。也用慢速加载帧测试没有问题。
参考文献:
- Microsoft - onreadystatechange event
- Microsoft - Specifying legacy document modes
- w3.org - Frameset Document Type Definition
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Frameset//EN" "http://www.w3.org/TR/html4/frameset.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=7" />
<title>Demo</title>
<script type="text/javascript">
window.onload = function() {
for (var i = 0; i < window.frames.length; i++) {
(function(frame) {
// called whenever a frame is loaded or reloaded
frame.onreadystatechange = function() {
if (frame.readyState === 'complete') {
updateLinks(frame);
}
}
// call once to apply to already loaded frames
frame.onreadystatechange();
})(window.frames[i].frameElement);
}
}
// modify the links within the frame
function updateLinks(frame) {
var i, links, doc;
doc = frame.contentDocument || frame.contentWindow.document;
links = doc.getElementsByTagName('A');
for (i = 0; i < links.length; i++) {
// modify the links here
links[i].href += '?time=' + (new Date()).getTime();
}
console.info('modified ' + links.length + ' links in frame ' + frame.src);
}
</script>
</head>
<frameset cols="*,*">
<frame src="frameLeft.html">
<frame src="frameRight.html">
</frameset>
</html>
问题:较旧的知识库软件,无论出于何种原因,其链接已损坏。它是一系列嵌套的框架。有些指向正确的目标,有些则没有,而且很多都坏了。当它不能顺利工作时,它使使用知识库变得很麻烦
我要完成的工作:我想确定特定框架何时加载,然后解析框架的文档,用正确的 href 和目标替换锚标记。
资源和限制:我可以访问一些 .aspx 页面。我的目标现在包含一个加载知识库文档的框架集。然而,此框架的 src 似乎不是实际的 .aspx 页面(物理文件)——不确定它是如何生成的,也不确定文档是如何存储的。我看到列出了 src,但无法在我有权访问的网络服务器上找到它。
基本信息: 页面是使用 .aspx 加载的(我不太了解其中的部分内容,也无法访问更深入的内容)。 .aspx 页面有一个在加载页面时构建的框架集。
.aspx 文件中的示例 Framset 代码:
<FRAMESET id="FrameSetMainView" runat="server" border="0" framespacing="0" frameborder="0">
<!-- This frame set is defined and generated in the code -->
</FRAMESET>
我试过在 FRAMESET
标签中添加 onload(这会导致页面在尝试加载时出错)。框架集接管了正文,因此我无法将内联脚本添加到页面底部以使其在加载后成为 运行。
此外,b/c 产品的年龄 - 它被强制进入兼容模式。所以必须使用 IE7 等效支持。 (没有 addeventlistener
选项)
当前策略: 我认为我可以开始工作,但感觉很花哨 - 将脚本添加到 <head>
。大致如下:
<SCRIPT>
function load(){
var frameset = window.frames;
if(frameset.length > 0){ // frames have loaded - commence replacement
}else{ // frames not loaded
setTimeout(load,1000); // wait 1 sec, try again
}
}
load();
</SCRIPT>
其他解决方案?
使用 onreadystatechange 事件
是的,有可靠的方法可以解决这个问题,而无需诉诸计时器或其他滴答声。当页面加载时,为每个帧 "onreadystatechange" 事件分配一个处理程序。并且您还必须调用它一次以确保它应用于已加载的帧。下面的代码在 IE 兼容模式 5、7、8、9、10 中进行了测试,并按预期工作(在 IE11 中失败)。也用慢速加载帧测试没有问题。
参考文献:
- Microsoft - onreadystatechange event
- Microsoft - Specifying legacy document modes
- w3.org - Frameset Document Type Definition
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Frameset//EN" "http://www.w3.org/TR/html4/frameset.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta http-equiv="X-UA-Compatible" content="IE=7" />
<title>Demo</title>
<script type="text/javascript">
window.onload = function() {
for (var i = 0; i < window.frames.length; i++) {
(function(frame) {
// called whenever a frame is loaded or reloaded
frame.onreadystatechange = function() {
if (frame.readyState === 'complete') {
updateLinks(frame);
}
}
// call once to apply to already loaded frames
frame.onreadystatechange();
})(window.frames[i].frameElement);
}
}
// modify the links within the frame
function updateLinks(frame) {
var i, links, doc;
doc = frame.contentDocument || frame.contentWindow.document;
links = doc.getElementsByTagName('A');
for (i = 0; i < links.length; i++) {
// modify the links here
links[i].href += '?time=' + (new Date()).getTime();
}
console.info('modified ' + links.length + ' links in frame ' + frame.src);
}
</script>
</head>
<frameset cols="*,*">
<frame src="frameLeft.html">
<frame src="frameRight.html">
</frameset>
</html>