代码之家  ›  专栏  ›  技术社区  ›  Zahid Saeed

动态组件名称与道具反应

  •  0
  • Zahid Saeed  · 技术社区  · 4 年前

    我有一个 PropertyCardList 接受一些的组件 props 。我只想从父级传递组件名称,列表应该会自动呈现它。

    PropertyCardList.tsx

    import React from "react";
    import { Grid, GridProps, GridSpacing } from "@material-ui/core";
    import { NamedExoticComponent } from "react";
    import { LargePropertyInfo, SmallPropertyInfo } from "../../@types/Property/Property";
    import { SmallPropertyCardProps } from "../PropertyCards/SmallPropertyCard/SmallPropertyCard";
    import { LargePropertyCardProps } from "../PropertyCards/LargePropertyCard/LargePropertyCard";
    
    interface Props
    {
        gridSpacing?: GridSpacing;
        gridItemProps?: GridProps;
        loading?: boolean;
        skeletonsCount?: number;
        properties: SmallPropertyInfo[] | LargePropertyInfo[];
        cardComponent: NamedExoticComponent <SmallPropertyCardProps> | NamedExoticComponent <LargePropertyCardProps>;
    }
    
    const PropertyCardList: React.FC <Props> = props =>
    {
        if (props.loading)
        {
            return (
                <Grid container spacing={props.gridSpacing}>
                    {new Array(props.skeletonsCount).fill(null).map((_, index) => (
                        <Grid
                            item
                            key={index}
                            {...props.gridItemProps}
                        >
                            <props.cardComponent
                                property={{}} // I have to typecast it using "as" but what should be the value?
                                loading={true}
                            />
                        </Grid>
                    ))}
                </Grid>
            )
        }
    
        return (
            <Grid container spacing={props.gridSpacing}>
                {props.properties.map((property) => (
                    <Grid
                        item
                        key={property.id}
                        {...props.gridItemProps}
                    >
                        <props.cardComponent
                            property={property} // I get error here saying that subType, ownership missing in SmallPropertyInfo. It makes sense but this needs to be dynamic as well
                        />
                    </Grid>
                ))}
            </Grid>
        );
    }
    
    PropertyCardList.defaultProps = {
        skeletonsCount: 3,
    }
    
    export default React.memo(PropertyCardList);
    
    

    接口

    export interface PropertyBase
    {
        id: string;
        images: string[];
        beds: number;
        baths: number;
        areaSize: number;
        price: PropertyPrice;
        address: ObjectWithTranslation;
    }
    
    export interface SmallPropertyInfo extends PropertyBase
    {
        purpose: PropertyPurpose;
    }
    
    export interface LargePropertyInfo extends SmallPropertyInfo
    {
        subType: PropertySubType;
        ownership: PropertyOwnership;
        installment: Omit <PropertyPrice, "type">;
    }
    
    

    以下是我如何使用列表组件:

    <PropertyCardList
        cardComponent={isMobile ? SmallPropertyCard : LargePropertyCard}
        properties={properties.data}
        gridSpacing={2}
        gridItemProps={{
            lg: 6,
            xs: 12
        }}
        loading={loading}
        skeletonsCount={5}
    />
    

    这是使列表组件通用的正确方法吗?还是应该为每种类型单独创建列表组件?(这将重复许多代码)

    0 回复  |  直到 4 年前
        1
  •  0
  •   Kavindu Vindika    4 年前

    在react中使用条件渲染是可能的,并且它确实有助于删除冗余的编码实现。

    您可以将其作为函数体中的变量,如下所示。

    const cardComponent= isMobile ? SmallPropertyCard : LargePropertyCard
    

    然后使用它传递到子组件,如下所示。

    <PropertyCardList
        cardComponent={cardComponent}
        properties={properties.data}
        gridSpacing={2}
        gridItemProps={{
            lg: 6,
            xs: 12
        }}
        loading={loading}
        skeletonsCount={5}
    />
    

    你使用它的方式也是正确的。