是否可以在NextJS中使用<Loading />
组件而不是nprogress?我认为您需要从路由器事件中访问一些高级道具,例如pageProps
,以便您可以切换加载状态,然后有条件地输出加载组件,但是我看不到这样做的方法。
例如
Router.events.on("routeChangeStart", (url, pageProps) => {
pageProps.loading = true;
});
和渲染中
const { Component, pageProps } = this.props;
return pageProps.loading ? <Loading /> : <Page />;
但是,当然routeChangeStart
不会传入pageProps。
答案 0 :(得分:1)
使用下面的钩子检查路由器的加载状态:
import Router from 'next/router'
import { useState, useEffect } from 'react'
const useRouterLoading = () => {
const [loading, setLoading] = useState(false)
useEffect(() => {
const start = () => setLoading(true)
const end = () => setLoading(false)
Router.events.on('routeChangeStart', start)
Router.events.on('routeChangeComplete', end)
Router.events.on('routeChangeError', end)
return () => {
Router.events.off('routeChangeStart', start)
Router.events.off('routeChangeComplete', end)
Router.events.off('routeChangeError', end)
}
}, [])
return loading
}
答案 1 :(得分:0)
是的,可以使用另一个组件代替nProgress来处理加载。我有一个类似的问题,发现下面的解决方案可以为我解决。
在./pages/_app.js
中执行所有这些操作很有意义,因为according to the documentation可以帮助持久保留页面之间的布局和状态。您可以在生命周期方法componentDidMount
上启动Router事件。重要的是要注意,_app.js
只能安装一次,但是启动路由器事件仍然可以在这里进行。这将使您能够设置状态。
下面是所有这些如何组合的示例:
import React, { Fragment } from 'react';
import App from 'next/app';
import Head from 'next/head';
import Router from 'next/router';
class MyApp extends App {
state = { isLoading: false }
componentDidMount() {
// Logging to prove _app.js only mounts once,
// but initializing router events here will also accomplishes
// goal of setting state on route change
console.log('MOUNT');
Router.events.on('routeChangeStart', () => {
this.setState({ isLoading: true });
});
Router.events.on('routeChangeComplete', () => {
this.setState({ isLoading: false });
});
Router.events.on('routeChangeError', () => {
this.setState({ isLoading: false });
});
}
render() {
const { Component, pageProps } = this.props;
const { isLoading } = this.state;
return (
<Fragment>
<Head>
<title>My App</title>
<meta name="viewport" content="width=device-width, initial-scale=1" />
<meta charSet="utf-8" />
</Head>
{/* You could also pass isLoading state to Component and handle logic there */}
<Component {...pageProps} />
{isLoading && 'STRING OR LOADING COMPONENT HERE...'}
</Fragment>
);
}
}
MyApp.getInitialProps = async ({ Component, ctx }) => {
let pageProps = {};
if (Component.getInitialProps) {
pageProps = await Component.getInitialProps(ctx);
}
return { pageProps };
};
export default MyApp;