Reactjs 基于父项的样式化组件中的条件呈现';道具

Reactjs 基于父项的样式化组件中的条件呈现';道具,reactjs,styled-components,Reactjs,Styled Components,如何根据父组件的道具将条件样式应用于已设置样式的组件 下面是我当前代码的高级示例设置: // File 1: GrandParent.js import React, { useState } from 'react'; import Parent from './parent'; export default function GrandParent() { const [ isExpanded, setIsExpanded ] = useState(false); re

如何根据父组件的道具将条件样式应用于已设置样式的组件

下面是我当前代码的高级示例设置:

// File 1: GrandParent.js

import React, { useState } from 'react';
import Parent from './parent';

export default function GrandParent() {
    const [ isExpanded, setIsExpanded ] = useState(false);

    render (
        <>
            <Parent isExpanded={isExpanded} />
            ...other Stuff
        </>
    );
}
但是有没有一种方法可以让我不用在
上作为道具传递“isExpanded”就可以做到这一点?在我的实际代码中,
中还有更多的孩子需要知道“isExpanded”的状态,以便进行样式设计,我真的不想把这个道具单独传递给他们

我认为上下文API可能是这里的关键,但我已经在React树中使用了一个比
祖父母
更高级别的上下文来进行全局样式设置,我担心如果我尝试嵌套第二个上下文(也许将其包装在
周围,让
及其所有子项知道“isExpanded”的状态),这样
都可能无法访问外部上下文……或者上下文嵌套不是这样工作的

我只知道我仍然需要
从外部上下文访问一些主题设置。我不知道在
级别引入第二个上下文仅仅为了跟踪单个“isExpanded”道具的状态是否有点过火

这里的另一个要求是,我需要
能够在其条件样式中处理媒体查询(例如,如果“isExpanded”为true,并且如果是桌面视口,则仅应用某些样式)


设置这个的正确方法是什么?

你是对的。上下文是正确的方法

Context被设计成一个轻量级的跨组件数据存储,在本例中使用2个Context绝对不过分;事实上,这个用例几乎就是创建Context的目的(有趣的是,在工作中我们使用了几十个嵌套的上下文)

export const ExpandedContext=createContext();
导出默认函数祖父母(){
常量[isExpanded,setIsExpanded]=useState(false);
渲染(
…其他东西
);
}
不幸的是,无法访问样式化组件内部的上下文,因此您必须通过props传入值

export default function Parent(props) {
    const { isExpanded } = useContext(ExpandedContext);
    render (
        <div>
            ... other stuff
            <Child isExpanded={isExpanded}>I'm a child.</Child>
        </div>
    );
}
导出默认函数父级(道具){
const{isExpanded}=useContext(ExpandedContext);
渲染(
…其他东西
我是个孩子。
);
}

您可以将父容器
div
设置为样式化组件,并将其设置为
子容器
。类似于:

export default function Parent(props) {
    render (
        <ParentContainer isExpanded={props.isExpanded}>
            ... other stuff
            <Child>I'm a child.</Child>
        </ParentContainer>
    );
}

const Child = styled.div`
    // ...
`;

const ParentContainer = styled.div`
  > ${Child} {
    background-color: ${props => props.isExpanded ? 'blue' : 'red'};
  }
`;
导出默认函数父级(道具){
渲染(
…其他东西
我是个孩子。
);
}
const Child=styled.div`
// ...
`;
const ParentContainer=styled.div`
>${Child}{
背景色:${props=>props.isExpanded?'blue':'red'};
}
`;

感谢您的快速回复和示例设置!尽管我理解正确,我可以在这个新的上下文中包装,但我仍然无法通过样式化组件访问此上下文的值?该死。因此,在这种情况下,如果您有许多子样式化组件需要条件样式化,那么就不会考虑它mal最终可能会有很多道具仅仅为了条件样式而传递?如果我保留当前的.expanded类依赖关系,会考虑多大程度的反模式?如果子组件是一个经常使用的组件,那么将样式化组件包装在一个名为Child的普通组件中,并将现有子组件更改为StyledChild、 然后您可以在普通组件中使用上下文并将其传递到样式化组件中。这样您就不必多次传递道具。好的。我会记住的。谢谢!
export const ExpandedContext = createContext();
export default function GrandParent() {
    const [ isExpanded, setIsExpanded ] = useState(false);
    
    render (
        <ExpandedContext.Provider value={{ isExpanded }}>
            <Parent />
            ...other Stuff
        <ExpandedContext.Provider/>
    );
}
export default function Parent(props) {
    const { isExpanded } = useContext(ExpandedContext);
    render (
        <div>
            ... other stuff
            <Child isExpanded={isExpanded}>I'm a child.</Child>
        </div>
    );
}
export default function Parent(props) {
    render (
        <ParentContainer isExpanded={props.isExpanded}>
            ... other stuff
            <Child>I'm a child.</Child>
        </ParentContainer>
    );
}

const Child = styled.div`
    // ...
`;

const ParentContainer = styled.div`
  > ${Child} {
    background-color: ${props => props.isExpanded ? 'blue' : 'red'};
  }
`;