使用useState更改列表中的活动状态

时间:2020-03-23 11:40:42

标签: javascript arrays reactjs

组件

这里是代码示例。我想要的是单击时为每个单独的列表项切换活动状态(是/否)。我不想一次全部更改。

对此有任何帮助吗?预先感谢。

import React, { useState } from "react";

const App = () => {
  const [active, setActive] = useState({});

  const items = [
   { name: 'Item 1' },
   { name: 'Item 2' },
   { name: 'Item 3' }
  ];

  handleClick = (index) => {
    ...
  }

  const list = items.map( (item, index) => {
    return(
      <li 
        key={index} 
        onClick={() => handleClick(index)} 
        className={active ? "active" : null}
     >
        {item.name}
     </li>
    )
  })

  return {
   <>
    <ul>{list}</ul>
   </>
  }
}

export default App;

2 个答案:

答案 0 :(得分:1)

第一个选项-为每个元素引入isActive属性

我会在items中为每个项目引入active属性,并根据点击的项目对其进行操作。需要将其添加到useState中,您可以在其中使用isActive更新.map()属性。

类似如下:

const [items, setItems] = useState([
   { name: 'Item 1', isActive: true },
   { name: 'Item 2', isActive: false },
   { name: 'Item 3', isActive: false }
]);

handleClick = (index) => {
   setItems(prevItems => 
      prevItems.map((e, i) => ({...e, isActive: i === index}))
   );
}

const list = items.map( (item, index) => {
    return(
      <li 
        key={index} 
        onClick={() => handleClick(index)} 
        className={item.isActive ? 'active' : null}
      >
         {item.name}
      </li>
    )
})

return {
   <>
    <ul>{list}</ul>
   </>
}

第二个选项-为点击的活动元素存储index

为被单击的元素存储index可以帮助您在.map()中标识哪个是活动的。因此,只需使用i === index进行简单检查,就可以将active类添加到<li>元素中。

您可以使用indexuseState创建状态,如下所示:

const [index, setIndex] = useState(0);

const items = [
   { name: 'Item 1' },
   { name: 'Item 2' },
   { name: 'Item 3' }
];

handleClick = (i) => {
   setIndex(i);
}

const list = items.map( (item, i) => {
    return(
      <li 
        key={i} 
        onClick={() => handleClick(i)} 
        className={i === index ? 'active' : null}
      >
         {item.name}
      </li>
    )
})

return {
   <>
    <ul>{list}</ul>
   </>
}

我希望这会有所帮助!

答案 1 :(得分:1)

内联添加了评论。

const App = () => {
  // active is active item, initially '' means, nothing selected.
  const [active, setActive] = useState("");

  const items = [{ name: "Item 1" }, { name: "Item 2" }, { name: "Item 3" }];

  const list = items.map(({ name }) => (
    <li
      key={name /* avoid using index for key */}
      onClick={() => setActive(name)}
      className={active === name ? "active" : ""}
    >
      {name}
    </li>
  ));

  // return the Element, not {}
  return (
    <>
      <ul>{list}</ul>
    </>
  );
};

export default App;