如果否则在某些条件下停止工作



我想出了这个简单的代码,但由于某种原因,它并不总是完全按照我想要的方式工作。

这是我所拥有的。有些磁贴在悬停时会翻转。有两种可能的情况和两种反应。

如果我将鼠标悬停在瓷砖上,该瓷砖应该翻转 180° 并保持在这个位置。如果鼠标离开的时间超过 1 秒,就会发生这种情况。取消悬停后,磁贴应翻转回其原始状态。

如果鼠标悬停在磁贴上并立即取消悬停,则磁贴应该在恢复到其原始状态之前进行完整的 180° 翻转。当鼠标在 1 秒的时间范围内离开时,就会发生这种情况。在这种情况下,JS 脚本会等待 CSS 过渡结束,然后再将磁贴翻转回来。

现在,在第二个场景发生之前,这工作正常。然后,由于某种原因,尽管鼠标没有离开磁贴,但磁贴在完全过渡后仍会恢复到其原始状态。为什么?关于如何克服这个问题的任何想法?

谢谢。

$(function() {
var timeoutId;
$(".tile").mouseenter(function() {
$(this).addClass("flip");
if (!timeoutId) {
timeoutId = window.setTimeout(function() {
timeoutId = null;}, 1000);
}
});
$(".tile").mouseleave(function() {
if (timeoutId) {
$(this).on('transitionend webkitTransitionEnd oTransitionEnd', function () {
$(this).removeClass("flip");
window.clearTimeout(timeoutId);
timeoutId = null;
});
}
else {
$(this).removeClass("flip");
}
});
})
body {
text-align: center;
background-color: #FFFFFF;
color: #454545;
}
.flex-container {
padding: 0;
margin: 0;
display: -webkit-box;
display: -moz-box;
display: -ms-flexbox;
display: -webkit-flex;
display: flex;
-webkit-flex-flow: row;
justify-content: space-around;
}
.tile {
background: #454545;
margin: 0px;
font-weight: bold;
flex: 1 0 auto;
height: auto;
border: 1px solid #454545;
border-radius: 10%;
}
.tile:before {
content: '';
float: left;
padding-top: 100%;
}
.tile-inner {
position: relative;
width: 100%;
height: 100%;
border-radius: 10%;
transform-style: preserve-3d;
transition: transform 4s;
}
.tile.flip .tile-inner {
transform: rotate3d(-1, 1, 0, 180deg);
transition: transform 1s;
}
.tile-front, .tile-off, .tile-semi, .tile-rsemi, .tile-on {
position: absolute;
width: 100%;
height: 100%;
backface-visibility: hidden;
border-radius: 10%;
}
.tile-front {
background-color: #1c1c1c;
background-size: 100%;
}
.tile-off {
background-color: #252525;
transform: rotate3d(-1, 1, 0, 180deg);
}
.tile-semi {
background: linear-gradient(to right bottom, #252525 50%, #dedede 50%);
transform: rotate3d(-1, 1, 0, 180deg);
}
.tile-rsemi {
background: linear-gradient(to right bottom, #dedede 50%, #252525 50%);
transform: rotate3d(-1, 1, 0, 180deg);
}
.tile-on {
background-color: #dedede;
transform: rotate3d(-1, 1, 0, 180deg);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
<body>
<div class="flex-container">
<div class="tile">
<div class="tile-inner">
<div class="tile-front"></div>
<div class="tile-semi"></div>
</div>
</div>
<div class="tile">
<div class="tile-inner">
<div class="tile-front"></div>
<div class="tile-on"></div>
</div>
</div>
<div class="tile">
<div class="tile-inner">
<div class="tile-front"></div>
<div class="tile-rsemi"></div>
</div>
</div>
</div>
</body>

您正在共享一个变量并将其用于所有其他磁贴。因此,当您将鼠标悬停在磁贴 1 上时,磁贴 1 的超时也将与磁贴 2 一起出现。您应该为每个单独设置超时。数据的基本概念。

$(function() {
$(".tile").mouseenter(function() {
var elem = $(this);
elem.addClass("flip");
if (!elem.data('timeoutId')) {
var tid = window.setTimeout(function() {
elem.removeData('timeoutId')
}, 1000);
elem.data('timeoutId', tid)
}
});
$(".tile").mouseleave(function() {
var elem = $(this);
var timeoutId = elem.data('timeoutId')
if (timeoutId) {
window.clearTimeout(timeoutId);
elem.removeData('timeoutId')
elem.off('transitionend webkitTransitionEnd oTransitionEnd')
elem.on('transitionend webkitTransitionEnd oTransitionEnd', function() {
elem.removeClass("flip");
});
} else {
$(this).removeClass("flip");
}
});
})
body {
text-align: center;
background-color: #FFFFFF;
color: #454545;
}
.flex-container {
padding: 0;
margin: 0;
display: -webkit-box;
display: -moz-box;
display: -ms-flexbox;
display: -webkit-flex;
display: flex;
-webkit-flex-flow: row;
justify-content: space-around;
}
.tile {
background: #454545;
margin: 0px;
font-weight: bold;
flex: 1 0 auto;
height: auto;
border: 1px solid #454545;
border-radius: 10%;
}
.tile:before {
content: '';
float: left;
padding-top: 100%;
}
.tile-inner {
position: relative;
width: 100%;
height: 100%;
border-radius: 10%;
transform-style: preserve-3d;
transition: transform 4s;
}
.tile.flip .tile-inner {
transform: rotate3d(-1, 1, 0, 180deg);
transition: transform 1s;
}
.tile-front,
.tile-off,
.tile-semi,
.tile-rsemi,
.tile-on {
position: absolute;
width: 100%;
height: 100%;
backface-visibility: hidden;
border-radius: 10%;
}
.tile-front {
background-color: #1c1c1c;
background-size: 100%;
}
.tile-off {
background-color: #252525;
transform: rotate3d(-1, 1, 0, 180deg);
}
.tile-semi {
background: linear-gradient(to right bottom, #252525 50%, #dedede 50%);
transform: rotate3d(-1, 1, 0, 180deg);
}
.tile-rsemi {
background: linear-gradient(to right bottom, #dedede 50%, #252525 50%);
transform: rotate3d(-1, 1, 0, 180deg);
}
.tile-on {
background-color: #dedede;
transform: rotate3d(-1, 1, 0, 180deg);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>
<body>
<div class="flex-container">
<div class="tile">
<div class="tile-inner">
<div class="tile-front"></div>
<div class="tile-semi"></div>
</div>
</div>
<div class="tile">
<div class="tile-inner">
<div class="tile-front"></div>
<div class="tile-on"></div>
</div>
</div>
<div class="tile">
<div class="tile-inner">
<div class="tile-front"></div>
<div class="tile-rsemi"></div>
</div>
</div>
</div>
</body>

问题是当你运行:

if (timeoutId) {
$(this).on('transitionend webkitTransitionEnd oTransitionEnd', function () {
$(this).removeClass("flip");
window.clearTimeout(timeoutId);
timeoutId = null;
});
}

事件无限期地保留在元素中。因此,下次将鼠标悬停在元素上时,当它完成转换时,会再次触发此事件。

您可能想要的是仅在以下once运行事件:

if (timeoutId) {
$(this).once('transitionend webkitTransitionEnd oTransitionEnd', function () {
$(this).removeClass("flip");
window.clearTimeout(timeoutId);
timeoutId = null;
});
}

最新更新