😀😊 Đây là giải thích đầy đủ, ngắn gọn và thực tế về các option quan trọng của ScrollTrigger (ok)
✅ 1. start
start
🔹 Ý nghĩa: Xác định khi nào trigger bắt đầu kích hoạt
🔹 Cú pháp: "triggerPosition viewportPosition"
"top top"
Khi top của trigger chạm top viewport
"bottom bottom"
Khi bottom của trigger chạm bottom viewport
"top center"
Khi top trigger chạm giữa viewport
"top+=100 top"
Khi top trigger + 100px chạm top viewport
"center center+=50"
Khi center trigger chạm center viewport + 50px
✅ Thường dùng: "top top"
hoặc "top center"
✅ 2. end
end
🔹 Ý nghĩa: Xác định khi nào trigger kết thúc
🔹 Cú pháp: giống start
"bottom top"
Khi bottom trigger chạm top viewport
"+=500"
Kết thúc sau khi scroll thêm 500px
"bottom+=200 top"
Bottom trigger + 200px chạm top viewport
✅ Thường dùng: "+=scrollDistance"
khi scroll horizontal gallery
✅ 3. pin
pin
🔹 Ý nghĩa: Pin (cố định) phần tử được trigger khi scroll
🔹 Giá trị: true
(pin trigger element) hoặc selector khác
pin: true
Pin chính trigger element
pin: ".my-element"
Pin element khác
✅ Ứng dụng: Pin section gallery, hero content, sticky sidebar
✅ 4. pinSpacing
pinSpacing
🔹 Ý nghĩa: Quyết định ScrollTrigger có tạo spacing phía dưới pinned element hay không
true
(default)
Tạo spacing bằng height pinned element, scroll tới content dưới bình thường
false
Không tạo spacing, pinned element sẽ che section dưới
✅ Thường giữ mặc định true
, chỉ dùng false
khi overlay fixed.
✅ 5. anticipatePin
anticipatePin
🔹 Ý nghĩa: Làm mượt hiện tượng jump khi pin bắt đầu
🔹 Giá trị: Số nguyên (thường 1
hoặc 2
)
🔹 Hoạt động: ScrollTrigger dự đoán pin trước khi thực hiện, giúp layout không giật khi pin activate.
✅ Thường dùng: anticipatePin: 1
✅ 6. scrub
scrub
🔹 Ý nghĩa: Gắn animation với scroll position 🔹 Giá trị:
true
Animation chạy bám sát scroll position
number
Delay scrub (mượt hơn, không quá gắt)
✅ Ứng dụng: Horizontal gallery scroll, text reveal bám scroll
🚀 7. Tóm tắt nhanh cấu hình chuẩn (example)
jsCopyEditScrollTrigger.create({
trigger: ".section",
start: "top top",
end: "+=1000",
pin: true,
pinSpacing: true,
anticipatePin: 1,
scrub: true,
markers: true
});
start
Bắt đầu khi top section chạm top viewport
end
Kết thúc sau 1000px scroll
pin
Pin section
pinSpacing
Tạo spacing phía dưới
anticipatePin
Mượt khi bắt đầu pin
scrub
Animation gắn chặt với scroll position
Dưới đây là 📚 Full Advanced GSAP ScrollTrigger Cheat Sheet + Gallery Horizontal Scroll + Hero Scroll Effect được hệ thống hóa tối ưu cho dự án của bạn, phục vụ học tập, triển khai production, và lưu làm notes GSAP nhanh.
✅ 1. Cấu hình cơ bản
trigger
Phần tử kích hoạt scroll
.section
start
Thời điểm bắt đầu trigger
"top center"
, "bottom bottom"
, "+=100"
end
Thời điểm kết thúc trigger
"bottom top"
, "+=500"
pin
Giữ cố định phần tử khi scroll
true
, ".sidebar"
pinSpacing
Có tạo spacing dưới pin không
true
(default) / false
scrub
Gắn animation theo scroll position
true
/ 0.5
anticipatePin
Mượt khi pin bắt đầu
1
markers
Hiện markers debug
true
✅ 2. Timeline integration
gsap.timeline({
scrollTrigger: {
trigger: ".section",
start: "top top",
end: "+=500",
scrub: true,
pin: true,
markers: true
}
})
.to(".element", { opacity: 1, y: -50 })
.to(".other", { scale: 1.2 });
✅ 3. Utility
ScrollTrigger.refresh()
Refresh tất cả ScrollTriggers
ScrollTrigger.kill()
Kill ScrollTrigger
gsap.utils.toArray(".class")
Convert NodeList to array
ScrollTrigger.getAll()
Lấy tất cả ScrollTriggers hiện tại
🎨 II. Hero Scroll Effect Example
✅ Goal
Pin hero section
Animate title và subtitle theo scroll (fade out + move up)
🔧 Code
htmlCopyEdit<section class="hero">
<h1>Hero Title</h1>
<p>Subtitle description here</p>
</section>
<section class="content">Main Content</section>
cssCopyEdit.hero {
height: 100vh;
background: #333;
color: white;
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
}
.content {
height: 200vh;
background: #eee;
}
jsCopyEditgsap.registerPlugin(ScrollTrigger);
const tl = gsap.timeline({
scrollTrigger: {
trigger: ".hero",
start: "top top",
end: "+=500",
scrub: true,
pin: true,
markers: true
}
});
tl.to(".hero h1", {
y: -100,
opacity: 0
})
.to(".hero p", {
y: -50,
opacity: 0
}, "<");
🖼️ III. Gallery Horizontal Scroll Example
✅ Goal
Pin gallery section
Scroll các item ngang theo vertical scroll
🔧 Code
htmlCopyEdit<section class="gallery-section">
<div class="gallery-container">
<div class="gallery-item">Item 1</div>
<div class="gallery-item">Item 2</div>
<div class="gallery-item">Item 3</div>
<div class="gallery-item">Item 4</div>
</div>
</section>
<section class="after">Section After</section>
cssCopyEdit.gallery-section {
height: 100vh;
overflow: hidden;
background: #111;
color: white;
}
.gallery-container {
display: flex;
height: 100%;
}
.gallery-item {
min-width: 100vw;
height: 100%;
display: flex;
justify-content: center;
align-items: center;
font-size: 3rem;
}
.after {
height: 100vh;
background: #eee;
}
jsCopyEditconst container = document.querySelector(".gallery-container");
const scrollWidth = container.scrollWidth;
const viewportWidth = window.innerWidth;
const scrollDistance = scrollWidth - viewportWidth;
gsap.to(container, {
x: -scrollDistance,
ease: "none",
scrollTrigger: {
trigger: ".gallery-section",
start: "top top",
end: () => "+=" + scrollDistance,
pin: true,
scrub: true,
anticipatePin: 1,
markers: true
}
});

🔥 IV. Kỹ thuật nâng cao
✅ 1. ScrollSmoother integration
jsCopyEditconst smoother = ScrollSmoother.create({
wrapper: "#wrapper",
content: "#content",
smooth: 1.5,
effects: true
});
✅ 2. SplitText + ScrollTrigger
jsCopyEditconst split = new SplitText(".text", { type: "chars" });
gsap.from(split.chars, {
y: 100,
opacity: 0,
stagger: 0.05,
scrollTrigger: {
trigger: ".text",
start: "top 80%",
end: "bottom top",
scrub: true,
markers: true
}
});
✅ 3. Counter animation on scroll
jsCopyEditScrollTrigger.create({
trigger: ".counter",
start: "top bottom",
onEnter: () => {
gsap.to(counterObj, {
value: endValue,
duration: 2,
ease: "power1.out",
onUpdate: () => {
counterEl.innerText = Math.floor(counterObj.value);
}
});
}
});
🎯 V. Kết luận
✅ Đây là Full Advanced Cheat Sheet + Hero Effect + Gallery Horizontal Scroll giúp bạn:
Nắm chắc ScrollTrigger options
Áp dụng nhanh gallery landing page
Tạo hero scroll effect mượt
💡 Tip cuối cùng
🔹 Luôn kiểm tra marker để debug start/end chính xác
🔹 Luôn ScrollTrigger.refresh()
khi load dynamic content hoặc resize window
Nếu bạn cần, tôi có thể viết template landing page GSAP production-ready kết hợp toàn bộ các hiệu ứng này cho dự án frontend của bạn tuần này. Hãy cho tôi biết để tôi lên cấu trúc tối ưu.
🔍 Rất hay khi bạn hỏi về endTrigger
trong ScrollTrigger, đây là một option quan trọng nhưng ít người hiểu rõ.
endTrigger
trong ScrollTrigger, đây là một option quan trọng nhưng ít người hiểu rõ.✅ 1. endTrigger
là gì?
endTrigger
là gì?🔹 endTrigger
xác định phần tử dùng làm mốc tính toán end
thay vì mặc định là trigger element.
⚠️ 2. Mặc định behavior
Nếu bạn viết:
jsCopyEditScrollTrigger.create({
trigger: ".section",
start: "top top",
end: "bottom top",
...
});
✅ end
sẽ tính dựa trên trigger element (.section
), ví dụ:
Khi bottom của
.section
chạm top viewport → ScrollTrigger kết thúc.
🔧 3. Khi dùng endTrigger
endTrigger
Nếu bạn muốn end dựa vào phần tử khác, ví dụ .footer
:
jsCopyEditScrollTrigger.create({
trigger: ".section",
start: "top top",
endTrigger: ".footer",
end: "bottom top",
...
});
✅ Ý nghĩa:
start
: Khi top.section
chạm top viewport.end
: Khi bottom.footer
chạm top viewport.
🎯 4. Ứng dụng thực tế
🔹 Pin sidebar tới footer:
jsCopyEditScrollTrigger.create({
trigger: ".sidebar",
start: "top top",
endTrigger: ".footer",
end: "top bottom",
pin: true,
scrub: true
});
✅ Sidebar được pin từ đầu đến khi .footer
bắt đầu scroll lên.
🔧 5. Ví dụ minh họa khác
jsCopyEditScrollTrigger.create({
trigger: ".section",
start: "top center",
endTrigger: ".next-section",
end: "top center",
scrub: true
});
➡️ Animation scrub từ khi .section
top chạm center viewport đến khi .next-section
top chạm center viewport.
✅ 6. Tóm tắt
endTrigger
Phần tử dùng làm mốc tính end
Mặc định
endTrigger = trigger
💡 Tip: Rất hữu ích khi bạn cần pin đến một phần tử khác hoặc control animation dài nhiều section.
Nếu cần, tôi có thể viết full bài học ScrollTrigger pin sidebar with endTrigger + ScrollSmoother integration để bạn áp dụng cho dự án tuần này. Hãy cho tôi biết.

<!DOCTYPE html>
<html lang="en" >
<head>
<meta charset="UTF-8">
<title>CodePen - Hero & Column Pin</title>
<link rel='stylesheet' href='https://codepen.io/GreenSock/pen/xxmzBrw.css'>
<style>
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
.header {
position: fixed;
width: 100%;
height: 200px;
background-color: #a0a0a0;
z-index: 10;
}
.wrapper {
padding-top: 200px;
}
.hero {
width: 100%;
height: 40vh;
}
.row {
display: flex;
justify-content: flex-start;
width: 100%;
height: 100vh;
}
.right-row {
justify-content: flex-end;
}
.column {
width: 50%;
height: 100%;
}
.spacer {
width: 100%;
height: 100vh;
}
</style>
</head>
<body>
<!-- partial:index.partial.html -->
<div class="header"></div>
<div class="wrapper">
<div class="hero gradient-purple"></div>
<div class="row left-row">
<div class="column gradient-green">
<h1>Lorem ipsum dolor sit amet.</h1>
</div>
</div>
<div class="row right-row">
<div class="column gradient-blue">
<h1>Lorem ipsum dolor sit amet.</h1>
</div>
</div>
</div>
<div class="spacer gradient-red"></div>
<!-- partial -->
<script src='https://unpkg.com/gsap@3/dist/gsap.min.js'></script>
<script src='https://unpkg.com/gsap@3/dist/ScrollTrigger.min.js'></script>
<script>
gsap.registerPlugin(ScrollTrigger);
// pin the image
const heroSt = ScrollTrigger.create({
trigger: ".hero",
start: "bottom 250",
end: "top bottom",
endTrigger: ".spacer",
pin: true,
pinSpacing: false,
// markers: true,
id: "hero"
});
// Pin left column
ScrollTrigger.create({
trigger: ".left-row",
start: () => heroSt.start,
end: () => heroSt.end,
pin: true,
pinSpacing: false,
// markers: { indent: 150 },
id: "lft"
});
// Pin right column
ScrollTrigger.create({
trigger: ".right-row",
start: "top 250",
end: heroSt.end,
pin: true,
pinSpacing: false,
// markers: { indent: 300 },
id: "rgt"
});
</script>
</body>
</html>
Last updated
Was this helpful?