中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

ahooks控制時機的hook如何實現

發布時間:2022-07-12 10:12:51 來源:億速云 閱讀:135 作者:iii 欄目:開發技術

本篇內容主要講解“ahooks控制時機的hook如何實現”,感興趣的朋友不妨來看看。本文介紹的方法操作簡單快捷,實用性強。下面就讓小編來帶大家學習“ahooks控制時機的hook如何實現”吧!

Function Component VS Class Component

學習類似 React 和 Vue 這種框架,對它們生命周期的掌握都是必須的,我們需要清楚的知道我們代碼的執行順序,并且在不同的階段執行不同操作的代碼,比如需要掛載完成之后才去獲取 dom 的值,否則可能會獲取不到相應的值。

Class Component

使用過 React 的 Class Component 的同學,就會知道其組件生命周期會分成三個狀態:

  • Mounting(掛載):已插入真實 DOM

  • Updating(更新):正在被重新渲染

  • Unmounting(卸載):已移出真實 DOM

簡單版如下所示:

ahooks控制時機的hook如何實現

其中每個狀態中還會按順序調用不同的方法,對應的詳細如下(這里不展開說):

ahooks控制時機的hook如何實現

可以通過官方提供這個網站查看詳情

可以看到,會有非常多的生命周期方法,而且在不同的版本,生命周期方法還不同。

Function Component

到了 Function Component ,會發現沒有直接提及生命周期的概念,它是更徹底的狀態驅動,它只有一個狀態,React 負責將狀態渲染到視圖中。

對于 Function Component 來說由狀態到頁面渲染只有三步:

  • 輸入狀態(prop、state)

  • 執行組件的邏輯,并在 useEffect/useLayoutEffect 中訂閱副作用

  • 輸出UI(Dom節點)

重點是第二步,React 通過 useEffect/useLayoutEffect 訂閱副作用。Class Component 中的生命周期都可以通過 useEffect/useLayoutEffect 來實現。它們兩個的功能非常相似,我們這里看下 useEffect。

使用 useEffect 相當于告訴 React 組件需要在渲染后執行某些操作,React 將在執行 DOM 更新之后調用它。React 保證了每次運行 useEffect 的時候,DOM 已經更新完畢。這就實現了 Class Component 中的 Mounting(掛載階段)。

當狀態發生變化的時候,它能夠執行對應的邏輯、更行狀態并將結果渲染到視圖中,這就完成了 Class Component 中的 Updating(更新階段)。

最后通過在 useEffect 中返回一個函數,它便可以清理副作用。它的規則是:

  • 首次渲染不會進行清理,會在下一次渲染,清除上一次的副作用。

  • 卸載階段也會執行清除操作。

通過返回一個函數,我們就能實現 Class Component 中的 Unmounting(卸載階段)。

基于 useEffect/useLayoutEffect,ahooks 做了一些封裝,能夠讓你更加清晰的知道你的代碼執行時機。

LifeCycle - 生命周期

useMount

只在組件初始化時執行的 Hook。 useEffect 依賴假如為空,只會在組件初始化的時候執行。

// 省略部分代碼
const useMount = (fn: () => void) => {
  // 省略部分代碼
  // 單純就在 useEffect 基礎上封裝了一層
  useEffect(() => {
    fn?.();
  }, []);
};
export default useMount;

useUnmount

useUnmount,組件卸載(unmount)時執行的 Hook。

useEffect 可以在組件渲染后實現各種不同的副作用。有些副作用可能需要清除,所以需要返回一個函數,這個函數會在組件卸載的時候執行。

const useUnmount = (fn: () => void) => {
  const fnRef = useLatest(fn);
  useEffect(
    // 在組件卸載(unmount)時執行的 Hook。
    // useEffect 的返回值中執行函數
    () => () => {
      fnRef.current();
    },
    [],
  );
};
export default useUnmount;

useUnmountedRef

獲取當前組件是否已經卸載的 Hook。

通過判斷有沒有執行 useEffect 中的返回值判斷當前組件是否已經卸載。

// 獲取當前組件是否已經卸載的 Hook。
const useUnmountedRef = () => {
  const unmountedRef = useRef(false);
  useEffect(() => {
    unmountedRef.current = false;
    // 如果已經卸載,則會執行 return 中的邏輯
    return () => {
      unmountedRef.current = true;
    };
  }, []);
  return unmountedRef;
};
export default useUnmountedRef;

Effect

這里只會講官方文檔 Effect 下面的幾個,有部分是定時器、防抖節流等,咱們后面的系列具體分析。

useUpdateEffect 和 useUpdateLayoutEffect

useUpdateEffect 和 useUpdateLayoutEffect 的用法跟 useEffect 和 useLayoutEffect 一樣,只是會忽略首次執行,只在依賴更新時執行。

實現思路:初始化一個標識符,剛開始為 false。當首次執行完的時候,置為 true。只有標識符為 true 的時候,才執行回調函數。

// 忽略首次執行
export const createUpdateEffect: (hook: effectHookType) => effectHookType =
  (hook) => (effect, deps) => {
    const isMounted = useRef(false);
    // for react-refresh
    hook(() => {
      return () => {
        isMounted.current = false;
      };
    }, []);
    hook(() => {
      // 首次執行完時候,設置為 true,從而下次依賴更新的時候可以執行邏輯
      if (!isMounted.current) {
        isMounted.current = true;
      } else {
        return effect();
      }
    }, deps);
  };

useDeepCompareEffect和useDeepCompareLayoutEffect

用法與 useEffect 一致,但 deps 通過 lodash isEqual 進行深比較。

通過 useRef 保存上一次的依賴的值,跟當前的依賴對比(使用 lodash 的 isEqual),并將對比結果作為 useEffect 的依賴項,從而決定回調函數是否執行。

const depsEqual = (aDeps: DependencyList, bDeps: DependencyList = []) => {
  return isEqual(aDeps, bDeps);
};
const useDeepCompareEffect = (effect: EffectCallback, deps: DependencyList) => {
  // 通過 useRef 保存上一次的依賴的值
  const ref = useRef<DependencyList>();
  const signalRef = useRef<number>(0);
  // 判斷最新的依賴和舊的區別
  // 如果相等,則變更 signalRef.current,從而觸發 useEffect 中的回調
  if (!depsEqual(deps, ref.current)) {
    ref.current = deps;
    signalRef.current += 1;
  }
  useEffect(effect, [signalRef.current]);
};

useUpdate

useUpdate 會返回一個函數,調用該函數會強制組件重新渲染。

返回的函數通過變更 useState 返回的 state,從而促使組件進行更新。

import { useCallback, useState } from 'react';
const useUpdate = () => {
  const [, setState] = useState({});
  // 通過設置一個全新的狀態,促使 function 組件更新
  return useCallback(() => setState({}), []);
};
export default useUpdate;

到此,相信大家對“ahooks控制時機的hook如何實現”有了更深的了解,不妨來實際操作一番吧!這里是億速云網站,更多相關內容可以進入相關頻道進行查詢,關注我們,繼續學習!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

许昌县| 宜兴市| 呼伦贝尔市| 靖远县| 华蓥市| 嘉祥县| 丰原市| 上高县| 武邑县| 大安市| 湘潭市| 新巴尔虎右旗| 高碑店市| 赤壁市| 霍山县| 无棣县| 望奎县| 正宁县| 长沙市| 富川| 左云县| 北海市| 永平县| 新巴尔虎左旗| 张家口市| 双桥区| 城市| 通江县| 乌拉特前旗| 公安县| 庆云县| 恭城| 鹤峰县| 聂荣县| 滦南县| 若尔盖县| 宁陕县| 任丘市| 嵊泗县| 郁南县| 新田县|