[英]Open a page in a Next.js website as an overlay
我有一个可以搜索的网站。 我希望用户能够单击搜索结果并在覆盖中打开产品而不是重新加载整个页面,但是我希望 url 栏中的 url 成为正确的产品页面,以便用户复制并粘贴它或在新选项卡中打开它,他们将获得产品页面。 我还希望后退按钮在这两种情况下都可以使用。
这是该过程的更详细说明。
起初我以为我可以使用 Next/Router 上的 {shallow:true} 选项来使其工作,但文档特别说这仅适用于同一页面导航(使用不同的查询字符串)。
我唯一的想法是,我可以将链接设置为正确的,但在浏览器中劫持它以在历史 state 中的纯 javascript 中执行某些操作,但我不确定是否可以从等式中删除下一个路由器。
需要明确的是,我不是在寻求产品页面或覆盖本身的帮助,我可以轻松创建在两种情况下显示相同内容的共享组件,特别是我请求帮助的路由和 URL 问题。
任何帮助,即使只是指向正确方向的指针,也将不胜感激。
这是我的做法。
您需要创建一个可选的 catch all route 。 即: pages/search/[[searchParams]].tsx
import { useRouter } from 'next/router';
import { GetServerSidePropsContext } from 'next';
import { ProductsView, ProductDetailsView } from '@/views';
export async function getServerSideProps({
params,
}: GetServerSidePropsContext) {
const [productId = null] = (params?.searchParams as string[]) || [];
return {
props: {
productId,
},
};
}
interface Props {
productId?: string;
}
function SearchProductsPage({ productId }: Props) {
const router = useRouter();
// You could use next/link in your views instead of using next/router
const onViewDetails = (productDetailsId: string) => {
router.push(productDetailsId, `product/${productDetailsId}`).catch((e) => {
console.error(e);
});
};
// Going back to /search will remove the productId and the overlay view will be removed
const onClose = () => {
router.push('/search').catch((e) => {
console.error(e);
});
};
// If you have a productId (catch from URL and received via Props)
// it will render the Product details view which contains the overlay and the product details
return (
<>
<ProductsView onViewDetails={onViewDetails} />
{productId && <ProductDetailsView productId={productId} onClose={onClose} />}
</>
);
}
export default SearchProductsPage;
请注意,路由到/product/${productDetailsId}
而不是product/${productDetailsId}
会给您一个错误。 因此,使用此代码,您最终会得到 URL ,例如/search/product/1
而不是/product/1
。
但是您可以创建一个单独的页面,即pages/product/[productId].tsx
来呈现产品详细信息视图,而不是在叠加层中。
我为您制作了一个代码沙箱,希望对您有所帮助。
https://codesandbox.io/s/overlay-4qhfb-4qhfb
我们使用了两个 React Hook,一个用来保存 state,一个用来处理事件。 我们使用window.history.pushState来处理 URL
我不知道任何 Next.js,但是您可以将History.pushState()
与模态结合使用吗?
您可以在推 URL 时添加 state 吗? 所以你可以跟踪以前的URL。
history.push({
pathname: PATH_NAME,
state: {
from: PREV_URL
},
});
我知道我迟到了,但我从NextJS 文档中找到了另一种可能有用的方法。
在您的情况下,您可以通过这种方式更新您的next.config
文件
module.exports = {
async rewrites() {
return [
{
source: '/product/:id*',
destination: '/search', // The :id parameter isn't used here so will be automatically passed in the query
},
]
},
}
然后在搜索页面中,您可以通过这种方式访问产品的 ID
const router = useRouter();
const { query } = router;
const productID = query?.id;
根据产品 ID 是否可用,您可以显示或隐藏产品模式/叠加层。
这样做可以减少代码开销,您还可以正常使用下一个链接,而无需手动更改路由
希望这可以帮助。 干杯!
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.