成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

【譯】TypeScript中的React Render Props

GeekGhc / 1810人閱讀

原文鏈接: https://medium.com/@jrwebdev/...

和之前的文章一樣,本文也要求你對render props有一些知識(shí)背景,如果沒有官方文檔可能會(huì)對你有很大的幫助。本文將會(huì)使用函數(shù)作為children的render props模式以及結(jié)合React的context API來作為例子。如果你想使用類似于render這樣子的render props,那也只需要把下面例子的children作為你要渲染的props即可。

為了展示render props,我們將要重寫之前文章的makeCounter HOC。這里先展示HOC的版本:

export interface InjectedCounterProps {
  value: number;
  onIncrement(): void;
  onDecrement(): void;
}

interface MakeCounterProps {
  minValue?: number;
  maxValue?: number;
}

interface MakeCounterState {
  value: number;
}

const makeCounter = 

( Component: React.ComponentType

) => class MakeCounter extends React.Component< Subtract & MakeCounterProps, MakeCounterState > { state: MakeCounterState = { value: 0, }; increment = () => { this.setState(prevState => ({ value: prevState.value === this.props.maxValue ? prevState.value : prevState.value + 1, })); }; decrement = () => { this.setState(prevState => ({ value: prevState.value === this.props.minValue ? prevState.value : prevState.value - 1, })); }; render() { const { minValue, maxValue, ...props } = this.props; return ( ); } };

HOC向組件注入了value和兩個(gè)回調(diào)函數(shù)(onIncrement 和 onDecrement),此外還在HOC內(nèi)部使用minValue和maxValue兩個(gè)props而沒有傳遞給組件。我們討論了如果組件需要知道這些值,如何不傳遞props可能會(huì)出現(xiàn)問題,并且如果使用多個(gè)HOC包裝組件,注入的props的命名也可能與其他HOC注入的props沖突。

makeCounter HOC將會(huì)被像下面這樣重寫:

interface InjectedCounterProps {
  value: number;
  onIncrement(): void;
  onDecrement(): void;
}

interface MakeCounterProps {
  minValue?: number;
  maxValue?: number;
  children(props: InjectedCounterProps): JSX.Element;
}

interface MakeCounterState {
  value: number;
}

class MakeCounter extends React.Component {
  state: MakeCounterState = {
    value: 0,
  };

  increment = () => {
    this.setState(prevState => ({
      value:
        prevState.value === this.props.maxValue
          ? prevState.value
          : prevState.value + 1,
    }));
  };

  decrement = () => {
    this.setState(prevState => ({
      value:
        prevState.value === this.props.minValue
          ? prevState.value
          : prevState.value - 1,
    }));
  };

  render() {
    return this.props.children({
      value: this.state.value,
      onIncrement: this.increment,
      onDecrement: this.decrement,
    });
  }
}

這里有一些需要注意的變化。首先,injectedCounterProps被保留,因?yàn)槲覀冃枰x一個(gè)props的interface在render props函數(shù)調(diào)用上而不是傳遞給組件的props(和HOC一樣)。MakeCounter(MakeCounterProps)的props已經(jīng)改變,加上以下內(nèi)容:

children(props: InjectedCounterProps): JSX.Element;

這是render prop,然后組件內(nèi)需要一個(gè)函數(shù)帶上注入的props并返回JSX element。下面是它用來突出顯示這一點(diǎn)的示例:

interface CounterProps {
  style: React.CSSProperties;
  minValue?: number;
  maxValue?: number;
}

const Counter = (props: CounterProps) => (
  
    {injectedProps => (
      
{injectedProps.value}
)}
);

MakeCounter自己的組件聲明變得簡單多了;它不再被包裝在函數(shù)中,因?yàn)樗辉偈桥R時(shí)的,輸入也更加簡單,不需要泛型、做差值和類型的交集。它只有簡單的MakeCounterProps和MakeCounterState,就像其他任何組成部分一樣:

class MakeCounter extends React.Component<
  MakeCounterProps, 
  MakeCounterState
>

最后,render()的工作也變少了;它只是一個(gè)函數(shù)調(diào)用并帶上注入的props-不需要破壞和對象的props擴(kuò)展運(yùn)算符展開了!

return this.props.children({
  value: this.state.value,
  onIncrement: this.increment,
  onDecrement: this.decrement,
});

然后,render prop組件允許對props的命名和在使用的靈活性上進(jìn)行更多的控制,這是和HOC等效的一個(gè)問題:

interface CounterProps {
  style: React.CSSProperties;
  value: number;
  minCounterValue?: number;
  maxCounterValue?: number;
}

const Counter = (props: CounterProps) => (
  
    {injectedProps => (
      
Some other value: {props.value}
{injectedProps.value}
{props.minCounterValue !== undefined ? (
Min value: {props.minCounterValue}
) : null} {props.maxCounterValue !== undefined ? (
Max value: {props.maxCounterValue}
) : null}
)}
);

有了所有這些好處,特別是更簡單的輸入,那么為什么不一直使用render props呢?當(dāng)然可以,這樣做不會(huì)有任何問題,但要注意render props組件的一些問題。

首先,這里有一個(gè)關(guān)注點(diǎn)以外的問題;MakeCounter組件現(xiàn)在被放在了Counter組件內(nèi)而不是包裝了它,這使得隔離測試這兩個(gè)組件更加困難。其次,由于props被注入到組件的渲染函數(shù)中,因此不能在生命周期方法中使用它們(前提是計(jì)數(shù)器被更改為類組件)。

這兩個(gè)問題都很容易解決,因?yàn)槟梢允褂胷ender props組件簡單地生成一個(gè)新組件:

interface CounterProps extends InjectedCounterProps {
  style: React.CSSProperties;
}

const Counter = (props: CounterProps) => (
  
{props.value}
); interface WrappedCounterProps extends CounterProps { minValue?: number; maxValue?: number; } const WrappedCounter = ({ minValue, maxValue, ...props }: WrappedCounterProps) => ( {injectedProps => } );

另一個(gè)問題是,一般來說,它不太方便,現(xiàn)在使用者需要編寫很多樣板文件,特別是如果他們只想將組件包裝在一個(gè)多帶帶的臨時(shí)文件中并按原樣使用props。這可以通過從render props組件生成HOC來補(bǔ)救:

import { Subtract, Omit } from "utility-types";
import MakeCounter, { MakeCounterProps, InjectedCounterProps } from "./MakeCounter";

type MakeCounterHocProps = Omit;

const makeCounter = 

( Component: React.ComponentType

): React.SFC & MakeCounterHocProps> => ({ minValue, maxValue, ...props }: MakeCounterHocProps) => ( {injectedProps => } );

在這里,上一篇文章的技術(shù),以及render props組件的現(xiàn)有類型,被用來生成HOC。這里唯一需要注意的是,我們必須從HOC的props中移除render prop(children),以便在使用時(shí)不暴露它:

type MakeCounterHocProps = Omit;

最后,HOC和render props組件之間的權(quán)衡歸結(jié)為靈活性和便利性。這可以通過首先編寫render props組件,然后從中生成HOC來解決,這使使用者能夠在兩者之間進(jìn)行選擇。這種方法在可重用組件庫中越來越常見,例如優(yōu)秀的render-fns庫。

就TypeScript而言,毫無疑問,hocs的類型定義要困難得多;盡管通過這兩篇文章中的示例,它表明這種負(fù)擔(dān)是由HOC的提供者而不是使用者承擔(dān)的。在使用方面,可以認(rèn)為使用HOC比使用render props組件更容易。

在react v16.8.0之前,我建議使用render props組件以提高鍵入的靈活性和簡單性,如果需要,例如構(gòu)建可重用的組件庫,或者對于簡單在項(xiàng)目中使用的render props組件,我將僅從中生成HOC。在react v16.8.0中釋放react hook之后,我強(qiáng)烈建議在可能的情況下對兩個(gè)高階組件或render props使用它們,因?yàn)樗鼈兊念愋透唵巍?/p>

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/103646.html

相關(guān)文章

  • TypeScript中的React高階組件

    摘要:原文鏈接高階組件在中是組件復(fù)用的一個(gè)強(qiáng)大工具。在本文中,高階組件將會(huì)被分為兩種基本模式,我們將其命名為和用附加的功能來包裹組件。這里我們使用泛型表示傳遞到的組件的。在這里,我們定義從返回的組件,并指定該組件將包括傳入組件的和的。 原文鏈接:https://medium.com/@jrwebdev/... 高階組件(HOCs)在React中是組件復(fù)用的一個(gè)強(qiáng)大工具。但是,經(jīng)常有開發(fā)者在...

    wizChen 評論0 收藏0
  • [] Focal:類型安全、表達(dá)力強(qiáng)、可組合的狀態(tài)管理方案

    摘要:致力于為應(yīng)用提供一個(gè)類型安全表達(dá)力強(qiáng)可組合的狀態(tài)管理方案。是一組的命名空間。是內(nèi)置組件的鏡像,但允許組件的額外接受類型的數(shù)據(jù)。這次內(nèi)容更新,是由組件處理的。這些小的組件不必知道所有的應(yīng)用狀態(tài)數(shù)據(jù)。這是因?yàn)榇蟛糠謱Φ难芯縼碜杂凇? Focal Focal 致力于為 React 應(yīng)用提供一個(gè)類型安全、表達(dá)力強(qiáng)、可組合的狀態(tài)管理方案。 用一個(gè)不可變的 (immutable) 、響應(yīng)式的 (o...

    suemi 評論0 收藏0
  • 我理想中的狀態(tài)管理工具

    摘要:現(xiàn)已存在許多成熟的狀態(tài)管理解決方案,還有基于的但對于我個(gè)人來說,理想的狀態(tài)管理工具只需同時(shí)滿足兩個(gè)特點(diǎn)簡單易用,并且適合中大型項(xiàng)目完美地支持要做到這兩點(diǎn)其實(shí)并不簡單。所以我決定自己造一個(gè)可能是基于和最好的狀態(tài)管理工具 現(xiàn)已存在許多成熟的狀態(tài)管理解決方案:Redux、Mobx、Mobx-state-tree,還有基于 Redux 的 Dva.js、Rematch... 但對于我個(gè)人來說,...

    roadtogeek 評論0 收藏0
  • 「每日一瞥

    摘要:即使中沒有錯(cuò)誤,仍然會(huì)執(zhí)行,這一點(diǎn)一般都是知道的。我們認(rèn)為這是正確的前進(jìn)道路,兼具戰(zhàn)略性和務(wù)實(shí)性降低使用門檻開發(fā)人員遷移到的障礙之一是從到的并不輕松的遷移。下一步將通過一系列功能和插件為的平滑過渡提供支持,并以此回饋社區(qū)。 showImg(https://segmentfault.com/img/remote/1460000017516912?w=1200&h=630); useSt...

    XboxYan 評論0 收藏0
  • With TypeScript 2.8+ :更好的 React 組件開發(fā)模式

    摘要:近兩年來一直在關(guān)注開發(fā),最近也開始全面應(yīng)用。首先,我們從無狀態(tài)組件開始。渲染回調(diào)模式有一種重用組件邏輯的設(shè)計(jì)方式是把組件的寫成渲染回調(diào)函數(shù)或者暴露一個(gè)函數(shù)屬性出來。最后,我們將這個(gè)回調(diào)函數(shù)的參數(shù)聲明為一個(gè)獨(dú)立的類型。 近兩年來一直在關(guān)注 React 開發(fā),最近也開始全面應(yīng)用 TypeScript 。國內(nèi)有很多講解 React 和 TypeScript 的教程,但如何將 TypeScri...

    simon_chen 評論0 收藏0

發(fā)表評論

0條評論

最新活動(dòng)
閱讀需要支付1元查看
<