@yyp92-cli/template-react-pc 2.2.0 → 2.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (77) hide show
  1. package/CHANGELOG.md +79 -0
  2. package/package.json +1 -4
  3. package/template/.env.development +5 -0
  4. package/template/.env.production +4 -0
  5. package/template/.env.test +4 -0
  6. package/template/.eslintrc.cjs +18 -0
  7. package/template/README.md +15 -0
  8. package/template/gitignore.template +24 -0
  9. package/template/index.html +13 -0
  10. package/template/package.json +42 -0
  11. package/template/pnpm-lock.yaml +3570 -0
  12. package/template/public/vite.svg +1 -0
  13. package/template/src/antdTheme/darkTheme.ts +285 -0
  14. package/template/src/antdTheme/lightTheme.ts +286 -0
  15. package/template/src/app.scss +29 -0
  16. package/template/src/app.tsx +14 -0
  17. package/template/src/assets/iconfont/demo.css +539 -0
  18. package/template/src/assets/iconfont/demo_index.html +211 -0
  19. package/template/src/assets/iconfont/iconfont.css +19 -0
  20. package/template/src/assets/iconfont/iconfont.js +1 -0
  21. package/template/src/assets/iconfont/iconfont.json +16 -0
  22. package/template/src/assets/iconfont/iconfont.ttf +0 -0
  23. package/template/src/assets/iconfont/iconfont.woff +0 -0
  24. package/template/src/assets/iconfont/iconfont.woff2 +0 -0
  25. package/template/src/assets/react.svg +1 -0
  26. package/template/src/components/403/index.tsx +22 -0
  27. package/template/src/components/404/index.tsx +24 -0
  28. package/template/src/components/index.ts +3 -0
  29. package/template/src/components/layout/content/index.module.scss +22 -0
  30. package/template/src/components/layout/content/index.tsx +109 -0
  31. package/template/src/components/layout/footer/index.module.scss +12 -0
  32. package/template/src/components/layout/footer/index.tsx +15 -0
  33. package/template/src/components/layout/header/index.module.scss +21 -0
  34. package/template/src/components/layout/header/index.tsx +115 -0
  35. package/template/src/components/layout/index.module.scss +8 -0
  36. package/template/src/components/layout/index.tsx +47 -0
  37. package/template/src/components/layout/side/index.module.scss +31 -0
  38. package/template/src/components/layout/side/index.tsx +109 -0
  39. package/template/src/components/layout-horizontal/content/index.module.scss +22 -0
  40. package/template/src/components/layout-horizontal/content/index.tsx +105 -0
  41. package/template/src/components/layout-horizontal/footer/index.module.scss +12 -0
  42. package/template/src/components/layout-horizontal/footer/index.tsx +15 -0
  43. package/template/src/components/layout-horizontal/header/index.module.scss +23 -0
  44. package/template/src/components/layout-horizontal/header/index.tsx +115 -0
  45. package/template/src/components/layout-horizontal/index.module.scss +8 -0
  46. package/template/src/components/layout-horizontal/index.tsx +48 -0
  47. package/template/src/components/layout-horizontal/side/index.module.scss +32 -0
  48. package/template/src/components/layout-horizontal/side/index.tsx +104 -0
  49. package/template/src/components/login/index.module.scss +23 -0
  50. package/template/src/components/login/index.tsx +133 -0
  51. package/template/src/global/constants.ts +5 -0
  52. package/template/src/pages/home/index.module.scss +0 -0
  53. package/template/src/pages/home/index.tsx +90 -0
  54. package/template/src/router/router.tsx +190 -0
  55. package/template/src/service/api.ts +9 -0
  56. package/template/src/service/config.ts +9 -0
  57. package/template/src/service/index.ts +1 -0
  58. package/template/src/service/request/index.ts +267 -0
  59. package/template/src/service/request/type.ts +5 -0
  60. package/template/src/service/service.ts +27 -0
  61. package/template/src/store/antdToken.ts +35 -0
  62. package/template/src/store/login.ts +38 -0
  63. package/template/src/store/menus.ts +30 -0
  64. package/template/src/store/permission.ts +30 -0
  65. package/template/src/store/token.ts +30 -0
  66. package/template/src/theme/darkTheme.scss +47 -0
  67. package/template/src/theme/lightTheme.scss +49 -0
  68. package/template/src/utils/base64ToBlob.ts +41 -0
  69. package/template/src/utils/cache.ts +44 -0
  70. package/template/src/utils/changeTheme.ts +14 -0
  71. package/template/src/utils/download.ts +45 -0
  72. package/template/src/utils/filterMenu.ts +34 -0
  73. package/template/src/utils/index.ts +5 -0
  74. package/template/src/vite-env.d.ts +5 -0
  75. package/template/tsconfig.json +45 -0
  76. package/template/tsconfig.node.json +10 -0
  77. package/template/vite.config.ts +49 -0
@@ -0,0 +1,211 @@
1
+ <!DOCTYPE html>
2
+ <html>
3
+ <head>
4
+ <meta charset="utf-8"/>
5
+ <title>iconfont Demo</title>
6
+ <link rel="shortcut icon" href="//img.alicdn.com/imgextra/i4/O1CN01Z5paLz1O0zuCC7osS_!!6000000001644-55-tps-83-82.svg" type="image/x-icon"/>
7
+ <link rel="icon" type="image/svg+xml" href="//img.alicdn.com/imgextra/i4/O1CN01Z5paLz1O0zuCC7osS_!!6000000001644-55-tps-83-82.svg"/>
8
+ <link rel="stylesheet" href="https://g.alicdn.com/thx/cube/1.3.2/cube.min.css">
9
+ <link rel="stylesheet" href="demo.css">
10
+ <link rel="stylesheet" href="iconfont.css">
11
+ <script src="iconfont.js"></script>
12
+ <!-- jQuery -->
13
+ <script src="https://a1.alicdn.com/oss/uploads/2018/12/26/7bfddb60-08e8-11e9-9b04-53e73bb6408b.js"></script>
14
+ <!-- 代码高亮 -->
15
+ <script src="https://a1.alicdn.com/oss/uploads/2018/12/26/a3f714d0-08e6-11e9-8a15-ebf944d7534c.js"></script>
16
+ <style>
17
+ .main .logo {
18
+ margin-top: 0;
19
+ height: auto;
20
+ }
21
+
22
+ .main .logo a {
23
+ display: flex;
24
+ align-items: center;
25
+ }
26
+
27
+ .main .logo .sub-title {
28
+ margin-left: 0.5em;
29
+ font-size: 22px;
30
+ color: #fff;
31
+ background: linear-gradient(-45deg, #3967FF, #B500FE);
32
+ -webkit-background-clip: text;
33
+ -webkit-text-fill-color: transparent;
34
+ }
35
+ </style>
36
+ </head>
37
+ <body>
38
+ <div class="main">
39
+ <h1 class="logo"><a href="https://www.iconfont.cn/" title="iconfont 首页" target="_blank">
40
+ <img width="200" src="https://img.alicdn.com/imgextra/i3/O1CN01Mn65HV1FfSEzR6DKv_!!6000000000514-55-tps-228-59.svg">
41
+
42
+ </a></h1>
43
+ <div class="nav-tabs">
44
+ <ul id="tabs" class="dib-box">
45
+ <li class="dib active"><span>Unicode</span></li>
46
+ <li class="dib"><span>Font class</span></li>
47
+ <li class="dib"><span>Symbol</span></li>
48
+ </ul>
49
+
50
+ <a href="https://www.iconfont.cn/manage/index?manage_type=myprojects&projectId=4984079" target="_blank" class="nav-more">查看项目</a>
51
+
52
+ </div>
53
+ <div class="tab-container">
54
+ <div class="content unicode" style="display: block;">
55
+ <ul class="icon_lists dib-box">
56
+
57
+ <li class="dib">
58
+ <span class="icon iconfont">&#xe6e0;</span>
59
+ <div class="name">全屏</div>
60
+ <div class="code-name">&amp;#xe6e0;</div>
61
+ </li>
62
+
63
+ </ul>
64
+ <div class="article markdown">
65
+ <h2 id="unicode-">Unicode 引用</h2>
66
+ <hr>
67
+
68
+ <p>Unicode 是字体在网页端最原始的应用方式,特点是:</p>
69
+ <ul>
70
+ <li>支持按字体的方式去动态调整图标大小,颜色等等。</li>
71
+ <li>默认情况下不支持多色,直接添加多色图标会自动去色。</li>
72
+ </ul>
73
+ <blockquote>
74
+ <p>注意:新版 iconfont 支持两种方式引用多色图标:SVG symbol 引用方式和彩色字体图标模式。(使用彩色字体图标需要在「编辑项目」中开启「彩色」选项后并重新生成。)</p>
75
+ </blockquote>
76
+ <p>Unicode 使用步骤如下:</p>
77
+ <h3 id="-font-face">第一步:拷贝项目下面生成的 <code>@font-face</code></h3>
78
+ <pre><code class="language-css"
79
+ >@font-face {
80
+ font-family: 'iconfont';
81
+ src: url('iconfont.woff2?t=1753425661104') format('woff2'),
82
+ url('iconfont.woff?t=1753425661104') format('woff'),
83
+ url('iconfont.ttf?t=1753425661104') format('truetype');
84
+ }
85
+ </code></pre>
86
+ <h3 id="-iconfont-">第二步:定义使用 iconfont 的样式</h3>
87
+ <pre><code class="language-css"
88
+ >.iconfont {
89
+ font-family: "iconfont" !important;
90
+ font-size: 16px;
91
+ font-style: normal;
92
+ -webkit-font-smoothing: antialiased;
93
+ -moz-osx-font-smoothing: grayscale;
94
+ }
95
+ </code></pre>
96
+ <h3 id="-">第三步:挑选相应图标并获取字体编码,应用于页面</h3>
97
+ <pre>
98
+ <code class="language-html"
99
+ >&lt;span class="iconfont"&gt;&amp;#x33;&lt;/span&gt;
100
+ </code></pre>
101
+ <blockquote>
102
+ <p>"iconfont" 是你项目下的 font-family。可以通过编辑项目查看,默认是 "iconfont"。</p>
103
+ </blockquote>
104
+ </div>
105
+ </div>
106
+ <div class="content font-class">
107
+ <ul class="icon_lists dib-box">
108
+
109
+ <li class="dib">
110
+ <span class="icon iconfont icon-quanping"></span>
111
+ <div class="name">
112
+ 全屏
113
+ </div>
114
+ <div class="code-name">.icon-quanping
115
+ </div>
116
+ </li>
117
+
118
+ </ul>
119
+ <div class="article markdown">
120
+ <h2 id="font-class-">font-class 引用</h2>
121
+ <hr>
122
+
123
+ <p>font-class 是 Unicode 使用方式的一种变种,主要是解决 Unicode 书写不直观,语意不明确的问题。</p>
124
+ <p>与 Unicode 使用方式相比,具有如下特点:</p>
125
+ <ul>
126
+ <li>相比于 Unicode 语意明确,书写更直观。可以很容易分辨这个 icon 是什么。</li>
127
+ <li>因为使用 class 来定义图标,所以当要替换图标时,只需要修改 class 里面的 Unicode 引用。</li>
128
+ </ul>
129
+ <p>使用步骤如下:</p>
130
+ <h3 id="-fontclass-">第一步:引入项目下面生成的 fontclass 代码:</h3>
131
+ <pre><code class="language-html">&lt;link rel="stylesheet" href="./iconfont.css"&gt;
132
+ </code></pre>
133
+ <h3 id="-">第二步:挑选相应图标并获取类名,应用于页面:</h3>
134
+ <pre><code class="language-html">&lt;span class="iconfont icon-xxx"&gt;&lt;/span&gt;
135
+ </code></pre>
136
+ <blockquote>
137
+ <p>"
138
+ iconfont" 是你项目下的 font-family。可以通过编辑项目查看,默认是 "iconfont"。</p>
139
+ </blockquote>
140
+ </div>
141
+ </div>
142
+ <div class="content symbol">
143
+ <ul class="icon_lists dib-box">
144
+
145
+ <li class="dib">
146
+ <svg class="icon svg-icon" aria-hidden="true">
147
+ <use xlink:href="#icon-quanping"></use>
148
+ </svg>
149
+ <div class="name">全屏</div>
150
+ <div class="code-name">#icon-quanping</div>
151
+ </li>
152
+
153
+ </ul>
154
+ <div class="article markdown">
155
+ <h2 id="symbol-">Symbol 引用</h2>
156
+ <hr>
157
+
158
+ <p>这是一种全新的使用方式,应该说这才是未来的主流,也是平台目前推荐的用法。相关介绍可以参考这篇<a href="">文章</a>
159
+ 这种用法其实是做了一个 SVG 的集合,与另外两种相比具有如下特点:</p>
160
+ <ul>
161
+ <li>支持多色图标了,不再受单色限制。</li>
162
+ <li>通过一些技巧,支持像字体那样,通过 <code>font-size</code>, <code>color</code> 来调整样式。</li>
163
+ <li>兼容性较差,支持 IE9+,及现代浏览器。</li>
164
+ <li>浏览器渲染 SVG 的性能一般,还不如 png。</li>
165
+ </ul>
166
+ <p>使用步骤如下:</p>
167
+ <h3 id="-symbol-">第一步:引入项目下面生成的 symbol 代码:</h3>
168
+ <pre><code class="language-html">&lt;script src="./iconfont.js"&gt;&lt;/script&gt;
169
+ </code></pre>
170
+ <h3 id="-css-">第二步:加入通用 CSS 代码(引入一次就行):</h3>
171
+ <pre><code class="language-html">&lt;style&gt;
172
+ .icon {
173
+ width: 1em;
174
+ height: 1em;
175
+ vertical-align: -0.15em;
176
+ fill: currentColor;
177
+ overflow: hidden;
178
+ }
179
+ &lt;/style&gt;
180
+ </code></pre>
181
+ <h3 id="-">第三步:挑选相应图标并获取类名,应用于页面:</h3>
182
+ <pre><code class="language-html">&lt;svg class="icon" aria-hidden="true"&gt;
183
+ &lt;use xlink:href="#icon-xxx"&gt;&lt;/use&gt;
184
+ &lt;/svg&gt;
185
+ </code></pre>
186
+ </div>
187
+ </div>
188
+
189
+ </div>
190
+ </div>
191
+ <script>
192
+ $(document).ready(function () {
193
+ $('.tab-container .content:first').show()
194
+
195
+ $('#tabs li').click(function (e) {
196
+ var tabContent = $('.tab-container .content')
197
+ var index = $(this).index()
198
+
199
+ if ($(this).hasClass('active')) {
200
+ return
201
+ } else {
202
+ $('#tabs li').removeClass('active')
203
+ $(this).addClass('active')
204
+
205
+ tabContent.hide().eq(index).fadeIn()
206
+ }
207
+ })
208
+ })
209
+ </script>
210
+ </body>
211
+ </html>
@@ -0,0 +1,19 @@
1
+ @font-face {
2
+ font-family: "iconfont"; /* Project id 4984079 */
3
+ src: url('iconfont.woff2?t=1753425661104') format('woff2'),
4
+ url('iconfont.woff?t=1753425661104') format('woff'),
5
+ url('iconfont.ttf?t=1753425661104') format('truetype');
6
+ }
7
+
8
+ .iconfont {
9
+ font-family: "iconfont" !important;
10
+ font-size: 16px;
11
+ font-style: normal;
12
+ -webkit-font-smoothing: antialiased;
13
+ -moz-osx-font-smoothing: grayscale;
14
+ }
15
+
16
+ .icon-quanping:before {
17
+ content: "\e6e0";
18
+ }
19
+
@@ -0,0 +1 @@
1
+ window._iconfont_svg_string_4984079='<svg><symbol id="icon-quanping" viewBox="0 0 1024 1024"><path d="M674.414 394.644l253.292-252.418-0.868 143.044c-0.348 11.864 9.244 22.327 21.106 21.979h15.177c11.864-0.349 21.804-7.326 21.979-19.364l0.699-212.995c0-0.175 0.348-11.338 0.348-11.338 0.175-5.929-1.222-11.338-5.060-15.177-3.838-3.838-9.067-6.279-15.177-6.106l-10.816 0.175c-0.174 0-0.344 0-0.52 0.175l-211.252-0.875c-11.864 0.349-21.804 10.122-21.979 22.156v15.177c1.747 14.129 12.907 22.329 24.77 21.979l139.205 0.349-252.593 251.549c-11.514 11.514-11.514 30.177 0 41.689 11.514 11.688 30.18 11.688 41.693 0h-0.004zM355.18 632.585l-253.465 251.551 0.873-142.352c0.349-11.859-9.248-22.323-21.11-21.979h-16.046c-11.864 0.349-21.804 7.327-21.979 19.365l-0.699 213.17c0 0.175-0.348 11.338-0.348 11.338-0.175 5.936 1.222 11.338 5.055 15.177 3.838 3.838 9.073 6.279 15.177 6.106l10.815-0.175c0.175 0 0.349 0 0.525-0.175l212.125 0.874c11.859-0.349 21.804-10.117 21.979-22.156v-15.176c-1.746-14.129-12.91-22.329-24.775-21.979l-139.206-0.349 252.419-251.543c11.514-11.514 11.514-30.181 0-41.693-11.334-11.688-29.824-11.688-41.34 0.001v0zM985.799 952.339l-0.524-213.17c-0.349-11.865-10.122-19.016-21.98-19.365h-15.176c-11.865-0.344-21.283 10.122-21.111 21.979l0.874 143.049-253.466-252.247c-11.514-11.514-30.18-11.514-41.693 0-11.509 11.513-11.509 30.18 0 41.693l252.422 251.542-139.205 0.349c-11.864-0.349-22.852 8.024-24.774 21.979v15.177c0.348 11.864 10.122 21.804 21.979 22.156l211.253-0.874c0.174 0 0.348 0.175 0.524 0.175l10.816 0.175c5.928 0.174 11.338-2.093 15.176-6.106 3.838-3.838 5.232-9.243 5.056-15.177 0 0-0.175-11.164-0.175-11.338h0.005zM144.282 101.407l139.205-0.349c11.859 0.349 22.848-8.024 24.77-21.979v-15.179c-0.349-11.864-10.117-21.804-21.979-22.156l-212.296 0.874c-0.175 0-0.349-0.175-0.525-0.175l-10.814-0.175c-5.936-0.174-11.338 2.093-15.177 6.106-3.838 3.838-5.237 9.243-5.055 15.177 0 0 0.348 11.164 0.348 11.338l0.52 213.17c0.175 11.86 10.122 19.016 21.979 19.36h16.051c11.864 0.348 21.282-10.117 21.105-21.979l-0.698-142.346 253.296 251.725c11.508 11.514 30.176 11.514 41.688 0 11.514-11.514 11.514-30.18 0-41.693l-252.419-251.716zM144.282 101.407z" fill="#272636" ></path></symbol></svg>',(n=>{var t=(e=(e=document.getElementsByTagName("script"))[e.length-1]).getAttribute("data-injectcss"),e=e.getAttribute("data-disable-injectsvg");if(!e){var c,i,o,l,d,s=function(t,e){e.parentNode.insertBefore(t,e)};if(t&&!n.__iconfont__svg__cssinject__){n.__iconfont__svg__cssinject__=!0;try{document.write("<style>.svgfont {display: inline-block;width: 1em;height: 1em;fill: currentColor;vertical-align: -0.1em;font-size:16px;}</style>")}catch(t){console&&console.log(t)}}c=function(){var t,e=document.createElement("div");e.innerHTML=n._iconfont_svg_string_4984079,(e=e.getElementsByTagName("svg")[0])&&(e.setAttribute("aria-hidden","true"),e.style.position="absolute",e.style.width=0,e.style.height=0,e.style.overflow="hidden",e=e,(t=document.body).firstChild?s(e,t.firstChild):t.appendChild(e))},document.addEventListener?~["complete","loaded","interactive"].indexOf(document.readyState)?setTimeout(c,0):(i=function(){document.removeEventListener("DOMContentLoaded",i,!1),c()},document.addEventListener("DOMContentLoaded",i,!1)):document.attachEvent&&(o=c,l=n.document,d=!1,r(),l.onreadystatechange=function(){"complete"==l.readyState&&(l.onreadystatechange=null,a())})}function a(){d||(d=!0,o())}function r(){try{l.documentElement.doScroll("left")}catch(t){return void setTimeout(r,50)}a()}})(window);
@@ -0,0 +1,16 @@
1
+ {
2
+ "id": "4984079",
3
+ "name": "项目模板",
4
+ "font_family": "iconfont",
5
+ "css_prefix_text": "icon-",
6
+ "description": "",
7
+ "glyphs": [
8
+ {
9
+ "icon_id": "791526",
10
+ "name": "全屏",
11
+ "font_class": "quanping",
12
+ "unicode": "e6e0",
13
+ "unicode_decimal": 59104
14
+ }
15
+ ]
16
+ }
@@ -0,0 +1 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" aria-hidden="true" role="img" class="iconify iconify--logos" width="35.93" height="32" preserveAspectRatio="xMidYMid meet" viewBox="0 0 256 228"><path fill="#00D8FF" d="M210.483 73.824a171.49 171.49 0 0 0-8.24-2.597c.465-1.9.893-3.777 1.273-5.621c6.238-30.281 2.16-54.676-11.769-62.708c-13.355-7.7-35.196.329-57.254 19.526a171.23 171.23 0 0 0-6.375 5.848a155.866 155.866 0 0 0-4.241-3.917C100.759 3.829 77.587-4.822 63.673 3.233C50.33 10.957 46.379 33.89 51.995 62.588a170.974 170.974 0 0 0 1.892 8.48c-3.28.932-6.445 1.924-9.474 2.98C17.309 83.498 0 98.307 0 113.668c0 15.865 18.582 31.778 46.812 41.427a145.52 145.52 0 0 0 6.921 2.165a167.467 167.467 0 0 0-2.01 9.138c-5.354 28.2-1.173 50.591 12.134 58.266c13.744 7.926 36.812-.22 59.273-19.855a145.567 145.567 0 0 0 5.342-4.923a168.064 168.064 0 0 0 6.92 6.314c21.758 18.722 43.246 26.282 56.54 18.586c13.731-7.949 18.194-32.003 12.4-61.268a145.016 145.016 0 0 0-1.535-6.842c1.62-.48 3.21-.974 4.76-1.488c29.348-9.723 48.443-25.443 48.443-41.52c0-15.417-17.868-30.326-45.517-39.844Zm-6.365 70.984c-1.4.463-2.836.91-4.3 1.345c-3.24-10.257-7.612-21.163-12.963-32.432c5.106-11 9.31-21.767 12.459-31.957c2.619.758 5.16 1.557 7.61 2.4c23.69 8.156 38.14 20.213 38.14 29.504c0 9.896-15.606 22.743-40.946 31.14Zm-10.514 20.834c2.562 12.94 2.927 24.64 1.23 33.787c-1.524 8.219-4.59 13.698-8.382 15.893c-8.067 4.67-25.32-1.4-43.927-17.412a156.726 156.726 0 0 1-6.437-5.87c7.214-7.889 14.423-17.06 21.459-27.246c12.376-1.098 24.068-2.894 34.671-5.345a134.17 134.17 0 0 1 1.386 6.193ZM87.276 214.515c-7.882 2.783-14.16 2.863-17.955.675c-8.075-4.657-11.432-22.636-6.853-46.752a156.923 156.923 0 0 1 1.869-8.499c10.486 2.32 22.093 3.988 34.498 4.994c7.084 9.967 14.501 19.128 21.976 27.15a134.668 134.668 0 0 1-4.877 4.492c-9.933 8.682-19.886 14.842-28.658 17.94ZM50.35 144.747c-12.483-4.267-22.792-9.812-29.858-15.863c-6.35-5.437-9.555-10.836-9.555-15.216c0-9.322 13.897-21.212 37.076-29.293c2.813-.98 5.757-1.905 8.812-2.773c3.204 10.42 7.406 21.315 12.477 32.332c-5.137 11.18-9.399 22.249-12.634 32.792a134.718 134.718 0 0 1-6.318-1.979Zm12.378-84.26c-4.811-24.587-1.616-43.134 6.425-47.789c8.564-4.958 27.502 2.111 47.463 19.835a144.318 144.318 0 0 1 3.841 3.545c-7.438 7.987-14.787 17.08-21.808 26.988c-12.04 1.116-23.565 2.908-34.161 5.309a160.342 160.342 0 0 1-1.76-7.887Zm110.427 27.268a347.8 347.8 0 0 0-7.785-12.803c8.168 1.033 15.994 2.404 23.343 4.08c-2.206 7.072-4.956 14.465-8.193 22.045a381.151 381.151 0 0 0-7.365-13.322Zm-45.032-43.861c5.044 5.465 10.096 11.566 15.065 18.186a322.04 322.04 0 0 0-30.257-.006c4.974-6.559 10.069-12.652 15.192-18.18ZM82.802 87.83a323.167 323.167 0 0 0-7.227 13.238c-3.184-7.553-5.909-14.98-8.134-22.152c7.304-1.634 15.093-2.97 23.209-3.984a321.524 321.524 0 0 0-7.848 12.897Zm8.081 65.352c-8.385-.936-16.291-2.203-23.593-3.793c2.26-7.3 5.045-14.885 8.298-22.6a321.187 321.187 0 0 0 7.257 13.246c2.594 4.48 5.28 8.868 8.038 13.147Zm37.542 31.03c-5.184-5.592-10.354-11.779-15.403-18.433c4.902.192 9.899.29 14.978.29c5.218 0 10.376-.117 15.453-.343c-4.985 6.774-10.018 12.97-15.028 18.486Zm52.198-57.817c3.422 7.8 6.306 15.345 8.596 22.52c-7.422 1.694-15.436 3.058-23.88 4.071a382.417 382.417 0 0 0 7.859-13.026a347.403 347.403 0 0 0 7.425-13.565Zm-16.898 8.101a358.557 358.557 0 0 1-12.281 19.815a329.4 329.4 0 0 1-23.444.823c-7.967 0-15.716-.248-23.178-.732a310.202 310.202 0 0 1-12.513-19.846h.001a307.41 307.41 0 0 1-10.923-20.627a310.278 310.278 0 0 1 10.89-20.637l-.001.001a307.318 307.318 0 0 1 12.413-19.761c7.613-.576 15.42-.876 23.31-.876H128c7.926 0 15.743.303 23.354.883a329.357 329.357 0 0 1 12.335 19.695a358.489 358.489 0 0 1 11.036 20.54a329.472 329.472 0 0 1-11 20.722Zm22.56-122.124c8.572 4.944 11.906 24.881 6.52 51.026c-.344 1.668-.73 3.367-1.15 5.09c-10.622-2.452-22.155-4.275-34.23-5.408c-7.034-10.017-14.323-19.124-21.64-27.008a160.789 160.789 0 0 1 5.888-5.4c18.9-16.447 36.564-22.941 44.612-18.3ZM128 90.808c12.625 0 22.86 10.235 22.86 22.86s-10.235 22.86-22.86 22.86s-22.86-10.235-22.86-22.86s10.235-22.86 22.86-22.86Z"></path></svg>
@@ -0,0 +1,22 @@
1
+ import React from 'react';
2
+ import { Button, Result } from 'antd';
3
+
4
+ export const Page403: React.FC = () => {
5
+ return (
6
+ <div
7
+ style={{
8
+ flex: '1',
9
+ display: 'flex',
10
+ justifyContent: 'center',
11
+ alignItems: 'center'
12
+ }}
13
+ >
14
+ <Result
15
+ status="403"
16
+ title="403"
17
+ subTitle="你没有此页面的访问权限。"
18
+ // extra={<Button type="primary">Back Home</Button>}
19
+ />
20
+ </div>
21
+ )
22
+ }
@@ -0,0 +1,24 @@
1
+ import React from 'react';
2
+ import { Button, Result } from 'antd';
3
+
4
+ export const Page404: React.FC = () => {
5
+ return (
6
+ <div
7
+ style={{
8
+ flex: '1',
9
+ display: 'flex',
10
+ justifyContent: 'center',
11
+ alignItems: 'center'
12
+ }}
13
+ >
14
+ <Result
15
+ status="404"
16
+ title="404"
17
+ subTitle="此页面未找到。"
18
+ // extra={<Button type="primary">Back Home</Button>}
19
+ />
20
+ </div>
21
+ )
22
+ }
23
+
24
+
@@ -0,0 +1,3 @@
1
+ export * from "./layout";
2
+ export * from "./404";
3
+ export * from "./403";
@@ -0,0 +1,22 @@
1
+ .layoutContent {
2
+ flex: 1;
3
+ width: 100%;
4
+ height: 100%;
5
+ display: flex;
6
+ }
7
+
8
+ .wraper {
9
+ flex: 1;
10
+ width: 100%;
11
+ height: 100%;
12
+ display: flex;
13
+ flex-direction: column;
14
+ }
15
+
16
+ .contentInner {
17
+ flex: 1;
18
+ display: flex;
19
+ flex-direction: column;
20
+ box-sizing: border-box;
21
+ padding: 16px 20px;
22
+ }
@@ -0,0 +1,109 @@
1
+ import React, { useEffect, useState } from 'react'
2
+ import {Outlet, useLocation, useNavigate} from 'react-router-dom'
3
+ import {Side} from '../side'
4
+ import {Header} from '../header'
5
+ import {Footer} from '../footer'
6
+ import {routerConfig} from '@/router/router'
7
+ import type {RouterConfigItemProps} from '@/router/router'
8
+ import { permissionStore } from '@/store/permission'
9
+ import { tokenStore } from '@/store/token'
10
+ import { menusStore } from '@/store/menus'
11
+
12
+ import styles from './index.module.scss'
13
+
14
+
15
+ interface ContentProps {
16
+ [key: string]: any
17
+ }
18
+
19
+
20
+ const Content: React.FC<ContentProps> = ({}) => {
21
+ const location = useLocation()
22
+ const navigate = useNavigate()
23
+ const {
24
+ permissions
25
+ } = permissionStore()
26
+ const {token} = tokenStore()
27
+ const {menus} = menusStore()
28
+
29
+ const [currentRouter, setCurrentRouter] = useState<RouterConfigItemProps | any>()
30
+
31
+ useEffect(() => {
32
+ const {pathname} = location ?? {}
33
+ const newPathname = pathname.slice(1)
34
+
35
+ if (!token) {
36
+ navigate('/login')
37
+ }
38
+ else if (newPathname !== '') {
39
+ const pathnameList = newPathname.split('/')
40
+ const getCcondition = () => {
41
+ if (pathnameList.length === 1) {
42
+ return permissions.includes(pathnameList[0])
43
+ }
44
+
45
+ if (pathnameList.length === 2) {
46
+ return permissions.includes(pathnameList[1])
47
+ }
48
+
49
+ if (pathnameList.length === 3) {
50
+ return permissions.includes(`${pathnameList[1]}/${pathnameList[2]}`)
51
+ }
52
+
53
+ return false
54
+ }
55
+
56
+ if (getCcondition()) {
57
+ let newCurrentRouter: any = {}
58
+
59
+ if (pathnameList.length === 1) {
60
+ newCurrentRouter = routerConfig[0]?.children?.find((group: any) => group.key === pathnameList[0]) ?? {}
61
+ }
62
+ else if (pathnameList.length === 2) {
63
+ const parent = routerConfig[0]?.children?.find((group: any) => group.key === pathnameList[0]) ?? {}
64
+ newCurrentRouter = parent?.children?.find((item: any) => item.key === pathnameList[1])
65
+ }
66
+ else if (pathnameList.length === 3) {
67
+ const parent = routerConfig[0]?.children?.find((group: any) => group.key === pathnameList[0]) ?? {}
68
+ newCurrentRouter = parent?.children?.find((item: any) => item.key === `${pathnameList[1]}/${pathnameList[2]}`)
69
+ }
70
+
71
+ setCurrentRouter(newCurrentRouter)
72
+ }
73
+ else {
74
+ navigate('/403')
75
+ }
76
+ }
77
+ else {
78
+ navigate(`/${menus[0]?.key}/${menus[0]?.children?.[0]?.key}`)
79
+ }
80
+ }, [location])
81
+
82
+
83
+ // ********** 渲染 **********
84
+ const renderContent = () => {
85
+ if (!currentRouter) {
86
+ return null
87
+ }
88
+
89
+ return (
90
+ <div className={styles.layoutContent}>
91
+ {!currentRouter?.showFullScreen && <Side />}
92
+
93
+ <div className={styles.wraper}>
94
+ {!currentRouter?.showFullScreen && <Header />}
95
+
96
+ <div className={styles.contentInner}>
97
+ <Outlet />
98
+ </div>
99
+
100
+ {!currentRouter?.showFullScreen && <Footer />}
101
+ </div>
102
+ </div>
103
+ )
104
+ }
105
+
106
+ return renderContent()
107
+ }
108
+
109
+ export default Content
@@ -0,0 +1,12 @@
1
+ .footer {
2
+ flex-shrink: 0;
3
+ width: 100%;
4
+ height: 50px;
5
+ box-sizing: border-box;
6
+ border-top: 1px solid var(--border-color-base);
7
+ display: flex;
8
+ justify-content: center;
9
+ align-items: center;
10
+ font-size: 12px;
11
+ background: var(--bg-grey-color);
12
+ }
@@ -0,0 +1,15 @@
1
+ import React from 'react'
2
+
3
+ import styles from './index.module.scss'
4
+
5
+ interface FooterProps {
6
+ [key: string]: any
7
+ }
8
+
9
+ export const Footer: React.FC<FooterProps> = ({}) => {
10
+ return (
11
+ <div className={styles.footer}>
12
+ <div>系统注意事项</div>
13
+ </div>
14
+ )
15
+ }
@@ -0,0 +1,21 @@
1
+ .header {
2
+ box-sizing: border-box;
3
+ flex-shrink: 0;
4
+ width: 100%;
5
+ height: 50px;
6
+ padding: 0 20px;
7
+ display: flex;
8
+ justify-content: space-between;
9
+ align-items: center;
10
+ border-bottom: 1px solid var(--border-color-base);
11
+
12
+ .avatar {
13
+ display: flex;
14
+ align-items: center;
15
+
16
+ & > div {
17
+ margin-left: 10px;
18
+ font-size: 12px;
19
+ }
20
+ }
21
+ }
@@ -0,0 +1,115 @@
1
+ import React, { useState } from 'react'
2
+ import {useNavigate} from 'react-router-dom'
3
+ import { Avatar, Button, Dropdown, Switch, Tooltip } from 'antd'
4
+ import type { MenuProps } from 'antd'
5
+ import { FullscreenExitOutlined, FullscreenOutlined, UserOutlined } from '@ant-design/icons'
6
+ import { getDarkTheme } from '@/utils'
7
+ import { userInfoStore } from '@/store/login'
8
+ import { tokenStore } from '@/store/token'
9
+ import { menusStore } from '@/store/menus'
10
+ import { permissionStore } from '@/store/permission'
11
+ import { antdTokenStore } from '@/store/antdToken'
12
+
13
+ import styles from './index.module.scss'
14
+
15
+ interface HeaderProps {
16
+ [key: string]: any
17
+ }
18
+
19
+ export const Header: React.FC<HeaderProps> = ({ }) => {
20
+ const navigate = useNavigate()
21
+ const {clearUserInfo} = userInfoStore()
22
+ const {setAntdToken} = antdTokenStore()
23
+ const {clearToken} = tokenStore()
24
+ const {clearMenus} = menusStore()
25
+ const {clearPermissions} = permissionStore()
26
+ const [isFullScreen, setIsFullScreen] = useState<boolean>(false)
27
+
28
+
29
+ // ********* 操作 *********
30
+ const handleLogout = () => {
31
+ clearToken()
32
+ clearUserInfo()
33
+ clearMenus()
34
+ clearPermissions()
35
+
36
+ navigate('/login')
37
+ }
38
+
39
+ const handleFullScreen = () => {
40
+ // dom对象的一个属性:可以用来判断当前是不是全屏模式
41
+ // 全屏:true, 不是全屏:false
42
+ const full = document.fullscreenElement
43
+
44
+ if (!full) {
45
+ setIsFullScreen(true)
46
+ document.documentElement.requestFullscreen()
47
+ }
48
+ else {
49
+ setIsFullScreen(false)
50
+ document.exitFullscreen()
51
+ }
52
+ }
53
+
54
+ const handleChangeTheme = (checked: boolean) => {
55
+ getDarkTheme(checked)
56
+ setAntdToken(checked)
57
+ }
58
+
59
+
60
+ // ********* 渲染 *********
61
+ const items: MenuProps['items'] = [
62
+ {
63
+ label: (
64
+ <div
65
+ onClick={handleLogout}
66
+ >退出登录</div>
67
+ ),
68
+ key: '0',
69
+ },
70
+ ]
71
+
72
+
73
+ return (
74
+ <div className={styles.header}>
75
+ <div></div>
76
+
77
+ <div className={styles.avatar}>
78
+ <Tooltip title="切换主题">
79
+ <Switch
80
+ checkedChildren="暗黑"
81
+ unCheckedChildren="明亮"
82
+ defaultChecked={false}
83
+ onChange={handleChangeTheme}
84
+ />
85
+ </Tooltip>
86
+
87
+ <Tooltip title="全屏">
88
+ <Button
89
+ style={{
90
+ margin: '0 10px'
91
+ }}
92
+ shape="circle"
93
+ icon={
94
+ !isFullScreen
95
+ ? <FullscreenOutlined />
96
+ : <FullscreenExitOutlined />
97
+ }
98
+ onClick={handleFullScreen}
99
+ />
100
+ </Tooltip>
101
+
102
+ <Avatar
103
+ style={{ backgroundColor: '#87d068' }}
104
+ icon={<UserOutlined />}
105
+ />
106
+
107
+ <Dropdown
108
+ menu={{ items }}
109
+ >
110
+ <div>{'xxx 已登录'}</div>
111
+ </Dropdown>
112
+ </div>
113
+ </div>
114
+ )
115
+ }
@@ -0,0 +1,8 @@
1
+ .layout {
2
+ width: 100%;
3
+ height: 100%;
4
+ min-width: 1000px;
5
+ display: flex;
6
+ background: var(--bg-white-color);
7
+ color: var(--text-color);
8
+ }