通过 Provider 将自定义 props 传递给每个样式化的组件

Posted

技术标签:

【中文标题】通过 Provider 将自定义 props 传递给每个样式化的组件【英文标题】:Passing custom props to each styled component through Provider 【发布时间】:2019-11-26 10:29:47 【问题描述】:

我想通过 Provider 将自定义 prop(确切地说:主题名称作为字符串)传递给每个传递的样式组件,因此它在整个 css 定义中都可用。 ThemeProvider 几乎做到了,但它需要对象,而不是字符串。我不想通过主题设置传递整个对象,只传递我的主题名称。

我不想使用特殊的主题道具或类似的道具,因为这样我每次创建新的样式组件时都必须手动进行。提供者似乎是最好的选择,如果它只与字符串合作。

是否有可能通过 Provider 将字符串传递给内置样式组件的 Consumer?

编辑:

[部分解决方案]

当我意识到 styled-components 导出它们的内部上下文时,我找到了我正在寻找的东西。就是这样。访问纯反应上下文为您提供原始提供者,没有任何“仅对象”限制(“仅对象”是样式化组件自定义提供者限制)。 现在,我可以将我想要的以及我想要的推送到每个样式化的组件。

import styled,  ThemeContext  from 'styled-components';

const StyledComponent = styled.div`
  color: $props => props.theme == 'dark' ? 'white' : 'black';
`;

const Component = props => 

  const theme = 'dark';

  return (
    <ThemeContext.Provider value=theme>
      <NextLevelComponent>
        <StyledComponent />
      </NextLevelComponent>
    </ThemeContext.Provider>
  );
;

【问题讨论】:

【参考方案1】:

希望我有这个正确的,从我已经能够收集到的。我还没有尝试过,但它似乎对你有用。这是 reactjs.org 文档中有关上下文的 lifted directly。它将主题的字符串名称向下传递。

const ThemeContext = React.createContext('green');

class App extends React.Component 
  render() 
    return (
      <ThemeContext.Provider value="blue">
        <SomeComponent />
      </ThemeContext.Provider>
    );
  


function SomeComponent(props) 
  return (
    <div> 
      <OtherComponent />
    </div>
  );


class OtherComponent extends React.Component 
  static contextType = ThemeContext;
  render() 
    return <ThirdComponent theme=this.context />
  

【讨论】:

你写的是Context的大致思路,大概没问题。但是在 styled-components 中已经有一个 Consumer 有自己的 context,并且它被注入到每个新的 styled 组件中。因此我需要以某种方式编辑 ThemeProvider 或者....获取现有上下文并创建我自己的提供者....嗯【参考方案2】:

我希望这可以帮助您从 styled-components 中理解 ThemeContext 背后的想法。我将字符串“blue”传递给 ThemeContext 只是为了表明它不应该是对象,您可以只使用字符串。

import React,  useContext  from "react";
import ReactDOM from "react-dom";
import styled,  ThemeContext  from "styled-components";

// Define styled button
const Button = styled.button`
  font-size: 1em;
  margin: 1em;
  padding: 0.25em 1em;
  border-radius: 3px;
  color: $props => props.theme;
  border: 2px solid $props => props.theme;
`;

// Define the name of the theme / color (string)
const themeName = "blue";

const ThemedButton = () => 
  // Get the name from context
  const themeName = useContext(ThemeContext);
  return <Button theme=themeName>Themed color: themeName</Button>;
;

function App() 
  return (
    <div className="App">
      <ThemeContext.Provider value=themeName>
        <ThemedButton />
      </ThemeContext.Provider>
    </div>
  );


const rootElement = document.getElementById("root");
ReactDOM.render(<App />, rootElement);

演示:https://codesandbox.io/s/styled-components-example-with-themecontext-cso55

【讨论】:

好吧,你的代码也是准确的,但它仍然不是我想要的。您使用 ThemedButton 作为一种中间件来应用上下文值。这意味着我必须包装 >each

以上是关于通过 Provider 将自定义 props 传递给每个样式化的组件的主要内容,如果未能解决你的问题,请参考以下文章

如何将自定义道具传递给 QueryRenderer 渲染函数?

通过 WatchConnectivity 的 sendMessageData 将自定义对象的 NSArray 作为 NSData 传递

通过拖放将自定义元素的对象引用传递给另一个自定义元素

前端开发日常 - 13React学习笔记——Props & State & Fragments

Django在使用默认视图时将自定义变量传递给模板

从标准 html 传递道具以反应组件