Bài toán về tính toán setState() số lượng touch như Hamster Kombat?
Dạ em chào mọi người hiện em đang dùng NEXTJS tự làm một dự án nhỏ tương tự như Hamster Kombat.
Ban đầu thì nghĩ khá đơn giản khi người dùng thực hiện click thì số lượng điểm sẽ tăng lên, hiện thị trên UI ở vị trí tab là đang cộng điểm và tính toán trừ đi số energy. Tuy nhiên thì về lâu dài kết quả hiện thị có đã không đúng, khi test với số lượng tab nhiều và nhanh lúc này state sẽ bị pending lại dẫn tới việc mặc dù về UI vẫn hiện đang cộng điểm chính đúng với số tab tuy nhiên số điểm lại hiển thị sai và chậm hơn rất nhiều so với UI.
Em lên đây hỏi các anh và các bạn để xin mọi người đưa ra cho em một vài giải pháp để xử lý mượt app hơn về mặt hiện thị và cả tính toán (vì chưa kể nhiều bài toán tính toán khác nữa như là sau mỗi 1 giây lại + thêm energy hoặc fetch api để lưu db cho user,... => nhưng tất cả chỉ được handle trong 1 event touch duy nhất). Để làm sao khi user touch 1 ngón hay nhiều ngón nhanh hay chậm thì về mặt UI lẫn tính toán đều chính xác ạ.
Em cảm ơn mọi người!
1 CÂU TRẢ LỜI
Dựa theo những gì bạn nói ở trên, bạn có thể cân nhắc một số giải pháp sau đây:
-
Sử dụng
useReducer
thay vìuseState
:useReducer
giúp quản lý state phức tạp tốt hơn so vớiuseState
, đặc biệt là khi có nhiều action cần được xử lý đồng thời. Bạn có thể dùng một reducer để xử lý các hành động tăng điểm và trừ năng lượng. https://react.dev/reference/react/useReducer
-
useTransition: update state ko block UI. https://react.dev/reference/react/useTransition
-
Debounce and Throttle:
- Khi người dùng click nhanh, bạn có thể sử dụng các kỹ thuật debounce hoặc throttle để giới hạn số lần xử lý hành động. Tham khảo
lodash
- Khi người dùng click nhanh, bạn có thể sử dụng các kỹ thuật debounce hoặc throttle để giới hạn số lần xử lý hành động. Tham khảo
-
Optimistic UI Updates:
- Cập nhật UI trước và đồng bộ hóa với backend sau. Ví dụ, khi người dùng click để tăng điểm, bạn có thể cập nhật UI ngay lập tức và sau đó gửi yêu cầu cập nhật đến server (
fetch
). Nếu có lỗi xảy ra trong quá trình cập nhật, bạn có thể rollback UI về trạng thái trước đó.
- Cập nhật UI trước và đồng bộ hóa với backend sau. Ví dụ, khi người dùng click để tăng điểm, bạn có thể cập nhật UI ngay lập tức và sau đó gửi yêu cầu cập nhật đến server (
dựa theo những cái bạn nói thì đây có thể là 1 cách phù hợp. Tham khảo: https://react.dev/reference/react/useOptimistic
-
Web Workers:
- Nếu có nhiều tính toán phức tạp cần thực hiện, bạn có thể sử dụng Web Workers để xử lý các tính toán này trong một thread riêng biệt, không làm chậm main thread (UI thread).
-
Memoization:
- Sử dụng
useMemo
vàuseCallback
để memoize các giá trị và hàm tính toán, giúp tránh việc tính toán lại không cần thiết trong quá trình render.
- Sử dụng
-
Request Animation Frame (RAF):
- Sử dụng
requestAnimationFrame
để cập nhật UI. Cái này (có thể) giúp đảm bảo rằng các cập nhật UI được thực hiện một cách mượt hơn ở mỗi frame. (cách này bạn phải thử để kiểm chứng liệu nó có hiệu quả ko 😁)
- Sử dụng
Dạ em cảm ơn anh vì những lời khuyên cũng như chia sẽ nhé