用React钩子创建和操纵组件

发布于 2025-02-08 13:58:38 字数 3177 浏览 2 评论 0 原文

我正在尝试创建一个主页旋转木马。它基本上是3个文章的3个Divs,我希望能够操纵某些内容,例如标题的字体大小和位置(带有保证金顶部)

我的初始代码是这样的:

const Home = () => {
  const [margin, setMargin] = useState('420px')
  const [font, setFont] = useState('20px')

  function mouseOver (){
    setMargin('320px')
    setFont('40px')
  }

  function mouseOut(){
    setMargin('420px')
    setFont('20px')
  }

  return(
    <div className='carousel'>
      <div className='column' id='column1' onMouseOver={mouseOver} onMouseOut={mouseOut}>
        <p className='title' id='title1' style={{marginTop: margin,fontSize: font ,color:'black'}} > Τitle 1  </p>
        <p className='markdown' id='markdown1'>mark1 </p>
      </div>
      <div className='column' id='column2' onMouseOver={mouseOver} onMouseOut={mouseOut}>
         <p className='title' id='title2' > Τitle 2</p>
         <p className='markdown' id='markdown2'> mark2</p>
      </div>
      <div className='column' id='column3'>
         <p className='title' id='title3' onMouseOver={mouseOver} onMouseOut={mouseOut}> Τitle 3 </p>
         <p className='markdown' id='markdown3'> mark3</p>
      </div>
    </div>
  )
}
  
export default Home;

每次我徘徊在任何徘徊在任何时在标题中,它们的大小改变了,因为我使用相同的值并在每个人中更改它。因此,我想以更多的反应方式进行操作,因为在我看来,这就像平面HTML带有一些反应,所以这就是我想到的。

const Home = () => {
  const [margin, setMargin] = useState('420px')
  const [font, setFont] = useState('20px')

  function mouseOver(){
    setMargin('320px')
    setFont('40px')
  }

  function mouseOut(){
    setMargin('420px')
    setFont('20px')
  }

  const arrayDivs =[]

  for (let i=0; i<=2; i++) {
    const div = React.createElement(
      'div', //type
      {key: i, className: 'column', id: `column${i+1}` }, //properties of element
      React.createElement(
        'p', //children of element
        {
          key: i,
          className: 'title',
          id: `title${i+1}`,
          style: {
            marginTop: margin,
            fontSize: font
          },
          onMouseOver: mouseOver(),
          onMouseOut:mouseOut()
        }
      ),
      `title${i+1}`
    )  
    arrayDivs.push(div)
  }

  return(
    <div className='carousel'>
      { arrayDivs }
    </div>
  )
}
  
export default Home;

但是我遇到了这个错误

Uncaught Error: Too many re-renders. React limits the number of renders to prevent an infinite loop.
at renderWithHooks (react-dom.development.js:16317:1)
at mountIndeterminateComponent (react-dom.development.js:20074:1)
at beginWork (react-dom.development.js:21587:1)
at HTMLUnknownElement.callCallback (react-dom.development.js:4164:1)
at Object.invokeGuardedCallbackDev (react-dom.development.js:4213:1)
at invokeGuardedCallback (react-dom.development.js:4277:1)
at beginWork$1 (react-dom.development.js:27451:1)
at performUnitOfWork (react-dom.development.js:26557:1)
at workLoopSync (react-dom.development.js:26466:1)
at renderRootSync (react-dom.development.js:26434:1)

I am trying to create a home page carousel. It is basically 3 divs with articles and I want to be able to manipulate certain things, like the title's font size and placement (with margin top)

My initial code was like this:

const Home = () => {
  const [margin, setMargin] = useState('420px')
  const [font, setFont] = useState('20px')

  function mouseOver (){
    setMargin('320px')
    setFont('40px')
  }

  function mouseOut(){
    setMargin('420px')
    setFont('20px')
  }

  return(
    <div className='carousel'>
      <div className='column' id='column1' onMouseOver={mouseOver} onMouseOut={mouseOut}>
        <p className='title' id='title1' style={{marginTop: margin,fontSize: font ,color:'black'}} > Τitle 1  </p>
        <p className='markdown' id='markdown1'>mark1 </p>
      </div>
      <div className='column' id='column2' onMouseOver={mouseOver} onMouseOut={mouseOut}>
         <p className='title' id='title2' > Τitle 2</p>
         <p className='markdown' id='markdown2'> mark2</p>
      </div>
      <div className='column' id='column3'>
         <p className='title' id='title3' onMouseOver={mouseOver} onMouseOut={mouseOut}> Τitle 3 </p>
         <p className='markdown' id='markdown3'> mark3</p>
      </div>
    </div>
  )
}
  
export default Home;

Every time I hovered over any of the titles, the size of all of them changed because I use the same value and change it in each and every one of them. So I wanted to do it in a more of a react way, cause this just seemed to me like plane html with some react, so here is what I came up with.

const Home = () => {
  const [margin, setMargin] = useState('420px')
  const [font, setFont] = useState('20px')

  function mouseOver(){
    setMargin('320px')
    setFont('40px')
  }

  function mouseOut(){
    setMargin('420px')
    setFont('20px')
  }

  const arrayDivs =[]

  for (let i=0; i<=2; i++) {
    const div = React.createElement(
      'div', //type
      {key: i, className: 'column', id: `column${i+1}` }, //properties of element
      React.createElement(
        'p', //children of element
        {
          key: i,
          className: 'title',
          id: `title${i+1}`,
          style: {
            marginTop: margin,
            fontSize: font
          },
          onMouseOver: mouseOver(),
          onMouseOut:mouseOut()
        }
      ),
      `title${i+1}`
    )  
    arrayDivs.push(div)
  }

  return(
    <div className='carousel'>
      { arrayDivs }
    </div>
  )
}
  
export default Home;

But I run in to this error:

Uncaught Error: Too many re-renders. React limits the number of renders to prevent an infinite loop.
at renderWithHooks (react-dom.development.js:16317:1)
at mountIndeterminateComponent (react-dom.development.js:20074:1)
at beginWork (react-dom.development.js:21587:1)
at HTMLUnknownElement.callCallback (react-dom.development.js:4164:1)
at Object.invokeGuardedCallbackDev (react-dom.development.js:4213:1)
at invokeGuardedCallback (react-dom.development.js:4277:1)
at beginWork$1 (react-dom.development.js:27451:1)
at performUnitOfWork (react-dom.development.js:26557:1)
at workLoopSync (react-dom.development.js:26466:1)
at renderRootSync (react-dom.development.js:26434:1)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

旧人哭 2025-02-15 13:58:38

该代码呈现循环,因为它立即调用处理程序:

for (let i=0; i<=2; i++){
  const div = React.createElement(
    'div', // type
    { key: i, className: 'column', id: `column${i+1}` }, // properties of element
    React.createElement(
      'p', // children of element
      {
        key: i,
        className: 'title',
        id: `title${i+1}`,
        style: { marginTop: margin, fontSize: font },
        onMouseOver: mouseOver(), // <-- immediately invoked
        onMouseOut: mouseOut()    // <-- immediately invoked
      }
    ),
    `title${i+1}`
  );  
  arrayDivs.push(div);
}

您将要传递对 MOUSTOVER Mouseout 处理程序的引用:

{
  key: i,
  className: 'title',
  id: `title${i+1}`,
  style: { marginTop: margin, fontSize: font },
  onMouseOver: mouseOver, // <-- pass reference
  onMouseOut: mouseOut    // <-- pass reference
}

使用 onmouseover onMouseout 处理程序在实践中往往不太好。无论是否被认为是“反应方式”,我都强烈建议使用CSS和A :Hover 规则应用CSS样式。

示例:

css

.column .title {
  margin-top: 420px;
  font-size: 20px;
}

.column:hover .title {
  margin-top: 320px;
  font-size: 40px;
}

.title {
  color: black;
}

home

const Home = () => {
  return(
    <div className='carousel'>
      <div className='column' id='column1'>
        <p className='title' id='title1'>Τitle 1</p>
        <p className='markdown' id='markdown1'>mark1</p>
      </div>
      <div className='column' id='column2'>
        <p className='title' id='title2'>Τitle 2</p>
        <p className='markdown' id='markdown2'>mark2</p>
      </div>
      <div className='column' id='column3'>
        <p className='title' id='title3'>Τitle 3</p>
        <p className='markdown' id='markdown3'>mark3</p>
      </div>
    </div>
  )
}

“

The code is render looping because it is immediately invoking the handlers:

for (let i=0; i<=2; i++){
  const div = React.createElement(
    'div', // type
    { key: i, className: 'column', id: `column${i+1}` }, // properties of element
    React.createElement(
      'p', // children of element
      {
        key: i,
        className: 'title',
        id: `title${i+1}`,
        style: { marginTop: margin, fontSize: font },
        onMouseOver: mouseOver(), // <-- immediately invoked
        onMouseOut: mouseOut()    // <-- immediately invoked
      }
    ),
    `title${i+1}`
  );  
  arrayDivs.push(div);
}

You will want to instead pass a reference to the mouseOver and mouseOut handlers:

{
  key: i,
  className: 'title',
  id: `title${i+1}`,
  style: { marginTop: margin, fontSize: font },
  onMouseOver: mouseOver, // <-- pass reference
  onMouseOut: mouseOut    // <-- pass reference
}

This being said, using the onMouseOver and onMouseOut handlers tend to not work that well in practice. Whether or not it's considered the "React Way" I highly recommend using CSS and a :hover rule to apply the CSS styling.

Example:

CSS

.column .title {
  margin-top: 420px;
  font-size: 20px;
}

.column:hover .title {
  margin-top: 320px;
  font-size: 40px;
}

.title {
  color: black;
}

Home

const Home = () => {
  return(
    <div className='carousel'>
      <div className='column' id='column1'>
        <p className='title' id='title1'>Τitle 1</p>
        <p className='markdown' id='markdown1'>mark1</p>
      </div>
      <div className='column' id='column2'>
        <p className='title' id='title2'>Τitle 2</p>
        <p className='markdown' id='markdown2'>mark2</p>
      </div>
      <div className='column' id='column3'>
        <p className='title' id='title3'>Τitle 3</p>
        <p className='markdown' id='markdown3'>mark3</p>
      </div>
    </div>
  )
}

Edit creating-and-manipulating-components-with-react-hooks

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文