我已经研究了 NextJS 文档中的此页面中描述的模态方法,以及像这样的Stack Overflow问题的答案
,但在所有这些示例中,当刷新页面时,模式就会出现作为自己的路线,背后没有原始内容。有没有一种方法可以设置文件夹结构:有一个页面,例如
/lorem
URL 更改为例如
/lorem/new
我已经成功地使用
layout.tsx
来呈现列表、返回
page.tsx
来处理
null
路线的
/lorem
以及嵌套
new/page.tsx
来呈现模式来实现此目的。然而,这会带来与访问 searchParams 等相关的其他问题,并且通常感觉非常hacky,让布局充当页面并且页面返回 null。因此,更“正确”的方式来做到这一点将是理想的。这也可能不是正确的方法,但它可以在没有充当页面的布局和返回 null 的页面的情况下工作:
例如,创建一个名为
[...slug]
的目录,其中包含 page.js
文件(当然也应该与 page.tsx
一起使用)。所以目录结构看起来像这样:
命名可确保所有路径和子路径都由该 page.js 文件提供服务。在该文件中,您可以获取输入的路径并决定显示或隐藏哪些内容。这是我的示例代码。如果我在
/lorem/new
刷新网站,它仍然显示常规内容和模式。您可能想根据自己的喜好添加样式。
src/app/[...slug]/page.js:
"use client";
import { useRouter } from "next/navigation";
export default function Page({ params }) {
const router = useRouter();
return (
params.slug[0] === "lorem" && (
<main>
<ul>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
<li>regular list content</li>
</ul>
{params.slug.length === 2 && params.slug[1] === "new" ? (
<>
<button onClick={() => router.push("/lorem")}>close modal</button>
<dialog style={{ display: "block" }}>This is only visible in /lorem/new</dialog>
</>
) : (
<button onClick={() => router.push("/lorem/new")}>show modal</button>
)}
</main>
)
);
}
必须考虑的是,显示模式的信息必须以某种方式传递到服务器。在此解决方案中,URL 的
new
部分会发生这种情况。但您也可以使用 searchParams 来实现这一点。