【问题标题】:React Bootstrap - Best practice for a conditional OverlayTriggerReact Bootstrap - 条件 OverlayTrigger 的最佳实践
【发布时间】:2024-05-02 21:55:02
【问题描述】:

我们有一个按钮,我们希望根据某些条件启用或禁用它。此外,我们希望按钮在禁用时的悬停效果显示一个工具提示,解释它为什么被禁用。

目前,我们有这样的东西:

export class NextButton extends React.Component {
    makePopover () {
        return (
            this.props.someCondition && <Popover>Please enter a title.</Popover>
        )
    }

    render () {
        return (
            <div>
                <OverlayTrigger placement='top' overlay={this.makePopover()}>
                    {/* wrap this in a div so when the button is disabled, the popover still works */}
                    <div>
                        <Button
                            onClick={() => this.props.goToNextPage()}
                            disabled={this.props.someCondition}
                        >
                            Next
                        </Button>
                    </div>
                </OverlayTrigger>
            </div>
        );
    }
}

现在,如果我们仔细观察makePopover 函数,如果someCondition 为假,Popover 将不会被渲染,OverlayTrigger 会在返回没有id 的任何内容时抛出错误。

因此,为了解决这个问题,我们尝试了:

this.props.someCondition ? <Popover>...</Popover> : <span>...</span>

这有助于但显示其他警告:

警告:未知道具placementarrowOffsetLeft, 标签上的arrowOffsetToppositionLeftpositionTop。消除 这些来自元素的道具。

现在,我们可以将条件包裹在整个 OverlayTrigger 本身周围,而不是有条件地显示 Popover,执行以下操作:

this.props.someCondition
?
    <OverlayTrigger>
        <Button>Next</Button>
    </OverlayTrigger>
:
<Button>Next</Button>

如何处理条件工具提示的最佳做法是什么?任何帮助将不胜感激。

【问题讨论】:

    标签: reactjs react-bootstrap


    【解决方案1】:

    我遇到了同样的问题,我认为最简单的解决方法是使用条件包装器。

    const ConditionalWrapper = ({
        condition,
        wrapper,
        children,
    }) => (condition ? wrapper(children) : children);
    
    
    export class NextButton extends React.Component {
        render () {
            return (
                <div>
                    <ConditionalWrapper
                        condition={this.props.someCondition}
                        wrapper={children => (
                            <OverlayTrigger
                                overlay={<Popover>Please enter a title.</Popover>}
                                placement='top'
                            >
                                {children}
                            </OverlayTrigger>
                            )}
                    >
                        {/* wrap this in a div so when the button is disabled, the popover still works */}
                        <div>
                            <Button
                                onClick={() => this.props.goToNextPage()}
                                disabled={this.props.someCondition}
                            >
                                Next
                            </Button>
                        </div>
                    </ConditionalWrapper>
                </div>
            );
        }
    }
    

    【讨论】:

    • 如何为 ConditionalWrapper 中的参数对象创建 typescript 接口?我在这里尝试了多种方法,但总是以拼写错误结束......
    【解决方案2】:

    这是在 Typescript 中为 CoolTarka 提供的 Alexus 答案(主要是):

    interface IConditionalWrapperProps {
        condition: boolean;
        wrapper: (children: React.ReactNode) => JSX.Element;
        children: JSX.Element;
    }
    
    const ConditionalWrapper = ({
        condition,
        wrapper,
        children,
    }: React.PropsWithChildren<IConditionalWrapperProps>) => (condition ? wrapper(children) : children);
    
    export class NextButton extends React.Component {
    render () {
        return (
            <div>
                <ConditionalWrapper
                    condition={this.props.someCondition}
                    wrapper={children => (
                        <OverlayTrigger
                            overlay={<Popover>Please enter a title.</Popover>}
                            placement='top'
                        >
                            {children}
                        </OverlayTrigger>
                        )}
                >
                    {/* wrap this in a div so when the button is disabled, the popover still works */}
                    <div>
                        <Button
                            onClick={() => this.props.goToNextPage()}
                            disabled={this.props.someCondition}
                        >
                            Next
                        </Button>
                    </div>
                </ConditionalWrapper>
            </div>
        );
    }
    

    【讨论】:

      最近更新 更多