2012-04-20 106 views
0

我對Javascript一般來說比較陌生,我拼湊了一些來自本網站大部分內容的小腳本,試圖獲得一個小的iframe通過一系列的鏈接循環播放,它的表現非常出色。不過,我也希望它在用戶點擊iframe或其任何內容時停止騎車。Javascript - JQuery - clearInterval/setInterval - iframe循環不會停止點擊

這是我到目前爲止的代碼。 HTML頁面上只有一個iframe。

<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.min.js"></script> 
<script type="text/javascript" charset="utf-8"> 
<!-- 
var sites = [ 
    "side/html5.html", 
    "side/silverlight.html", 
    "side/wordpress.html", 
    "side/mysql.html", 
    "side/php.html", 
    "side/css3.html" 
]; 
var currentSite = sites.length; 
var timerId; 
var iframeDoc = $("iframe").contents().get(0); 

$(document).ready(function() 
{ 
    var $iframe = $("iframe").attr("src","side/html5.html"); 

    timerId = setInterval(function() 
    { 
    (currentSite == 0) ? currentSite = sites.length - 1 : currentSite = currentSite -1; 
    $iframe.attr("src",sites[currentSite]); 
    }, 4000); 

    $(iframeDoc).bind('click', function() 
    { 
    clearInterval(timerId); 
    }); 

}); 
//--> 
</script> 
</head> 

<body> 

<sidebar> 
<iframe name="sideframe" src="side/html5.html"></iframe> 
</sidebar> ..etc.. 

請幫幫忙,我想學習JavaScript一樣快,我可以,但就我所看到的,它應該工作,但它確實沒有。

感謝您給我提供的任何幫助,非常感謝。


編輯:

好吧,我已經有了一個新的腳本現在,大多是基於關閉Elias的工作,但它也不管用。我已經將它固定在Firebug中,它的意思是說timerCallback.currentSite的值是正確更新的,儘管我找不到$ iframe的src值來明確地檢查它。據我所知,它正在更新變量,它只是不正確地更新iframe。我是否在此代碼中正確調用/設置iframe?此外,鏈接在jquery庫足夠我的目的?我有點失去了所有的這些庫鏈接到的......

<script type="text/javascript" src="http://code.jquery.com/jquery.js"></script> 
<script type="text/javascript" charset="utf-8"> 

<!-- 

var sites = 
[ 
    "side/html5.html", 
    "side/silverlight.html", 
    "side/wordpress.html", 
    "side/mysql.html", 
    "side/php.html", 
    "side/css3.html" 
]; 

var $iframe = $("iframe").attr("src","side/html5.html"); 

function timerCallback() 
{ 
    timerCallback.currentSite = (timerCallback.currentSite ? timerCallback.currentSite : sites.length) -1; 
    $iframe.attr("src",sites[timerCallback.currentSite]); 

    $($('iframe').contents().get('body')).ready(function() 
    { 
     $(this).unbind('click').bind('click',function() 
     { 
      var theWindow = (window.location !== window.parent.location ? window.parent : window); 
      theWindow.clearInterval(theWindow.timerId); 
     }); 
    }); 

} 

var timerId = setInterval(timerCallback, 4000); 

//--> 

</script> 
+0

當用戶將鼠標懸停在iframe上時,如何暫停它? – 2012-04-20 11:17:41

+0

'$('iframe')'位不起作用,它將返回一個1(或更多,取決於頁面上iframe的數量)的數組。對不起,但它是僞代碼。嘗試使用'$('iframe')[0]'或給iFrame一個id,並使用id選擇器'$('#iFrameId')' – 2012-04-20 13:54:49

+0

我試過了你的建議和'$('#sideframe') '並且'$('iframe')[0]是未定義的',因爲錯誤(對其他人也是如此)。完整的:'var $ iframe = $('iframe')[0] .attr(「src」,「side/html5.html」);' - 我會把這個在線並讓你看到它的行動。編輯:見http://www.gandcdesign.co.uk/ – 2012-04-20 14:36:08

回答

1

我覺得你的代碼是不工作,因爲這

var iframeDoc = $("iframe").contents().get(0); 

這可以得到的iFrame因爲頭您將iframeDoc值保存到iframe的第一個孩子,即head標記,實際上,如果您的窗口中有多個iframe,則iframeDoc將爲undefined,因爲$("iframe")會獲取文檔的所有iframe。

BTW your currentSite value condition is wrong, you asign the same value for both conditions

現在我給你舉個例子:

<iframe id="myFrame" src="http://www.google.com/"></iframe> 

和腳本:

<script type="text/javascript" src="http://code.jquery.com/jquery.js"></script> 
<script type="text/javascript"> 

var sites = [ 
"site1", 
"site2" 
]; 

var myFrame = document.getElementsByTagName('iframe')[0]; 
var currentSite = myFrame.getAttribute('src'); 
var timerId; 

var myFrameDoc = window.frames[0].document; 

$(document).ready(function() 
{ 
    myFrame.setAttribute('src', 'side/html5.html'); 

    timerId = setInterval(function() 
    { 
     //WRONGG 
     (currentSite == 0) ? currentSite = sites.length - 1 : currentSite = currentSite -1; 
     myFrame.setAttribute('src', sites[currentSite]); 
     $(myFrame).off("click").on("click", clearInterval(timerId)); 
    }, 4000); 

    //Won't work because you are trying to get events from an inside of a iframe 
    //$(myFrameDoc).on("click", clearInterval(timerId)); 
    //This may work 
    $(myFrameDoc).off("click").on("click", clearInterval(timerId)); 
}); 

</script> 

當您嘗試追蹤你必須要小心,因爲一個iframe的事件一個iframe包含一個完全不同的JavaScript purprouses文檔,所以基本上你必須進入新文檔,解開你需要使用的事件,並將它們綁定正如@Elias指出的那樣。但要注意,你不斷地改變你的iframe的src,所以如果yu真的需要這樣做,你將不得不分開代碼去解綁並重新綁定你的clearInterval,因此,$.on()可能適合你。

編輯:調用到iframe中應該以這種方式工作IF iframe的SRC是同一個域裏,用相同的端口和相同的協議:

var myFrameDoc = window.frames[0].document; 

我添加了一個新變量因爲我們想要將點擊事件綁定和解除綁定到iframe的文檔,而不是iframe,我們使用該窗口。幀集合屬性,但現代瀏覽器會拋出異常並拒絕訪問,如果您嘗試訪問一個幀,並且您使用相同的端口和相同的協議不在同一個域中...

另外使用$.on()$.off()而不是$.bind$.unbind()是因爲第一個是新的,儘管我們沒有在這裏使用它們,但它們能夠不斷地監視新元素的DOM,如果這段代碼仍然不起作用,這可能對這種情況有用。如果是這樣的話,你仍然可以改變這一點:

var myFrameDoc = window.frames[0].window; 

這:

$(myFrameDoc).off("click", "document").on("click", "document", clearInterval(timerId)); 

這將事件處理程序重新綁定到新文檔增加。未經測試,但可以工作。

+0

我已經嘗試了你的解決方案,大衛和埃利亞斯,但不幸的是,它似乎甚至沒有循環瀏覽任何頁面更多,使測試停止功能有點困難。我可以看看你是從哪裏來的,因爲iframe的難度叫它是父窗口。我試圖用Firebug來調試它,但它拒絕打斷點,它幾乎就像它沒有運行... – 2012-04-20 12:51:10

+0

編輯:在大衛的代碼,它的說myFrame是未定義的,即使它通過後滾動getElementsByTagName方法。 – 2012-04-20 12:57:38

+0

@SarahCarter:你有權訪問該網站在iFrame中的加載情況,還是他們是外部的?否則,最快的解決辦法是編寫一個js文件,並將其包含在所有這些站點中......或者使用ajax來獲取內容服務器端,並在其中添加js – 2012-04-20 13:38:10

1

如果我是你,我會安全地玩。既然你說你對JS相當陌生,它可能證明非常有用。現在

function timerCallback() 
{ 
    timerCallback.currentSite = (timerCallback.currentSite ? timerCallback.currentSite : sites.length) -1; 
    $iframe.attr("src",sites[timerCallback.currentSite]); 
} 
var timerId = setInterval(timerCallback, 4000); 
$($('iframe').contents().get('body')).unbind('click').bind('click', function() 
{ 
    var theWindow = (window.location !== window.parent.location ? window.parent : window); 
    theWindow.clearInterval(theWindow.timerId); 
}); 

我必須承認,這個代碼是測試,在所有。雖然我認爲它提供了一些事情讓你的方式:

1)的時間間隔是使用一個回調函數來設置,因爲它是噸的原因

1B)在回調只有更好,我利用了這個事實,即函數是對象,並創建了一個靜態變量var,設置爲您的站點數組的長度(當undefined或0時),在兩種情況下1都被減1

2)jQuery的,get()方法返回一個DOM元素,而不是jquery對象,這就是爲什麼我將它包裝在$(),一個新的jQ obj中,爲您提供了所需的方法。

3)因爲你操縱iFrame中的DOM,這是最好的解除綁定要綁定

4)iFrame中的事件,您不必父窗口,直接進入您的間隔是。

你可能想如何處理內部框架,因爲他們可以是一個有點faff的不時

編輯讀了起來: 大衛·迭斯是正確的,最簡單的方法解決這個是結合了結合在超時功能:

function timerCallback() 
{ 
    timerCallback.currentSide = ...//uncanged 
    //add this: 
    $($('iframe').contents().get('body')).ready(function() 
    { 
     $(this).unbind('click').bind('click',function() 
     { 
      //this needn't change 
     }); 
    }); 
} 

從理論上講,這應該click事件綁定到身體已經加載

Ë後dit2

我一直在搞亂一點,你可以保持你的代碼,是的。只需添加一個功能:

function unsetInterval() 
{ 
    window.clearInterval(window.timerId); 
} 

,並添加到您的setInterval函數:

$('#idOfIframe').load(function() 
{ 
    var parentWindow = window.parent; 
    $('body').on('click',function() 
    { 
     parentWindow.clearInterval(); 
    }); 
}); 

這將得到儘快的iFrame內容加載觸發,並綁定click事件取消設置定時器,就像你想

+1

'$('iframe')。contents()。get('body'))。unbind('click')。bind '是一個非常棒的技巧,但要小心,這不會工作,因爲他的代碼不斷地改變iframe中的DOM,所以基本上他不能跟蹤iframe中的事件!如果功能是分開的,可以使用'。.on()'而不是'$ .bind()' – 2012-04-20 11:52:15

+0

@DavidDiez:增加了一個理論上的解決方法,沒有經過測試,但基本的想法是綁定'ready'事件,這應該和'on'有相同的效果 – 2012-04-20 12:39:49