我有一個簡單的懸停 CSS 影片,它可以在影像之間進行滑動過渡。
當用戶在 SECTION ONE 上懸停并且在影片結束之前在 SECTION 2 上懸停時,影片重新開始并進行滯后移動。
我的代碼:
var $circle = $('#circle');
function moveCircle(e) {
TweenLite.to($circle, 0.8, {
css: {
left: e.pageX,
top: e.pageY
}
});
}
$(window).on('mousemove', moveCircle);
@import "compass/css3";
@keyframes in {
from {
transform: translateY(-100%);
}
to {
transform: translateY(0);
}
}
@keyframes out {
from {
transform: translateY(0);
}
to {
transform: translateY(100%);
}
}
html {
background: #0E3741;
}
#circle {
position: absolute;
pointer-events : none;
width: 400px;
height: 200px;
top: 50%;
left: 50%;
margin: -50px 0 0 -50px;
}
#circle .circle-wrapper {
overflow: hidden;
width: 400px;
height: 200px;
position: relative;
}
#circle img {
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
width: 400px;
height: 200px;
object-fit: cover;
overflow: hidden;
}
#wrapper {
display: flex;
flex-direction: column;
}
.special-element {
width: 100%;
height: 100px;
display: flex;
justify-content: center;
align-items: center;
}
#one {
background: blue;
}
#two {
background: red;
}
#one:hover ~ #circle .circle-wrapper #imgOne {
animation: in 1s ease-in-out;
z-index: 2;
}
#one:hover ~ #circle .circle-wrapper #imgTwo {
animation: out 1s ease-in-out;
}
#two:hover ~ #circle .circle-wrapper #imgTwo {
animation: in 1s ease-in-out;
z-index: 2;
}
#two:hover ~ #circle .circle-wrapper #imgOne {
animation: out 1s ease-in-out;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/1.11.4/TweenMax.min.js"></script>
<section id="wrapper">
<section class="special-element" id="one">
section one
</section>
<section class="special-element" id="two">
section two
</section>
<div id="circle">
<div class="circle-wrapper">
<img id="imgOne" src="https://upload.wikimedia.org/wikipedia/commons/3/3b/Coca-cat.jpg">
<img id="imgTwo" src="https://staticcdn.sk/images/photoarchive/sized/700/2020/07/29/ohrozeny-vtak-krakla-belasa.jpg">
</div>
</div>
</section>
有什么解決方案可以防止這個滯后問題嗎?
也許有什么解決方案可以解決我的問題并使這個影片流暢?
我正在這個網站上尋找類似影片的東西。
uj5u.com熱心網友回復:
我認為這個問題是因為“動圈功能”。左右移動 dom 元素對性能不利。你應該用“變換”移動圓圈。變換與 GPU 加速一起運行,它的性能更好并使移動更流暢。
試試這個代碼。
function moveCircle(e) {
TweenLite.to($circle, 0.8, {
css: {
transform: `translate(${e.pageX}px, ${e.pageY}px)`
}
});
}
uj5u.com熱心網友回復:
我今天一直在玩 gsap 庫。老實說,我從來沒有做過或喜歡它。嘗試使用您可能傳遞給 gsap 的 x 和 y 引數來執行此操作。它將處理轉換 - TimeLine 的東西也很方便。
結果不是很好,影片看起來也可以做得更好,但也許它仍然可以幫助你。您也可以改進一些邏輯和影片。至少它運行非常穩定 - 性能明智。
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/[email protected]/reset.min.css" />
<script type="application/javascript" defer src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.9.1/gsap.min.js"></script>
<script type="application/javascript" defer src="https://cdnjs.cloudflare.com/ajax/libs/gsap/latest/plugins/CSSPlugin.min.js"></script>
<style type="text/css">
.section {
display: block;
width: 100%;
height: 200px;
border-bottom: 1px solid red;
}
.overlay {
position: absolute;
top: 0;
left: 0;
display: none;
border: none; // 1px dashed black;
background: transparent; // lavender;
overflow: hidden;
}
.stack {
position: relative;
left: 0;
right: 0;
top: 0;
bottom: 0;
min-width: 300px;
min-height: 300px;
width: 480px;
height: 320px;
z-index: 0;
}
.anim-img {
position: absolute;
top: 0;
left: 0;
width: auto;
height: auto;
max-width: 100%;
object-fit: contain;
z-index: 1;
}
</style>
</head>
<body>
<main class="main">
<section class="section section-1">section 1</section>
<section class="section section-2">section 2</section>
<div class="overlay">
<div class="stack">
<img id="img-1" class="anim-img" src="https://upload.wikimedia.org/wikipedia/commons/3/3b/Coca-cat.jpg">
<img id="img-2" class="anim-img" src="https://staticcdn.sk/images/photoarchive/sized/700/2020/07/29/ohrozeny-vtak-krakla-belasa.jpg">
</div>
</div>
</main>
<script type="application/javascript">
window.onload = () => {
const overlay = document.querySelector(".overlay");
const img1 = document.getElementById("img-1");
const img2 = document.getElementById("img-2");
const s1 = document.querySelector(".section-1");
const s2 = document.querySelector(".section-2");
const main = document.querySelector(".main");
let anim;
let isS1active = false;
let isS2active = false;
let showEl;
let hideEl;
let leaveTimeout;
function reverseFadeInOut(showEl, hideEl) {
console.log("create reverse timeline anim -> ", {
showEl,
hideEl
});
const tl = gsap.timeline({
paused: true
});
tl
.to(showEl, {
zIndex: 1
}, 0)
.to(hideEl, {
zIndex: 10
}, 0)
.to(hideEl, {
y: "-100%",
duration: 0.375
}, 0)
.to(hideEl, {
display: "none"
}, 0.375)
.to(hideEl, {
zIndex: 1
}, 0.375)
.to(showEl, {
display: "block",
zIndex: 10
}, 0.375)
.fromTo(showEl, {
y: "-100%"
}, {
y: 0,
duration: .375
}, 0.375)
.to(hideEl, {
display: "none"
});
return tl;
}
function fadeInOut(showEl, hideEl) {
console.log("create timeline anim -> ", {
showEl,
hideEl
});
const tl = gsap.timeline({
paused: true
});
tl
.to(hideEl, {
zIndex: 1
}, 0)
.to(showEl, {
display: "block",
zIndex: 10
}, 0)
.fromTo(showEl, {
y: "-100%"
}, {
y: 0,
duration: .75
}, 0)
.fromTo(hideEl, {
y: 0
}, {
y: "-100%",
duration: .75
}, 0)
.to(hideEl, {
display: "none"
}, 0.75);
return tl;
}
function animateImage() {
if (isS1active || isS2active) {
if (isS1active) {
showEl = img1;
hideEl = img2;
} else if (isS2active) {
showEl = img2;
hideEl = img1;
}
if (!anim) {
console.log("create new animation");
anim = fadeInOut(showEl, hideEl);
anim.play();
} else {
console.log("anim active:", anim.isActive());
if (anim.isActive()) {
console.log("reverse");
anim.kill();
anim = reverseFadeInOut(showEl, hideEl);
anim.play();
} else {
anim = fadeInOut(showEl, hideEl);
anim.play();
}
}
}
}
function moveOverlay(e) {
e.preventDefault();
e.stopPropagation();
gsap.set(overlay, {
x: e.pageX 15,
y: e.pageY 15,
display: isS1active || isS2active ? "block" : "none"
});
}
function mouseOver(e, el, isEntering) {
e.preventDefault();
e.stopPropagation();
el.classList.toggle("active");
isS1active = s1.classList.contains("active");
isS2active = s2.classList.contains("active");
if (isEntering) {
clearTimeout(leaveTimeout);
animateImage();
} else {
leaveTimeout = setTimeout(() => {
if (anim) {
console.log("kill anim");
anim.kill();
anim = null;
}
gsap.timeline({
onComplete: () => {
console.log("clear props");
gsap.set(".anim-img", {
clearProps: true
});
}
});
}, 500);
}
}
gsap.set(overlay, {
x: "0",
y: "0"
});
gsap.set(img1, {
x: "0",
y: "-100%"
});
gsap.set(img2, {
x: "0",
y: "-100%"
});
window.addEventListener("mousemove", moveOverlay);
s1.addEventListener("mouseenter", (e) => {
mouseOver(e, s1, true);
});
s1.addEventListener("mouseleave", (e) => {
mouseOver(e, s1, false);
});
s2.addEventListener("mouseenter", (e) => {
mouseOver(e, s2, true);
});
s2.addEventListener("mouseleave", (e) => {
mouseOver(e, s2, false);
});
}
</script>
</body>
</html>
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/396425.html
標籤:javascript html css
