如何将 useState setter 作为函数参数传递?

时间:2021-01-18 22:20:57

标签: javascript reactjs

我有一个代码,可以在单击按钮时在深色主题和浅色主题之间切换,如下所示:

App.js:

import React, { useState } from "react";
import Card from "./Card";
import { ChangeTheme } from "./functions/ChangeTheme";

export default function App() {
  const [theme, setTheme] = useState("dark-theme");

  const changeTheme = (theme) => {
    return theme === "dark-theme" ? setTheme("") : setTheme("dark-theme");
  };

  return (
    <div className="App">
      <Card theme={theme} changeTheme={() => ChangeTheme(theme)} />
    </div>
  );
}

Card.js:

import React from "react";
import "./Card.scss";

const Card = ({ theme, changeTheme }) => {
  return (
    <>
      <div className={theme}>Card title</div>
      <button onClick={changeTheme}>Click me</button>
    </>
  );
};

export default Card;

卡片.scss:

.dark-theme {
  color: green;
}

上面的代码运行良好。这里的工作示例:https://codesandbox.io/s/zealous-water-y1j0o

现在我想将 changeTheme 提取到一个单独的函数中。我试图将 themesetTheme 作为参数传递给 ChangeTheme

ChangeTheme.js

export const ChangeTheme = ({ theme, setTheme }) => {
  return theme === "dark-theme" ? setTheme("") : setTheme("dark-theme");
};

并在 App.js 中像这样使用它:

import React, { useState } from "react";
import Card from "./Card";
import { ChangeTheme } from "./functions/ChangeTheme";

export default function App() {
  const [theme, setTheme] = useState("dark-theme");

  return (
    <div className="App">
      <Card theme={theme} changeTheme={() => ChangeTheme(theme, setTheme)} />
    </div>
  );
}

我收到错误:setTheme is not a function,知道为什么以及如何解决吗?

2 个答案:

答案 0 :(得分:4)

函数的两个参数而不是一个

用代码和盒子更新:)

https://codesandbox.io/s/holy-thunder-tbgd6

并改进条件(三元)运算符

export const changeTheme = (theme, setTheme) => {
  setTheme(theme === "dark-theme" ? "" : "dark-theme");
};

答案 1 :(得分:0)

您需要在 App.js 中将参数作为对象键传递:

// Lacks {}
ChangeTheme(theme, setTheme)

// Change to:
ChangeTheme({theme, setTheme})

因此,App 组件变为:

export default function App() {
  const [theme, setTheme] = useState("dark-theme");

  return (
    <div className="App">
      <Card theme={theme} changeTheme={() => ChangeTheme({theme, setTheme})} />
    </div>
  );
}