useRef দুটো অসম্পর্কিত সমস্যা সমাধান করে যা কাকতালীয়ভাবে একটি হুক শেয়ার করে: সরাসরি একটি প্রকৃত DOM এলিমেন্টে পৌঁছানো, আর render জুড়ে একটি মান ধরে রাখা যা বদলালে re-render ট্রিগার করা উচিত নয়।
কখনো কখনো আপনার আসল DOM এলিমেন্ট দরকার — একটি input-এ ফোকাস করা, একটি এলিমেন্টের আকার মাপা, একটি non-React লাইব্রেরি একত্রিত করা। একটি JSX এলিমেন্টে একটি ref যুক্ত করলে ঠিক এটাই পাওয়া যায়:
function SearchBox() {
const inputRef = useRef(null);
function focusInput() {
inputRef.current.focus(); // .current is the real <input> DOM node
}
return (
<div>
<input ref={inputRef} />
<button onClick={focusInput}>Focus the input</button>
</div>
);
}React সত্যিই <input> render না করা পর্যন্ত inputRef.current null, এরপর প্রকৃত DOM node হয়ে যায় — JavaScript DOM পাঠে document.querySelector থেকে আপনি যে একই HTMLInputElement পেতেন।
এই অংশটাই useState থেকে আসা মানুষদের হোঁচট খাওয়ায়: ref.current বদলালে re-render হয় না। এটা একটি সীমাবদ্ধতা নয়, একটি ফিচার — একটি ইন্টারভাল ID বা একটি আগের মান ট্র্যাক করার মতো কিছুর জন্য, প্রতিবার বদলালে একটি re-render নির্দিষ্টভাবে আপনি চান না:
function Stopwatch() {
const [running, setRunning] = useState(false);
const intervalRef = useRef(null);
function start() {
setRunning(true);
intervalRef.current = setInterval(() => {
console.log('tick');
}, 1000);
}
function stop() {
setRunning(false);
clearInterval(intervalRef.current); // reading it back later, no re-render involved either way
}
return <button onClick={running ? stop : start}>{running ? 'Stop' : 'Start'}</button>;
}| এটা বদলালে re-render ট্রিগার হয়? | কীসের জন্য ব্যবহার | |
|---|---|---|
| useState | হ্যাঁ | UI-তে দৃশ্যত প্রতিফলিত হওয়া উচিত এমন যেকোনো কিছু |
| useRef | না | DOM অ্যাক্সেস, বা এমন একটি মান যা কম্পোনেন্টের মনে রাখা দরকার কিন্তু সরাসরি দেখায় না |
render-এর সময় ref পড়বেন/লিখবেন না
Render-এর সময় (একটি ইভেন্ট হ্যান্ডলার বা একটি effect-এর ভেতরে নয়) ref.current পড়া বা লেখা একটি ভুল যা খেয়াল রাখতে হবে — এটা re-render ট্রিগার না করায়, UI চুপচাপ ref আসলে কী ধরে আছে তার সাথে সামঞ্জস্যহীন হয়ে যেতে পারে। ref পড়া/লেখা হ্যান্ডলার আর effect-এর ভেতরেই রাখুন।