代替html标签显示$$ typeof:Symbol(react.element)?

时间:2019-03-20 14:01:48

标签: javascript reactjs

我正在努力整理带有html标签的已编辑项目。但是在渲染时会显示$$ typeof:Symbol(react.element)。我想念的是什么?

    let modalMessage="Hello, my name is /# Ann #/. I'm working for /# IStaff #/, could you please call me back"
    let arrayText = modalMessage.split("/")
    let newArray = []
    for (let i = 0; i < arrayText.length; i++) {
      newArray.push(arrayText[i])
      if (arrayText[i].includes("#")) {
        newArray.push((arrayText[i] = <input value={arrayText[i]} />))
      }
    }
    console.log(newArray.join(" "))

1 个答案:

答案 0 :(得分:1)

这里有几个问题,但是主要的是:

newArray.join(" ")

newArray是一个既包含字符串又包含React元素(它们是JavaScript对象,而不是HTML字符串)的数组。当您在其上调用join时,就是在告诉JavaScript(尝试)将每个元素转换为字符串,然后将这些字符串连接为单个字符串。 $$typeof : Symbol(react.element)是该尝试的结果。

您根本不需要做join。 React知道如何渲染混合元素的数组。您只需要返回数组即可,尽管您可能需要根据需要将其包装在例如首先<p>

代码中的另一个问题是您正在调用newArray.push,但同时也要分配给arrayText[i]

for (let i = 0; i < arrayText.length; i++) {
  newArray.push(arrayText[i])
  if (arrayText[i].includes("#")) {
    newArray.push((arrayText[i] = <input value={arrayText[i]} />))
  }
}

您应该选择一个,例如:

for (let i = 0; i < arrayText.length; i++) {
  if (arrayText[i].includes("#")) {
    arrayText[i] = <input value={arrayText[i]} />;
  }
}

这会将其中包含#的元素替换为<input>,而其他元素保持不变。这是一个工作示例:

 
const App = ({ modalMessage }) => {
  const arrayText = modalMessage.split("/");

  for (let i = 0; i < arrayText.length; i++) {
    if (arrayText[i].includes("#")) {
      arrayText[i] = <input value={arrayText[i]} />;
    }
  }

  return <p>{arrayText}</p>;
};

ReactDOM.render(
  <App modalMessage="Hello, my name is /# Ann #/. I'm working for /# IStaff #/, could you please call me back" />,
  document.querySelector("div")
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.6.3/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.6.3/umd/react-dom.production.min.js"></script>
<div></div>

但是,更惯用的版本将使用map

const App = ({ modalMessage }) => (
  <p>
    {modalMessage
      .split("/")
      .map(text => (text.includes("#") ? <input value={text} /> : text))}
  </p>
);