首页 > 解决方案 > 如何在反应应用程序中从一页过渡到另一页

问题描述

我正在尝试创建从一页到另一页的过渡屏幕

function MainPage(){    
     
     return ( 
            <div>
                {pagestate.navigating == "true" ? (
                      <FadeIn>
                         <div className="d-flex justify-content-center align-items-center">
                          <h1>signing you in ....</h1>
                          <Link to="/" color="black"  >sign in</Link>

                          {pagestate.loading =="false" ? (
                             <Lottie options={defaultOptions} height={120} width={120} />
                                                 ) : (
                            <Lottie options={defaultOptions2} height={220} width={120} />
                                                )}
                            </div>
                        </FadeIn>
                         ) : (
    <div>
        <h1>hello world</h1>
        <Link to="/" color="black"  >sign in</Link>
   </div>
                                        
        
)}

该代码工作正常,但我希望它在 pagestate.loading =“false”时导航到 /page2。我能够通过使用实现页面导航

  const history = useHistory()

然后像这样调用导航

  history.push('/page2') 

我尝试了几种方法,但无法让它在转换逻辑中工作。在上面的转换逻辑中将加载状态更改为 false 后,如何将导航合并到新页面中?

标签: javascriptreactjs

解决方案


几天前遇到,我找到了一个解决方案,但它有点奇怪,我已经使用 redux 完成了,我制作了一个名为LinkWithAnimation的链接组件,创建了一个减速器作为RouteReducer它将存储当前的转换状态,2状态:第一个是用于过渡。第二个是为了过渡。用 div 包装我的应用程序并传递存储在 redux 中的转换,每次单击LinkWithAnimation都会发生这种情况:调度一个用于转换的动作等待(延迟)直到转换完成(取决于它的持续时间)调度一个动作过渡出去。然后使用History API推送新路径。注意:使用 Redux Thunk。

ActionTypes.js

export const ActionsType = {
    ...otherActions,
    ANIMATION_IN: "animation-in",
    ANIMATION_OUT: "animation-out",
};

ActionsCreator.js

import { ActionsType } from "./ActionsType.js";
import { history } from "../index.js";
export const ActionsCreator = {
    ...otherActionCreators,
    userLogout: () => ({ type: ActionsType.LOGOUT }),
    animateIn: () => ({ type: ActionsType.ANIMATION_IN }),
    animateOut: () => ({ type: ActionsType.ANIMATION_OUT }),
    pageTransition: (duration, path) => {
        return async (dispatch) => {
            const delay = async () => {
                return new Promise((resolve) => setTimeout(resolve, duration));
            };
            dispatch(ActionsCreator.animateOut());
            await delay();
            dispatch(ActionsCreator.animateIn());
            history.push(path);
        };
    },
};

index.js

 import React from "react";
import ReactDOM from "react-dom";
import App from "./App";
import { Router } from "react-router-dom";
import { createBrowserHistory } from "history";
export const history = createBrowserHistory();
ReactDOM.render(
    <Router history={history}>
        <React.StrictMode>
            <App />
        </React.StrictMode>
    </Router>,
    document.getElementById("root")
);

LinkWithAnimation.js

import React, { useRef, useEffect } from "react";
import { Link } from "react-router-dom";
import { ActionsCreator } from "../actions/ActionsCreator.js";
import { connect } from "react-redux";
const LinkWithAnimation = ({
    className,
    additionalFunction,
    PageTransitioning,
    to,
    children,
    style,
    component,
    ReactTo,
    disabled,
}) => {
    const LinkRef = useRef();
    // This Effect To Handle Page Transition Once The User Is Signed In
    useEffect(() => {
        if (ReactTo === true) {
            LinkRef.current.click();
        }
    }, [ReactTo]);

    const componentProp =
        component !== undefined
            ? {
                    component: component,
              }
            : {};
    return (
        <>
            <Link
                onClick={async () => {
                    if (disabled) return;
                    PageTransitioning(230, to);
                    if (additionalFunction !== undefined) {
                        additionalFunction();
                    }
                }}
                ref={LinkRef}
                className={className}
                style={{ ...style }}
                {...componentProp}
            >
                {children}
            </Link>
        </>
    );
};
const mapDispatchToProps = (dispatch) => ({
    PageTransitioning: (duration, path) => {
        dispatch(ActionsCreator.pageTransition(duration, path));
    },
});
export default connect(null, mapDispatchToProps)(LinkWithAnimation);

主.js

import React, { Fragment } from "react";
import { Switch, Route } from "react-router-dom";
import { connect } from "react-redux";
import Homepage from "./Homepage/Homepage.js";
import Signup from "./Signup/Signup.js";
import UserInterface from "./UserInterface/UserInterface.js";
import { SignIn } from "./SignIn/SignIn.js";
import { useRouteTransitionScroll } from "../hooks/useRouteTransitionScroll.js";
const Main = ({ keyframe }) => {
    useRouteTransitionScroll({
        from: "/signup",
        to: "/home",
        scroll_y: 650,
    });
    return (
        <Switch component={Fragment}>
            <div
                style={{
                    animationName: keyframe,
                    animationDuration: "250ms",
                    animationTimingFunction: "linear",
                }}
            >
                <Route path="/mainpage">
                    <UserInterface />
                </Route>
                <Route path="/home">
                    <Homepage />
                </Route>
                <Route path="/signin">
                    <SignIn />
                </Route>
                <Route path="/signup">
                    <Signup />
                </Route>
            </div>
        </Switch>
    );
};
const mapStateToProps = (state) => ({
    keyframe: state.Route.animationName,
});
export default connect(mapStateToProps)(Main);


推荐阅读