我正在使用Backbone和require.js以及jQuery。
我要做的是简单地将事件绑定到应该显示(鼠标悬停)或隐藏(mouseout)视频的容器。事件发生但不幸的是很多次(我在.intro-content
内有几个孩子)。我尝试使用ev.stopPropagation()
(如代码中所示)和ev.stopImmediatePropagation
,但这并不能阻止冒泡。我做错了什么?
查看:
define([
'jquery',
'underscore',
'backbone',
'global'
], function($, _, Backbone, Global){
var VideoView = Backbone.View.extend({
el: $('#splitlayout'),
events: {
'mouseover .side-left .intro-content': 'checkVideoState',
'mouseout .side-left .intro-content': 'checkVideoState'
},
render: function(){
this.playVideo('video', '0GsrOOV0gQM');
this.delegateEvents();
},
initialize: function() {
_.bindAll(this);
this.render();
},
checkVideoState: function(ev) {
ev.stopPropagation();
if(!$('#video').hasClass('active') && ev.type == 'mouseover') {
this.showVideo();
} else if($('#video').hasClass('active') && ev.type == 'mouseout') {
this.hideVideo();
}
},
showVideo: function() {
console.log('test');
$('#video').addClass('active');
player.playVideo();
},
hideVideo: function() {
console.log('test');
$('#video').removeClass('active');
player.pauseVideo();
},
playVideo: function(container, videoId) {
var self = this;
if (typeof(YT) == 'undefined' || typeof(YT.Player) == 'undefined') {
window.onYouTubeIframeAPIReady = function() {
self.loadPlayer(container, videoId);
};
$.getScript('//www.youtube.com/iframe_api');
} else {
self.loadPlayer(container, videoId);
}
},
loadPlayer: function(container, videoId) {
player = new YT.Player(container, {
videoId: videoId,
playerVars: {
controls: 0,
loop: 1,
modestbranding: 0,
rel: 0,
showinfo: 0
},
events: {
'onReady': this.onPlayerReady
}
});
},
onPlayerReady: function() {
player.setPlaybackQuality('hd720');
player.seekTo(8,false);
player.pauseVideo();
}
});
return VideoView;
});
答案 0 :(得分:1)
您多次收到该活动,因为您的容器中有多个孩子。每次鼠标移动到容器中的新子项时,都会触发新事件。基本上,您想要使用mouseenter
代替。请查看JQuery documentation底部的示例。
此事件类型可能会因事件冒泡而导致许多令人头疼的问题。对于 例如,当鼠标指针在此内部元素上移动时 例如,鼠标悬停事件将被发送到该事件,然后涓涓细流 外。这可以在inopportune触发我们绑定的mouseover处理程序 倍。有关有用的替代方法,请参阅.mouseenter()的讨论。
答案 1 :(得分:1)
您可能已经初始化了两次视图。
以下是双事件http://jsfiddle.net/rph4R的示例,您可以通过删除最后一行new VideoView();
来解决这个问题。
要检查这一点,您可以添加
console.log('initialize');
到VideoView.initialize()
方法并检查控制台或使用debugger
或console.trace()
查看完整的调用堆栈。
您还可以检查在您的文件中搜索此代码并计算
new VideoView();