React Router 6 - 嵌套路由、路由传递参数

一、嵌套路由

1、基本介绍
  1. 默认情况下,子组件匹配成功,父组件的导航也会高亮,当 NavLink 上添加了 end 属性后,子组件匹配成功,父组件的导航不会高亮

  2. <Outlet> 组件用于,当前 <Route> 产生嵌套时,渲染其对应的后续子路由

2、演示
(1)page
  1. About 页面
tsx 复制代码
export default function About() {
    return <h3>About Content</h3>;
}
  1. Home 页面
tsx 复制代码
import { NavLink, Outlet } from "react-router-dom";

export default function Home() {
    function computedClassName({ isActive }) {
        return isActive ? "my-item active" : "my-item";
    }

    return (
        <div>
            <h3>Home Content</h3>
            <ul>
                <li>
                    <NavLink className={computedClassName} to="news">
                        News
                    </NavLink>
                </li>
                <li>
                    <NavLink className={computedClassName} to="message">
                        Message
                    </NavLink>
                </li>
            </ul>
            <Outlet />
        </div>
    );
}
  1. News 页面
tsx 复制代码
export default function News() {
    return (
        <ul>
            <li>news001</li>
            <li>news002</li>
            <li>news003</li>
        </ul>
    );
}
  1. Message 页面
tsx 复制代码
export default function Message() {
    return (
        <div>
            <ul>
                <li>
                    <a href="/message1">message001</a>&nbsp;&nbsp;
                </li>
                <li>
                    <a href="/message2">message002</a>&nbsp;&nbsp;
                </li>
                <li>
                    <a href="/message3">message003</a>&nbsp;&nbsp;
                </li>
            </ul>
        </div>
    );
}
(2)route
  • index.tsx
tsx 复制代码
import About from "../pages/About";
import Home from "../pages/Home";
import News from "../pages/News";
import Message from "../pages/Message";
import { Navigate } from "react-router-dom";

export default [
    {
        path: "/about",
        element: <About />,
    },
    {
        path: "/home",
        element: <Home />,
        children: [
            {
                path: "news",
                element: <News />,
            },
            {
                path: "message",
                element: <Message />,
            },
        ],
    },
    {
        path: "/",
        element: <Navigate to="/about" />,
    },
];
(3)main
  1. App 组件
tsx 复制代码
import { NavLink, useRoutes } from "react-router-dom";
import routes from "./routes";
import "./App.css";

export default function App() {
    const element = useRoutes(routes);

    function computedClassName({ isActive }) {
        return isActive ? "my-item active" : "my-item";
    }

    return (
        <div>
            <div>
                <NavLink className={computedClassName} to="/about">
                    About
                </NavLink>
                <NavLink className={computedClassName} to="/home">
                    Home
                </NavLink>
            </div>
            <div>{element}</div>
        </div>
    );
}
css 复制代码
.my-item {
    padding: 10px;
    cursor: pointer;
}

.active {
    color: red;
}
  1. index.tsx
tsx 复制代码
import { StrictMode } from "react";
import { createRoot } from "react-dom/client";
import { BrowserRouter } from "react-router-dom";
import App from "./App.tsx";

createRoot(document.getElementById("root")!).render(
    <StrictMode>
        <BrowserRouter>
            <App />
        </BrowserRouter>
    </StrictMode>,
);

二、路由传递参数

1、演示
(1)page
  1. Message 页面
tsx 复制代码
import { useState } from "react";
import { NavLink, Outlet } from "react-router-dom";

export default function Message() {
    const [messages] = useState([
        { id: "01", title: "消息 1" },
        { id: "02", title: "消息 2" },
        { id: "03", title: "消息 3" },
    ]);

    return (
        <div>
            <h3>传递 params 参数</h3>
            <ul>
                {messages.map((item) => (
                    <li key={item.id}>
                        <NavLink to={`/message/detail/${item.id}/${item.title}`}>{item.title}</NavLink>
                    </li>
                ))}
            </ul>

            <h3>传递 search 参数</h3>
            <ul>
                {messages.map((item) => (
                    <li key={item.id}>
                        <NavLink to={`/message/news?id=${item.id}&title=${item.title}`}>{item.title}</NavLink>
                    </li>
                ))}
            </ul>

            <h3>传递 state 参数</h3>
            <ul>
                {messages.map((item) => (
                    <li key={item.id}>
                        <NavLink to="/message/tip" state={{ id: item.id, title: item.title }}>
                            {item.title}
                        </NavLink>
                    </li>
                ))}
            </ul>

            <Outlet />
        </div>
    );
}
  1. Detail 页面
tsx 复制代码
import { useParams, useMatch } from "react-router-dom";

export default function Detail() {
    const { id, title } = useParams();

    // const x1 = useMatch("/message/detail/:id/:title");
    // console.log(x1);
    // const x2 = useMatch("/message/detail/:id");
    // console.log(x2);

    return (
        <ul>
            <li>id: {id}</li>
            <li>title: {title}</li>
        </ul>
    );
}
  1. News 页面
tsx 复制代码
import { useSearchParams, useLocation } from "react-router-dom";

export default function News() {
    const [search, setSearch] = useSearchParams();
    const id = search.get("id");
    const title = search.get("title");

    const x = useLocation();
    console.log(x);

    return (
        <div>
            <button onClick={() => setSearch("id=04&title=消息 4")}>点击更新一下收到的 search 参数</button>
            <ul>
                <li>id: {id}</li>
                <li>title: {title}</li>
            </ul>
        </div>
    );
}
  1. Tip 页面
tsx 复制代码
import { useLocation } from "react-router-dom";

export default function Tip() {
    const {
        state: { id, title },
    } = useLocation();

    return (
        <ul>
            <li>id: {id}</li>
            <li>title: {title}</li>
        </ul>
    );
}
(2)route
  • index.tsx
tsx 复制代码
import Message from "../pages/Message";
import Detail from "../pages/Detail";
import News from "../pages/News";
import Tip from "../pages/Tip";
import { Navigate } from "react-router-dom";

export default [
    {
        path: "/message",
        element: <Message />,
        children: [
            {
                path: "detail/:id/:title",
                element: <Detail />,
            },
            {
                path: "news",
                element: <News />,
            },
            {
                path: "tip",
                element: <Tip />,
            },
        ],
    },
    {
        path: "/",
        element: <Navigate to="/message" />,
    },
];
(3)main
  1. App 组件
tsx 复制代码
import { useRoutes } from "react-router-dom";
import routes from "./routes";

export default function App() {
    const element = useRoutes(routes);

    return <div>{element}</div>;
}
  1. main.tsx
tsx 复制代码
import { StrictMode } from "react";
import { createRoot } from "react-dom/client";
import { BrowserRouter } from "react-router-dom";
import App from "./App.tsx";

createRoot(document.getElementById("root")!).render(
    <StrictMode>
        <BrowserRouter>
            <App />
        </BrowserRouter>
    </StrictMode>,
);
2、补充学习
  1. useParams:用于返回当前匹配路由的 params 参数

  2. useSearchParams:用于读取和修改当前位置的 URL 中的查询字符串,返回一个包含两个值的数组,内容分别为,当前的 search 参数、更新 search 的函数

  3. useMatch:用于匹配当前 URL 是否与指定路径模式匹配,如果不匹配,返回 null

  4. useLocation:用于返回当前 URL 的 location 对象,让开发者能够获取和监听当前路由信息

相关推荐
flash俊杰5 分钟前
ASR 转写与字幕时间轴:强制对齐、CPS 约束与 SRT 工程化
前端
前端炒粉7 分钟前
AI工具面经
前端
唐小码26 分钟前
裁员的风刮到了三线荒凉的城市
前端
晚安日记wanna38 分钟前
React 为何不做双端 diff?Vue 与 React 更新逻辑的三层差异
前端·react.js·面试
flash俊杰41 分钟前
AI 分段引擎与自动剪辑决策:从语义片段到时间线草稿的映射
前端·ai编程
flash俊杰1 小时前
时间线交互引擎:从像素到帧的逆向映射与磁吸网格
前端
光影少年1 小时前
setImmediate 和 setTimeout(0) 的区别
android·前端·react.js·ios·前端框架
flash俊杰1 小时前
LLM 结构化输出的契约化工程:JSON Mode、Schema 约束与重试降级
前端·ai编程
༄久梦༒长醉༻1 小时前
AI面试助手:本地运行,一键备战
前端·ai编程
Web4Browser1 小时前
浏览器指纹逆向到底在分析什么:从 JavaScript 采集、Canvas 与 WebGL 到环境一致性校验
java·服务器·前端