0

我正在向现有网站添加一些 React 模块。为此,我正在通过 React Portal 安装我的 React 组件。

简而言之,虽然我的组件确实按预期安装,但不会触发动画。例如,他们仍然坚持使用opacityof 0。我希望这些组件opacity 0根据. 1_ 0_1initial animateexit<AnimatePresence>

可以在此处的 CodeSandbox 上找到显示该错误的人为但有效的示例。

CodeSandbox 中的代码如下所示:

索引.html

<!DOCTYPE html>
<html lang="en">
  <head>
   ...
  </head>

  <body>
    <div id="react-root"></div>
    <h1>Static Content</h1>
    <button id="start-portal">Show Modal</button>
    <div id="portal"></div>
  </body>
</html>

上下文.js

import React from "react";

const INITIAL_STATE = {
  activeItem: -1
};

const Context = React.createContext(null);

const ContextProvider = ({ children }) => {
  const [store, setStore] = React.useState(INITIAL_STATE);

  React.useEffect(() => {
    const startEl = document.getElementById("start-portal");
    startEl.addEventListener("click", () => setActiveItem(0));
    return () => {
      startEl.removeEventListener("click", () => setActiveItem(0));
    };
  }, []);

  const setActiveItem = (activeItem) => {
    console.log("SETTING ACTIVE ITEM TO " + activeItem);
    setStore((prevState) => {
      return {
        ...prevState,
        activeItem
      };
    });
  };

  return (
    <Context.Provider
      value={{
        ...store,
        setActiveItem
      }}
    >
      {children}
    </Context.Provider>
  );
};

function useContext() {
  return React.useContext(Context);
}

export { ContextProvider, useContext };

index.js

import React from "react";
import ReactDOM from "react-dom";

import Modal from "./Modal";

import { ContextProvider } from "./Context";

import "./styles.css";

const REACT_ROOT = document.getElementById("react-root");
const PORTAL_ROOT = document.getElementById("portal");

const PortalModal = () => {
  if (!PORTAL_ROOT) return null;
  return ReactDOM.createPortal(<Modal />, PORTAL_ROOT);
};

const App = () => (
  <ContextProvider>
    <PortalModal />
  </ContextProvider>
);

ReactDOM.render(<App />, REACT_ROOT);

模态.js

import React from "react";
import { AnimatePresence, m } from "framer-motion";

import { useContext } from "./Context";

const Modal = () => {
  const { activeItem, setActiveItem } = useContext();

  return (
    <AnimatePresence exitBeforeEnter>
      {activeItem === 0 && (
        <m.div
          key={"step-1"}
          className={"step"}
          initial={{ opacity: 0 }}
          animate={{ opacity: 1 }}
          exit={{ opacity: 0 }}
        >
          <h2>STEP 1</h2>
          <button onClick={() => setActiveItem(-1)}>CLOSE</button>
          <button onClick={() => setActiveItem(1)}>NEXT</button>
        </m.div>
      )}
      {activeItem === 1 && (
        <m.div
          key={"step-2"}
          className={"step"}
          initial={{ opacity: 0 }}
          animate={{ opacity: 1 }}
          exit={{ opacity: 0 }}
        >
          <h2>STEP 2</h2>
          <button onClick={() => setActiveItem(-1)}>CLOSE</button>
          <button onClick={() => setActiveItem(0)}>PREV</button>
        </m.div>
      )}
    </AnimatePresence>
  );
};

export default Modal;

4

1 回答 1

0

您可以从mto motion(在导入和组件中)切换,一切都按预期工作。

m不是 1:1motion的别名,而是精简版。如果你想在m组件中使用动画,你需要导入一个额外的“功能包”,比如domAnimationor domMax

更多信息: Framer.com:减少捆绑包大小

于 2021-11-29T22:18:30.810 回答