[英]Debounce inside functional component in React.js
嘗試在具有隨更改更新的輸入字段的反應組件上創建延遲。
這是代碼:
import React from 'react';
import Input from "@material-ui/core/Input";
import {debounce} from "lodash";
...
const SampleRow = () => {
let [newFriend, setNewFriend] = React.useState({name: '', lastSeen: '', contactIn: ''});
const onAddFriend = debounce(() => {
if(newFriend.name.length === 0){
return;
}
console.log(newFriend.name);
}, 2000);
return (
<TableRow>
<TableCell component="th" scope="row">
<Input
value={newFriend.name}
onChange={(event) => {
setNewFriend({...newFriend, name: event.target.value});
onAddFriend();
}}
placeholder={"Add friend"}
disableUnderline={true}
/>
</TableCell>
<TableCell align="left">{newFriend.lastSeen ? newFriend.lastSeen : ''}</TableCell>
<TableCell align="left">{newFriend.contactIn ? newFriend.contactIn : ''}</TableCell>
<TableCell align="left" className={classes.externalLinks}/>
</TableRow>
)
};
發生的情況是console.log
打印出每個更改(在 2s 超時之后),並且不會取消以前的觸發器。
問題是為什么會這樣? 這怎么可能解決?
我在復雜的
useDebounce
邏輯或類組件中發現了類似的問題。 沒有找到這個問題的參考。
這里的問題是您的去抖動 function 正在每次渲染上重新創建。
解決此問題的一種方法是將其移出功能組件。 另一種方法是將組件更改為 Class 組件並將去抖動的 function 保存為屬性。
const { useState } = React const { debounce } = _; const onAddFriend = debounce(console.log, 2000); const App = () => { const [newFriend, setNewFriend] = useState({name: '', lastSeen: '', contactIn: ''}); const handleInput = (event) => { setNewFriend({...newFriend, name: event.target.value}); onAddFriend(event.target.value); } return ( <div className="box"> <form className="form"> <div class="field"> <label for="name-1">Update {newFriend.name}</label> <div class="control"> <input type="text" name="name-1" value={newFriend.name} onChange={handleInput} class="input"/> </div> </div> </form> </div> ) } ReactDOM.render(<App />, document.getElementById("root"))
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.19/lodash.min.js"></script> <script src="https://unpkg.com/react@16.7.0-alpha.0/umd/react.production.min.js"></script> <script src="https://unpkg.com/react-dom@16.7.0-alpha.0/umd/react-dom.production.min.js"></script> <div id="root"></div>
Ciao,嘗試取消之前的觸發器:
import React from 'react';
import Input from "@material-ui/core/Input";
import {debounce} from "lodash";
...
const SampleRow = () => {
let [newFriend, setNewFriend] = React.useState({name: '', lastSeen: '', contactIn:
''});
const onAddFriend = debounce((abort) => {
if(abort){
return;
}
console.log(newFriend.name);
}, 2000);
return (
<TableRow>
<TableCell component="th" scope="row">
<Input
value={newFriend.name}
onChange={(event) => {
setNewFriend({...newFriend, name: event.target.value});
let abort = false;
if(event.target.value.length === 0){
abort = true;
}
onAddFriend(abort);
}}
placeholder={"Add friend"}
disableUnderline={true}
/>
</TableCell>
<TableCell align="left">{newFriend.lastSeen ? newFriend.lastSeen : ''}</TableCell>
<TableCell align="left">{newFriend.contactIn ? newFriend.contactIn : ''}</TableCell>
<TableCell align="left" className={classes.externalLinks}/>
</TableRow>
)
};
嘗試這個。 它將始終檢查隊列中現有的去抖動,並取消它找到任何。 參考: 如何在調用之后和執行之前取消去抖動的 function?
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.