Transisi Shader
Dalam pelajaran ini kita akan belajar bagaimana membuat transisi menggunakan shader.
Efek pertama yang akan kita buat adalah efek transisi layar:
Kita memiliki kontrol penuh atas efek transisi, kita bisa mengubah durasi, fungsi easing, dan shader itu sendiri.
Efek kedua yang akan kita buat adalah efek transisi model:
Saat memudar keluar, model akan terlarut dan warna menjadi putih, kebalikannya terjadi saat memudar masuk.
Paket Awal
Berikut adalah semua model 3D yang akan kita gunakan dalam pelajaran ini oleh Ergoni dan dilisensikan di bawah Creative Commons Attribution:
Paket awal menggunakan paket-paket berikut:
- Tailwind CSS untuk styling
- Framer Motion untuk animasi
- Jotai library untuk mengelola state yang dibagikan antar komponen
Dua font yang digunakan adalah Kanit dan Rubik Doodle Shadow, keduanya dari Google Fonts.
Jangan ragu untuk menyesuaikan komponen apapun sesuai dengan preferensi Anda.
Anda dapat menyesuaikan warna dengan bermain menggunakan kontrol Leva di sudut kanan atas. Setelah Anda menemukan warna yang Anda suka, tambahkan prop hidden ke komponen Leva di App.jsx:
// ... function App() { // ... return ( <> <Leva hidden /> {/* ... */} </> ); } // ...
Transisi Layar
Mari kita mulai dengan membuat efek transisi layar kita. Kita akan membuat sebuah komponen bernama ScreenTransition yang akan menangani efek transisi.
Mari buat file baru bernama ScreenTransition.jsx di dalam folder components:
export const ScreenTransition = ({ transition, color }) => { return ( <mesh> <planeGeometry args={[2, 2]} /> <meshBasicMaterial color={color} /> </mesh> ); };
Dalam komponen ini, kita membuat sebuah plane dengan warna yang akan menutupi seluruh layar. Kita akan menggunakan plane ini untuk melakukan transisi antar layar.
Komponen kita menerima dua props:
- transition: sebuah boolean untuk mengetahui apakah komponen harus menampilkan efek transisi
- color: warna utama dari efek transisi
Mari tambahkan komponen ScreenTransition ke App.jsx:
// ... import { ScreenTransition } from "./components/ScreenTransition"; function App() { // ... return ( <> {/* ... */} <Canvas camera={{ position: [0, 1.8, 5], fov: 42 }}> <color attach="background" args={[backgroundColor]} /> <fog attach="fog" args={[backgroundColor, 5, 12]} /> <ScreenTransition transition color="#a5b4fc" /> <Suspense> <Experience /> </Suspense> </Canvas> </> ); } export default App;
Saat ini kita memaksa efek transisi ditampilkan dengan memberikan true pada prop transition. Kita akan menambahkan logika untuk mengendalikan efek transisi nanti.
Sesuaikan warna sesuai keinginan Anda. Jika Anda mengubahnya, pastikan untuk memperbarui warna di file index.css untuk menghindari kilatan warna saat situs web dimuat:
// ... html { background-color: #a5b4fc; }
Plane berada di tengah adegan.
Bidang layar penuh
Kami ingin bidang kami menutupi seluruh layar. Kami bisa menggunakan dimensi viewport dan membuatnya menghadap kamera, tetapi kami juga ingin bidang tersebut berada di atas segala sesuatu.
Untuk mencapai ini, Drei menyediakan komponen Hud yang akan merender elemen anak-anaknya di atas segala sesuatu. Kita dapat menambahkan kamera tetap pada komponen Hud untuk memastikan itu sejajar sempurna dengan bidang kita:
import { Hud, OrthographicCamera } from "@react-three/drei"; export const ScreenTransition = ({ transition, color }) => { return ( <Hud> <OrthographicCamera makeDefault top={1} right={1} bottom={-1} left={-1} near={0} far={1} /> <mesh> <planeGeometry args={[2, 2]} /> <meshBasicMaterial color={color} /> </mesh> </Hud> ); };
Kami menggunakan OrthographicCamera untuk dengan mudah menutupi seluruh layar apa pun jarak antara kamera dan bidang.
Bidang sekarang menutupi seluruh layar.
Logika Transisi
Satu hal terakhir sebelum membuat shader kustom kita, mari kita definisikan state transition di UI.jsx
:
// ... import { atom } from "jotai"; export const transitionAtom = atom(true); // ...
Kita menetapkan nilai awal menjadi true untuk memulai dengan efek fade-out setelah situs web dimuat.
Kita akan menggunakan state ini untuk mengontrol efek transisi.
Masih di UI.jsx
, kita akan mendefinisikan dua konstanta untuk mengontrol durasi dan penundaan dari efek transisi:
// ... export const TRANSITION_DELAY = 0.8; export const TRANSITION_DURATION = 3.2; // ...
Sekarang mari kita ganti pemanggilan fungsi setScreen
dengan yang baru yang akan menangani efek transisi:
// ... import { useAtom } from "jotai"; import { useRef } from "react"; // ... export const UI = () => { // ... const [transition, setTransition] = useAtom(transitionAtom); const timeout = useRef(); // ... const transitionToScreen = (newScreen) => { setTransition(true); clearTimeout(timeout.current); timeout.current = setTimeout(() => { setScreen(newScreen); setTransition(false); }, TRANSITION_DURATION * 1000 + TRANSITION_DELAY * 1000); }; // ... };
Alih-alih langsung menetapkan layar baru, kita menetapkan state transition ke true dan menggunakan setTimeout untuk menetapkan layar baru setelah efek transisi selesai (durasi dari efek transisi ditambah penundaan).
Sekarang fungsi kita sudah siap, carilah pemanggilan setScreen
dalam komponen UI
dan gantilah dengan transitionToScreen
.
Dari home ke menu:
<motion.button onClick={() => transitionToScreen("menu")} // ... >
Dan dari menu ke home:
<motion.button onClick={() => transitionToScreen("home")} // ... >
React Three Fiber: The Ultimate Guide to 3D Web Development
✨ You have reached the end of the preview ✨
Go to the next level with Three.js and React Three Fiber!
Get full access to this lesson and the complete course when you enroll:
- 🔓 Full lesson videos with no limits
- 💻 Access to the final source code
- 🎓 Course progress tracking & completion
- 💬 Invite to our private Discord community
One-time payment. Lifetime updates included.