# 什么是SPA

包括像vuereact等主流前端框架,目前都是采用单页面应用(single page application)的形式构建一个web应用 单页面顾名思义就是页面开始就一个节点,后面所有的操作都是在这个节点上进行增删改查,动态实现页面的跳转,从而实现页面的切换(路由操作) 本质:根据地址栏变化(不重新想服务器发送请求), 去局部更新不同的页面内容, 完成前端业务场景切换

# 实现单页面功能

主要功能点 支持路由懒加载 支持重定向功能 本文只实现hash模式下的路由侦测

1.html部分:

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <style>
        /* 一堆 CSS 代码, 与简单实现时一样, 这里不做重复书写 */
    </style>
</head>

<body>
    <div class="box">
        <div class="top"> 顶部通栏 </div>
        <div class="bottom">
            <div class="slide">
                <a href="#/pageA">pageA</a>
                <a href="#/pageB">pageB</a>
                <a href="#/pageC">pageC</a>
                <a href="#/pageD">pageD</a>
            </div>
            <div class="content router-view"></div>
        </div>
    </div>

    <!-- 注意使用模块发的方式导入文件 -->
    <script src="./index.js" type="module"></script>
</body>

</html>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

2.router.js:

功能点

1.路由懒加载 2.重定向

const router = [
    {
        name: "/pageA",
        compoment: () => import("./components/templateA.js"),
    },
    {
        name: "/pageB",
        compoment: () => import("./components/templateB.js"),
    },
    {
        name: "/pageC",
        compoment: () => import("./components/templateC.js"),
    },
    {
        name: "/pageD",
        compoment: () => import("./components/templateD.js"),
    },
    {
        // 如果当前的 路由是 /, 那么就重定向到 /pageA
        name: "/",
        redirect: "/pageA",
    },
];

// 导出路由表
export default router;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26

3.index.js:

主要实现hash模式


import router from "./router.js";

// 注册 hash 改变事件
window.onhashchange = hashChangeHandler;
hashChangeHandler();
function hashChangeHandler() {
    const hash = window.location.hash.slice(1) || "/";
    const info = router.find((t) => t.name === hash);

    // 路由表中 重定向的优先级最高
    if (info.redirect) return (window.location.hash = info.redirect);

    // 调用 component 的到一个返回值, 如果是普通引入, 那么这里一定是 undefined, 我们直接 return 即可
    const res = info.compoment();
    if (res === undefined) return;

    // 代码能运行到这里说明我们 调用 component 得到的是一个 promise 对象, 所以我们可以通过 then 方法以及他的参数去调用我们实际导出的内容
    res.then((result) => result.default());
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20

- SPA/components/templateA.js:

const temAHtml = `<div id="pageA">pageA_template</div>`;
const routerView = document.querySelector('.router-view')
function rander () {
    routerView.innerHTML = temAHtml
}
export default rander
1
2
3
4
5
6

- SPA/components/templateB.js:

const temBHtml = `<div id="pageB">pageB_template</div>`;
const routerView = document.querySelector('.router-view')
function rander () {
    routerView.innerHTML = temBHtml
}
export default rander
1
2
3
4
5
6

- SPA/components/templateC.js:

const temCHtml = `<div id="pageC">pageC_template</div>`;
const routerView = document.querySelector('.router-view')
function rander () {
    routerView.innerHTML = temCHtml
}
export default rander
1
2
3
4
5
6

- SPA/components/templateD.js:

const temDHtml = `<div id="pageD">pageD_template</div>`;
const routerView = document.querySelector('.router-view')
function rander () {
    routerView.innerHTML = temDHtml
}
export default rander
1
2
3
4
5
6
最后更新时间: 6/26/2023, 5:05:01 PM