2017-09-16 124 views
2

我有一个简单的表示性组件,它在一个设计良好的盒子里显示文本,即一堆DIV。我的组件预计有三个道具:header,displayTextisHtml处理可能包含或不包含HTML的道具

有时,我需要传递给我的displayText prop简单文本和其他时间的东西,其中包含HTML,如超链接。

例如,我可以将Hello World!<a href="http://www.google.com">Click for Google</a>传递给displayText支柱。每当我通过HTML到displayText,isHtml设置为TRUE

我遇到的问题是,PropType设置为stringdisplayText但如果我用HTML标签发送文字,它成为一个object,我得到一个错误说道具收到object但期待string

我该如何处理这个scneario?

我的组件看起来是这样的:

const MyComponent = ({ header, displayText, isHtml }) => { 

    const renderHtml =() => { 

     return { __html: displayText } 
    } 

    return (
     <div className="my-fancy-classes"> 
      <span className="some-more-fancy-classes">{header}</span> 
      {isHtml 
       ? <div className="some-class" dangerouslySetInnerHTML={renderHtml()} /> 
       : <div className="some-class">{displayText}</div> 
      } 
     </div> 
    ); 
} 

MyComponent.propTypes = { 

    header: PropTypes.string.isRequired, 
    displayText: PropTypes.string.isRequired, 
    isHtml: PropTypes.bool.isRequired 
}; 

这里就是我的组件声明看起来像父JSX组件内部IF发送HTML:

getMyText() { 

    let displayText = ""; 
    if(this.props.isHtml) 
     displayText = '<a href="http://www.google.com">Click for Google</a>'; 

    return displayText; 
} 

... 
<div> 
    <MyComponent header="Title" displayText={this.getMyText()} isHtml={true} /> 
</div> 

如果我发送简单的文本,它会看起来像这样:

<div> 
    <MyComponent header="Title" displayText={this.props.someProp} isHtml={false} /> 
</div> 
+0

您正在发送HTML或JSX?我相信你在displayText而不是HTML中发送JSX标签。 – Panther

+0

我在原始帖子的底部添加了一个部分。请看我如何将数据发送到我的组件。所以,我想你说我发送的是JSX,而不是HTML。无论何时我需要发送HTML,我都会像在我的例子中一样调用一个像getMyText()这样的函数。如果我发送简单文本,我只需要执行一些操作,例如'displayText = {this.props.someProp}'。所以,不知道如何处理这个。 – Sam

+0

物体的形状是什么?当它是html的对象 – Chris

回答

2

根据https://facebook.github.io/react/docs/typechecking-with-proptypes.html你应该使用PropTypes.node为任何能呈现:

//任何可以被呈现:数字,字符串,元件或含这些类型的阵列 //(或片段)。 optionalNode:PropTypes.node,

所以你必须

MyComponent.propTypes = { 
    header: PropTypes.string.isRequired, 
    displayText: PropTypes.node.isRequired, 
    isHtml: PropTypes.bool.isRequired 
}; 

你也可以使用oneOfType如果你想有多种类型PropTypes的一个道具


编辑

另外它看起来像你甚至不需要做dangerouslySetInnerHTML,等等,如果你只是直接返回JSX:

getMyText() { 
    let displayText = ""; 
    if (this.props.isHtml) 
    // Remove quotes around html 
    displayText = <a href="http://www.google.com">Click for Google</a>; 

    return displayText; 
} 

-

const MyComponent = ({ header, displayText, isHtml }) => { 
    return (
    <div className="my-fancy-classes"> 
     <span className="some-more-fancy-classes">{header}</span> 
     <div className="some-class">{displayText}</div> 
    </div> 
); 
} 
+0

我尝试过'PropTypes.node',但仍然收到错误消息。错误信息如下:失败的道具类型:提供给“MyComponent”的propTextText无效,需要一个ReactNode。它将它渲染为'[object Object]' – Sam

+0

我也尝试过'oneOfType',它消除了错误,但它根本不呈现HTML。它仍然显示'[object Object]' – Sam

+0

我编辑了我的答案,请看一看 - 如果我理解正确,您可能会删除一些代码以使其工作。 –

0

既然您已经定义了displayText道具是字符串类型,它获得不适用于html对象。你需要像这样定义它。

displayText: PropTypes.any.isRequired, 

在这里任何可以让你通过任何类型的内容在displayText道具。