簡體   English   中英

useState Hook 在事件偵聽器中不起作用

[英]useState Hook not working inside event listener

使用 useState 的設置器 function 在事件偵聽器 function 中不起作用。

  • 訪問沙箱: https://codesandbox.io/s/mystifying-austin-e9zgh
  • 點擊搜索框,將出現一個建議下拉菜單
  • 按向下鍵,它將突出顯示下一項
  • 再次按下向下鍵不起作用 [問題],預期行為:向下鍵應指向下一項

問題陳述:開發具有“向下/向上”鍵可訪問性的搜索建議。

執行:

  • 創建一個搜索欄組件。
              <input
                  style={{ outline: "none" }}
                  placeholder="Search Here"
                  className="w-full text-gray-800"
                  onClick={() => {
                    setShowSuggestion(true);
                    document.addEventListener("keydown", escFunction, false);
                  }}
                  onChange={(event) => setTitle(event.target.value)}
                  value={value}
                />
  • 創建一個建議組件。
              <div
                className={
                  !showSuggestion
                    ? "hidden"
                    : "flex flex-row border border-gray-300 border-t-0  mx-auto w-3/4 space-x-4"
                }
              >
                <ul className="w-full">
                  {people.map((person) => (
                    <li
                      key={person.id}
                      className={cursor === person.id ? "bg-red-500" : ""}
                    >
                      {person.name}
                    </li>
                  ))}
                </ul>
              </div>
  • 單擊搜索欄添加事件列表以檢查按鍵
  • 在keyevent ==“向下箭頭鍵”上,設置選定的推薦=列表中的下一項。

  function escFunction(event) {
    if (event.keyCode === 27) {
      document.removeEventListener("keydown", escFunction);
      setShowSuggestion(false);
    }

    if (event.keyCode === 40) {
      const nextId = cursor + 1;
      setCursor(nextId);   //---------------> this line not setting the value
      setTitle(people[nextId].name);
    }
  }

**問題:** keypress 事件被觸發,但是 setter function 在第一次點擊后不起作用。

而不是將事件偵聽器添加到文檔中,您應該將其添加到輸入 keydown 事件。 在訪問其名稱 - people[nextId].name之前,還要檢查人員 object 的密鑰的可用性。 那應該可以解決您的問題:

<input
                  style={{ outline: "none" }}
                  placeholder="Search Here"
                  className="w-full text-gray-800"
                  onClick={() => {
                    setShowSuggestion(true);
                  }}
                  onKeyDown={escFunction}
                  onChange={(event) => setTitle(event.target.value)}
                  value={value}
                />

cursor 的值(更新值)在cursor執行期間不可用。 為了訪問該值,它必須轉換為setCursor(currentId => currentId + 1); 或者

setCursor(currentId =>{

// do pre processing
return cursor+1
})

正如評論中所暗示的:

  • 傳遞回調允許您訪問當前的 state 值。 您的代碼在最后一次呈現子項時圍繞 state 值創建了一個閉包。

  • cursor 來自 state 里面的那個閉包 function 總是初始值,因為閉包 ZC1C4145268E17A94D

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM