在React.js中单击即可在组件之间切换

发布时间:2020-07-07 17:55

我有一个组件可以用作我的单页网站的首页。

我有以下内容:

<div className="flex mb-0 items-center">
        <h2 className="capitalize tracking-tight text-4xl mt-16 mr-8 md:mt-24 font-black hvr-underline-from-left pb-1">
          recent projects
        </h2>
        <h2 className="capitalize tracking-tight text-4xl mt-16 md:mt-24 font-black text-gray-400 hvr-underline-from-left pb-1">
          open source
        </h2>
      </div>
      <Projects />
      <OpenSource />

当前,我的组件显示在彼此下面。我希望能够在两者之间切换,如果用户单击“最近的项目”,它将显示<Projects />组件。如果用户单击“开源”,它将隐藏<Projects />组件并显示<OpenSource/>

我很想创建像幻灯片这样的动画,并带有类似react spring的东西。但是很高兴现在让他们切换。

有什么建议吗?

回答1
import React, { useState, useCallback } from "react";

export default function App() {
  const [activeComponent, setActiveComponent] = useState("projects");

  const modifyActiveComponent = useCallback(
    newActiveComponent => {
      setActiveComponent(newActiveComponent);
    },
    [setActiveComponent]
  );

  return (
    <>
      <div className="flex mb-0 items-center">
        <h2
          onClick={() => modifyActiveComponent("projects")}
          className="capitalize tracking-tight text-4xl mt-16 mr-8 md:mt-24 font-black hvr-underline-from-left pb-1"
        >
          recent projects
        </h2>
        <h2
          onClick={() => modifyActiveComponent("open_source")}
          className="capitalize tracking-tight text-4xl mt-16 md:mt-24 font-black text-gray-400 hvr-underline-from-left pb-1"
        >
          open source
        </h2>
      </div>
      {activeComponent === "projects" && <h1>Projects</h1>}
      {activeComponent === "open_source" && <h1>OpenSource</h1>}
    </>
  );
}

上面,我创建了一个简单的示例来切换两个组件。我使用了useState钩子来保存活动组件。我还为代码添加了useCallback钩子以处理对项目的单击并随后更新了活动组件。

您可以播放演示:https://codesandbox.io/s/lucid-carson-jghdi?file=/src/App.js:0-1042

回答2

我用react转换组https://codesandbox.io/s/epic-curie-nq3wo?file=/src/App.js

在那里您可以看到动画效果,可以定义每个过渡和很多有趣的东西。 (我在.section-exit中做了一个小技巧,以便能够显示出平滑的过渡效果,即position: absolute,没有重叠的部分。

文档: https://github.com/reactjs/react-transition-group

JS: https://codesandbox.io/s/epic-curie-nq3wo?file=/src/App.js

import React, { useState } from "react";
import ReactDOM from "react-dom";
import { CSSTransition } from "react-transition-group";

import "./styles.css";

function App() {
  const sections = ["PROJECTS", "OPENSOURCE"];
  const [activeSection, setActiveSection] = useState(sections[0]);

  const setProject = () => setActiveSection(sections[0]);
  const setOpenSource = () => setActiveSection(sections[1]);
  return (
    <div>
      <button onClick={setProject}>Project</button>
      <button onClick={setOpenSource}>Open Source</button>
      <CSSTransition
        classNames="section"
        in={activeSection === sections[0]}
        timeout={300}
        unmountOnExit
      >
        <h1>Projects</h1>
      </CSSTransition>
      <CSSTransition
        classNames="section"
        in={activeSection === sections[1]}
        timeout={300}
        unmountOnExit
      >
        <h1>Open Source</h1>
      </CSSTransition>
    </div>
  );
}

export default App;

CSS: https://codesandbox.io/s/epic-curie-nq3wo?file=/src/styles.css

.section-enter {
  opacity: 0;
  transform: translateX(100%);
}

.section-enter-active {
  opacity: 1;
  transform: translateX(0);
  transition: opacity 300ms, transform 300ms;
}

.section-exit {
  opacity: 1;
  position: absolute;
}

.section-exit-active {
  opacity: 0;
  transform: translateX(100%);
  transition: opacity 300, transform 300;
}

在那里您可以看到效果。