簡體   English   中英

如何在功能組件的 React 中的 props 中使用 generics?

[英]How to use generics in props in React in a functional component?

在基於 class 的組件中,我可以輕松編寫如下代碼:

import * as React from 'react';
import { render } from 'react-dom';

interface IProps<T> {
    collapsed: boolean;
    listOfData: T[];
    displayData: (data: T, index: number) => React.ReactNode;
}

class CollapsableDataList<T> extends React.Component<IProps<T>> {
    render () {
        if (!this.props.collapsed) {
            return <span>total: {this.props.listOfData.length}</span>
        } else {
            return (
                <>
                    {
                        this.props.listOfData.map(this.props.displayData)
                    }
                </>
            )
        }
    }
}

render(
    <CollapsableDataList
        collapsed={false}
        listOfData={[{a: 1, b: 2}, {a: 3, b: 4}]}
        displayData={(data, index) => (<span key={index}>{data.a + data.b}</span>)}
    />,
    document.getElementById('root'),
)

實際上這個CollapsableDataList組件應該是一個功能組件,因為它是無狀態的,但我不知道如何編寫 function 組件並在道具中使用 generics,對我有什么建議嗎?

在基於類的組件中,我可以輕松地編寫如下代碼:

import * as React from 'react';
import { render } from 'react-dom';

interface IProps<T> {
    collapsed: boolean;
    listOfData: T[];
    displayData: (data: T, index: number) => React.ReactNode;
}

class CollapsableDataList<T> extends React.Component<IProps<T>> {
    render () {
        if (!this.props.collapsed) {
            return <span>total: {this.props.listOfData.length}</span>
        } else {
            return (
                <>
                    {
                        this.props.listOfData.map(this.props.displayData)
                    }
                </>
            )
        }
    }
}

render(
    <CollapsableDataList
        collapsed={false}
        listOfData={[{a: 1, b: 2}, {a: 3, b: 4}]}
        displayData={(data, index) => (<span key={index}>{data.a + data.b}</span>)}
    />,
    document.getElementById('root'),
)

實際上,此CollapsableDataList組件應該是功能組件,因為它是無狀態的,但是我無法弄清楚如何編寫功能組件並在props中使用泛型,對我有什么建議?

在基於類的組件中,我可以輕松地編寫如下代碼:

import * as React from 'react';
import { render } from 'react-dom';

interface IProps<T> {
    collapsed: boolean;
    listOfData: T[];
    displayData: (data: T, index: number) => React.ReactNode;
}

class CollapsableDataList<T> extends React.Component<IProps<T>> {
    render () {
        if (!this.props.collapsed) {
            return <span>total: {this.props.listOfData.length}</span>
        } else {
            return (
                <>
                    {
                        this.props.listOfData.map(this.props.displayData)
                    }
                </>
            )
        }
    }
}

render(
    <CollapsableDataList
        collapsed={false}
        listOfData={[{a: 1, b: 2}, {a: 3, b: 4}]}
        displayData={(data, index) => (<span key={index}>{data.a + data.b}</span>)}
    />,
    document.getElementById('root'),
)

實際上,此CollapsableDataList組件應該是功能組件,因為它是無狀態的,但是我無法弄清楚如何編寫功能組件並在props中使用泛型,對我有什么建議?

在基於類的組件中,我可以輕松地編寫如下代碼:

import * as React from 'react';
import { render } from 'react-dom';

interface IProps<T> {
    collapsed: boolean;
    listOfData: T[];
    displayData: (data: T, index: number) => React.ReactNode;
}

class CollapsableDataList<T> extends React.Component<IProps<T>> {
    render () {
        if (!this.props.collapsed) {
            return <span>total: {this.props.listOfData.length}</span>
        } else {
            return (
                <>
                    {
                        this.props.listOfData.map(this.props.displayData)
                    }
                </>
            )
        }
    }
}

render(
    <CollapsableDataList
        collapsed={false}
        listOfData={[{a: 1, b: 2}, {a: 3, b: 4}]}
        displayData={(data, index) => (<span key={index}>{data.a + data.b}</span>)}
    />,
    document.getElementById('root'),
)

實際上,此CollapsableDataList組件應該是功能組件,因為它是無狀態的,但是我無法弄清楚如何編寫功能組件並在props中使用泛型,對我有什么建議?

在基於類的組件中,我可以輕松地編寫如下代碼:

import * as React from 'react';
import { render } from 'react-dom';

interface IProps<T> {
    collapsed: boolean;
    listOfData: T[];
    displayData: (data: T, index: number) => React.ReactNode;
}

class CollapsableDataList<T> extends React.Component<IProps<T>> {
    render () {
        if (!this.props.collapsed) {
            return <span>total: {this.props.listOfData.length}</span>
        } else {
            return (
                <>
                    {
                        this.props.listOfData.map(this.props.displayData)
                    }
                </>
            )
        }
    }
}

render(
    <CollapsableDataList
        collapsed={false}
        listOfData={[{a: 1, b: 2}, {a: 3, b: 4}]}
        displayData={(data, index) => (<span key={index}>{data.a + data.b}</span>)}
    />,
    document.getElementById('root'),
)

實際上,此CollapsableDataList組件應該是功能組件,因為它是無狀態的,但是我無法弄清楚如何編寫功能組件並在props中使用泛型,對我有什么建議?

補充 #1。

如果要將組件導出為 FunctionComponent 並傳遞 eslint displayName 錯誤。

你可以這樣做。

const yourComponentWithLowerCase: <T>(props: PropsWithChildren<Props<T>>) => ReactElement | null = (props) => {
  // code
}

export const YourComponentWithUpperCase = yourComponentWithLowerCase;
(YourComponentWithUpperCase as FunctionComponent).displayName = 'something'


這個答案是一個很好的例子,因為它正確定義了函數的 props 和返回類型。

作為替代,這些可以定義為函數而不是箭頭函數。 這繞過了擴展 prop 類型以提示 TS 編譯器這不是反應組件的需要。

export function CollapsableDataList<T>(
  props: PropsWithChildren<IProps<T>>
): ReturnType<FunctionComponent<IProps<T>>> {
  // ...
}

反應 18,Typescript 4.6.3

interface IProps<T> {
  data: T[];
}
export const YourComponent = <T,>(props: IProps<T>) => {}

暫無
暫無

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

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