Compare commits
No commits in common. "master" and "couter-ajax" have entirely different histories.
master
...
couter-aja
|
@ -96,8 +96,5 @@ module.exports = {
|
|||
net: 'empty',
|
||||
tls: 'empty',
|
||||
child_process: 'empty'
|
||||
},
|
||||
externals: {
|
||||
'AMap': 'AMap'
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
module.exports = {
|
||||
NODE_ENV: '"production"',
|
||||
ENV_CONFIG: '"prod"',
|
||||
BASE_API: '"http://47.106.73.20:8000/"'
|
||||
//BASE_API: '"https://mosq.celex-iot.com:8000/"'
|
||||
BASE_API: '"http://127.0.0.1:8000/"'
|
||||
}
|
||||
|
|
|
@ -8,9 +8,8 @@
|
|||
<title>celex-iot</title>
|
||||
</head>
|
||||
<body>
|
||||
<!-- <script src=<%= htmlWebpackPlugin.options.path %>/tinymce4.7.5/tinymce.min.js></script> -->
|
||||
<script src=<%= htmlWebpackPlugin.options.path %>/tinymce4.7.5/tinymce.min.js></script>
|
||||
<div id="app"></div>
|
||||
<!-- built files will be auto injected -->
|
||||
<script type="text/javascript" src="https://webapi.amap.com/maps?v=1.4.8&key=250fde87c69f9f46d0a2bdbc561a82a8"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
@ -41,15 +41,12 @@
|
|||
"dropzone": "5.2.0",
|
||||
"echarts": "3.8.5",
|
||||
"element-ui": "2.3.2",
|
||||
"eslint-plugin-vue": "^6.2.2",
|
||||
"file-saver": "1.3.3",
|
||||
"font-awesome": "4.7.0",
|
||||
"js-cookie": "2.2.0",
|
||||
"jsonlint": "1.6.3",
|
||||
"jszip": "3.1.5",
|
||||
"mockjs": "1.0.1-beta3",
|
||||
"moment": "^2.27.0",
|
||||
"node-sass": "^7.0.1",
|
||||
"normalize.css": "7.0.0",
|
||||
"nprogress": "0.2.0",
|
||||
"screenfull": "3.3.2",
|
||||
|
@ -58,13 +55,12 @@
|
|||
"simplemde": "1.11.2",
|
||||
"sortablejs": "1.7.0",
|
||||
"vue": "2.5.10",
|
||||
"vue-amap": "^0.5.8",
|
||||
"vue-count-to": "1.0.13",
|
||||
"vue-i18n": "7.3.2",
|
||||
"vue-multiselect": "2.0.8",
|
||||
"vue-router": "3.0.1",
|
||||
"vue-splitpane": "1.0.2",
|
||||
"vuedraggable": "^2.24.1",
|
||||
"vuedraggable": "^2.16.0",
|
||||
"vuex": "3.0.1",
|
||||
"xlsx": "^0.11.16"
|
||||
},
|
||||
|
@ -95,6 +91,7 @@
|
|||
"husky": "0.14.3",
|
||||
"lint-staged": "7.2.0",
|
||||
"node-notifier": "5.1.2",
|
||||
"node-sass": "^4.7.2",
|
||||
"optimize-css-assets-webpack-plugin": "3.2.0",
|
||||
"ora": "1.3.0",
|
||||
"portfinder": "1.0.13",
|
||||
|
@ -102,7 +99,6 @@
|
|||
"postcss-loader": "2.0.9",
|
||||
"postcss-url": "7.3.0",
|
||||
"rimraf": "2.6.2",
|
||||
"sass": "^1.54.4",
|
||||
"sass-loader": "6.0.6",
|
||||
"script-loader": "0.7.2",
|
||||
"semver": "5.4.1",
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
import request from '@/utils/request'
|
||||
|
||||
// device list api
|
||||
export function fetchDeviceList(query) {
|
||||
return request({
|
||||
url: '/api/counter/device/',
|
||||
|
@ -8,82 +7,3 @@ export function fetchDeviceList(query) {
|
|||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// device log list api
|
||||
export function fetchDeviceLogs(query) {
|
||||
request.defaults.timeout = 50000 * 6
|
||||
return request({
|
||||
url: '/api/counter/logs/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// reset timeout
|
||||
request.defaults.timeout = 50000
|
||||
|
||||
// device logs history api
|
||||
export function fetchDeviceLogsHistory(query) {
|
||||
return request({
|
||||
url: '/api/counter/device/daily/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// device info statistic api
|
||||
export function fetchDeviceInfoStatistic(query) {
|
||||
return request({
|
||||
url: '/api/counter/device/status/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// device log statistic api
|
||||
export function fetchDeviceLogStatistic(query) {
|
||||
return request({
|
||||
url: '/api/counter/latest/statistic/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// log statistic history api
|
||||
export function fetchLogStatisticHistory(query) {
|
||||
return request({
|
||||
url: '/api/counter/latest/daily/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// device temp log statistic api
|
||||
|
||||
export function fetchDeviceTempLog(query) {
|
||||
return request({
|
||||
url: '/api/mosq/temp/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// weather device log api
|
||||
|
||||
export function fetchWeatherLog(query) {
|
||||
return request({
|
||||
url: '/api/mosq/weather/',
|
||||
method: 'get',
|
||||
params: query
|
||||
})
|
||||
}
|
||||
|
||||
// device v2 remote control
|
||||
|
||||
export function fetchRemoteControl(deviceID, data) {
|
||||
return request({
|
||||
url: `/api/mosq/device/${deviceID}/mqtt/pub/`,
|
||||
method: 'post',
|
||||
data
|
||||
})
|
||||
}
|
||||
|
|
|
@ -14,7 +14,7 @@ export function loginByUsername(username, password) {
|
|||
|
||||
export function logout() {
|
||||
return request({
|
||||
url: '/api/users/logout/',
|
||||
url: '/api/users/logout',
|
||||
method: 'get'
|
||||
})
|
||||
}
|
||||
|
|
|
@ -1,539 +0,0 @@
|
|||
/* Logo 字体 */
|
||||
@font-face {
|
||||
font-family: "iconfont logo";
|
||||
src: url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834');
|
||||
src: url('https://at.alicdn.com/t/font_985780_km7mi63cihi.eot?t=1545807318834#iefix') format('embedded-opentype'),
|
||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.woff?t=1545807318834') format('woff'),
|
||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.ttf?t=1545807318834') format('truetype'),
|
||||
url('https://at.alicdn.com/t/font_985780_km7mi63cihi.svg?t=1545807318834#iconfont') format('svg');
|
||||
}
|
||||
|
||||
.logo {
|
||||
font-family: "iconfont logo";
|
||||
font-size: 160px;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
/* tabs */
|
||||
.nav-tabs {
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.nav-tabs .nav-more {
|
||||
position: absolute;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
height: 42px;
|
||||
line-height: 42px;
|
||||
color: #666;
|
||||
}
|
||||
|
||||
#tabs {
|
||||
border-bottom: 1px solid #eee;
|
||||
}
|
||||
|
||||
#tabs li {
|
||||
cursor: pointer;
|
||||
width: 100px;
|
||||
height: 40px;
|
||||
line-height: 40px;
|
||||
text-align: center;
|
||||
font-size: 16px;
|
||||
border-bottom: 2px solid transparent;
|
||||
position: relative;
|
||||
z-index: 1;
|
||||
margin-bottom: -1px;
|
||||
color: #666;
|
||||
}
|
||||
|
||||
|
||||
#tabs .active {
|
||||
border-bottom-color: #f00;
|
||||
color: #222;
|
||||
}
|
||||
|
||||
.tab-container .content {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/* 页面布局 */
|
||||
.main {
|
||||
padding: 30px 100px;
|
||||
width: 960px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
.main .logo {
|
||||
color: #333;
|
||||
text-align: left;
|
||||
margin-bottom: 30px;
|
||||
line-height: 1;
|
||||
height: 110px;
|
||||
margin-top: -50px;
|
||||
overflow: hidden;
|
||||
*zoom: 1;
|
||||
}
|
||||
|
||||
.main .logo a {
|
||||
font-size: 160px;
|
||||
color: #333;
|
||||
}
|
||||
|
||||
.helps {
|
||||
margin-top: 40px;
|
||||
}
|
||||
|
||||
.helps pre {
|
||||
padding: 20px;
|
||||
margin: 10px 0;
|
||||
border: solid 1px #e7e1cd;
|
||||
background-color: #fffdef;
|
||||
overflow: auto;
|
||||
}
|
||||
|
||||
.icon_lists {
|
||||
width: 100% !important;
|
||||
overflow: hidden;
|
||||
*zoom: 1;
|
||||
}
|
||||
|
||||
.icon_lists li {
|
||||
width: 100px;
|
||||
margin-bottom: 10px;
|
||||
margin-right: 20px;
|
||||
text-align: center;
|
||||
list-style: none !important;
|
||||
cursor: default;
|
||||
}
|
||||
|
||||
.icon_lists li .code-name {
|
||||
line-height: 1.2;
|
||||
}
|
||||
|
||||
.icon_lists .icon {
|
||||
display: block;
|
||||
height: 100px;
|
||||
line-height: 100px;
|
||||
font-size: 42px;
|
||||
margin: 10px auto;
|
||||
color: #333;
|
||||
-webkit-transition: font-size 0.25s linear, width 0.25s linear;
|
||||
-moz-transition: font-size 0.25s linear, width 0.25s linear;
|
||||
transition: font-size 0.25s linear, width 0.25s linear;
|
||||
}
|
||||
|
||||
.icon_lists .icon:hover {
|
||||
font-size: 100px;
|
||||
}
|
||||
|
||||
.icon_lists .svg-icon {
|
||||
/* 通过设置 font-size 来改变图标大小 */
|
||||
width: 1em;
|
||||
/* 图标和文字相邻时,垂直对齐 */
|
||||
vertical-align: -0.15em;
|
||||
/* 通过设置 color 来改变 SVG 的颜色/fill */
|
||||
fill: currentColor;
|
||||
/* path 和 stroke 溢出 viewBox 部分在 IE 下会显示
|
||||
normalize.css 中也包含这行 */
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.icon_lists li .name,
|
||||
.icon_lists li .code-name {
|
||||
color: #666;
|
||||
}
|
||||
|
||||
/* markdown 样式 */
|
||||
.markdown {
|
||||
color: #666;
|
||||
font-size: 14px;
|
||||
line-height: 1.8;
|
||||
}
|
||||
|
||||
.highlight {
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.markdown img {
|
||||
vertical-align: middle;
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.markdown h1 {
|
||||
color: #404040;
|
||||
font-weight: 500;
|
||||
line-height: 40px;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
|
||||
.markdown h2,
|
||||
.markdown h3,
|
||||
.markdown h4,
|
||||
.markdown h5,
|
||||
.markdown h6 {
|
||||
color: #404040;
|
||||
margin: 1.6em 0 0.6em 0;
|
||||
font-weight: 500;
|
||||
clear: both;
|
||||
}
|
||||
|
||||
.markdown h1 {
|
||||
font-size: 28px;
|
||||
}
|
||||
|
||||
.markdown h2 {
|
||||
font-size: 22px;
|
||||
}
|
||||
|
||||
.markdown h3 {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.markdown h4 {
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.markdown h5 {
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.markdown h6 {
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.markdown hr {
|
||||
height: 1px;
|
||||
border: 0;
|
||||
background: #e9e9e9;
|
||||
margin: 16px 0;
|
||||
clear: both;
|
||||
}
|
||||
|
||||
.markdown p {
|
||||
margin: 1em 0;
|
||||
}
|
||||
|
||||
.markdown>p,
|
||||
.markdown>blockquote,
|
||||
.markdown>.highlight,
|
||||
.markdown>ol,
|
||||
.markdown>ul {
|
||||
width: 80%;
|
||||
}
|
||||
|
||||
.markdown ul>li {
|
||||
list-style: circle;
|
||||
}
|
||||
|
||||
.markdown>ul li,
|
||||
.markdown blockquote ul>li {
|
||||
margin-left: 20px;
|
||||
padding-left: 4px;
|
||||
}
|
||||
|
||||
.markdown>ul li p,
|
||||
.markdown>ol li p {
|
||||
margin: 0.6em 0;
|
||||
}
|
||||
|
||||
.markdown ol>li {
|
||||
list-style: decimal;
|
||||
}
|
||||
|
||||
.markdown>ol li,
|
||||
.markdown blockquote ol>li {
|
||||
margin-left: 20px;
|
||||
padding-left: 4px;
|
||||
}
|
||||
|
||||
.markdown code {
|
||||
margin: 0 3px;
|
||||
padding: 0 5px;
|
||||
background: #eee;
|
||||
border-radius: 3px;
|
||||
}
|
||||
|
||||
.markdown strong,
|
||||
.markdown b {
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
.markdown>table {
|
||||
border-collapse: collapse;
|
||||
border-spacing: 0px;
|
||||
empty-cells: show;
|
||||
border: 1px solid #e9e9e9;
|
||||
width: 95%;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
|
||||
.markdown>table th {
|
||||
white-space: nowrap;
|
||||
color: #333;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
.markdown>table th,
|
||||
.markdown>table td {
|
||||
border: 1px solid #e9e9e9;
|
||||
padding: 8px 16px;
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.markdown>table th {
|
||||
background: #F7F7F7;
|
||||
}
|
||||
|
||||
.markdown blockquote {
|
||||
font-size: 90%;
|
||||
color: #999;
|
||||
border-left: 4px solid #e9e9e9;
|
||||
padding-left: 0.8em;
|
||||
margin: 1em 0;
|
||||
}
|
||||
|
||||
.markdown blockquote p {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
.markdown .anchor {
|
||||
opacity: 0;
|
||||
transition: opacity 0.3s ease;
|
||||
margin-left: 8px;
|
||||
}
|
||||
|
||||
.markdown .waiting {
|
||||
color: #ccc;
|
||||
}
|
||||
|
||||
.markdown h1:hover .anchor,
|
||||
.markdown h2:hover .anchor,
|
||||
.markdown h3:hover .anchor,
|
||||
.markdown h4:hover .anchor,
|
||||
.markdown h5:hover .anchor,
|
||||
.markdown h6:hover .anchor {
|
||||
opacity: 1;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.markdown>br,
|
||||
.markdown>p>br {
|
||||
clear: both;
|
||||
}
|
||||
|
||||
|
||||
.hljs {
|
||||
display: block;
|
||||
background: white;
|
||||
padding: 0.5em;
|
||||
color: #333333;
|
||||
overflow-x: auto;
|
||||
}
|
||||
|
||||
.hljs-comment,
|
||||
.hljs-meta {
|
||||
color: #969896;
|
||||
}
|
||||
|
||||
.hljs-string,
|
||||
.hljs-variable,
|
||||
.hljs-template-variable,
|
||||
.hljs-strong,
|
||||
.hljs-emphasis,
|
||||
.hljs-quote {
|
||||
color: #df5000;
|
||||
}
|
||||
|
||||
.hljs-keyword,
|
||||
.hljs-selector-tag,
|
||||
.hljs-type {
|
||||
color: #a71d5d;
|
||||
}
|
||||
|
||||
.hljs-literal,
|
||||
.hljs-symbol,
|
||||
.hljs-bullet,
|
||||
.hljs-attribute {
|
||||
color: #0086b3;
|
||||
}
|
||||
|
||||
.hljs-section,
|
||||
.hljs-name {
|
||||
color: #63a35c;
|
||||
}
|
||||
|
||||
.hljs-tag {
|
||||
color: #333333;
|
||||
}
|
||||
|
||||
.hljs-title,
|
||||
.hljs-attr,
|
||||
.hljs-selector-id,
|
||||
.hljs-selector-class,
|
||||
.hljs-selector-attr,
|
||||
.hljs-selector-pseudo {
|
||||
color: #795da3;
|
||||
}
|
||||
|
||||
.hljs-addition {
|
||||
color: #55a532;
|
||||
background-color: #eaffea;
|
||||
}
|
||||
|
||||
.hljs-deletion {
|
||||
color: #bd2c00;
|
||||
background-color: #ffecec;
|
||||
}
|
||||
|
||||
.hljs-link {
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
/* 代码高亮 */
|
||||
/* PrismJS 1.15.0
|
||||
https://prismjs.com/download.html#themes=prism&languages=markup+css+clike+javascript */
|
||||
/**
|
||||
* prism.js default theme for JavaScript, CSS and HTML
|
||||
* Based on dabblet (http://dabblet.com)
|
||||
* @author Lea Verou
|
||||
*/
|
||||
code[class*="language-"],
|
||||
pre[class*="language-"] {
|
||||
color: black;
|
||||
background: none;
|
||||
text-shadow: 0 1px white;
|
||||
font-family: Consolas, Monaco, 'Andale Mono', 'Ubuntu Mono', monospace;
|
||||
text-align: left;
|
||||
white-space: pre;
|
||||
word-spacing: normal;
|
||||
word-break: normal;
|
||||
word-wrap: normal;
|
||||
line-height: 1.5;
|
||||
|
||||
-moz-tab-size: 4;
|
||||
-o-tab-size: 4;
|
||||
tab-size: 4;
|
||||
|
||||
-webkit-hyphens: none;
|
||||
-moz-hyphens: none;
|
||||
-ms-hyphens: none;
|
||||
hyphens: none;
|
||||
}
|
||||
|
||||
pre[class*="language-"]::-moz-selection,
|
||||
pre[class*="language-"] ::-moz-selection,
|
||||
code[class*="language-"]::-moz-selection,
|
||||
code[class*="language-"] ::-moz-selection {
|
||||
text-shadow: none;
|
||||
background: #b3d4fc;
|
||||
}
|
||||
|
||||
pre[class*="language-"]::selection,
|
||||
pre[class*="language-"] ::selection,
|
||||
code[class*="language-"]::selection,
|
||||
code[class*="language-"] ::selection {
|
||||
text-shadow: none;
|
||||
background: #b3d4fc;
|
||||
}
|
||||
|
||||
@media print {
|
||||
|
||||
code[class*="language-"],
|
||||
pre[class*="language-"] {
|
||||
text-shadow: none;
|
||||
}
|
||||
}
|
||||
|
||||
/* Code blocks */
|
||||
pre[class*="language-"] {
|
||||
padding: 1em;
|
||||
margin: .5em 0;
|
||||
overflow: auto;
|
||||
}
|
||||
|
||||
:not(pre)>code[class*="language-"],
|
||||
pre[class*="language-"] {
|
||||
background: #f5f2f0;
|
||||
}
|
||||
|
||||
/* Inline code */
|
||||
:not(pre)>code[class*="language-"] {
|
||||
padding: .1em;
|
||||
border-radius: .3em;
|
||||
white-space: normal;
|
||||
}
|
||||
|
||||
.token.comment,
|
||||
.token.prolog,
|
||||
.token.doctype,
|
||||
.token.cdata {
|
||||
color: slategray;
|
||||
}
|
||||
|
||||
.token.punctuation {
|
||||
color: #999;
|
||||
}
|
||||
|
||||
.namespace {
|
||||
opacity: .7;
|
||||
}
|
||||
|
||||
.token.property,
|
||||
.token.tag,
|
||||
.token.boolean,
|
||||
.token.number,
|
||||
.token.constant,
|
||||
.token.symbol,
|
||||
.token.deleted {
|
||||
color: #905;
|
||||
}
|
||||
|
||||
.token.selector,
|
||||
.token.attr-name,
|
||||
.token.string,
|
||||
.token.char,
|
||||
.token.builtin,
|
||||
.token.inserted {
|
||||
color: #690;
|
||||
}
|
||||
|
||||
.token.operator,
|
||||
.token.entity,
|
||||
.token.url,
|
||||
.language-css .token.string,
|
||||
.style .token.string {
|
||||
color: #9a6e3a;
|
||||
background: hsla(0, 0%, 100%, .5);
|
||||
}
|
||||
|
||||
.token.atrule,
|
||||
.token.attr-value,
|
||||
.token.keyword {
|
||||
color: #07a;
|
||||
}
|
||||
|
||||
.token.function,
|
||||
.token.class-name {
|
||||
color: #DD4A68;
|
||||
}
|
||||
|
||||
.token.regex,
|
||||
.token.important,
|
||||
.token.variable {
|
||||
color: #e90;
|
||||
}
|
||||
|
||||
.token.important,
|
||||
.token.bold {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.token.italic {
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
.token.entity {
|
||||
cursor: help;
|
||||
}
|
|
@ -1,630 +0,0 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8"/>
|
||||
<title>IconFont Demo</title>
|
||||
<link rel="shortcut icon" href="https://img.alicdn.com/tps/i4/TB1_oz6GVXXXXaFXpXXJDFnIXXX-64-64.ico" type="image/x-icon"/>
|
||||
<link rel="stylesheet" href="https://g.alicdn.com/thx/cube/1.3.2/cube.min.css">
|
||||
<link rel="stylesheet" href="demo.css">
|
||||
<link rel="stylesheet" href="iconfont.css">
|
||||
<script src="iconfont.js"></script>
|
||||
<!-- jQuery -->
|
||||
<script src="https://a1.alicdn.com/oss/uploads/2018/12/26/7bfddb60-08e8-11e9-9b04-53e73bb6408b.js"></script>
|
||||
<!-- 代码高亮 -->
|
||||
<script src="https://a1.alicdn.com/oss/uploads/2018/12/26/a3f714d0-08e6-11e9-8a15-ebf944d7534c.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<div class="main">
|
||||
<h1 class="logo"><a href="https://www.iconfont.cn/" title="iconfont 首页" target="_blank"></a></h1>
|
||||
<div class="nav-tabs">
|
||||
<ul id="tabs" class="dib-box">
|
||||
<li class="dib active"><span>Unicode</span></li>
|
||||
<li class="dib"><span>Font class</span></li>
|
||||
<li class="dib"><span>Symbol</span></li>
|
||||
</ul>
|
||||
|
||||
<a href="https://www.iconfont.cn/manage/index?manage_type=myprojects&projectId=2058344" target="_blank" class="nav-more">查看项目</a>
|
||||
|
||||
</div>
|
||||
<div class="tab-container">
|
||||
<div class="content unicode" style="display: block;">
|
||||
<ul class="icon_lists dib-box">
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">abb_temperature-cels</div>
|
||||
<div class="code-name">&#xe632;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">humidity</div>
|
||||
<div class="code-name">&#xe82f;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">map</div>
|
||||
<div class="code-name">&#xe683;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">detail</div>
|
||||
<div class="code-name">&#xe620;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">signal-2</div>
|
||||
<div class="code-name">&#xe857;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">signal-1</div>
|
||||
<div class="code-name">&#xe818;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">signal-3</div>
|
||||
<div class="code-name">&#xe81a;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">signal-4</div>
|
||||
<div class="code-name">&#xf60e;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">mosquito.1</div>
|
||||
<div class="code-name">&#xebf6;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">mosquito</div>
|
||||
<div class="code-name">&#xebf5;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_0</div>
|
||||
<div class="code-name">&#xe617;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_1</div>
|
||||
<div class="code-name">&#xe618;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_2</div>
|
||||
<div class="code-name">&#xe619;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_3</div>
|
||||
<div class="code-name">&#xe61a;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_4</div>
|
||||
<div class="code-name">&#xe61b;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_5</div>
|
||||
<div class="code-name">&#xe61c;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_6</div>
|
||||
<div class="code-name">&#xe61d;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_8</div>
|
||||
<div class="code-name">&#xe61e;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_7</div>
|
||||
<div class="code-name">&#xe61f;</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont"></span>
|
||||
<div class="name">power_9</div>
|
||||
<div class="code-name">&#xe625;</div>
|
||||
</li>
|
||||
|
||||
</ul>
|
||||
<div class="article markdown">
|
||||
<h2 id="unicode-">Unicode 引用</h2>
|
||||
<hr>
|
||||
|
||||
<p>Unicode 是字体在网页端最原始的应用方式,特点是:</p>
|
||||
<ul>
|
||||
<li>兼容性最好,支持 IE6+,及所有现代浏览器。</li>
|
||||
<li>支持按字体的方式去动态调整图标大小,颜色等等。</li>
|
||||
<li>但是因为是字体,所以不支持多色。只能使用平台里单色的图标,就算项目里有多色图标也会自动去色。</li>
|
||||
</ul>
|
||||
<blockquote>
|
||||
<p>注意:新版 iconfont 支持多色图标,这些多色图标在 Unicode 模式下将不能使用,如果有需求建议使用symbol 的引用方式</p>
|
||||
</blockquote>
|
||||
<p>Unicode 使用步骤如下:</p>
|
||||
<h3 id="-font-face">第一步:拷贝项目下面生成的 <code>@font-face</code></h3>
|
||||
<pre><code class="language-css"
|
||||
>@font-face {
|
||||
font-family: 'iconfont';
|
||||
src: url('iconfont.eot');
|
||||
src: url('iconfont.eot?#iefix') format('embedded-opentype'),
|
||||
url('iconfont.woff2') format('woff2'),
|
||||
url('iconfont.woff') format('woff'),
|
||||
url('iconfont.ttf') format('truetype'),
|
||||
url('iconfont.svg#iconfont') format('svg');
|
||||
}
|
||||
</code></pre>
|
||||
<h3 id="-iconfont-">第二步:定义使用 iconfont 的样式</h3>
|
||||
<pre><code class="language-css"
|
||||
>.iconfont {
|
||||
font-family: "iconfont" !important;
|
||||
font-size: 16px;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
</code></pre>
|
||||
<h3 id="-">第三步:挑选相应图标并获取字体编码,应用于页面</h3>
|
||||
<pre>
|
||||
<code class="language-html"
|
||||
><span class="iconfont">&#x33;</span>
|
||||
</code></pre>
|
||||
<blockquote>
|
||||
<p>"iconfont" 是你项目下的 font-family。可以通过编辑项目查看,默认是 "iconfont"。</p>
|
||||
</blockquote>
|
||||
</div>
|
||||
</div>
|
||||
<div class="content font-class">
|
||||
<ul class="icon_lists dib-box">
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-aliabb_temperature-cels"></span>
|
||||
<div class="name">
|
||||
abb_temperature-cels
|
||||
</div>
|
||||
<div class="code-name">.el-icon-aliabb_temperature-cels
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alihumidity"></span>
|
||||
<div class="name">
|
||||
humidity
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alihumidity
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alimap"></span>
|
||||
<div class="name">
|
||||
map
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alimap
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alixiangqing"></span>
|
||||
<div class="name">
|
||||
detail
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alixiangqing
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alisignal-2"></span>
|
||||
<div class="name">
|
||||
signal-2
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alisignal-2
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alisignal-1"></span>
|
||||
<div class="name">
|
||||
signal-1
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alisignal-1
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alisignal-3"></span>
|
||||
<div class="name">
|
||||
signal-3
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alisignal-3
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alisignal-4"></span>
|
||||
<div class="name">
|
||||
signal-4
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alisignal-4
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alimosquito1"></span>
|
||||
<div class="name">
|
||||
mosquito.1
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alimosquito1
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alimosquito"></span>
|
||||
<div class="name">
|
||||
mosquito
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alimosquito
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_"></span>
|
||||
<div class="name">
|
||||
power_0
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_1"></span>
|
||||
<div class="name">
|
||||
power_1
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_1
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_2"></span>
|
||||
<div class="name">
|
||||
power_2
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_2
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_3"></span>
|
||||
<div class="name">
|
||||
power_3
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_3
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_4"></span>
|
||||
<div class="name">
|
||||
power_4
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_4
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_5"></span>
|
||||
<div class="name">
|
||||
power_5
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_5
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_6"></span>
|
||||
<div class="name">
|
||||
power_6
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_6
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_8"></span>
|
||||
<div class="name">
|
||||
power_8
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_8
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_7"></span>
|
||||
<div class="name">
|
||||
power_7
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_7
|
||||
</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<span class="icon iconfont el-icon-alipower_9"></span>
|
||||
<div class="name">
|
||||
power_9
|
||||
</div>
|
||||
<div class="code-name">.el-icon-alipower_9
|
||||
</div>
|
||||
</li>
|
||||
|
||||
</ul>
|
||||
<div class="article markdown">
|
||||
<h2 id="font-class-">font-class 引用</h2>
|
||||
<hr>
|
||||
|
||||
<p>font-class 是 Unicode 使用方式的一种变种,主要是解决 Unicode 书写不直观,语意不明确的问题。</p>
|
||||
<p>与 Unicode 使用方式相比,具有如下特点:</p>
|
||||
<ul>
|
||||
<li>兼容性良好,支持 IE8+,及所有现代浏览器。</li>
|
||||
<li>相比于 Unicode 语意明确,书写更直观。可以很容易分辨这个 icon 是什么。</li>
|
||||
<li>因为使用 class 来定义图标,所以当要替换图标时,只需要修改 class 里面的 Unicode 引用。</li>
|
||||
<li>不过因为本质上还是使用的字体,所以多色图标还是不支持的。</li>
|
||||
</ul>
|
||||
<p>使用步骤如下:</p>
|
||||
<h3 id="-fontclass-">第一步:引入项目下面生成的 fontclass 代码:</h3>
|
||||
<pre><code class="language-html"><link rel="stylesheet" href="./iconfont.css">
|
||||
</code></pre>
|
||||
<h3 id="-">第二步:挑选相应图标并获取类名,应用于页面:</h3>
|
||||
<pre><code class="language-html"><span class="iconfont el-icon-alixxx"></span>
|
||||
</code></pre>
|
||||
<blockquote>
|
||||
<p>"
|
||||
iconfont" 是你项目下的 font-family。可以通过编辑项目查看,默认是 "iconfont"。</p>
|
||||
</blockquote>
|
||||
</div>
|
||||
</div>
|
||||
<div class="content symbol">
|
||||
<ul class="icon_lists dib-box">
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-aliabb_temperature-cels"></use>
|
||||
</svg>
|
||||
<div class="name">abb_temperature-cels</div>
|
||||
<div class="code-name">#el-icon-aliabb_temperature-cels</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alihumidity"></use>
|
||||
</svg>
|
||||
<div class="name">humidity</div>
|
||||
<div class="code-name">#el-icon-alihumidity</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alimap"></use>
|
||||
</svg>
|
||||
<div class="name">map</div>
|
||||
<div class="code-name">#el-icon-alimap</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alixiangqing"></use>
|
||||
</svg>
|
||||
<div class="name">detail</div>
|
||||
<div class="code-name">#el-icon-alixiangqing</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alisignal-2"></use>
|
||||
</svg>
|
||||
<div class="name">signal-2</div>
|
||||
<div class="code-name">#el-icon-alisignal-2</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alisignal-1"></use>
|
||||
</svg>
|
||||
<div class="name">signal-1</div>
|
||||
<div class="code-name">#el-icon-alisignal-1</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alisignal-3"></use>
|
||||
</svg>
|
||||
<div class="name">signal-3</div>
|
||||
<div class="code-name">#el-icon-alisignal-3</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alisignal-4"></use>
|
||||
</svg>
|
||||
<div class="name">signal-4</div>
|
||||
<div class="code-name">#el-icon-alisignal-4</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alimosquito1"></use>
|
||||
</svg>
|
||||
<div class="name">mosquito.1</div>
|
||||
<div class="code-name">#el-icon-alimosquito1</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alimosquito"></use>
|
||||
</svg>
|
||||
<div class="name">mosquito</div>
|
||||
<div class="code-name">#el-icon-alimosquito</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_"></use>
|
||||
</svg>
|
||||
<div class="name">power_0</div>
|
||||
<div class="code-name">#el-icon-alipower_</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_1"></use>
|
||||
</svg>
|
||||
<div class="name">power_1</div>
|
||||
<div class="code-name">#el-icon-alipower_1</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_2"></use>
|
||||
</svg>
|
||||
<div class="name">power_2</div>
|
||||
<div class="code-name">#el-icon-alipower_2</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_3"></use>
|
||||
</svg>
|
||||
<div class="name">power_3</div>
|
||||
<div class="code-name">#el-icon-alipower_3</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_4"></use>
|
||||
</svg>
|
||||
<div class="name">power_4</div>
|
||||
<div class="code-name">#el-icon-alipower_4</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_5"></use>
|
||||
</svg>
|
||||
<div class="name">power_5</div>
|
||||
<div class="code-name">#el-icon-alipower_5</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_6"></use>
|
||||
</svg>
|
||||
<div class="name">power_6</div>
|
||||
<div class="code-name">#el-icon-alipower_6</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_8"></use>
|
||||
</svg>
|
||||
<div class="name">power_8</div>
|
||||
<div class="code-name">#el-icon-alipower_8</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_7"></use>
|
||||
</svg>
|
||||
<div class="name">power_7</div>
|
||||
<div class="code-name">#el-icon-alipower_7</div>
|
||||
</li>
|
||||
|
||||
<li class="dib">
|
||||
<svg class="icon svg-icon" aria-hidden="true">
|
||||
<use xlink:href="#el-icon-alipower_9"></use>
|
||||
</svg>
|
||||
<div class="name">power_9</div>
|
||||
<div class="code-name">#el-icon-alipower_9</div>
|
||||
</li>
|
||||
|
||||
</ul>
|
||||
<div class="article markdown">
|
||||
<h2 id="symbol-">Symbol 引用</h2>
|
||||
<hr>
|
||||
|
||||
<p>这是一种全新的使用方式,应该说这才是未来的主流,也是平台目前推荐的用法。相关介绍可以参考这篇<a href="">文章</a>
|
||||
这种用法其实是做了一个 SVG 的集合,与另外两种相比具有如下特点:</p>
|
||||
<ul>
|
||||
<li>支持多色图标了,不再受单色限制。</li>
|
||||
<li>通过一些技巧,支持像字体那样,通过 <code>font-size</code>, <code>color</code> 来调整样式。</li>
|
||||
<li>兼容性较差,支持 IE9+,及现代浏览器。</li>
|
||||
<li>浏览器渲染 SVG 的性能一般,还不如 png。</li>
|
||||
</ul>
|
||||
<p>使用步骤如下:</p>
|
||||
<h3 id="-symbol-">第一步:引入项目下面生成的 symbol 代码:</h3>
|
||||
<pre><code class="language-html"><script src="./iconfont.js"></script>
|
||||
</code></pre>
|
||||
<h3 id="-css-">第二步:加入通用 CSS 代码(引入一次就行):</h3>
|
||||
<pre><code class="language-html"><style>
|
||||
.icon {
|
||||
width: 1em;
|
||||
height: 1em;
|
||||
vertical-align: -0.15em;
|
||||
fill: currentColor;
|
||||
overflow: hidden;
|
||||
}
|
||||
</style>
|
||||
</code></pre>
|
||||
<h3 id="-">第三步:挑选相应图标并获取类名,应用于页面:</h3>
|
||||
<pre><code class="language-html"><svg class="icon" aria-hidden="true">
|
||||
<use xlink:href="#icon-xxx"></use>
|
||||
</svg>
|
||||
</code></pre>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<script>
|
||||
$(document).ready(function () {
|
||||
$('.tab-container .content:first').show()
|
||||
|
||||
$('#tabs li').click(function (e) {
|
||||
var tabContent = $('.tab-container .content')
|
||||
var index = $(this).index()
|
||||
|
||||
if ($(this).hasClass('active')) {
|
||||
return
|
||||
} else {
|
||||
$('#tabs li').removeClass('active')
|
||||
$(this).addClass('active')
|
||||
|
||||
tabContent.hide().eq(index).fadeIn()
|
||||
}
|
||||
})
|
||||
})
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
|
@ -1,107 +0,0 @@
|
|||
@font-face {font-family: "iconfont";
|
||||
src: url('iconfont.eot?t=1600056086767'); /* IE9 */
|
||||
src: url('iconfont.eot?t=1600056086767#iefix') format('embedded-opentype'), /* IE6-IE8 */
|
||||
url('data:application/x-font-woff2;charset=utf-8;base64,d09GMgABAAAAAAqMAAsAAAAAGIwAAAo8AAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAHEIGVgCFQgqgAJojATYCJANUCywABCAFhG0HggEbuBQRVax7JfuiwHZ0swRH1LDmfOLN8X+pLdU8D+KBfr/25751aeAJNtJ9Og0ymSHT2NBgOlE1ksiEpl/vVxkeN/PfI0mFYFoJUjun9VNK1QM5h94KJ2Jhc9gcqRr0xIVekc3Z9v9EjP9d0zLrqI5LZEce7eFPmqNw4fk5PSE3YSbkhBwDOJjcN0AAQdj55l5tktcrga0juLJw7CobZT/QBYrIsq9CAgpFBIp9eRN6alZ+OSXnPSusNoZVxEXHU12bgKJB08CF0moSxEhjVECO1ZXLm0GMy1M6RiPIu2RD5szcha8DTD55ifEAAJv624cvIDPEAIlMCrB1LVpKWoDuM+lvHISO0GAx8hKgy/PHeT5S6AHShLvQwFuAmKin08Ww/KgtAHTxDt9SNio/S/ks87NnvpB9EfeF5gvq699+u5EIUQqZXytjnQVdk/i2pgBKyiqqaur4BIRQbVCNv+bJSWQUFeQJWUDblZnILNpAlEpIiSiDlIlySIUYB6kS4yE1YoK7+ptJBKQBRALSBKIC0gKiEpImpvDrZzLhLoB5BpAUH2XusjoTB3c5MBq4S8BQgGT48qu7IpjfACnwn8PfL4F01DkmALMAZJoAZJ8BY3d0lOV0euVkDlLSAq2Ybromk02KZcnFQhxnsWMJvowHZSwW5LHudjlRGV/8XCiEyRi8ktA1nnN6QtF9zQi7n+QG/enoBX8gMMsTwO1pt0OhoBZ0+vzB2d4gtB6fGo/1hHKGLspRuSewnHnqEgF7LufhJx8m4tZjl+4xmbY7F44A0D968S6O2+9fPg6ZnQ8sJ3z0uH3C+oS0udo73CNDTkCPUterkIFQ2c2AinG34Cqg/ZC3BbcPQwtCIao/WClBui/ZLiQwRHf8ykBgEeIes3sAY/dqQ9aRfeoJ0XN9aXtQ4vDL2jz2sflWgYv2y2tvh5L6b8Mp+wK7/X4yENDjhS0xGJx/6pL1sv0ifYHqSqRQ0uBi2kTqFJjeidulaQMacllUM8WPNXqHPhgkHSdSLwUNwaCIyWjefXKe8yBAt+c6zjA5p7SuQxDrye84j6/nlIzQE86dDgsGDRtsEleHlHIPifWKBU+riHQMSwzPX8uyea1jUrbTQ4+Sdn7mcqZtFDD6nkHKMAYRq9fkBgCDNlHVSsuPA2gLY+DXBaKw6KvYHfSXU24ple+2umyieoeIJKG7I856LRe222TgxBXQJQcGg9UlMbhcDodYr3fKYe4FyTMq+uDkoZtDvsw0MekAvf7iQTolFEqi5Bf8yk5/crK0TifulI6F2BQacWegwGOfet1KSA8GyE5S7GKx3Q3dLslwkOgPauP1fQH9iDX1VlBdx1dIhwJ6++2p59X9ux/5yYYRc+M7+o/lQtewDgBujvTKDQaXREsCaPG8RlkKBqsdBxLoeeluh/JIh+iY4HDQTvxCiLEr/bUOSUdCST1XIpQhsS+Q4nRfiWuEFNnrRJIX9zjtyUCJ/XbaZdh9iMIx5k64Dthd6wLfjeC+4l7/L5KMzivZu05dI7Ce63m7T15NpNgYK6E0cjEOkUY+xiPSKMQExHl2Y7uG/O/SZd3lr5ZBvO3IETxxuMxYzrz/7f0C5tp8Iwsq9ejSSQ3atyviJomy7i2qT9kev/XixZ3GhsQGTvwpQpeSdMA1EusvSN3qKtrJHPknvjYsFBZE0DfRiE6YzkV1hKXdTAgJc7uFeFNhtocxK3Qod9o/tL6Rb6HBkraP+dXGzA8EksNMNh/8+E9eegwtKdGlyyWIjtWKqsozkxeWli5INi9IKS2xtpgJyn6XUnDrVkjhc0xVQ/cZ35V+x7g/WDWnGYdU0FYyZzk42coinuOvF5I5H4R933KQbS8oRMlFSUI6ZDLYnrS9aak215ydTZakjc3KybpSoiouEuxedWPVrpU3djPsXYPkty1V0GyG1TE1L/0vdoUmZsVLX8aWw2qzuRqC+yK+5LPDn0pbMs+4qz5rDvL4v18znam90FX4Gfee5/vSCyZN1HqTcAuvl5KPjQsl3jKFjfgp26YKbJx98XW1uTymqvA1VlFqd9R6kDWmCSsjctkWDiPSJ225Le+HXulTJS21cMUKWLsF1qxYWQtbai4YgyM42ndfAzdN8A7Yp5z58uQZa9urb4VOjh5Niff8cG/k9dbXXb7+EdbgYW4WkRk+HM4ksjh9jvxccJ5v4vA5tBTqHuzLJ/aKh0s7Bof3P6qXgf7xCHSOoKN/jAWAqx8xmLtSVJbyfrZnQxGJZp6OlLDbOMXqekxzYlcl0rkPylVRuUApN6+UIX8i/tuvGWBAQVZR8TXPtGKNLnMYI9cUtb2bU5r0kK3a37xvTFUG9ykssywqRyyRd/oOUDLgWl/qfCJ5ojqkTtGWdhXOlSZvQeqRcE0jtkx35PNZeviejcwmD7zfNOtz3RFyd2vI7xA+L2oLJppb0qUtTVFXhyaS5xOpWp8BB8Pu5J0msDKdRTVrxb7EMqj6pvkhex6Y87v454yySF46o0miPWcx8O/z9Z4sdN6ZZl0bDMcWxp4XnFfjwrCtWfcIR7M8+tgTMFi05yRNpTOK5GeUV/70oPm+9d+qTWZhrF59IhHTjL1I5zgSA3PO9aj5SZK75DtJ8N+XnbLqoYi2TjCl6Og/U0lwe2fp3NKdmh859R+P2xRB4Moim395rW7Ly//CpKZ33pHMV0fPuW5gVn289IuaMSzxhF4tNwvr1R/s9+WjHjA2xew1m+u9XlhuNJbBhUdAGTQZYblb1kQYh00HyBEC1kkv8kN6SLv0n4jJLYFsuVdO9mPvY7LrvHVkj3vHyc735pN933uf7N+9v5NNeSmugbyydkuZZiPyB4j8F+kj/yIvAaBrfITs13Ij3yAr8VeorWER0Ad10AQ+QGsyfAyAIfgVrZeRX5CNCW8iXyOr8WNEUwgNwQ+FsawtWPqxkTv31xj8v0PMw3MsCeW1n5uOi0h5SVRQ4GdBqej5kf8AyC1dRAx13u7SfefrVM4W/EsoJ0HaCXLL/Bp0OrpAdHyCIm/DD4TQpg/b4dr58vUP8i7BWS+RM6CXkjeOp0FPL6NkSi8rb1qvaBLvef6qLikrvRFSqWufRC+t5Usvo+EbZcPAL8oB/OnlDfxLClApq1fxUXeJVcNo5V6Co8FH7hlRjyVY+OiKkfMFiIkcSUXHiT5AKsoSNB1NPinPkIAsYxp1IDOtMcKSxeiJTAFRxBCXLABPj/ZI5rvxGF+nHXksTlXck4BDq0Z9iOtsnfIwCdyxVvG9/gtAGBGHjKnwaf0DkBQ6eGRqZJICf6aTVBW2Jb9yQMxo6o8hWVxiYsgT9QcRT2QQHj5aAHi0kX2OeG5nTBvCaelR/Wy8DejU4quU3Uy/jCQrqqYbpmU7rudr6+jq6RuE3l3X0hDzadmakXDnQaRKexNTn+pzNnZ4+USdhAgqS5YUJYkT3c0M2ansfMJFOWZKGKrZtHQqUuDsCNIqauz0BGZgDhZgCVZgA9YB21QKAAAA') format('woff2'),
|
||||
url('iconfont.woff?t=1600056086767') format('woff'),
|
||||
url('iconfont.ttf?t=1600056086767') format('truetype'), /* chrome, firefox, opera, Safari, Android, iOS 4.2+ */
|
||||
url('iconfont.svg?t=1600056086767#iconfont') format('svg'); /* iOS 4.1- */
|
||||
}
|
||||
|
||||
.iconfont {
|
||||
font-family: "iconfont" !important;
|
||||
font-size: 16px;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
[class^="el-icon-ali"],
|
||||
[class*=" el-icon-ali"]/*这里有空格*/
|
||||
{
|
||||
font-family: "iconfont" !important;
|
||||
font-size: 16px;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
.el-icon-aliabb_temperature-cels:before {
|
||||
content: "\e632";
|
||||
}
|
||||
|
||||
.el-icon-alihumidity:before {
|
||||
content: "\e82f";
|
||||
}
|
||||
|
||||
.el-icon-alimap:before {
|
||||
content: "\e683";
|
||||
}
|
||||
|
||||
.el-icon-alixiangqing:before {
|
||||
content: "\e620";
|
||||
}
|
||||
|
||||
.el-icon-alisignal-2:before {
|
||||
content: "\e857";
|
||||
}
|
||||
|
||||
.el-icon-alisignal-1:before {
|
||||
content: "\e818";
|
||||
}
|
||||
|
||||
.el-icon-alisignal-3:before {
|
||||
content: "\e81a";
|
||||
}
|
||||
|
||||
.el-icon-alisignal-4:before {
|
||||
content: "\f60e";
|
||||
}
|
||||
|
||||
.el-icon-alimosquito1:before {
|
||||
content: "\ebf6";
|
||||
}
|
||||
|
||||
.el-icon-alimosquito:before {
|
||||
content: "\ebf5";
|
||||
}
|
||||
|
||||
.el-icon-alipower_:before {
|
||||
content: "\e617";
|
||||
}
|
||||
|
||||
.el-icon-alipower_1:before {
|
||||
content: "\e618";
|
||||
}
|
||||
|
||||
.el-icon-alipower_2:before {
|
||||
content: "\e619";
|
||||
}
|
||||
|
||||
.el-icon-alipower_3:before {
|
||||
content: "\e61a";
|
||||
}
|
||||
|
||||
.el-icon-alipower_4:before {
|
||||
content: "\e61b";
|
||||
}
|
||||
|
||||
.el-icon-alipower_5:before {
|
||||
content: "\e61c";
|
||||
}
|
||||
|
||||
.el-icon-alipower_6:before {
|
||||
content: "\e61d";
|
||||
}
|
||||
|
||||
.el-icon-alipower_8:before {
|
||||
content: "\e61e";
|
||||
}
|
||||
|
||||
.el-icon-alipower_7:before {
|
||||
content: "\e61f";
|
||||
}
|
||||
|
||||
.el-icon-alipower_9:before {
|
||||
content: "\e625";
|
||||
}
|
||||
|
|
@ -1,149 +0,0 @@
|
|||
{
|
||||
"id": "2058344",
|
||||
"name": "eleThirdIcon",
|
||||
"font_family": "iconfont",
|
||||
"css_prefix_text": "el-icon-ali",
|
||||
"description": "",
|
||||
"glyphs": [
|
||||
{
|
||||
"icon_id": "7658801",
|
||||
"name": "abb_temperature-cels",
|
||||
"font_class": "abb_temperature-cels",
|
||||
"unicode": "e632",
|
||||
"unicode_decimal": 58930
|
||||
},
|
||||
{
|
||||
"icon_id": "17013987",
|
||||
"name": "humidity",
|
||||
"font_class": "humidity",
|
||||
"unicode": "e82f",
|
||||
"unicode_decimal": 59439
|
||||
},
|
||||
{
|
||||
"icon_id": "691221",
|
||||
"name": "map",
|
||||
"font_class": "map",
|
||||
"unicode": "e683",
|
||||
"unicode_decimal": 59011
|
||||
},
|
||||
{
|
||||
"icon_id": "13738103",
|
||||
"name": "detail",
|
||||
"font_class": "xiangqing",
|
||||
"unicode": "e620",
|
||||
"unicode_decimal": 58912
|
||||
},
|
||||
{
|
||||
"icon_id": "10023646",
|
||||
"name": "signal-2",
|
||||
"font_class": "signal-2",
|
||||
"unicode": "e857",
|
||||
"unicode_decimal": 59479
|
||||
},
|
||||
{
|
||||
"icon_id": "10248563",
|
||||
"name": "signal-1",
|
||||
"font_class": "signal-1",
|
||||
"unicode": "e818",
|
||||
"unicode_decimal": 59416
|
||||
},
|
||||
{
|
||||
"icon_id": "10248566",
|
||||
"name": "signal-3",
|
||||
"font_class": "signal-3",
|
||||
"unicode": "e81a",
|
||||
"unicode_decimal": 59418
|
||||
},
|
||||
{
|
||||
"icon_id": "14536693",
|
||||
"name": "signal-4",
|
||||
"font_class": "signal-4",
|
||||
"unicode": "f60e",
|
||||
"unicode_decimal": 62990
|
||||
},
|
||||
{
|
||||
"icon_id": "7757423",
|
||||
"name": "mosquito.1",
|
||||
"font_class": "mosquito1",
|
||||
"unicode": "ebf6",
|
||||
"unicode_decimal": 60406
|
||||
},
|
||||
{
|
||||
"icon_id": "7757432",
|
||||
"name": "mosquito",
|
||||
"font_class": "mosquito",
|
||||
"unicode": "ebf5",
|
||||
"unicode_decimal": 60405
|
||||
},
|
||||
{
|
||||
"icon_id": "6697986",
|
||||
"name": "power_0",
|
||||
"font_class": "power_",
|
||||
"unicode": "e617",
|
||||
"unicode_decimal": 58903
|
||||
},
|
||||
{
|
||||
"icon_id": "6697988",
|
||||
"name": "power_1",
|
||||
"font_class": "power_1",
|
||||
"unicode": "e618",
|
||||
"unicode_decimal": 58904
|
||||
},
|
||||
{
|
||||
"icon_id": "6697989",
|
||||
"name": "power_2",
|
||||
"font_class": "power_2",
|
||||
"unicode": "e619",
|
||||
"unicode_decimal": 58905
|
||||
},
|
||||
{
|
||||
"icon_id": "6697991",
|
||||
"name": "power_3",
|
||||
"font_class": "power_3",
|
||||
"unicode": "e61a",
|
||||
"unicode_decimal": 58906
|
||||
},
|
||||
{
|
||||
"icon_id": "6697992",
|
||||
"name": "power_4",
|
||||
"font_class": "power_4",
|
||||
"unicode": "e61b",
|
||||
"unicode_decimal": 58907
|
||||
},
|
||||
{
|
||||
"icon_id": "6697993",
|
||||
"name": "power_5",
|
||||
"font_class": "power_5",
|
||||
"unicode": "e61c",
|
||||
"unicode_decimal": 58908
|
||||
},
|
||||
{
|
||||
"icon_id": "6697994",
|
||||
"name": "power_6",
|
||||
"font_class": "power_6",
|
||||
"unicode": "e61d",
|
||||
"unicode_decimal": 58909
|
||||
},
|
||||
{
|
||||
"icon_id": "6697995",
|
||||
"name": "power_8",
|
||||
"font_class": "power_8",
|
||||
"unicode": "e61e",
|
||||
"unicode_decimal": 58910
|
||||
},
|
||||
{
|
||||
"icon_id": "6697996",
|
||||
"name": "power_7",
|
||||
"font_class": "power_7",
|
||||
"unicode": "e61f",
|
||||
"unicode_decimal": 58911
|
||||
},
|
||||
{
|
||||
"icon_id": "6697997",
|
||||
"name": "power_9",
|
||||
"font_class": "power_9",
|
||||
"unicode": "e625",
|
||||
"unicode_decimal": 58917
|
||||
}
|
||||
]
|
||||
}
|
|
@ -1,86 +0,0 @@
|
|||
<?xml version="1.0" standalone="no"?>
|
||||
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" >
|
||||
<!--
|
||||
2013-9-30: Created.
|
||||
-->
|
||||
<svg>
|
||||
<metadata>
|
||||
Created by iconfont
|
||||
</metadata>
|
||||
<defs>
|
||||
|
||||
<font id="iconfont" horiz-adv-x="1024" >
|
||||
<font-face
|
||||
font-family="iconfont"
|
||||
font-weight="500"
|
||||
font-stretch="normal"
|
||||
units-per-em="1024"
|
||||
ascent="896"
|
||||
descent="-128"
|
||||
/>
|
||||
<missing-glyph />
|
||||
|
||||
<glyph glyph-name="abb_temperature-cels" unicode="" d="M255.209807 191.012258V637.62942H191.407355v-446.617162a102.721947 102.721947 0 0 1-71.458746-95.703677 103.359972 103.359972 0 0 1 206.719943 0A102.721947 102.721947 0 0 1 255.209807 191.012258zM382.81471 765.234323v9.570368A169.076497 169.076497 0 0 1 262.228076 892.839227 174.180693 174.180693 0 0 1 63.802452 776.08074v-524.456153a223.308581 223.308581 0 0 1 15.950613-327.306577 225.222654 225.222654 0 0 1 144.19354-52.31801 213.100189 213.100189 0 0 1 39.55752 3.828147A222.670556 222.670556 0 0 1 382.81471 251.624587z m0-701.826968a159.506129 159.506129 0 0 0-259.675978-93.789604A161.420203 161.420203 0 0 0 63.802452 95.308581a158.868105 158.868105 0 0 0 52.956035 118.67256l10.846416 24.244932V758.854078A110.378241 110.378241 0 0 0 248.191537 829.036775 102.083923 102.083923 0 0 0 319.012258 760.130127v-521.904054l10.846417-24.244932A160.144154 160.144154 0 0 0 382.81471 63.407355zM870.903465 382.419613h-19.140735A86.771334 86.771334 0 0 0 765.62942 468.552923v146.745639A86.771334 86.771334 0 0 0 851.76273 701.431872h19.140735A86.771334 86.771334 0 0 0 957.036775 615.298562h63.802452A149.935761 149.935761 0 0 1 870.903465 765.234323h-19.140735A149.935761 149.935761 0 0 1 701.826968 615.298562v-146.745639A149.935761 149.935761 0 0 1 851.76273 318.617162h19.140735A149.935761 149.935761 0 0 1 1020.839227 468.552923h-63.802452A86.771334 86.771334 0 0 0 870.903465 382.419613zM606.123291 892.839227A95.703677 95.703677 0 1 1 701.826968 797.135549 95.703677 95.703677 0 0 1 606.123291 892.839227z m0-127.604904a31.901226 31.901226 0 1 0 31.901226 31.901226 31.901226 31.901226 0 0 0-31.901226-31.901226z" horiz-adv-x="1024" />
|
||||
|
||||
|
||||
<glyph glyph-name="humidity" unicode="" d="M241.664 252.928c21.504 34.816 51.712 63.488 87.04 83.968V771.072C328.704 839.168 384 894.976 452.608 894.976c68.608 0 123.904-55.296 123.904-123.904v-434.176c35.328-20.48 65.536-49.152 87.04-83.968 24.576-39.424 37.888-84.992 37.888-132.096 0-66.56-26.112-129.024-72.704-176.128-47.104-47.104-109.568-72.704-176.128-72.704s-129.024 26.112-176.128 72.704c-47.104 47.104-72.704 109.568-72.704 176.128 0.512 47.104 13.312 92.672 37.888 132.096zM453.12-87.04c114.688 0 207.872 93.184 207.872 207.872 0 78.848-43.52 149.504-113.664 185.344l-11.264 5.632V771.072c0 46.08-37.376 82.944-82.944 82.944s-82.944-37.376-82.944-82.944V312.32l-11.264-5.632c-70.144-35.84-113.664-107.008-113.664-185.344 0-114.688 93.184-208.384 207.872-208.384zM416.256 228.864V632.832c0 19.968 16.384 36.864 36.864 36.864 19.968 0 36.864-16.384 36.864-36.864v-403.456c42.496-14.848 73.216-55.808 73.216-103.424 0-60.416-49.152-110.08-110.08-110.08-60.416 0-110.08 49.152-110.08 110.08 0 47.616 30.72 88.064 73.216 102.912z m-167.936 532.48c0 23.04-41.984 92.672-41.984 92.672s-41.984-69.632-41.984-92.672c0-23.04 18.944-41.472 41.984-41.472 23.552-0.512 41.984 18.432 41.984 41.472zM164.352 393.216c0 34.304-62.976 138.24-62.976 138.24S38.4 427.52 38.4 393.216c0-34.304 28.16-62.464 62.976-62.464 34.816 0 62.976 28.16 62.976 62.464z m704.512-95.744c67.072 0 121.856 53.76 121.856 120.32s-121.856 267.776-121.856 267.776-121.856-201.216-121.856-267.776 54.272-120.32 121.856-120.32z" horiz-adv-x="1024" />
|
||||
|
||||
|
||||
<glyph glyph-name="map" unicode="" d="M590.385244 868.220491c-99.849476 0-180.759546-80.948617-180.759546-180.746697 0-99.836627 157.618521-277.833641 157.618521-412.118401l46.294899 0c0 133.809348 157.605672 320.415183 157.605672 412.118401C771.131941 787.271874 690.221871 868.220491 590.385244 868.220491zM590.385244 608.028509c-43.866441 0-79.458134 35.578844-79.458134 79.445285 0 43.866441 35.591693 79.445285 79.458134 79.445285 43.866441 0 79.445285-35.578844 79.445285-79.445285C669.830529 643.607353 634.251685 608.028509 590.385244 608.028509zM810.269954 775.643541c9.495401-23.616438 15.200351-49.108827 16.575193-75.744777l101.558391 50.804894 0-695.862576-152.645963-76.322981-230.896292 98.924349c-9.456854 4.073129-19.543309 6.09042-29.604065 6.09042-11.525541 0-23.038233-2.634042-33.587251-7.927825l-194.173888-97.086944-185.372332 79.406738L102.123747 758.335956l158.183876-67.778405c9.456854-4.073129 19.543309-6.09042 29.604065-6.09042 11.512692 0 23.025384 2.634042 33.587251 7.927825l30.799021 15.405935c3.122304 36.349784 14.493657 70.232562 32.21241 100.093607l-96.611531-48.299341L27.00857 872.255072l0-863.850229 262.915967-112.672765 225.34553 112.672765 262.915967-112.672765 225.34553 112.672765L1003.531564 872.255072 810.269954 775.643541zM515.270067 8.404843l224.369007-96.161817C729.53977 163.235134 608.283882 204.339043 515.270067 204.339043c-20.391342 0-36.349784-23.693532-75.128026-1.875952-65.465588 36.863743-44.444645 138.062363-150.217504 143.960048-93.913244 93.900395-225.358379 75.128026-225.358379 75.128026L27.00857 421.551164l0-413.14632 262.915967-112.672765L515.270067 8.404843z" horiz-adv-x="1031" />
|
||||
|
||||
|
||||
<glyph glyph-name="xiangqing" unicode="" d="M818.176 815.104c30.72 0 59.392-12.288 81.92-33.792 21.504-21.504 33.792-51.2 33.792-81.92v-628.736c0-30.72-12.288-59.392-33.792-81.92-21.504-21.504-51.2-33.792-81.92-33.792H205.824c-30.72 0-59.392 12.288-81.92 33.792-21.504 21.504-33.792 51.2-33.792 81.92V699.392c0 30.72 12.288 59.392 33.792 81.92 21.504 21.504 51.2 33.792 81.92 33.792h612.352m0 69.632H205.824c-102.4 0-185.344-83.968-185.344-185.344v-628.736c0-101.376 82.944-185.344 185.344-185.344h612.352c101.376 0 185.344 82.944 185.344 185.344V699.392c0 101.376-83.968 185.344-185.344 185.344z m0 0M191.488 416.768c-10.24 0-20.48 4.096-27.648 13.312-11.264 15.36-9.216 36.864 6.144 48.128L404.48 660.48c14.336 11.264 33.792 9.216 46.08-3.072l143.36-148.48L809.984 691.2c14.336 12.288 36.864 10.24 49.152-4.096 12.288-14.336 10.24-36.864-4.096-49.152L614.4 435.2c-14.336-11.264-34.816-10.24-47.104 2.048L421.888 587.776 212.992 424.96c-7.168-5.12-14.336-8.192-21.504-8.192zM727.04 251.904H295.936c-19.456 0-34.816 15.36-34.816 34.816s15.36 34.816 34.816 34.816H727.04c19.456 0 34.816-15.36 34.816-34.816 0-18.432-15.36-34.816-34.816-34.816z m0-161.792H295.936c-19.456 0-34.816 15.36-34.816 34.816s15.36 34.816 34.816 34.816H727.04c19.456 0 34.816-15.36 34.816-34.816s-15.36-34.816-34.816-34.816z m0 0" horiz-adv-x="1024" />
|
||||
|
||||
|
||||
<glyph glyph-name="signal-2" unicode="" d="M432 320h-96c-17.68 0-32-14.32-32-32v-384c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32V288c0 17.68-14.32 32-32 32zM176 128H80c-17.68 0-32-14.32-32-32v-192c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32v192c0 17.68-14.32 32-32 32z" horiz-adv-x="1280" />
|
||||
|
||||
|
||||
<glyph glyph-name="signal-1" unicode="" d="M176 128H80c-17.68 0-32-14.32-32-32v-192c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32v192c0 17.68-14.32 32-32 32z" horiz-adv-x="1280" />
|
||||
|
||||
|
||||
<glyph glyph-name="signal-3" unicode="" d="M432 320h-96c-17.68 0-32-14.32-32-32v-384c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32V288c0 17.68-14.32 32-32 32zM176 128H80c-17.68 0-32-14.32-32-32v-192c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32v192c0 17.68-14.32 32-32 32z m512 384h-96c-17.68 0-32-14.32-32-32v-576c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32V480c0 17.68-14.32 32-32 32z" horiz-adv-x="1280" />
|
||||
|
||||
|
||||
<glyph glyph-name="signal-4" unicode="" d="M432 320h-96c-17.68 0-32-14.32-32-32v-384c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32V288c0 17.68-14.32 32-32 32zM176 128H80c-17.68 0-32-14.32-32-32v-192c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32v192c0 17.68-14.32 32-32 32z m512 384h-96c-17.68 0-32-14.32-32-32v-576c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32V480c0 17.68-14.32 32-32 32z m256 192h-96c-17.68 0-32-14.32-32-32v-768c0-17.68 14.32-32 32-32h96c17.68 0 32 14.32 32 32V672c0 17.68-14.32 32-32 32z" horiz-adv-x="1280" />
|
||||
|
||||
|
||||
<glyph glyph-name="mosquito1" unicode="" d="M965.973333 578.56c-85.333333 58.026667-283.306667-13.653333-351.573333-40.96l112.64 68.266667c3.413333 3.413333 6.826667 6.826667 6.826667 10.24L785.066667 800.426667l47.786666 47.786666c6.826667 6.826667 6.826667 17.066667 0 23.893334s-17.066667 6.826667-23.893333 0l-51.2-51.2c-3.413333 0-6.826667-3.413333-6.826667-6.826667l-47.786666-180.906667L580.266667 558.08v3.413333c13.653333 17.066667 17.066667 37.546667 17.066666 61.44 0 30.72-23.893333 75.093333-68.266666 81.92V759.466667c0 10.24-6.826667 17.066667-17.066667 17.066666s-17.066667-6.826667-17.066667-17.066666v-54.613334c-44.373333-10.24-68.266667-51.2-68.266666-81.92 0-23.893333 6.826667-44.373333 17.066666-61.44v-3.413333L320.853333 633.173333 273.066667 797.013333c0 3.413333 0 3.413333-3.413334 6.826667L218.453333 872.106667C211.626667 878.933333 201.386667 882.346667 194.56 875.52s-10.24-17.066667-3.413333-23.893333L238.933333 786.773333l51.2-167.253333c0-3.413333 3.413333-6.826667 6.826667-10.24l109.226667-68.266667c-68.266667 27.306667-262.826667 98.986667-348.16 44.373334-30.72-20.48-44.373333-51.2-44.373334-92.16 0-44.373333 17.066667-75.093333 47.786667-98.986667 30.72-20.48 71.68-27.306667 116.053333-27.306667 92.16 0 194.56 34.133333 221.866667 40.96l3.413333-10.24-102.4-34.133333c-6.826667-3.413333-10.24-6.826667-10.24-13.653333-3.413333-71.68-37.546667-256-119.466666-256-10.24 0-17.066667-6.826667-17.066667-17.066667s6.826667-17.066667 17.066667-17.066667c119.466667 0 146.773333 218.453333 153.6 276.48l88.746666 30.72 3.413334-20.48c-58.026667-34.133333-126.293333-249.173333-126.293334-303.786666 0-47.786667-61.44-105.813333-92.16-122.88-6.826667-3.413333-10.24-13.653333-6.826666-23.893334 3.413333-6.826667 10.24-10.24 13.653333-10.24 3.413333 0 6.826667 0 6.826667 3.413334 37.546667 20.48 112.64 85.333333 112.64 150.186666 0 54.613333 61.44 221.866667 98.986666 266.24l3.413334-10.24c-3.413333-37.546667-20.48-252.586667 37.546666-317.44 13.653333-13.653333 30.72-20.48 47.786667-20.48s34.133333 6.826667 47.786667 20.48c61.44 68.266667 40.96 283.306667 37.546666 317.44l3.413334 10.24c37.546667-44.373333 98.986667-211.626667 98.986666-266.24 0-64.853333 75.093333-133.12 112.64-150.186666 3.413333 0 6.826667-3.413333 6.826667-3.413334 6.826667 0 13.653333 3.413333 13.653333 10.24 3.413333 6.826667 0 17.066667-6.826666 23.893334-30.72 17.066667-92.16 75.093333-92.16 122.88 0 54.613333-68.266667 269.653333-126.293334 303.786666l3.413334 20.48 88.746666-30.72c6.826667-58.026667 34.133333-276.48 153.6-276.48 10.24 0 17.066667 6.826667 17.066667 17.066667s-6.826667 17.066667-17.066667 17.066667c-81.92 0-116.053333 184.32-119.466666 256 0 6.826667-3.413333 13.653333-10.24 13.653333l-102.4 34.133333 3.413333 10.24c27.306667-10.24 129.706667-40.96 221.866667-40.96 44.373333 0 88.746667 6.826667 119.466666 30.72 30.72 20.48 44.373333 51.2 44.373334 92.16-3.413333 40.96-17.066667 71.68-44.373334 88.746667z" horiz-adv-x="1024" />
|
||||
|
||||
|
||||
<glyph glyph-name="mosquito" unicode="" d="M958.933333 579.541333c-75.306667 49.365333-229.418667 4.778667-313.941333-25.856l70.826667 47.232a21.333333 21.333333 0 0 1 8.405333 11.008l62.421333 187.221334 39.082667 39.082666a21.333333 21.333333 0 0 1-30.165333 30.165334l-42.666667-42.666667a20.608 20.608 0 0 1-5.162667-8.32l-61.696-185.045333-98.133333-65.450667c7.381333 16.938667 9.429333 34.602667 9.429333 51.754667 0 30.848-20.096 72.490667-64 82.858666V768a21.333333 21.333333 0 0 1-42.666666 0v-66.474667C446.762667 691.157333 426.666667 649.514667 426.666667 618.666667c0-17.194667 2.048-34.858667 9.429333-51.797334L337.92 632.362667 276.224 817.408a20.608 20.608 0 0 1-5.162667 8.32l-42.666666 42.666667a21.333333 21.333333 0 0 1-30.165334-30.165334l39.125334-39.082666 62.421333-187.221334a21.162667 21.162667 0 0 1 8.405333-11.008l70.784-47.189333c-84.522667 30.677333-238.634667 75.264-313.898666 25.813333C45.098667 566.485333 21.333333 540.458667 21.333333 490.666667c0-41.813333 15.36-74.026667 45.696-95.701334 30.805333-21.973333 74.410667-29.653333 120.32-29.653333 70.656 0 146.730667 18.176 189.909334 30.421333l-86.528-34.602666a21.376 21.376 0 0 1-13.397334-18.773334C274.346667 281.216 248.277333 106.666667 170.666667 106.666667a21.333333 21.333333 0 0 1 0-42.666667c119.424 0 143.829333 202.752 148.394666 262.485333l88.661334 35.456 1.92-6.741333C353.536 312.32 277.333333 99.456 277.333333 42.666667c0-43.52-43.050667-92.885333-73.984-109.141334a21.333333 21.333333 0 1 1 19.925334-37.717333C262.272-83.669333 320-22.826667 320 42.666667c0 48 64.213333 216.917333 102.784 266.581333l3.541333-12.330667c-4.266667-37.76-22.656-229.845333 34.730667-294.570666 13.738667-15.488 31.36-23.68 50.944-23.68s37.205333 8.192 50.944 23.637333c57.386667 64.725333 38.997333 256.853333 34.730667 294.570667l3.541333 12.373333C639.829333 259.498667 704 90.666667 704 42.666667c0-65.493333 57.728-126.336 96.768-146.858667a21.12 21.12 0 0 1 28.757333 8.917333 21.333333 21.333333 0 0 1-8.917333 28.8C789.717333-50.218667 746.666667-0.853333 746.666667 42.666667c0 56.746667-76.117333 269.525333-132.309334 312.576l1.92 6.741333 88.618667-35.456c4.608-59.776 29.013333-262.528 148.437333-262.528a21.333333 21.333333 0 0 1-0.042666 42.709333c-77.568 0-103.68 174.549333-106.666667 235.690667a21.376 21.376 0 0 1-13.397333 18.773333l-85.888 34.346667c43.306667-12.245333 118.954667-30.250667 189.269333-30.250667 45.909333 0 89.514667 7.68 120.32 29.653334 30.378667 21.717333 45.738667 53.930667 45.738667 95.744 0 49.792-23.765333 75.818667-43.733334 88.874666z" horiz-adv-x="1024" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_" unicode="" d="M172 42.666h100.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_1" unicode="" d="M172 42.666h280.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_2" unicode="" d="M172 42.666h462.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_3" unicode="" d="M172 42.666h590.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_4" unicode="" d="M172 42.666h720.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_5" unicode="" d="M172 42.666h830.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_6" unicode="" d="M172 42.666h970.66V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_8" unicode="" d="M172 42.666000000000054h1270.66V725.3340000000001H172v-682.668z m1621.334 512V725.3340000000001C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.3340000000001v-682.668C1.334-51.200000000000045 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.33399999999995c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.3340000000001c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_7" unicode="" d="M172 42.666000000000054h1110.66V725.3340000000001H172v-682.668z m1621.334 512V725.3340000000001C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.3340000000001v-682.668C1.334-51.200000000000045 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.33399999999995c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.3340000000001c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
<glyph glyph-name="power_9" unicode="" d="M172 42.666h1450.666V725.334H172v-682.668z m1621.334 512V725.334C1793.334 819.2 1716.534 896 1622.666 896H172C78.134 896 1.334 819.2 1.334 725.334v-682.668C1.334-51.2 78.134-128 172-128h1450.666c93.868 0 170.668 76.8 170.668 170.666V213.334c46.932 0 85.332 38.4 85.332 85.332V469.334c0 46.932-38.4 85.332-85.332 85.332zM1708 469.334v-426.668c0-46.932-38.4-85.332-85.334-85.332H172c-46.934 0-85.334 38.4-85.334 85.332V725.334c0 46.932 38.4 85.332 85.334 85.332h1450.666c46.934 0 85.334-38.4 85.334-85.332v-256z" horiz-adv-x="1880" />
|
||||
|
||||
|
||||
|
||||
|
||||
</font>
|
||||
</defs></svg>
|
Before Width: | Height: | Size: 20 KiB |
Before Width: | Height: | Size: 46 KiB After Width: | Height: | Size: 17 KiB |
|
@ -4,8 +4,7 @@
|
|||
<svg-icon class-name='international-icon' icon-class="language" />
|
||||
</div>
|
||||
<el-dropdown-menu slot="dropdown">
|
||||
<el-dropdown-item command="zh" :disabled="language==='zh'">简体</el-dropdown-item>
|
||||
<el-dropdown-item command="hk" :disabled="language==='hk'">繁体</el-dropdown-item>
|
||||
<el-dropdown-item command="zh" :disabled="language==='zh'">中文</el-dropdown-item>
|
||||
<el-dropdown-item command="en" :disabled="language==='en'">English</el-dropdown-item>
|
||||
</el-dropdown-menu>
|
||||
</el-dropdown>
|
||||
|
|
|
@ -1,42 +0,0 @@
|
|||
|
||||
import { addResizeListener, removeResizeListener } from 'element-ui/src/utils/resize-event'
|
||||
|
||||
/**
|
||||
* How to use
|
||||
* <el-table height="100px" v-el-height-adaptive-table="{bottomOffset: 30}">...</el-table>
|
||||
* el-table height is must be set
|
||||
* bottomOffset: 30(default) // The height of the table from the bottom of the page.
|
||||
*/
|
||||
|
||||
const doResize = (el, binding, vnode) => {
|
||||
const { componentInstance: $table } = vnode
|
||||
|
||||
const { value } = binding
|
||||
|
||||
if (!$table.height) {
|
||||
throw new Error(`el-$table must set the height. Such as height='100px'`)
|
||||
}
|
||||
const bottomOffset = (value && value.bottomOffset) || 30
|
||||
|
||||
if (!$table) return
|
||||
|
||||
const height = window.innerHeight - el.getBoundingClientRect().top - bottomOffset
|
||||
$table.layout.setHeight(height)
|
||||
$table.doLayout()
|
||||
}
|
||||
|
||||
export default {
|
||||
bind(el, binding, vnode) {
|
||||
el.resizeListener = () => {
|
||||
doResize(el, binding, vnode)
|
||||
}
|
||||
|
||||
addResizeListener(el, el.resizeListener)
|
||||
},
|
||||
inserted(el, binding, vnode) {
|
||||
doResize(el, binding, vnode)
|
||||
},
|
||||
unbind(el) {
|
||||
removeResizeListener(el, el.resizeListener)
|
||||
}
|
||||
}
|
|
@ -1,14 +0,0 @@
|
|||
|
||||
import adaptive from './adaptive'
|
||||
|
||||
const install = function(Vue) {
|
||||
Vue.directive('el-height-adaptive-table', adaptive)
|
||||
}
|
||||
|
||||
if (window.Vue) {
|
||||
window['el-height-adaptive-table'] = adaptive
|
||||
Vue.use(install); // eslint-disable-line
|
||||
}
|
||||
|
||||
adaptive.install = install
|
||||
export default adaptive
|
|
@ -1 +0,0 @@
|
|||
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1534320378407" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1009" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><defs><style type="text/css"></style></defs><path d="M959.68 642.944l-1.472-10.432-96.96-338.816C834.688 201.088 741.312 128 649.6 128L409.536 128C318.272 128 221.824 198.08 189.312 287.68l-123.008 339.2L64 640l0 73.088C64 813.952 141.568 896 236.992 896l550.656 0c95.488 0 172.864-82.24 172.352-183.424L959.68 642.944zM253.696 313.92c22.208-61.312 93.12-112.768 155.84-112.768l240.064 0c61.44 0 127.936 52.032 145.6 113.728l83.904 293.12L147.072 608 253.696 313.92zM787.648 822.784 236.992 822.784c-57.344 0-104-49.344-104-109.76L132.992 672l757.824 0 0.192 40.96C891.328 773.568 844.928 822.784 787.648 822.784z" p-id="1010"></path><path d="M736 704l64 0 0 64-64 0 0-64Z" p-id="1011"></path></svg>
|
Before Width: | Height: | Size: 1.0 KiB |
|
@ -1 +0,0 @@
|
|||
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1533866109364" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="13626" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><defs><style type="text/css"></style></defs><path d="M683.323077 710.892308c9.846154-9.846154 9.846154-25.6 0-35.446154l-35.446154-35.446154c-9.846154-9.846154-25.6-9.846154-35.446154 0l-86.646154 86.646154c-5.907692 5.907692-17.723077 5.907692-23.630769 0l-86.646154-86.646154c-9.846154-9.846154-25.6-9.846154-35.446154 0l-35.446153 35.446154c-9.846154 9.846154-9.846154 25.6 0 35.446154l86.646153 86.646154c5.907692 5.907692 5.907692 17.723077 0 23.630769l-86.646153 86.646154c-9.846154 9.846154-9.846154 25.6 0 35.446153l35.446153 35.446154c9.846154 9.846154 25.6 9.846154 35.446154 0l86.646154-86.646154c5.907692-5.907692 17.723077-5.907692 23.630769 0l86.646154 86.646154c9.846154 9.846154 25.6 9.846154 35.446154 0l35.446154-35.446154c9.846154-9.846154 9.846154-25.6 0-35.446153l-86.646154-86.646154c-5.907692-5.907692-5.907692-17.723077 0-23.630769l86.646154-86.646154z m256-482.461539c-108.307692-120.123077-261.907692-187.076923-425.353846-187.076923S196.923077 108.307692 88.615385 228.430769c-7.876923 7.876923-5.907692 21.661538 1.96923 27.569231l59.076923 51.2c7.876923 7.876923 19.692308 5.907692 27.569231-1.969231 86.646154-92.553846 208.738462-145.723077 336.738462-145.723077s250.092308 53.169231 336.738461 145.723077c7.876923 7.876923 19.692308 7.876923 27.569231 1.969231l59.076923-51.2c7.876923-7.876923 9.846154-19.692308 1.969231-27.569231z m-425.353846 88.615385c-82.707692 0-161.476923 35.446154-216.615385 98.461538-7.876923 7.876923-5.907692 21.661538 1.969231 29.538462l63.015385 47.261538c7.876923 5.907692 19.692308 5.907692 25.6-1.96923 33.476923-35.446154 78.769231-55.138462 126.030769-55.138462s92.553846 19.692308 124.061538 53.169231c5.907692 7.876923 17.723077 7.876923 25.6 1.969231l63.015385-47.261539c9.846154-7.876923 9.846154-19.692308 1.969231-29.538461-53.169231-61.046154-131.938462-96.492308-214.646154-96.492308z" p-id="13627"></path></svg>
|
Before Width: | Height: | Size: 2.2 KiB |
Before Width: | Height: | Size: 14 KiB |
|
@ -1 +0,0 @@
|
|||
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1533866120081" class="icon" style="" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="13747" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><defs><style type="text/css"></style></defs><path d="M832 1024H192c-106.048 0-192-86.016-192-192V192a192 192 0 0 1 192-192h640a192 192 0 0 1 192 192v640c0 105.984-85.952 192-192 192z m64-832a64 64 0 0 0-64-64H192a64 64 0 0 0-64 64v640c0 35.392 28.608 64 64 64h640c35.392 0 64-28.608 64-64V192z m-192 384h-128v128c0 35.392-28.608 64-64 64s-64-28.608-64-64v-128h-128a64 64 0 1 1 0-128h128v-128a64 64 0 1 1 128 0v128h128a64 64 0 1 1 0 128z" fill="" p-id="13748"></path></svg>
|
Before Width: | Height: | Size: 806 B |
|
@ -1 +0,0 @@
|
|||
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1533866073593" class="icon" style="" viewBox="0 0 1025 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="13505" xmlns:xlink="http://www.w3.org/1999/xlink" width="200.1953125" height="200"><defs><style type="text/css"></style></defs><path d="M977.19856 256H785.19856a48 48 0 1 0 0 96h76.112L655.26256 558.064l-27.808 27.808-4.768 4.768L561.19856 652.128 339.13456 430.064A47.824 47.824 0 0 0 305.19856 416a47.84 47.84 0 0 0-33.936 14.064l-256 256a48 48 0 1 0 67.872 67.872L305.19856 531.888l222.064 222.064A47.904 47.904 0 0 0 561.19856 768a47.84 47.84 0 0 0 33.936-14.064l95.424-95.44L929.19856 419.888V496a48 48 0 1 0 96 0V304a48 48 0 0 0-48-48z" fill="" p-id="13506"></path></svg>
|
Before Width: | Height: | Size: 836 B |
|
@ -1 +0,0 @@
|
|||
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1534320364216" class="icon" style="" viewBox="0 0 1170 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="895" xmlns:xlink="http://www.w3.org/1999/xlink" width="228.515625" height="200"><defs><style type="text/css"></style></defs><path d="M787.333533 588.946109a75.190803 75.190803 0 0 0-75.09328 75.09328 75.190803 75.190803 0 0 0 75.09328 75.093279 75.166423 75.166423 0 0 0 75.068899-75.093279 75.166423 75.166423 0 0 0-75.068899-75.09328m0 222.841745a147.919132 147.919132 0 0 1-147.748466-147.748465c0-81.456704 66.291762-147.748466 147.748466-147.748466 81.432323 0 147.748466 66.291762 147.748466 147.748466 0 81.481085-66.316143 147.748466-147.748466 147.748465m89.45365 102.107356c0.341333 0.243809 1.31657 0.585142 2.316189 0.585143h0.121905l71.484901-39.497115c-1.706665-4.022854-9.606088-23.47884-9.606088-43.739397a113.858966 113.858966 0 0 1 107.739351-113.615157c0.853333-4.729901 5.558853-31.524549 5.558853-51.638821s-4.70552-46.884538-5.558853-51.63882A113.858966 113.858966 0 0 1 941.10409 500.784648c0-20.358081 7.923804-39.814067 9.606088-43.81254l-70.314616-39.058258-0.292572-0.024381a5.339425 5.339425 0 0 0-2.706283 0.731428 196.754145 196.754145 0 0 1-26.014458 21.820937c-21.699032 15.238084-42.154637 22.966841-60.952337 22.966841-18.919606 0-39.594638-7.875042-61.391195-23.405698a194.706147 194.706147 0 0 1-26.160743-22.284174 5.778282 5.778282 0 0 0-2.730665-0.707048h-0.243809l-72.825853 40.033496c1.706665 4.047235 9.581707 23.47884 9.581708 43.739397a113.858966 113.858966 0 0 1-107.763733 113.566395c-0.853333 4.729901-5.510091 31.524549-5.510091 51.63882s4.656759 46.908919 5.534472 51.663202a113.858966 113.858966 0 0 1 107.763733 113.590776c0 20.3337-7.972566 39.862829-9.679231 43.788159l68.973665 38.546258h0.146285c1.023999 0 1.950475-0.365714 2.316189-0.585143a200.850142 200.850142 0 0 1 26.428933-23.161888c22.089127-16.188941 43.081112-24.429697 62.415194-24.429697 19.55351 0 40.716161 8.387042 62.951574 24.917316 14.921132 11.068944 25.258649 22.186651 26.550838 23.576364m22.67427 108.397637c-13.775228-0.024381-27.135981-5.705139-35.766832-15.213703-11.775992-12.897515-49.005679-46.445681-79.53061-46.445682-30.281121 0-68.120332 33.767595-78.994229 45.543587-8.60647 9.38666-21.869699 14.969894-35.498641 14.969894-6.485329 0-12.604943-1.243428-18.188178-3.705902l-0.975237-0.414476-92.696315-51.833868-0.926475-0.682666a44.470825 44.470825 0 0 1-14.921133-53.735581c0.048762-0.146286 8.533327-19.699795 8.533328-37.595401a98.377073 98.377073 0 0 0-98.255168-98.255168h-3.90095c-15.506275 0-28.15998-13.799609-32.182834-35.108547-0.341333-1.706665-7.923804-42.179017-7.923804-74.044899 0-31.914644 7.55809-72.362615 7.899423-74.118042 4.120378-21.577127 16.993512-35.449879 32.816738-35.084166h3.267046a98.401454 98.401454 0 0 0 98.279549-98.30393c0-17.846844-8.484565-37.400354-8.557709-37.619782a44.348921 44.348921 0 0 1 15.067418-53.662438l0.950857-0.658285 97.840692-53.759962 1.023999-0.414476c5.48571-2.364951 11.507801-3.535236 17.895606-3.535235 13.604562 0 26.892171 5.436948 35.596165 14.628561 11.580944 12.117325 48.176727 43.641874 77.775183 43.641873 29.354646 0 65.755382-30.915026 77.287564-42.812922 8.655232-8.996565 21.845318-14.33599 35.303594-14.335989 6.50971 0 12.653705 1.219047 18.285701 3.65714l0.975237 0.414476 94.476123 52.516534 0.950857 0.658285c16.895988 11.751611 23.332555 34.889118 14.945513 53.735581-0.048762 0.146286-8.533327 19.699795-8.533328 37.546639a98.401454 98.401454 0 0 0 98.255168 98.279549h3.291427c15.774465-0.341333 28.720741 13.507038 32.816738 35.108547 0.316952 1.706665 7.899423 42.203398 7.899423 74.06928 0 31.890263-7.582471 72.411377-7.948185 74.118042-4.047235 21.552747-16.993512 35.425499-32.767976 35.059785h-3.291427a98.401454 98.401454 0 0 0-98.255168 98.279549c0 17.846844 8.484565 37.449116 8.557709 37.619782a44.422064 44.422064 0 0 1-15.018656 53.7112l-0.926476 0.682666-96.134026 53.101677-0.975238 0.414475a44.885301 44.885301 0 0 1-17.846844 3.583998zM1121.523008 316.952398a48.76187 48.76187 0 1 1-97.523739 0V121.978061C1023.999269 108.519785 1013.125372 97.523984 999.691476 97.523984H121.831532C108.568303 97.523984 97.52374 108.495404 97.52374 121.978061v584.996154c0 13.458276 10.873897 24.454078 24.307792 24.454078H341.33309a48.76187 48.76187 0 1 1 0 97.52374H48.908156A48.76187 48.76187 0 0 1 0 780.190163V48.762114C0 21.821181 21.89408 0.000244 48.908156 0.000244h1023.706697A48.76187 48.76187 0 0 1 1121.523008 48.762114v268.190284zM219.428415 975.237642c0-26.940933 21.991603-48.76187 48.981298-48.761869h194.608623a48.76187 48.76187 0 1 1 0 97.523739H268.434094A48.76187 48.76187 0 0 1 219.428415 975.237642z" p-id="896"></path></svg>
|
Before Width: | Height: | Size: 4.7 KiB |
|
@ -4,14 +4,9 @@ export default {
|
|||
introduction: 'Introduction',
|
||||
documentation: 'Documentation',
|
||||
counter: 'Counter',
|
||||
statistic: 'data statistics',
|
||||
device: 'Device Status',
|
||||
detail: 'Device Detail',
|
||||
logs: 'Log List',
|
||||
map: 'Map',
|
||||
weather: 'Weather Station',
|
||||
deviceSetting: 'Device Setting',
|
||||
systemSetting: 'System Setting',
|
||||
statistic: 'Statistic',
|
||||
device: 'Device',
|
||||
count: 'Count',
|
||||
guide: 'Guide',
|
||||
permission: 'Permission',
|
||||
pagePermission: 'Page Permission',
|
||||
|
@ -153,86 +148,5 @@ export default {
|
|||
close: 'Close',
|
||||
closeOthers: 'Close Others',
|
||||
closeAll: 'Close All'
|
||||
},
|
||||
counter: {
|
||||
online: 'online',
|
||||
offline: 'offline',
|
||||
all: 'all',
|
||||
inputDeviceID: 'Device ID',
|
||||
inputStatus: 'status',
|
||||
search: 'search',
|
||||
reset: 'reset',
|
||||
detail: 'Detail',
|
||||
map: 'Map',
|
||||
sn: 'No.',
|
||||
device: 'Device',
|
||||
status: 'Status',
|
||||
count: 'Count',
|
||||
signal: 'Signal',
|
||||
energy: 'Energy',
|
||||
time: 'Time',
|
||||
date: 'Date',
|
||||
coordinate: 'Coordinate',
|
||||
action: 'Action',
|
||||
logDesc: 'Mosquito killer log list',
|
||||
screen: 'Screen chart',
|
||||
trendChart: 'Trend chart',
|
||||
region: 'Region',
|
||||
deviceName: 'Device Name',
|
||||
noName: 'No Name',
|
||||
humitureChart: 'Humiture chart',
|
||||
temperature: 'Temperature',
|
||||
humidity: 'Humidity',
|
||||
logSeachContent: 'Device ID/Name',
|
||||
to: 'To',
|
||||
start_date: 'Start Date',
|
||||
end_date: 'End Date'
|
||||
},
|
||||
weather: {
|
||||
online: 'online',
|
||||
offline: 'offline',
|
||||
all: 'all',
|
||||
inputDeviceID: 'Device ID',
|
||||
inputStatus: 'status',
|
||||
search: 'search',
|
||||
reset: 'reset',
|
||||
detail: 'Detail',
|
||||
map: 'Map',
|
||||
sn: 'No.',
|
||||
device: 'Device ID',
|
||||
status: 'Status',
|
||||
count: 'Count',
|
||||
signal: 'Signal',
|
||||
energy: 'Energy',
|
||||
time: 'Time',
|
||||
date: 'Date',
|
||||
coordinate: 'Coordinate',
|
||||
action: 'Action',
|
||||
logDesc: 'Mosquito killer log list',
|
||||
screen: 'Screen chart',
|
||||
trendChart: 'Trend chart',
|
||||
region: 'Region',
|
||||
deviceName: 'Device Name',
|
||||
humitureChart: 'Humiture chart',
|
||||
temperature: 'Temperature(℃)',
|
||||
humidity: 'Humidity',
|
||||
logSeachContent: 'Device ID/Name',
|
||||
to: 'To',
|
||||
start_date: 'Start Date',
|
||||
end_date: 'End Date',
|
||||
envTemp: 'Env. Temp(℃)',
|
||||
dewPointTemp: 'Daw Point Temp(℃)',
|
||||
envHumi: 'Env. Humi(%RH)',
|
||||
airPressure: 'Air Pressure(hPa)',
|
||||
totalRadiation1Ins: 'Total Radiation 1 Ins(W/㎡)',
|
||||
windDirection: 'Wind Directiong(°)',
|
||||
windSpeedIns: 'Wind Speed Ins(m/s)',
|
||||
windSpeed2mins: 'Wind Speed 2mins(m/s)',
|
||||
windSpeed10mins: 'Wind Speed 10mins(m/s)',
|
||||
rainfallIntervalCum: 'Rainfall Interval Cum(mm)',
|
||||
totalRadiation1IntervalCum: 'Total Radiation 1 Interval Cum(MJ/㎡)',
|
||||
rainfallDailyCum: 'Rainfall Daily Cum(mm)',
|
||||
totalRadiation1DailyCum: 'Total Radiation 1 Daily Cum(MJ/㎡)',
|
||||
power: 'Power(%)'
|
||||
}
|
||||
}
|
||||
|
|
238
src/lang/hk.js
|
@ -1,238 +0,0 @@
|
|||
export default {
|
||||
route: {
|
||||
dashboard: '儀表板',
|
||||
introduction: '簡述',
|
||||
documentation: '文檔',
|
||||
counter: '滅蚊燈數據',
|
||||
statistic: '數據統計',
|
||||
device: '狀態監控',
|
||||
detail: '設備詳情',
|
||||
logs: '日誌列表',
|
||||
map: '區域地圖',
|
||||
weather: '氣象台',
|
||||
deviceSetting: '設備設置',
|
||||
systemSetting: '系統設置',
|
||||
guide: '引導頁',
|
||||
permission: '權限測試頁',
|
||||
pagePermission: '頁面權限',
|
||||
directivePermission: '指令權限',
|
||||
icons: '圖標',
|
||||
components: '組件',
|
||||
componentIndex: '介紹',
|
||||
tinymce: '富文本編輯器',
|
||||
markdown: 'Markdown',
|
||||
jsonEditor: 'JSON編輯器',
|
||||
dndList: '列表拖拽',
|
||||
splitPane: 'Splitpane',
|
||||
avatarUpload: '頭像上傳',
|
||||
dropzone: 'Dropzone',
|
||||
sticky: 'Sticky',
|
||||
countTo: 'CountTo',
|
||||
componentMixin: '小組件',
|
||||
backToTop: '返回頂部',
|
||||
dragDialog: '拖拽 Dialog',
|
||||
dragKanban: '可拖拽看板',
|
||||
charts: '圖表',
|
||||
keyboardChart: '鍵盤圖表',
|
||||
lineChart: '折線圖',
|
||||
mixChart: '混合圖表',
|
||||
example: '綜合實例',
|
||||
nested: '路由嵌套',
|
||||
bar: 'Bar',
|
||||
barProfile: 'Profile',
|
||||
barPosts: 'Posts',
|
||||
Table: 'Table',
|
||||
dynamicTable: '動態Table',
|
||||
dragTable: '拖拽Table',
|
||||
inlineEditTable: 'Table內編輯',
|
||||
complexTable: '綜合Table',
|
||||
treeTable: '樹形表格',
|
||||
customTreeTable: '自定義樹表',
|
||||
tab: 'Tab',
|
||||
form: '表單',
|
||||
createArticle: '創建文章',
|
||||
editArticle: '編輯文章',
|
||||
articleList: '文章列表',
|
||||
errorPages: '錯誤頁面',
|
||||
page401: '401',
|
||||
page404: '404',
|
||||
errorLog: '錯誤日誌',
|
||||
excel: 'Excel',
|
||||
exportExcel: '導出 Excel',
|
||||
selectExcel: '導出選定',
|
||||
uploadExcel: '上傳 Excel',
|
||||
zip: 'Zip',
|
||||
exportZip: '導出 Zip',
|
||||
theme: '換膚',
|
||||
clipboardDemo: 'Clipboard',
|
||||
i18n: '國際化'
|
||||
},
|
||||
navbar: {
|
||||
logOut: '退出登錄',
|
||||
dashboard: '首頁',
|
||||
github: '項目地址',
|
||||
screenfull: '全屏',
|
||||
theme: '換膚'
|
||||
},
|
||||
login: {
|
||||
title: '系統登錄',
|
||||
logIn: '登錄',
|
||||
username: '賬號',
|
||||
password: '密碼',
|
||||
any: '隨便填',
|
||||
thirdparty: '第三方登錄',
|
||||
thirdpartyTips: '本地不能模擬,請結合自己業務進行模擬!!!'
|
||||
},
|
||||
documentation: {
|
||||
documentation: '文檔',
|
||||
github: 'Github 地址'
|
||||
},
|
||||
permission: {
|
||||
roles: '你的權限',
|
||||
switchRoles: '切換權限'
|
||||
},
|
||||
guide: {
|
||||
description: '引導頁對於一些第一次進入項目的人很有用,你可以簡單介紹下項目的功能。本 Demo 是基於',
|
||||
button: '打開引導'
|
||||
},
|
||||
components: {
|
||||
documentation: '文檔',
|
||||
tinymceTips: '富文本是管理後臺一個核心的功能,但同時又是一個有很多坑的地方。在選擇富文本的過程中我也走了不少的彎路,市面上常見的富文本都基本用過了,最終權衡了一下選擇了Tinymce。更詳細的富文本比較和介紹見',
|
||||
dropzoneTips: '由於我司業務有特殊需求,而且要傳七牛 所以沒用第三方,選擇了自己封裝。代碼非常的簡單,具體代碼你可以在這裡看到 @/components/Dropzone',
|
||||
stickyTips: '當頁面滾動到預設的位置會吸附在頂部',
|
||||
backToTopTips1: '頁面滾動到指定位置會在右下角出現返回頂部按鈕',
|
||||
backToTopTips2: '可自定義按鈕的樣式、show/hide、出現的高度、返回的位置 如需文字提示,可在外部使用Element的el-tooltip元素',
|
||||
imageUploadTips: '由於我在使用時它只有vue@1版本,而且和mockjs不兼容,所以自己改造了一下,如果大家要使用的話,優先還是使用官方版本。'
|
||||
},
|
||||
table: {
|
||||
dynamicTips1: '固定表頭, 按照表頭順序排序',
|
||||
dynamicTips2: '不固定表頭, 按照點擊順序排序',
|
||||
dragTips1: '默認順序',
|
||||
dragTips2: '拖拽後順序',
|
||||
title: '標題',
|
||||
importance: '重要性',
|
||||
type: '類型',
|
||||
remark: '點評',
|
||||
search: '搜索',
|
||||
add: '添加',
|
||||
export: '導出',
|
||||
reviewer: '審核人',
|
||||
id: '序號',
|
||||
date: '時間',
|
||||
author: '作者',
|
||||
readings: '閱讀數',
|
||||
status: '狀態',
|
||||
actions: '操作',
|
||||
edit: '編輯',
|
||||
publish: '發布',
|
||||
draft: '草稿',
|
||||
delete: '刪除',
|
||||
cancel: '取 消',
|
||||
confirm: '確 定'
|
||||
},
|
||||
errorLog: {
|
||||
tips: '請點擊右上角bug小圖標',
|
||||
description: '現在的管理後臺基本都是spa的形式了,它增強了用戶體驗,但同時也會增加頁面出問題的可能性,可能一個小小的疏忽就導致整個頁面的死鎖。好在 Vue 官網提供了一個方法來捕獲處理異常,你可以在其中進行錯誤處理或者異常上報。',
|
||||
documentation: '文檔介紹'
|
||||
},
|
||||
excel: {
|
||||
export: '導出',
|
||||
selectedExport: '導出已選擇項',
|
||||
placeholder: '請輸入文件名(默認excel-list)'
|
||||
},
|
||||
zip: {
|
||||
export: '導出',
|
||||
placeholder: '請輸入文件名(默認file)'
|
||||
},
|
||||
theme: {
|
||||
change: '換膚',
|
||||
documentation: '換膚文檔',
|
||||
tips: 'Tips: 它區別於 navbar 上的 theme-pick, 是兩種不同的換膚方法,各自有不同的應用場景,具體請參考文檔。'
|
||||
},
|
||||
tagsView: {
|
||||
close: '關閉',
|
||||
closeOthers: '關閉其它',
|
||||
closeAll: '關閉所有'
|
||||
},
|
||||
counter: {
|
||||
online: '在線',
|
||||
offline: '離線',
|
||||
all: '全部',
|
||||
inputDeviceID: '設備 ID',
|
||||
inputStatus: '狀態',
|
||||
search: '搜索',
|
||||
reset: '重置',
|
||||
detail: '詳情',
|
||||
map: '地圖',
|
||||
sn: '序號',
|
||||
device: '設備ID',
|
||||
status: '狀態',
|
||||
count: '計數',
|
||||
signal: '信號',
|
||||
energy: '電量',
|
||||
time: '時間',
|
||||
date: '日期',
|
||||
coordinate: '坐標',
|
||||
action: '操作',
|
||||
logDesc: '滅蚊器日誌列表',
|
||||
screen: '顯示屏',
|
||||
trendChart: '趨勢圖',
|
||||
region: '地區',
|
||||
deviceName: '設備名稱',
|
||||
noName: '未命名',
|
||||
humitureChart: '溫濕度',
|
||||
temperature: '溫度',
|
||||
humidity: '濕度',
|
||||
to: '至',
|
||||
logSeachContent: '設備名稱/ID',
|
||||
start_date: '開始日期',
|
||||
end_date: '結束日期'
|
||||
},
|
||||
weather: {
|
||||
online: '在線',
|
||||
offline: '離線',
|
||||
all: '全部',
|
||||
inputDeviceID: '設備 ID',
|
||||
inputStatus: '狀態',
|
||||
search: '搜索',
|
||||
reset: '重置',
|
||||
detail: '詳情',
|
||||
map: '地圖',
|
||||
sn: '序號',
|
||||
device: '設備ID',
|
||||
status: '狀態',
|
||||
count: '計數',
|
||||
signal: '信號',
|
||||
energy: '電量',
|
||||
time: '時間',
|
||||
date: '日期',
|
||||
coordinate: '坐標',
|
||||
action: '操作',
|
||||
logDesc: '滅蚊器日誌列表',
|
||||
screen: '顯示屏',
|
||||
trendChart: '趨勢圖',
|
||||
region: '地區',
|
||||
deviceName: '設備名稱',
|
||||
humitureChart: '溫濕度',
|
||||
temperature: '溫度',
|
||||
humidity: '濕度',
|
||||
to: '至',
|
||||
logSeachContent: '設備名稱/ID',
|
||||
start_date: '開始日期',
|
||||
end_date: '結束日期',
|
||||
envTemp: '環溫(℃)',
|
||||
dewPointTemp: '露點溫度(℃)',
|
||||
envHumi: '環濕(%RH)',
|
||||
airPressure: '氣壓(hPa)',
|
||||
totalRadiation1Ins: '總輻射1瞬時(W/㎡)',
|
||||
windDirection: '風向(°)',
|
||||
windSpeedIns: '瞬時風速(m/s)',
|
||||
windSpeed2mins: '2分鐘風速(m/s)',
|
||||
windSpeed10mins: '10分鐘風速(m/s)',
|
||||
rainfallIntervalCum: '雨量間隔累計(mm)',
|
||||
totalRadiation1IntervalCum: '總輻射1間隔累計(MJ/㎡)',
|
||||
rainfallDailyCum: '雨量日累計(mm)',
|
||||
totalRadiation1DailyCum: '總輻射1日累計(MJ/㎡)',
|
||||
power: '電量(%)'
|
||||
}
|
||||
}
|
|
@ -3,10 +3,8 @@ import VueI18n from 'vue-i18n'
|
|||
import Cookies from 'js-cookie'
|
||||
import elementEnLocale from 'element-ui/lib/locale/lang/en' // element-ui lang
|
||||
import elementZhLocale from 'element-ui/lib/locale/lang/zh-CN'// element-ui lang
|
||||
import elementHkLocale from 'element-ui/lib/locale/lang/zh-TW'// element-ui lang
|
||||
import enLocale from './en'
|
||||
import zhLocale from './zh'
|
||||
import hkLocale from './hk'
|
||||
|
||||
Vue.use(VueI18n)
|
||||
|
||||
|
@ -18,10 +16,6 @@ const messages = {
|
|||
zh: {
|
||||
...zhLocale,
|
||||
...elementZhLocale
|
||||
},
|
||||
hk: {
|
||||
...hkLocale,
|
||||
...elementHkLocale
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,17 +1,12 @@
|
|||
export default {
|
||||
route: {
|
||||
dashboard: '仪表盘',
|
||||
dashboard: '首页',
|
||||
introduction: '简述',
|
||||
documentation: '文档',
|
||||
counter: '灭蚊灯数据',
|
||||
statistic: '数据统计',
|
||||
device: '状态监控',
|
||||
detail: '设备详情',
|
||||
logs: '日志列表',
|
||||
map: '区域地图',
|
||||
weather: '气象台',
|
||||
deviceSetting: '设备设置',
|
||||
systemSetting: '系统设置',
|
||||
counter: '灭蚊器',
|
||||
statistic: '统计',
|
||||
device: '设备',
|
||||
count: '计数',
|
||||
guide: '引导页',
|
||||
permission: '权限测试页',
|
||||
pagePermission: '页面权限',
|
||||
|
@ -153,86 +148,5 @@ export default {
|
|||
close: '关闭',
|
||||
closeOthers: '关闭其它',
|
||||
closeAll: '关闭所有'
|
||||
},
|
||||
counter: {
|
||||
online: '在线',
|
||||
offline: '离线',
|
||||
all: '全部',
|
||||
inputDeviceID: '设备 ID',
|
||||
inputStatus: '状态',
|
||||
search: '搜索',
|
||||
reset: '重置',
|
||||
detail: '详情',
|
||||
map: '地图',
|
||||
sn: '序号',
|
||||
device: '设备ID',
|
||||
status: '状态',
|
||||
count: '计数',
|
||||
signal: '信号',
|
||||
energy: '电量',
|
||||
time: '时间',
|
||||
date: '日期',
|
||||
coordinate: '坐标',
|
||||
action: '操作',
|
||||
logDesc: '灭蚊器日志列表',
|
||||
screen: '显示屏',
|
||||
trendChart: '趋势图',
|
||||
region: '地区',
|
||||
deviceName: '设备名称',
|
||||
noName: '未命名',
|
||||
humitureChart: '温湿度',
|
||||
temperature: '温度',
|
||||
humidity: '湿度',
|
||||
to: '至',
|
||||
logSeachContent: '设备名称/ID',
|
||||
start_date: '开始日期',
|
||||
end_date: '结束日期'
|
||||
},
|
||||
weather: {
|
||||
online: '在线',
|
||||
offline: '离线',
|
||||
all: '全部',
|
||||
inputDeviceID: '设备 ID',
|
||||
inputStatus: '状态',
|
||||
search: '搜索',
|
||||
reset: '重置',
|
||||
detail: '详情',
|
||||
map: '地图',
|
||||
sn: '序号',
|
||||
device: '设备ID',
|
||||
status: '状态',
|
||||
count: '计数',
|
||||
signal: '信号',
|
||||
energy: '电量',
|
||||
time: '时间',
|
||||
date: '日期',
|
||||
coordinate: '坐标',
|
||||
action: '操作',
|
||||
logDesc: '灭蚊器日志列表',
|
||||
screen: '显示屏',
|
||||
trendChart: '趋势图',
|
||||
region: '地区',
|
||||
deviceName: '设备名称',
|
||||
humitureChart: '温湿度',
|
||||
temperature: '温度',
|
||||
humidity: '湿度',
|
||||
to: '至',
|
||||
logSeachContent: '设备名称/ID',
|
||||
start_date: '开始日期',
|
||||
end_date: '结束日期',
|
||||
envTemp: '环温(℃)',
|
||||
dewPointTemp: '露点温度(℃)',
|
||||
envHumi: '环湿(%RH)',
|
||||
airPressure: '气压(hPa)',
|
||||
totalRadiation1Ins: '总辐射1瞬时(W/㎡)',
|
||||
windDirection: '风向(°)',
|
||||
windSpeedIns: '瞬时风速(m/s)',
|
||||
windSpeed2mins: '2分钟风速(m/s)',
|
||||
windSpeed10mins: '10分钟风速(m/s)',
|
||||
rainfallIntervalCum: '雨量间隔累计(mm)',
|
||||
totalRadiation1IntervalCum: '总辐射1间隔累计(MJ/㎡)',
|
||||
rainfallDailyCum: '雨量日累计(mm)',
|
||||
totalRadiation1DailyCum: '总辐射1日累计(MJ/㎡)',
|
||||
power: '电量(%)'
|
||||
}
|
||||
}
|
||||
|
|
22
src/main.js
|
@ -13,33 +13,11 @@ import store from './store'
|
|||
|
||||
import i18n from './lang' // Internationalization
|
||||
import './icons' // icon
|
||||
import './assets/icon/iconfont.css' // ali icon
|
||||
import './errorLog'// error log
|
||||
import './permission' // permission control
|
||||
// import './mock' // simulation data
|
||||
|
||||
import * as filters from './filters' // global filters
|
||||
// import VueAMap from 'vue-amap'
|
||||
// Vue.use(VueAMap)
|
||||
|
||||
// VueAMap.initAMapApiLoader({
|
||||
// key: '250fde87c69f9f46d0a2bdbc561a82a8',
|
||||
// plugin: [
|
||||
// 'AMap.Geolocation',
|
||||
// 'AMap.Driving',
|
||||
// 'AMap.Walking',
|
||||
// 'AMap.Autocomplete',
|
||||
// 'AMap.PlaceSearch',
|
||||
// 'AMap.Scale',
|
||||
// 'AMap.OverView',
|
||||
// 'AMap.ToolBar',
|
||||
// 'AMap.MapType',
|
||||
// 'AMap.PolyEditor',
|
||||
// 'AMap.CircleEditor'
|
||||
// ],
|
||||
// // 默认高德 sdk 版本为 1.4.4
|
||||
// v: '1.4.4'
|
||||
// })
|
||||
|
||||
Vue.use(Element, {
|
||||
size: 'medium', // set element-ui default size
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { param2Obj } from '@/utils'
|
||||
import { param2Obj } from '@/utils'
|
||||
|
||||
const userMap = {
|
||||
admin: {
|
||||
|
|
|
@ -61,24 +61,22 @@ export const constantRouterMap = [
|
|||
icon: 'chart'
|
||||
},
|
||||
children: [
|
||||
// { path: 'index', component: () => import('@/views/counter/index'), name: 'statistic', meta: { title: 'statistic' }},
|
||||
{ path: 'index', component: () => import('@/views/counter/index'), name: 'statistic', meta: { title: 'statistic' }},
|
||||
{ path: 'device', component: () => import('@/views/counter/device'), name: 'device', meta: { title: 'device' }},
|
||||
{ path: 'detail', component: () => import('@/views/counter/detail'), name: 'detail', meta: { title: 'detail' }},
|
||||
{ path: 'logs', component: () => import('@/views/counter/logs'), name: 'logs', meta: { title: 'logs' }},
|
||||
{ path: 'map', component: () => import('@/views/counter/map2'), name: 'map', meta: { title: 'map' }}
|
||||
{ path: 'count', component: () => import('@/views/counter/count'), name: 'count', meta: { title: 'count' }}
|
||||
]
|
||||
},
|
||||
{
|
||||
path: '',
|
||||
component: Layout,
|
||||
redirect: 'weather',
|
||||
children: [{
|
||||
path: 'weather',
|
||||
component: () => import('@/views/weather/index'),
|
||||
name: 'weather',
|
||||
meta: { title: 'weather', icon: 'international', noCache: true }
|
||||
}]
|
||||
}
|
||||
// {
|
||||
// path: '/guide',
|
||||
// component: Layout,
|
||||
// redirect: '/guide/index',
|
||||
// children: [{
|
||||
// path: 'index',
|
||||
// component: () => import('@/views/guide/index'),
|
||||
// name: 'guide',
|
||||
// meta: { title: 'guide', icon: 'guide', noCache: true }
|
||||
// }]
|
||||
// }
|
||||
]
|
||||
|
||||
export default new Router({
|
||||
|
@ -88,5 +86,233 @@ export default new Router({
|
|||
})
|
||||
|
||||
export const asyncRouterMap = [
|
||||
{
|
||||
path: '/permission',
|
||||
component: Layout,
|
||||
redirect: '/permission/index',
|
||||
alwaysShow: true, // will always show the root menu
|
||||
meta: {
|
||||
title: 'permission',
|
||||
icon: 'lock',
|
||||
roles: ['admin', 'editor'] // you can set roles in root nav
|
||||
},
|
||||
children: [{
|
||||
path: 'page',
|
||||
component: () => import('@/views/permission/page'),
|
||||
name: 'pagePermission',
|
||||
meta: {
|
||||
title: 'pagePermission',
|
||||
roles: ['admin'] // or you can only set roles in sub nav
|
||||
}
|
||||
}, {
|
||||
path: 'directive',
|
||||
component: () => import('@/views/permission/directive'),
|
||||
name: 'directivePermission',
|
||||
meta: {
|
||||
title: 'directivePermission'
|
||||
// if do not set roles, means: this page does not require permission
|
||||
}
|
||||
}]
|
||||
},
|
||||
|
||||
{
|
||||
path: '/icon',
|
||||
component: Layout,
|
||||
children: [{
|
||||
path: 'index',
|
||||
component: () => import('@/views/svg-icons/index'),
|
||||
name: 'icons',
|
||||
meta: { title: 'icons', icon: 'icon', noCache: true }
|
||||
}]
|
||||
},
|
||||
|
||||
// {
|
||||
// path: '/components',
|
||||
// component: Layout,
|
||||
// redirect: 'noredirect',
|
||||
// name: 'component-demo',
|
||||
// meta: {
|
||||
// title: 'components',
|
||||
// icon: 'component'
|
||||
// },
|
||||
// children: [
|
||||
// { path: 'tinymce', component: () => import('@/views/components-demo/tinymce'), name: 'tinymce-demo', meta: { title: 'tinymce' }},
|
||||
// { path: 'markdown', component: () => import('@/views/components-demo/markdown'), name: 'markdown-demo', meta: { title: 'markdown' }},
|
||||
// { path: 'json-editor', component: () => import('@/views/components-demo/jsonEditor'), name: 'jsonEditor-demo', meta: { title: 'jsonEditor' }},
|
||||
// { path: 'splitpane', component: () => import('@/views/components-demo/splitpane'), name: 'splitpane-demo', meta: { title: 'splitPane' }},
|
||||
// { path: 'avatar-upload', component: () => import('@/views/components-demo/avatarUpload'), name: 'avatarUpload-demo', meta: { title: 'avatarUpload' }},
|
||||
// { path: 'dropzone', component: () => import('@/views/components-demo/dropzone'), name: 'dropzone-demo', meta: { title: 'dropzone' }},
|
||||
// { path: 'sticky', component: () => import('@/views/components-demo/sticky'), name: 'sticky-demo', meta: { title: 'sticky' }},
|
||||
// { path: 'count-to', component: () => import('@/views/components-demo/countTo'), name: 'countTo-demo', meta: { title: 'countTo' }},
|
||||
// { path: 'mixin', component: () => import('@/views/components-demo/mixin'), name: 'componentMixin-demo', meta: { title: 'componentMixin' }},
|
||||
// { path: 'back-to-top', component: () => import('@/views/components-demo/backToTop'), name: 'backToTop-demo', meta: { title: 'backToTop' }},
|
||||
// { path: 'drag-dialog', component: () => import('@/views/components-demo/dragDialog'), name: 'dragDialog-demo', meta: { title: 'dragDialog' }},
|
||||
// { path: 'dnd-list', component: () => import('@/views/components-demo/dndList'), name: 'dndList-demo', meta: { title: 'dndList' }},
|
||||
// { path: 'drag-kanban', component: () => import('@/views/components-demo/dragKanban'), name: 'dragKanban-demo', meta: { title: 'dragKanban' }}
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/charts',
|
||||
// component: Layout,
|
||||
// redirect: 'noredirect',
|
||||
// name: 'charts',
|
||||
// meta: {
|
||||
// title: 'charts',
|
||||
// icon: 'chart'
|
||||
// },
|
||||
// children: [
|
||||
// { path: 'keyboard', component: () => import('@/views/charts/keyboard'), name: 'keyboardChart', meta: { title: 'keyboardChart', noCache: true }},
|
||||
// { path: 'line', component: () => import('@/views/charts/line'), name: 'lineChart', meta: { title: 'lineChart', noCache: true }},
|
||||
// { path: 'mixchart', component: () => import('@/views/charts/mixChart'), name: 'mixChart', meta: { title: 'mixChart', noCache: true }}
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/tab',
|
||||
// component: Layout,
|
||||
// children: [{
|
||||
// path: 'index',
|
||||
// component: () => import('@/views/tab/index'),
|
||||
// name: 'tab',
|
||||
// meta: { title: 'tab', icon: 'tab' }
|
||||
// }]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/table',
|
||||
// component: Layout,
|
||||
// redirect: '/table/complex-table',
|
||||
// name: 'table',
|
||||
// meta: {
|
||||
// title: 'Table',
|
||||
// icon: 'table'
|
||||
// },
|
||||
// children: [
|
||||
// { path: 'dynamic-table', component: () => import('@/views/table/dynamicTable/index'), name: 'dynamicTable', meta: { title: 'dynamicTable' }},
|
||||
// { path: 'drag-table', component: () => import('@/views/table/dragTable'), name: 'dragTable', meta: { title: 'dragTable' }},
|
||||
// { path: 'inline-edit-table', component: () => import('@/views/table/inlineEditTable'), name: 'inlineEditTable', meta: { title: 'inlineEditTable' }},
|
||||
// { path: 'tree-table', component: () => import('@/views/table/treeTable/treeTable'), name: 'treeTableDemo', meta: { title: 'treeTable' }},
|
||||
// { path: 'custom-tree-table', component: () => import('@/views/table/treeTable/customTreeTable'), name: 'customTreeTableDemo', meta: { title: 'customTreeTable' }},
|
||||
// { path: 'complex-table', component: () => import('@/views/table/complexTable'), name: 'complexTable', meta: { title: 'complexTable' }}
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/example',
|
||||
// component: Layout,
|
||||
// redirect: '/example/list',
|
||||
// name: 'example',
|
||||
// meta: {
|
||||
// title: 'example',
|
||||
// icon: 'example'
|
||||
// },
|
||||
// children: [
|
||||
// { path: 'create', component: () => import('@/views/example/create'), name: 'createArticle', meta: { title: 'createArticle', icon: 'edit' }},
|
||||
// { path: 'edit/:id(\\d+)', component: () => import('@/views/example/edit'), name: 'editArticle', meta: { title: 'editArticle', noCache: true }, hidden: true },
|
||||
// { path: 'list', component: () => import('@/views/example/list'), name: 'articleList', meta: { title: 'articleList', icon: 'list' }}
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/nested',
|
||||
// component: Layout,
|
||||
// redirect: '/nested/bar/profile',
|
||||
// name: 'nested',
|
||||
// meta: {
|
||||
// title: 'nested',
|
||||
// icon: 'nested'
|
||||
// },
|
||||
// children: [
|
||||
// {
|
||||
// path: '/nested/bar', // Must write the full path
|
||||
// component: () => import('@/views/nested/bar/index'), // Parent router-view
|
||||
// name: 'bar',
|
||||
// meta: { title: 'bar' },
|
||||
// children: [
|
||||
// {
|
||||
// path: 'profile',
|
||||
// component: () => import('@/views/nested/bar/profile'),
|
||||
// name: 'bar-profile',
|
||||
// meta: { title: 'barProfile' }
|
||||
// },
|
||||
// {
|
||||
// path: 'posts',
|
||||
// component: () => import('@/views/nested/bar/posts'),
|
||||
// name: 'bar-posts',
|
||||
// meta: { title: 'barPosts' }
|
||||
// }
|
||||
// ]
|
||||
// }
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/error',
|
||||
// component: Layout,
|
||||
// redirect: 'noredirect',
|
||||
// name: 'errorPages',
|
||||
// meta: {
|
||||
// title: 'errorPages',
|
||||
// icon: '404'
|
||||
// },
|
||||
// children: [
|
||||
// { path: '401', component: () => import('@/views/errorPage/401'), name: 'page401', meta: { title: 'page401', noCache: true }},
|
||||
// { path: '404', component: () => import('@/views/errorPage/404'), name: 'page404', meta: { title: 'page404', noCache: true }}
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/error-log',
|
||||
// component: Layout,
|
||||
// redirect: 'noredirect',
|
||||
// children: [{ path: 'log', component: () => import('@/views/errorLog/index'), name: 'errorLog', meta: { title: 'errorLog', icon: 'bug' }}]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/excel',
|
||||
// component: Layout,
|
||||
// redirect: '/excel/export-excel',
|
||||
// name: 'excel',
|
||||
// meta: {
|
||||
// title: 'excel',
|
||||
// icon: 'excel'
|
||||
// },
|
||||
// children: [
|
||||
// { path: 'export-excel', component: () => import('@/views/excel/exportExcel'), name: 'exportExcel', meta: { title: 'exportExcel' }},
|
||||
// { path: 'export-selected-excel', component: () => import('@/views/excel/selectExcel'), name: 'selectExcel', meta: { title: 'selectExcel' }},
|
||||
// { path: 'upload-excel', component: () => import('@/views/excel/uploadExcel'), name: 'uploadExcel', meta: { title: 'uploadExcel' }}
|
||||
// ]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/zip',
|
||||
// component: Layout,
|
||||
// redirect: '/zip/download',
|
||||
// alwaysShow: true,
|
||||
// meta: { title: 'zip', icon: 'zip' },
|
||||
// children: [{ path: 'download', component: () => import('@/views/zip/index'), name: 'exportZip', meta: { title: 'exportZip' }}]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/theme',
|
||||
// component: Layout,
|
||||
// redirect: 'noredirect',
|
||||
// children: [{ path: 'index', component: () => import('@/views/theme/index'), name: 'theme', meta: { title: 'theme', icon: 'theme' }}]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/clipboard',
|
||||
// component: Layout,
|
||||
// redirect: 'noredirect',
|
||||
// children: [{ path: 'index', component: () => import('@/views/clipboard/index'), name: 'clipboardDemo', meta: { title: 'clipboardDemo', icon: 'clipboard' }}]
|
||||
// },
|
||||
|
||||
// {
|
||||
// path: '/i18n',
|
||||
// component: Layout,
|
||||
// children: [{ path: 'index', component: () => import('@/views/i18n-demo/index'), name: 'i18n', meta: { title: 'i18n', icon: 'international' }}]
|
||||
// },
|
||||
|
||||
{ path: '*', redirect: '/404', hidden: true }
|
||||
]
|
||||
|
|
|
@ -13,8 +13,6 @@ const getters = {
|
|||
setting: state => state.user.setting,
|
||||
permission_routers: state => state.permission.routers,
|
||||
addRouters: state => state.permission.addRouters,
|
||||
errorLogs: state => state.errorLog.logs,
|
||||
deviceID: state => state.counter.deviceID,
|
||||
mapClick: state => state.counter.mapClick
|
||||
errorLogs: state => state.errorLog.logs
|
||||
}
|
||||
export default getters
|
||||
|
|
|
@ -5,7 +5,6 @@ import errorLog from './modules/errorLog'
|
|||
import permission from './modules/permission'
|
||||
import tagsView from './modules/tagsView'
|
||||
import user from './modules/user'
|
||||
import counter from './modules/counter'
|
||||
import getters from './getters'
|
||||
|
||||
Vue.use(Vuex)
|
||||
|
@ -16,8 +15,7 @@ const store = new Vuex.Store({
|
|||
errorLog,
|
||||
permission,
|
||||
tagsView,
|
||||
user,
|
||||
counter
|
||||
user
|
||||
},
|
||||
getters
|
||||
})
|
||||
|
|
|
@ -1,33 +0,0 @@
|
|||
const counter = {
|
||||
state: {
|
||||
deviceID: '',
|
||||
mapClick: false
|
||||
},
|
||||
mutations: {
|
||||
CHANGE_DEVICE_ID: (state, deviceID) => {
|
||||
state.deviceID = deviceID
|
||||
localStorage.deviceID = deviceID
|
||||
},
|
||||
CHANGE_MAP_CLICK: (state, mapClick) => {
|
||||
state.mapClick = mapClick
|
||||
}
|
||||
},
|
||||
actions: {
|
||||
changeDeviceID({ commit }, deviceID) {
|
||||
commit('CHANGE_DEVICE_ID', deviceID)
|
||||
},
|
||||
changeMapClick({ commit }, mapClick) {
|
||||
commit('CHANGE_MAP_CLICK', mapClick)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
if (localStorage.deviceID) {
|
||||
counter.state.deviceID = localStorage.deviceID
|
||||
}
|
||||
} catch (e) {
|
||||
console.log(e)
|
||||
}
|
||||
|
||||
export default counter
|
|
@ -100,12 +100,11 @@ const user = {
|
|||
// },
|
||||
|
||||
// 登出
|
||||
LogOut({ commit, state, rootState }) {
|
||||
LogOut({ commit, state }) {
|
||||
return new Promise((resolve, reject) => {
|
||||
logout(state.token).then(() => {
|
||||
commit('SET_TOKEN', '')
|
||||
commit('SET_ROLES', [])
|
||||
commit('CHANGE_DEVICE_ID', '', { root: true })
|
||||
removeToken()
|
||||
resolve()
|
||||
}).catch(error => {
|
||||
|
|
|
@ -4,7 +4,6 @@
|
|||
@import './element-ui.scss';
|
||||
@import './sidebar.scss';
|
||||
@import './btn.scss';
|
||||
@import './pagination.scss';
|
||||
|
||||
body {
|
||||
height: 100%;
|
||||
|
@ -129,7 +128,7 @@ code {
|
|||
|
||||
//main-container全局样式
|
||||
.app-container {
|
||||
padding: 10px;
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.components-container {
|
||||
|
|
|
@ -1,60 +0,0 @@
|
|||
.pagination {
|
||||
float: right;
|
||||
font-weight: normal;
|
||||
padding: 2rem 0 1rem 0;
|
||||
.btn-prev {
|
||||
border: 1px solid #d1dbe5;
|
||||
border-right: 0;
|
||||
border-radius: 0 !important;
|
||||
background: #fff !important;
|
||||
margin: 0 !important;
|
||||
}
|
||||
.btn-next {
|
||||
border: 1px solid #d1dbe5;
|
||||
// border-left: 0;
|
||||
background: #fff !important;
|
||||
border-radius: 0!important;
|
||||
margin: 0 !important;
|
||||
}
|
||||
.el-pager li {
|
||||
border: 1px solid #d1dbe5;
|
||||
box-sizing: border-box;
|
||||
background: #fff !important;
|
||||
border-radius: 0!important;
|
||||
border-right: 0;
|
||||
padding: 0;
|
||||
margin: 0 !important;
|
||||
}
|
||||
.el-pager li:not(.disabled).active {
|
||||
background: #409EFF !important;
|
||||
border-color: #409EFF;
|
||||
}
|
||||
.el-pagination__jump {
|
||||
margin-left: .8rem;
|
||||
}
|
||||
.el-pagination__editor.el-input {
|
||||
width: 2.5rem;
|
||||
}
|
||||
}
|
||||
// mobile
|
||||
@media screen and (max-width: 375px) {
|
||||
.pagination {
|
||||
display: flex !important;
|
||||
justify-content: center;
|
||||
float: none;
|
||||
padding: 1rem 0 1rem 0;
|
||||
.el-pager li {
|
||||
// height: 1.5rem;
|
||||
// line-height: 1.5rem;
|
||||
font-size: .5rem !important;
|
||||
// min-width: 1.5rem !important;
|
||||
}
|
||||
.el-pagination__total {
|
||||
// margin-right: 2rem;
|
||||
display: none !important;
|
||||
}
|
||||
.el-pagination__jump {
|
||||
display: none !important;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,12 +1,12 @@
|
|||
import axios from 'axios'
|
||||
import { Message, MessageBox } from 'element-ui'
|
||||
import { Message } from 'element-ui'
|
||||
import store from '@/store'
|
||||
import { getToken } from '@/utils/auth'
|
||||
|
||||
// create an axios instance
|
||||
const service = axios.create({
|
||||
baseURL: process.env.BASE_API, // api的base_url
|
||||
timeout: 50000 // request timeout
|
||||
timeout: 5000 // request timeout
|
||||
})
|
||||
|
||||
// request interceptor
|
||||
|
@ -62,27 +62,7 @@ service.interceptors.response.use(
|
|||
// },
|
||||
error => {
|
||||
console.log('err' + error)
|
||||
if (error && error.response) { // 401 token 过期
|
||||
if (error.response.status === 401) {
|
||||
const ret = error.response
|
||||
const url = ret.config.url
|
||||
const target = '/users/info'
|
||||
console.log(url.indexOf(target))
|
||||
// check if 401 get /api/users/info/ then redirect to /login
|
||||
if (url.indexOf(target) === -1) {
|
||||
MessageBox.confirm('登录过期已被登出,取消继续留在该页面,或者重新登录', '确定登出', {
|
||||
confirmButtonText: '重新登录',
|
||||
cancelButtonText: '取消',
|
||||
type: 'warning'
|
||||
}).then(() => {
|
||||
store.dispatch('FedLogOut').then(() => {
|
||||
location.reload() // 为了重新实例化vue-router对象 避免bug
|
||||
})
|
||||
})
|
||||
return Promise.reject(error)
|
||||
}
|
||||
error.message = ret.data.detail
|
||||
}
|
||||
if (error && error.response) {
|
||||
// check login error response from server api
|
||||
const login_error = error.response.data.non_field_errors
|
||||
if (login_error) {
|
||||
|
|
|
@ -5,7 +5,7 @@
|
|||
export function isvalidUsername(str) {
|
||||
// const valid_map = ['xianfuxing', 'editor']
|
||||
// return valid_map.indexOf(str.trim()) >= 0
|
||||
const usernameRegex = /^(?![0-9]+$)[0-9A-Za-z_]{4,}$/
|
||||
const usernameRegex = /^(?![0-9]+$)[0-9A-Za-z]{4,}$/
|
||||
return usernameRegex.test(str)
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<el-tabs v-model="activeName">
|
||||
<el-tab-pane label="use clipboard directly" name="directly">
|
||||
<el-input v-model="inputData" placeholder="Please input" style='width:400px;'></el-input>
|
||||
<el-button type="primary" icon="document" @click='handleCopy(inputData,$event)'>copy</el-button>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane label="use clipboard by v-directive" name="v-directive">
|
||||
<el-input v-model="inputData" placeholder="Please input" style='width:400px;'></el-input>
|
||||
<el-button type="primary" icon="document" v-clipboard:copy='inputData' v-clipboard:success='clipboardSuccess'>copy</el-button>
|
||||
</el-tab-pane>
|
||||
</el-tabs>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import clip from '@/utils/clipboard' // use clipboard directly
|
||||
import clipboard from '@/directive/clipboard/index.js' // use clipboard by v-directive
|
||||
|
||||
export default {
|
||||
name: 'clipboardDemo',
|
||||
directives: {
|
||||
clipboard
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
activeName: 'directly',
|
||||
inputData: 'https://github.com/PanJiaChen/vue-element-admin'
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
handleCopy(text, event) {
|
||||
clip(text, event)
|
||||
},
|
||||
clipboardSuccess() {
|
||||
this.$message({
|
||||
message: '复制成功',
|
||||
type: 'success',
|
||||
duration: 1500
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -0,0 +1,52 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>This is based on
|
||||
<a class="link-type" href="//github.com/dai-siki/vue-image-crop-upload"> vue-image-crop-upload</a>.
|
||||
{{$t('components.imageUploadTips')}}
|
||||
</code>
|
||||
|
||||
<pan-thumb :image="image"></pan-thumb>
|
||||
|
||||
<el-button type="primary" icon="upload" style="position: absolute;bottom: 15px;margin-left: 40px;" @click="imagecropperShow=true">Change avatar
|
||||
</el-button>
|
||||
|
||||
<image-cropper :width="300" :height="300" url="https://httpbin.org/post" @close='close' @crop-upload-success="cropSuccess" langType="en"
|
||||
:key="imagecropperKey" v-show="imagecropperShow"></image-cropper>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import ImageCropper from '@/components/ImageCropper'
|
||||
import PanThumb from '@/components/PanThumb'
|
||||
|
||||
export default {
|
||||
name: 'avatarUpload-demo',
|
||||
components: { ImageCropper, PanThumb },
|
||||
data() {
|
||||
return {
|
||||
imagecropperShow: false,
|
||||
imagecropperKey: 0,
|
||||
image: 'https://wpimg.wallstcn.com/577965b9-bb9e-4e02-9f0c-095b41417191'
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
cropSuccess(resData) {
|
||||
this.imagecropperShow = false
|
||||
this.imagecropperKey = this.imagecropperKey + 1
|
||||
this.image = resData.files.avatar
|
||||
},
|
||||
close() {
|
||||
this.imagecropperShow = false
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.avatar{
|
||||
width: 200px;
|
||||
height: 200px;
|
||||
border-radius: 50%;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -0,0 +1,150 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>{{$t('components.backToTopTips1')}}</code>
|
||||
<code>{{$t('components.backToTopTips2')}}</code>
|
||||
<div class="placeholder-container">
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
</div>
|
||||
<!--可自定义按钮的样式、show/hide临界点、返回的位置 -->
|
||||
<!--如需文字提示,可在外部添加element的<el-tooltip></el-tooltip>元素 -->
|
||||
<el-tooltip placement="top" content="tooltip">
|
||||
<back-to-top transitionName="fade" :customStyle="myBackToTopStyle" :visibilityHeight="300" :backPosition="50"></back-to-top>
|
||||
</el-tooltip>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import BackToTop from '@/components/BackToTop'
|
||||
|
||||
export default {
|
||||
name: 'backToTop-demo',
|
||||
components: { BackToTop },
|
||||
data() {
|
||||
return {
|
||||
myBackToTopStyle: {
|
||||
right: '50px',
|
||||
bottom: '50px',
|
||||
width: '40px',
|
||||
height: '40px',
|
||||
'border-radius': '4px',
|
||||
'line-height': '45px', // 请保持与高度一致以垂直居中 Please keep consistent with height to center vertically
|
||||
background: '#e7eaf1'// 按钮的背景颜色 The background color of the button
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.placeholder-container div {
|
||||
margin: 10px;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,205 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<p class="warn-content">
|
||||
<a href="https://github.com/PanJiaChen/vue-countTo" target="_blank">countTo-component</a>
|
||||
</p>
|
||||
<count-to ref="example" class="example" :start-val="_startVal" :end-val="_endVal" :duration="_duration" :decimals="_decimals"
|
||||
:separator="_separator" :prefix="_prefix" :suffix="_suffix" :autoplay="false"></count-to>
|
||||
<div style="margin-left: 25%;margin-top: 40px;">
|
||||
<label class="label" for="startValInput">startVal:
|
||||
<input type="number" v-model.number="setStartVal" name="startValInput" />
|
||||
</label>
|
||||
<label class="label" for="endValInput">endVal:
|
||||
<input type="number" v-model.number="setEndVal" name="endVaInput" />
|
||||
</label>
|
||||
<label class="label" for="durationInput">duration:
|
||||
<input type="number" v-model.number="setDuration" name="durationInput" />
|
||||
</label>
|
||||
<div class="startBtn example-btn" @click="start">开始</div>
|
||||
<div class="pause-resume-btn example-btn" @click="pauseResume">暂停/恢复</div>
|
||||
<br/>
|
||||
<label class="label" for="decimalsInput">decimals:
|
||||
<input type="number" v-model.number="setDecimals" name="decimalsInput" />
|
||||
</label>
|
||||
<label class="label" for="separatorInput">separator:
|
||||
<input v-model="setSeparator" name="separatorInput" />
|
||||
</label>
|
||||
<label class="label" for="prefixInput">prefix:
|
||||
<input v-model="setPrefix" name="prefixInput" />
|
||||
</label>
|
||||
<label class="label" for="suffixInput">suffix:
|
||||
<input v-model="setSuffix" name="suffixInput" />
|
||||
</label>
|
||||
</div>
|
||||
<code><count-to :start-val='{{_startVal}}' :end-val='{{_endVal}}' :duration='{{_duration}}'
|
||||
:decimals='{{_decimals}}' :separator='{{_separator}}' :prefix='{{_prefix}}' :suffix='{{_suffix}}'
|
||||
:autoplay=false></code>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import countTo from 'vue-count-to'
|
||||
|
||||
export default {
|
||||
name: 'countTo-demo',
|
||||
components: { countTo },
|
||||
data() {
|
||||
return {
|
||||
setStartVal: 0,
|
||||
setEndVal: 2017,
|
||||
setDuration: 4000,
|
||||
setDecimals: 0,
|
||||
setSeparator: ',',
|
||||
setSuffix: ' rmb',
|
||||
setPrefix: '¥ '
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
_startVal() {
|
||||
if (this.setStartVal) {
|
||||
return this.setStartVal
|
||||
} else {
|
||||
return 0
|
||||
}
|
||||
},
|
||||
_endVal() {
|
||||
if (this.setEndVal) {
|
||||
return this.setEndVal
|
||||
} else {
|
||||
return 0
|
||||
}
|
||||
},
|
||||
_duration() {
|
||||
if (this.setDuration) {
|
||||
return this.setDuration
|
||||
} else {
|
||||
return 100
|
||||
}
|
||||
},
|
||||
_decimals() {
|
||||
if (this.setDecimals) {
|
||||
if (this.setDecimals < 0 || this.setDecimals > 20) {
|
||||
alert('digits argument must be between 0 and 20')
|
||||
return 0
|
||||
}
|
||||
return this.setDecimals
|
||||
} else {
|
||||
return 0
|
||||
}
|
||||
},
|
||||
_separator() {
|
||||
return this.setSeparator
|
||||
},
|
||||
_suffix() {
|
||||
return this.setSuffix
|
||||
},
|
||||
_prefix() {
|
||||
return this.setPrefix
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
start() {
|
||||
this.$refs.example.start()
|
||||
},
|
||||
pauseResume() {
|
||||
this.$refs.example.pauseResume()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.example-btn {
|
||||
display: inline-block;
|
||||
margin-bottom: 0;
|
||||
font-weight: 500;
|
||||
text-align: center;
|
||||
-ms-touch-action: manipulation;
|
||||
touch-action: manipulation;
|
||||
cursor: pointer;
|
||||
background-image: none;
|
||||
border: 1px solid transparent;
|
||||
white-space: nowrap;
|
||||
line-height: 1.5;
|
||||
padding: 4px 15px;
|
||||
font-size: 12px;
|
||||
border-radius: 4px;
|
||||
-webkit-user-select: none;
|
||||
-moz-user-select: none;
|
||||
-ms-user-select: none;
|
||||
user-select: none;
|
||||
-webkit-transition: all .3s cubic-bezier(.645, .045, .355, 1);
|
||||
transition: all .3s cubic-bezier(.645, .045, .355, 1);
|
||||
position: relative;
|
||||
color: rgba(0, 0, 0, .65);
|
||||
background-color: #fff;
|
||||
border-color: #d9d9d9;
|
||||
}
|
||||
|
||||
.example-btn:hover {
|
||||
color: #4AB7BD;
|
||||
background-color: #fff;
|
||||
border-color: #4AB7BD;
|
||||
}
|
||||
.example {
|
||||
font-size: 50px;
|
||||
color: #F6416C;
|
||||
display: block;
|
||||
margin: 10px 0;
|
||||
text-align: center;
|
||||
font-size: 80px;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.label {
|
||||
color: #2f4f4f;
|
||||
font-size: 16px;
|
||||
display: inline-block;
|
||||
margin: 15px 30px 15px 0;
|
||||
}
|
||||
|
||||
input {
|
||||
position: relative;
|
||||
display: inline-block;
|
||||
padding: 4px 7px;
|
||||
width: 70px;
|
||||
height: 28px;
|
||||
cursor: text;
|
||||
font-size: 12px;
|
||||
line-height: 1.5;
|
||||
color: rgba(0, 0, 0, .65);
|
||||
background-color: #fff;
|
||||
background-image: none;
|
||||
border: 1px solid #d9d9d9;
|
||||
border-radius: 4px;
|
||||
-webkit-transition: all .3s;
|
||||
transition: all .3s;
|
||||
}
|
||||
|
||||
.startBtn {
|
||||
margin-left: 20px;
|
||||
font-size: 20px;
|
||||
color: #30B08F;
|
||||
background-color: #fff;
|
||||
}
|
||||
|
||||
.startBtn:hover {
|
||||
background-color: #30B08F;
|
||||
color: #fff;
|
||||
border-color: #30B08F;
|
||||
}
|
||||
|
||||
.pause-resume-btn {
|
||||
font-size: 20px;
|
||||
color: #E65D6E;
|
||||
background-color: #fff;
|
||||
}
|
||||
|
||||
.pause-resume-btn:hover {
|
||||
background-color: #E65D6E;
|
||||
color: #fff;
|
||||
border-color: #E65D6E;
|
||||
}
|
||||
</style>
|
||||
|
||||
|
|
@ -0,0 +1,40 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>drag-list base on
|
||||
<a href="https://github.com/SortableJS/Vue.Draggable" target="_blank">Vue.Draggable</a>
|
||||
</code>
|
||||
<div class="editor-container">
|
||||
<dnd-list :list1="list1" :list2="list2" list1Title="List" list2Title="Article pool"></dnd-list>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import DndList from '@/components/DndList'
|
||||
import { fetchList } from '@/api/article'
|
||||
|
||||
export default {
|
||||
name: 'dndList-demo',
|
||||
components: { DndList },
|
||||
data() {
|
||||
return {
|
||||
list1: [],
|
||||
list2: []
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getData()
|
||||
},
|
||||
methods: {
|
||||
getData() {
|
||||
this.listLoading = true
|
||||
fetchList().then(response => {
|
||||
this.list1 = response.data.items.splice(0, 5)
|
||||
this.list2 = response.data.items
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
@ -0,0 +1,60 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<el-button type="primary" @click="dialogTableVisible = true">open a Drag Dialog</el-button>
|
||||
<el-dialog v-el-drag-dialog @dragDialog="handleDrag" title="Shipping address" :visible.sync="dialogTableVisible">
|
||||
<el-select ref="select" v-model="value" placeholder="请选择">
|
||||
<el-option v-for="item in options" :key="item.value" :label="item.label" :value="item.value">
|
||||
</el-option>
|
||||
</el-select>
|
||||
<el-table :data="gridData">
|
||||
<el-table-column property="date" label="Date" width="150"></el-table-column>
|
||||
<el-table-column property="name" label="Name" width="200"></el-table-column>
|
||||
<el-table-column property="address" label="Address"></el-table-column>
|
||||
</el-table>
|
||||
</el-dialog>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import elDragDialog from '@/directive/el-dragDialog' // base on element-ui
|
||||
|
||||
export default {
|
||||
name: 'dragDialog-demo',
|
||||
directives: { elDragDialog },
|
||||
data() {
|
||||
return {
|
||||
dialogTableVisible: false,
|
||||
options: [
|
||||
{ value: '选项1', label: '黄金糕' },
|
||||
{ value: '选项2', label: '双皮奶' },
|
||||
{ value: '选项3', label: '蚵仔煎' },
|
||||
{ value: '选项4', label: '龙须面' }
|
||||
],
|
||||
value: '',
|
||||
gridData: [{
|
||||
date: '2016-05-02',
|
||||
name: 'John Smith',
|
||||
address: 'No.1518, Jinshajiang Road, Putuo District'
|
||||
}, {
|
||||
date: '2016-05-04',
|
||||
name: 'John Smith',
|
||||
address: 'No.1518, Jinshajiang Road, Putuo District'
|
||||
}, {
|
||||
date: '2016-05-01',
|
||||
name: 'John Smith',
|
||||
address: 'No.1518, Jinshajiang Road, Putuo District'
|
||||
}, {
|
||||
date: '2016-05-03',
|
||||
name: 'John Smith',
|
||||
address: 'No.1518, Jinshajiang Road, Putuo District'
|
||||
}]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
// v-el-drag-dialog onDrag callback function
|
||||
handleDrag() {
|
||||
this.$refs.select.blur()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,68 @@
|
|||
<template>
|
||||
<div class="components-container board">
|
||||
<Kanban :key="1" class="kanban todo" :list="list1" :options="options" header-text="Todo"/>
|
||||
<Kanban :key="2" class="kanban working" :list="list2" :options="options" header-text="Working"/>
|
||||
<Kanban :key="3" class="kanban done" :list="list3" :options="options" header-text="Done"/>
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
import Kanban from '@/components/Kanban'
|
||||
|
||||
export default {
|
||||
name: 'dragKanban-demo',
|
||||
components: {
|
||||
Kanban
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
options: {
|
||||
group: 'mission'
|
||||
},
|
||||
list1: [
|
||||
{ name: 'Mission', id: 1 },
|
||||
{ name: 'Mission', id: 2 },
|
||||
{ name: 'Mission', id: 3 },
|
||||
{ name: 'Mission', id: 4 }
|
||||
],
|
||||
list2: [
|
||||
{ name: 'Mission', id: 5 },
|
||||
{ name: 'Mission', id: 6 },
|
||||
{ name: 'Mission', id: 7 }
|
||||
],
|
||||
list3: [
|
||||
{ name: 'Mission', id: 8 },
|
||||
{ name: 'Mission', id: 9 },
|
||||
{ name: 'Mission', id: 10 }
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
<style lang="scss">
|
||||
.board {
|
||||
width: 1000px;
|
||||
margin-left: 20px;
|
||||
display: flex;
|
||||
justify-content: space-around;
|
||||
flex-direction: row;
|
||||
align-items: flex-start;
|
||||
}
|
||||
.kanban {
|
||||
&.todo {
|
||||
.board-column-header {
|
||||
background: #4A9FF9;
|
||||
}
|
||||
}
|
||||
&.working {
|
||||
.board-column-header {
|
||||
background: #f9944a;
|
||||
}
|
||||
}
|
||||
&.done {
|
||||
.board-column-header {
|
||||
background: #2ac06d;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
@ -0,0 +1,32 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>
|
||||
Based on <a class="link-type" href="https://github.com/rowanwins/vue-dropzone"> dropzone </a>.
|
||||
{{$t('components.dropzoneTips')}}
|
||||
</code>
|
||||
<div class="editor-container">
|
||||
<dropzone v-on:dropzone-removedFile="dropzoneR" v-on:dropzone-success="dropzoneS" id="myVueDropzone" url="https://httpbin.org/post"></dropzone>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Dropzone from '@/components/Dropzone'
|
||||
|
||||
export default {
|
||||
name: 'dropzone-demo',
|
||||
components: { Dropzone },
|
||||
methods: {
|
||||
dropzoneS(file) {
|
||||
console.log(file)
|
||||
this.$message({ message: 'Upload success', type: 'success' })
|
||||
},
|
||||
dropzoneR(file) {
|
||||
console.log(file)
|
||||
this.$message({ message: 'Delete success', type: 'success' })
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
@ -0,0 +1,32 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>JsonEditor is base on <a href="https://github.com/codemirror/CodeMirror" target="_blank">CodeMirrorr</a> , lint base on json-lint </code>
|
||||
<div class="editor-container">
|
||||
<json-editor ref="jsonEditor" v-model="value"></json-editor>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import JsonEditor from '@/components/JsonEditor'
|
||||
|
||||
const jsonData = '[{"items":[{"market_type":"forexdata","symbol":"XAUUSD"},{"market_type":"forexdata","symbol":"UKOIL"},{"market_type":"forexdata","symbol":"CORN"}],"name":""},{"items":[{"market_type":"forexdata","symbol":"XAUUSD"},{"market_type":"forexdata","symbol":"XAGUSD"},{"market_type":"forexdata","symbol":"AUTD"},{"market_type":"forexdata","symbol":"AGTD"}],"name":"贵金属"},{"items":[{"market_type":"forexdata","symbol":"CORN"},{"market_type":"forexdata","symbol":"WHEAT"},{"market_type":"forexdata","symbol":"SOYBEAN"},{"market_type":"forexdata","symbol":"SUGAR"}],"name":"农产品"},{"items":[{"market_type":"forexdata","symbol":"UKOIL"},{"market_type":"forexdata","symbol":"USOIL"},{"market_type":"forexdata","symbol":"NGAS"}],"name":"能源化工"}]'
|
||||
|
||||
export default {
|
||||
name: 'jsonEditor-demo',
|
||||
components: { JsonEditor },
|
||||
data() {
|
||||
return {
|
||||
value: JSON.parse(jsonData)
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.editor-container{
|
||||
position: relative;
|
||||
height: 100%;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -0,0 +1,49 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>Markdown is based on
|
||||
<a href="https://github.com/sparksuite/simplemde-markdown-editor" target="_blank">simplemde-markdown-editor</a> ,Simply encapsulated in Vue.
|
||||
<a target="_blank" href="https://segmentfault.com/a/1190000009762198#articleHeader14">
|
||||
相关文章 </a>
|
||||
</code>
|
||||
<div class="editor-container">
|
||||
<markdown-editor id="contentEditor" ref="contentEditor" v-model="content" :height="300" :zIndex="20"></markdown-editor>
|
||||
</div>
|
||||
<el-button @click="markdown2Html" style="margin-top:80px;" type="primary" icon="el-icon-document">To HTML</el-button>
|
||||
<div v-html="html"></div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import MarkdownEditor from '@/components/MarkdownEditor'
|
||||
|
||||
const content = `
|
||||
**this is test**
|
||||
|
||||
* vue
|
||||
* element
|
||||
* webpack
|
||||
|
||||
## Simplemde
|
||||
`
|
||||
|
||||
export default {
|
||||
name: 'markdown-demo',
|
||||
components: { MarkdownEditor },
|
||||
data() {
|
||||
return {
|
||||
content: content,
|
||||
html: ''
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
markdown2Html() {
|
||||
import('showdown').then(showdown => {
|
||||
const converter = new showdown.Converter()
|
||||
this.html = converter.makeHtml(this.content)
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
|
|
@ -0,0 +1,154 @@
|
|||
<template>
|
||||
<div class="mixin-components-container">
|
||||
<el-row>
|
||||
<el-card class="box-card">
|
||||
<div slot="header" class="clearfix">
|
||||
<span>Buttons</span>
|
||||
</div>
|
||||
<div style="margin-bottom:50px;">
|
||||
<el-col :span="4" class="text-center">
|
||||
<router-link class="pan-btn blue-btn" to="/components/index">Components</router-link>
|
||||
</el-col>
|
||||
<el-col :span="4" class="text-center">
|
||||
<router-link class="pan-btn light-blue-btn" to="/charts/index">Charts</router-link>
|
||||
</el-col>
|
||||
<el-col :span="4" class="text-center">
|
||||
<router-link class="pan-btn pink-btn" to="/excel/download">Excel</router-link>
|
||||
</el-col>
|
||||
<el-col :span="4" class="text-center">
|
||||
<router-link class="pan-btn green-btn" to="/example/table/complex-table">Table</router-link>
|
||||
</el-col>
|
||||
<el-col :span="4" class="text-center">
|
||||
<router-link class="pan-btn tiffany-btn" to="/form/edit-form">Form</router-link>
|
||||
</el-col>
|
||||
<el-col :span="4" class="text-center">
|
||||
<router-link class="pan-btn yellow-btn" to="/theme/index">Theme</router-link>
|
||||
</el-col>
|
||||
</div>
|
||||
</el-card>
|
||||
</el-row>
|
||||
|
||||
<el-row :gutter="20" style="margin-top:50px;">
|
||||
<el-col :span="6">
|
||||
<el-card class="box-card">
|
||||
<div slot="header" class="clearfix">
|
||||
<span>Material Design 的input</span>
|
||||
</div>
|
||||
<div style="height:100px;">
|
||||
<el-form :model="demo" :rules="demoRules">
|
||||
<el-form-item prop="title">
|
||||
<md-input icon="search" name="title" placeholder="输入标题" v-model="demo.title">标题</md-input>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</div>
|
||||
</el-card>
|
||||
</el-col>
|
||||
|
||||
<el-col :span="6">
|
||||
<el-card class="box-card">
|
||||
<div slot="header" class="clearfix">
|
||||
<span>图片hover效果</span>
|
||||
</div>
|
||||
<div class="component-item">
|
||||
<pan-thumb width="100px" height="100px" image="https://wpimg.wallstcn.com/577965b9-bb9e-4e02-9f0c-095b41417191">
|
||||
vue-element-admin
|
||||
</pan-thumb>
|
||||
</div>
|
||||
</el-card>
|
||||
</el-col>
|
||||
|
||||
<el-col :span="6">
|
||||
<el-card class="box-card">
|
||||
<div slot="header" class="clearfix">
|
||||
<span>水波纹 waves v-directive</span>
|
||||
</div>
|
||||
<div class="component-item">
|
||||
<el-button v-waves type="primary">水波纹效果</el-button>
|
||||
</div>
|
||||
</el-card>
|
||||
</el-col>
|
||||
|
||||
<el-col :span="6">
|
||||
<el-card class="box-card">
|
||||
<div slot="header" class="clearfix">
|
||||
<span>hover text</span>
|
||||
</div>
|
||||
<div class="component-item">
|
||||
<mallki className="mallki-text" text="vue-element-admin"></mallki>
|
||||
</div>
|
||||
</el-card>
|
||||
</el-col>
|
||||
</el-row>
|
||||
|
||||
<el-row :gutter="20" style="margin-top:50px;">
|
||||
<el-col :span="6">
|
||||
<el-card class="box-card">
|
||||
<div slot="header" class="clearfix">
|
||||
<span>Share</span>
|
||||
</div>
|
||||
<div class="component-item" style="height:420px;">
|
||||
<dropdown-menu style="margin:0 auto;" title='系列文章' :items='articleList'></dropdown-menu>
|
||||
</div>
|
||||
</el-card>
|
||||
</el-col>
|
||||
</el-row>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import PanThumb from '@/components/PanThumb'
|
||||
import MdInput from '@/components/MDinput'
|
||||
import Mallki from '@/components/TextHoverEffect/Mallki'
|
||||
import DropdownMenu from '@/components/Share/dropdownMenu'
|
||||
import waves from '@/directive/waves/index.js' // 水波纹指令
|
||||
|
||||
export default {
|
||||
name: 'componentMixin-demo',
|
||||
components: {
|
||||
PanThumb,
|
||||
MdInput,
|
||||
Mallki,
|
||||
DropdownMenu
|
||||
},
|
||||
directives: {
|
||||
waves
|
||||
},
|
||||
data() {
|
||||
const validate = (rule, value, callback) => {
|
||||
if (value.length !== 6) {
|
||||
callback(new Error('请输入六个字符'))
|
||||
} else {
|
||||
callback()
|
||||
}
|
||||
}
|
||||
return {
|
||||
demo: {
|
||||
title: ''
|
||||
},
|
||||
demoRules: {
|
||||
title: [{ required: true, trigger: 'change', validator: validate }]
|
||||
},
|
||||
articleList: [
|
||||
{ title: '基础篇', href: 'https://segmentfault.com/a/1190000009275424' },
|
||||
{ title: '登录权限篇', href: 'https://segmentfault.com/a/1190000009506097' },
|
||||
{ title: '实战篇', href: 'https://segmentfault.com/a/1190000009762198' },
|
||||
{ title: 'vueAdmin-template 篇', href: 'https://segmentfault.com/a/1190000010043013' },
|
||||
{ title: '自行封装 component', href: 'https://segmentfault.com/a/1190000009090836' },
|
||||
{ title: '优雅的使用 icon', href: 'https://segmentfault.com/a/https://segmentfault.com/a/1190000012213278' }
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.mixin-components-container {
|
||||
background-color: #f0f2f5;
|
||||
padding: 30px;
|
||||
min-height: calc(100vh - 84px);
|
||||
}
|
||||
.component-item{
|
||||
min-height: 100px;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,67 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code><strong>SplitPane</strong> If you've used
|
||||
<a href="http://codepen.io/" target="_blank"> codepen</a>,
|
||||
<a href="https://jsfiddle.net/" target="_blank"> jsfiddle </a>will not be unfamiliar.
|
||||
<a href="https://github.com/PanJiaChen/vue-split-pane" target='_blank'> Github repository</a>
|
||||
</code>
|
||||
<split-pane v-on:resize="resize" split="vertical">
|
||||
<template slot="paneL">
|
||||
<div class="left-container"></div>
|
||||
</template>
|
||||
<template slot="paneR">
|
||||
<split-pane split="horizontal">
|
||||
<template slot="paneL">
|
||||
<div class="top-container"></div>
|
||||
</template>
|
||||
<template slot="paneR">
|
||||
<div class="bottom-container"></div>
|
||||
</template>
|
||||
</split-pane>
|
||||
</template>
|
||||
</split-pane>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import splitPane from 'vue-splitpane'
|
||||
|
||||
export default {
|
||||
name: 'splitpane-demo',
|
||||
components: { splitPane },
|
||||
methods: {
|
||||
resize() {
|
||||
console.log('resize')
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.components-container {
|
||||
position: relative;
|
||||
height: 100vh;
|
||||
}
|
||||
|
||||
.left-container {
|
||||
background-color: #F38181;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.right-container {
|
||||
background-color: #FCE38A;
|
||||
height: 200px;
|
||||
}
|
||||
|
||||
.top-container {
|
||||
background-color: #FCE38A;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.bottom-container {
|
||||
width: 100%;
|
||||
background-color: #95E1D3;
|
||||
height: 100%;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,130 @@
|
|||
<template>
|
||||
<div>
|
||||
<sticky className="sub-navbar">
|
||||
<el-dropdown trigger="click">
|
||||
<el-button plain>
|
||||
Platform<i class="el-icon-caret-bottom el-icon--right"></i>
|
||||
</el-button>
|
||||
<el-dropdown-menu class="no-border" slot="dropdown">
|
||||
<el-checkbox-group v-model="platforms" style="padding: 5px 15px;">
|
||||
<el-checkbox v-for="item in platformsOptions" :label="item.key" :key="item.key">
|
||||
{{item.name}}
|
||||
</el-checkbox>
|
||||
</el-checkbox-group>
|
||||
</el-dropdown-menu>
|
||||
</el-dropdown>
|
||||
|
||||
<el-dropdown trigger="click">
|
||||
<el-button plain>
|
||||
Link<i class="el-icon-caret-bottom el-icon--right"></i>
|
||||
</el-button>
|
||||
<el-dropdown-menu class="no-padding no-border" style="width:300px" slot="dropdown">
|
||||
<el-input placeholder="Please enter the content" v-model="url">
|
||||
<template slot="prepend">Url</template>
|
||||
</el-input>
|
||||
</el-dropdown-menu>
|
||||
</el-dropdown>
|
||||
|
||||
<div class="time-container">
|
||||
<el-date-picker v-model="time" type="datetime" :picker-options="pickerOptions" format="yyyy-MM-dd HH:mm:ss" placeholder="Release time">
|
||||
</el-date-picker>
|
||||
</div>
|
||||
|
||||
<el-button style="margin-left: 10px;" type="success">publish
|
||||
</el-button>
|
||||
</sticky>
|
||||
|
||||
<div class="components-container">
|
||||
<code>Sticky header, {{$t('components.stickyTips')}}</code>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
<div>placeholder</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
|
||||
<script>
|
||||
import Sticky from '@/components/Sticky'
|
||||
|
||||
export default {
|
||||
name: 'sticky-demo',
|
||||
components: { Sticky },
|
||||
data() {
|
||||
return {
|
||||
time: '',
|
||||
url: '',
|
||||
platforms: ['a-platform'],
|
||||
platformsOptions: [
|
||||
{ key: 'a-platform', name: 'platformA' },
|
||||
{ key: 'b-platform', name: 'platformB' },
|
||||
{ key: 'c-platform', name: 'platformC' }
|
||||
],
|
||||
pickerOptions: {
|
||||
disabledDate(time) {
|
||||
return time.getTime() > Date.now()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.components-container div {
|
||||
margin: 10px;
|
||||
}
|
||||
|
||||
.time-container {
|
||||
display: inline-block;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,37 @@
|
|||
<template>
|
||||
<div class="components-container">
|
||||
<code>
|
||||
{{$t('components.tinymceTips')}}
|
||||
<a target="_blank" class="link-type" href="https://panjiachen.github.io/vue-element-admin-site/component/rich-editor.html"> {{$t('components.documentation')}}</a>
|
||||
</code>
|
||||
<div>
|
||||
<tinymce :height="300" v-model="content"></tinymce>
|
||||
</div>
|
||||
<div class="editor-content" v-html="content"></div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Tinymce from '@/components/Tinymce'
|
||||
|
||||
export default {
|
||||
name: 'tinymce-demo',
|
||||
components: { Tinymce },
|
||||
data() {
|
||||
return {
|
||||
content:
|
||||
`<h1 style="text-align: center;">Welcome to the TinyMCE demo!</h1><p style="text-align: center; font-size: 15px;"><img title="TinyMCE Logo" src="//www.tinymce.com/images/glyph-tinymce@2x.png" alt="TinyMCE Logo" width="110" height="97" /><ul>
|
||||
<li>Our <a href="//www.tinymce.com/docs/">documentation</a> is a great resource for learning how to configure TinyMCE.</li><li>Have a specific question? Visit the <a href="https://community.tinymce.com/forum/">Community Forum</a>.</li><li>We also offer enterprise grade support as part of <a href="https://tinymce.com/pricing">TinyMCE premium subscriptions</a>.</li>
|
||||
</ul>`
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.editor-content{
|
||||
margin-top: 20px;
|
||||
}
|
||||
</style>
|
||||
|
||||
|
|
@ -1,172 +0,0 @@
|
|||
<template>
|
||||
<div id="chart" :class="className" :style="{height:height,width:width}"></div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import echarts from 'echarts'
|
||||
require('echarts/theme/macarons') // echarts theme
|
||||
import { debounce } from '@/utils'
|
||||
|
||||
export default {
|
||||
props: {
|
||||
className: {
|
||||
type: String,
|
||||
default: 'chart'
|
||||
},
|
||||
width: {
|
||||
type: String,
|
||||
default: '100%'
|
||||
},
|
||||
height: {
|
||||
type: String,
|
||||
default: '350px'
|
||||
},
|
||||
autoResize: {
|
||||
type: Boolean,
|
||||
default: true
|
||||
},
|
||||
chartData: {
|
||||
type: Object
|
||||
},
|
||||
showChart: {
|
||||
type: Boolean
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
chart: null,
|
||||
rotate: 0,
|
||||
screenWidth: document.body.clientWidth
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
window.screenWidth = document.body.clientWidth
|
||||
if (window.screenWidth <= 400) {
|
||||
this.rotate = 30
|
||||
}
|
||||
this.initChart()
|
||||
if (this.autoResize) {
|
||||
this.__resizeHanlder = debounce(() => {
|
||||
if (this.chart) {
|
||||
this.chart.resize()
|
||||
}
|
||||
}, 100)
|
||||
window.addEventListener('resize', this.__resizeHanlder)
|
||||
}
|
||||
|
||||
// 监听侧边栏的变化
|
||||
const sidebarElm = document.getElementsByClassName('sidebar-container')[0]
|
||||
sidebarElm.addEventListener('transitionend', this.__resizeHanlder)
|
||||
|
||||
// 监听窗体大小
|
||||
const that = this
|
||||
window.onresize = () => {
|
||||
return (() => {
|
||||
window.screenWidth = document.body.clientWidth
|
||||
that.screenWidth = window.screenWidth
|
||||
console.log(window.screenWidth)
|
||||
if (window.screenWidth <= 400) {
|
||||
this.rotate = 30
|
||||
}
|
||||
})()
|
||||
}
|
||||
},
|
||||
beforeDestroy() {
|
||||
if (!this.chart) {
|
||||
return
|
||||
}
|
||||
if (this.autoResize) {
|
||||
window.removeEventListener('resize', this.__resizeHanlder)
|
||||
}
|
||||
|
||||
const sidebarElm = document.getElementsByClassName('sidebar-container')[0]
|
||||
sidebarElm.removeEventListener('transitionend', this.__resizeHanlder)
|
||||
|
||||
this.chart.dispose()
|
||||
this.chart = null
|
||||
},
|
||||
watch: {
|
||||
chartData: {
|
||||
deep: true,
|
||||
handler(val) {
|
||||
this.setOptions(val)
|
||||
}
|
||||
},
|
||||
showChart(val) {
|
||||
if (val) {
|
||||
this.chart.resize()
|
||||
}
|
||||
},
|
||||
screenWidth(val) {
|
||||
this.screenWidth = val
|
||||
if (val <= 400) {
|
||||
this.rotate = 30
|
||||
this.setOptions(this.chartData)
|
||||
} else {
|
||||
this.rotate = 0
|
||||
this.setOptions(this.chartData)
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
setOptions({ historyData, xAxis, title } = {}) {
|
||||
this.chart.setOption({
|
||||
xAxis: {
|
||||
// data: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'],
|
||||
data: xAxis,
|
||||
boundaryGap: false,
|
||||
axisLabel: {
|
||||
interval: 0,
|
||||
rotate: this.rotate
|
||||
},
|
||||
axisTick: {
|
||||
show: false
|
||||
}
|
||||
},
|
||||
grid: {
|
||||
left: 10,
|
||||
right: 10,
|
||||
bottom: 20,
|
||||
top: 30,
|
||||
containLabel: true
|
||||
},
|
||||
tooltip: {
|
||||
trigger: 'axis',
|
||||
axisPointer: {
|
||||
type: 'cross'
|
||||
},
|
||||
padding: [5, 10]
|
||||
},
|
||||
yAxis: {
|
||||
axisTick: {
|
||||
show: false
|
||||
}
|
||||
},
|
||||
legend: {
|
||||
data: [title]
|
||||
},
|
||||
series: [{
|
||||
name: title, itemStyle: {
|
||||
normal: {
|
||||
color: '#FF005A',
|
||||
lineStyle: {
|
||||
color: '#FF005A',
|
||||
width: 2
|
||||
}
|
||||
}
|
||||
},
|
||||
smooth: true,
|
||||
type: 'line',
|
||||
data: historyData,
|
||||
animationDuration: 2800,
|
||||
animationEasing: 'cubicInOut'
|
||||
}]
|
||||
})
|
||||
},
|
||||
initChart() {
|
||||
this.chart = echarts.init(this.$el, 'macarons')
|
||||
// this.setOptions(this.chartData)
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -1,189 +0,0 @@
|
|||
<template>
|
||||
<div id="chart" :class="className" :style="{height:height,width:width}"></div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import echarts from 'echarts'
|
||||
require('echarts/theme/macarons') // echarts theme
|
||||
import { debounce } from '@/utils'
|
||||
|
||||
export default {
|
||||
props: {
|
||||
className: {
|
||||
type: String,
|
||||
default: 'chart'
|
||||
},
|
||||
width: {
|
||||
type: String,
|
||||
default: '100%'
|
||||
},
|
||||
height: {
|
||||
type: String,
|
||||
default: '350px'
|
||||
},
|
||||
autoResize: {
|
||||
type: Boolean,
|
||||
default: true
|
||||
},
|
||||
HumitureData: {
|
||||
type: Object
|
||||
},
|
||||
showHumiture: {
|
||||
type: Boolean
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
chart: null,
|
||||
rotate: 0,
|
||||
screenWidth: document.body.clientWidth
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
window.screenWidth = document.body.clientWidth
|
||||
if (window.screenWidth <= 400) {
|
||||
this.rotate = 30
|
||||
}
|
||||
this.initChart()
|
||||
if (this.autoResize) {
|
||||
this.__resizeHanlder = debounce(() => {
|
||||
if (this.chart) {
|
||||
this.chart.resize()
|
||||
}
|
||||
}, 100)
|
||||
window.addEventListener('resize', this.__resizeHanlder)
|
||||
}
|
||||
|
||||
// 监听侧边栏的变化
|
||||
const sidebarElm = document.getElementsByClassName('sidebar-container')[0]
|
||||
sidebarElm.addEventListener('transitionend', this.__resizeHanlder)
|
||||
|
||||
// 监听窗体大小
|
||||
const that = this
|
||||
window.onresize = () => {
|
||||
return (() => {
|
||||
window.screenWidth = document.body.clientWidth
|
||||
that.screenWidth = window.screenWidth
|
||||
console.log(window.screenWidth)
|
||||
if (window.screenWidth <= 400) {
|
||||
this.rotate = 30
|
||||
}
|
||||
})()
|
||||
}
|
||||
},
|
||||
beforeDestroy() {
|
||||
if (!this.chart) {
|
||||
return
|
||||
}
|
||||
if (this.autoResize) {
|
||||
window.removeEventListener('resize', this.__resizeHanlder)
|
||||
}
|
||||
|
||||
const sidebarElm = document.getElementsByClassName('sidebar-container')[0]
|
||||
sidebarElm.removeEventListener('transitionend', this.__resizeHanlder)
|
||||
|
||||
this.chart.dispose()
|
||||
this.chart = null
|
||||
},
|
||||
watch: {
|
||||
HumitureData: {
|
||||
deep: true,
|
||||
handler(val) {
|
||||
this.setOptions(val)
|
||||
}
|
||||
},
|
||||
showHumiture(val) {
|
||||
if (val) {
|
||||
this.chart.resize()
|
||||
}
|
||||
},
|
||||
screenWidth(val) {
|
||||
this.screenWidth = val
|
||||
if (val <= 400) {
|
||||
this.rotate = 30
|
||||
this.setOptions(this.HumitureData)
|
||||
} else {
|
||||
this.rotate = 0
|
||||
this.setOptions(this.HumitureData)
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
setOptions({ historyData, xAxis, title } = {}) {
|
||||
this.chart.setOption({
|
||||
xAxis: {
|
||||
// data: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'],
|
||||
data: xAxis,
|
||||
boundaryGap: false,
|
||||
axisLabel: {
|
||||
interval: 0,
|
||||
rotate: this.rotate
|
||||
},
|
||||
axisTick: {
|
||||
show: false
|
||||
}
|
||||
},
|
||||
grid: {
|
||||
left: 10,
|
||||
right: 10,
|
||||
bottom: 20,
|
||||
top: 30,
|
||||
containLabel: true
|
||||
},
|
||||
tooltip: {
|
||||
trigger: 'axis',
|
||||
axisPointer: {
|
||||
type: 'cross'
|
||||
},
|
||||
padding: [5, 10]
|
||||
},
|
||||
yAxis: {
|
||||
axisTick: {
|
||||
show: false
|
||||
}
|
||||
},
|
||||
legend: {
|
||||
data: title
|
||||
},
|
||||
series: [{
|
||||
name: title[0], itemStyle: {
|
||||
normal: {
|
||||
color: '#FF005A',
|
||||
lineStyle: {
|
||||
color: '#FF005A',
|
||||
width: 2
|
||||
}
|
||||
}
|
||||
},
|
||||
smooth: true,
|
||||
type: 'line',
|
||||
data: historyData.temperature,
|
||||
animationDuration: 2800,
|
||||
animationEasing: 'cubicInOut'
|
||||
},
|
||||
{
|
||||
name: title[1], itemStyle: {
|
||||
normal: {
|
||||
color: '#3888fa',
|
||||
lineStyle: {
|
||||
color: '#3888fa',
|
||||
width: 2
|
||||
}
|
||||
}
|
||||
},
|
||||
smooth: true,
|
||||
type: 'line',
|
||||
data: historyData.humidity,
|
||||
animationDuration: 2800,
|
||||
animationEasing: 'cubicInOut'
|
||||
}]
|
||||
})
|
||||
},
|
||||
initChart() {
|
||||
this.chart = echarts.init(this.$el, 'macarons')
|
||||
console.log(this.HumitureData)
|
||||
// this.setOptions(this.HumitureData)
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -1,296 +0,0 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<div class="base-wrapper">
|
||||
<div class="device-base">
|
||||
<p class="item"><span class="keyword">{{$t('counter.device')}}: </span><el-tag>{{deviceID}}</el-tag></p>
|
||||
<p class="item" v-if="lastItem.device_name"><span class="keyword">{{$t('counter.deviceName')}}: </span><el-tag>{{lastItem.device_name}}</el-tag></p>
|
||||
<p class="item" v-else><span class="keyword">{{$t('counter.deviceName')}}: </span><el-tag>{{$t('counter.noName')}}</el-tag></p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="screen-wrapper">
|
||||
<div class="device-screen">
|
||||
<table cellspacing="0">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td v-for="(item, index) of lastTime" :key="index">
|
||||
{{item}}
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td v-for="(item, index) of lastCount" :key="index">
|
||||
{{item}}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div class="device-status">
|
||||
<ul>
|
||||
<li>Status:
|
||||
<span
|
||||
:class="lastItem.status ? 'text-success' : 'text-danger'"
|
||||
v-if="lastItem.status == 0"
|
||||
>
|
||||
Offline
|
||||
</span>
|
||||
<span
|
||||
:class="lastItem.status ? 'text-success' : 'text-danger'"
|
||||
v-if="lastItem.status == 1"
|
||||
>
|
||||
Online
|
||||
</span>
|
||||
</li>
|
||||
<li class="signal">Signal: <span>{{lastItem.signal}}/31</span></li>
|
||||
<li>Power: <span>{{lastItem.energy.replace('%','')}}%</span></li>
|
||||
</ul>
|
||||
</div>
|
||||
<div class="device-status"
|
||||
v-if="lastItem.chip_type === 'AIR-V2'"
|
||||
>
|
||||
<ul>
|
||||
<li>
|
||||
<p>LED开关
|
||||
<el-switch
|
||||
v-model="led"
|
||||
active-color="#13ce66"
|
||||
inactive-color="#ff4949"
|
||||
@change="handleLedSwitchChange"
|
||||
>
|
||||
</el-switch>
|
||||
</p>
|
||||
</li>
|
||||
<li>
|
||||
<el-button type="primary" icon="el-icon-refresh" size="mini" @click="handleCountClear" :loading="clearCountLoading">计数清零</el-button>
|
||||
</li>
|
||||
<!-- <li>
|
||||
<el-button type="primary" icon="el-icon-delete" size="mini" @click="handleMosqClean">自动清扫</el-button>
|
||||
</li> -->
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<!-- 计数器清零确认弹窗 -->
|
||||
<el-dialog
|
||||
title="确认"
|
||||
:visible.sync="dialogCountVisible"
|
||||
:width="dialogWidth"
|
||||
center
|
||||
>
|
||||
<span>确定要清零计数器吗?</span>
|
||||
<span slot="footer" class="dialog-footer">
|
||||
<el-button @click="dialogCountVisible = false">取消</el-button>
|
||||
<el-button type="primary" @click="handleCountClear">确定</el-button>
|
||||
</span>
|
||||
</el-dialog>
|
||||
|
||||
<!-- 清理速度选择、确认弹窗 -->
|
||||
<el-dialog
|
||||
title="请选择清理速度,并确定!"
|
||||
:visible.sync="dialogMosqVisible"
|
||||
:width="dialogWidth"
|
||||
center
|
||||
>
|
||||
|
||||
<div class="block">
|
||||
<el-row>
|
||||
<el-col :span="12"><div class="grid-content bg-purple">
|
||||
<span style="display: flex; justify-content: flex-start;">慢🐢</span>
|
||||
</div></el-col>
|
||||
<el-col :span="12"><div class="grid-content bg-purple">
|
||||
<span style="display: flex; justify-content: flex-end;">🐰快</span>
|
||||
</div></el-col>
|
||||
</el-row>
|
||||
<el-slider
|
||||
v-model="cleanSpeed"
|
||||
:step="1"
|
||||
:min="1"
|
||||
:max="9"
|
||||
show-stops>
|
||||
</el-slider>
|
||||
</div>
|
||||
<span slot="footer" class="dialog-footer">
|
||||
<el-button @click="dialogMosqVisible = false">取消</el-button>
|
||||
<el-button type="primary" @click="handleMosqClean">确定</el-button>
|
||||
</span>
|
||||
</el-dialog>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import moment from 'moment'
|
||||
import { fetchRemoteControl } from '@/api/counter'
|
||||
|
||||
export default {
|
||||
name: 'screen',
|
||||
props: {
|
||||
deviceID: String,
|
||||
lastItem: Object
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
led: undefined,
|
||||
dialogCountVisible: false,
|
||||
dialogMosqVisible: false,
|
||||
clearCountLoading: false,
|
||||
cleanSpeed: 6
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
sleep(time) {
|
||||
return new Promise(resolve => setTimeout(resolve, time))
|
||||
},
|
||||
async handleLedSwitchChange() {
|
||||
const action = this.led ? 'ledOn' : 'ledOff'
|
||||
await this.sendRemoteControlCommand(action)
|
||||
},
|
||||
async handleCountClear() {
|
||||
if (!this.dialogCountVisible) {
|
||||
this.showCountConfirmationDialog()
|
||||
} else {
|
||||
await this.sendRemoteControlCommand('countClear')
|
||||
this.clearCountLoading = true
|
||||
this.sleep(7000).then(() => {
|
||||
this.clearCountLoading = false
|
||||
this.$emit('countClear')
|
||||
})
|
||||
}
|
||||
},
|
||||
async handleMosqClean() {
|
||||
if (!this.dialogMosqVisible) {
|
||||
this.showMosqConfirmationDialog()
|
||||
} else {
|
||||
await this.sendRemoteControlCommand('mosqClean', { speed: this.cleanSpeed })
|
||||
}
|
||||
},
|
||||
async sendRemoteControlCommand(command, options = {}) {
|
||||
try {
|
||||
const { speed } = options
|
||||
const deviceID = this.deviceID
|
||||
console.log(deviceID, command, speed)
|
||||
|
||||
const requestData = { command, speed }
|
||||
|
||||
const response = await fetchRemoteControl(deviceID, requestData)
|
||||
console.log('Command sent successfully:', response.data)
|
||||
} catch (error) {
|
||||
console.error('Error sending command:', error)
|
||||
} finally {
|
||||
this.dialogCountVisible = false
|
||||
this.dialogMosqVisible = false
|
||||
}
|
||||
},
|
||||
showCountConfirmationDialog() {
|
||||
this.dialogCountVisible = true
|
||||
},
|
||||
showMosqConfirmationDialog() {
|
||||
this.dialogMosqVisible = true
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
lastTime() {
|
||||
const curTime = moment().format('YYYY-MM-DD HH:mm')
|
||||
return curTime.split('')
|
||||
// return this.lastItem.calc_time.substr(0, 16).split('')
|
||||
},
|
||||
lastCount() {
|
||||
const count = this.lastItem.count
|
||||
const qty = 'Qty.' + ' '.repeat(10 - count.length) + '00' + count
|
||||
return qty.split('')
|
||||
},
|
||||
dialogWidth() {
|
||||
// 获取当前浏览器窗口宽度
|
||||
const windowWidth = window.innerWidth || document.documentElement.clientWidth || document.body.clientWidth
|
||||
|
||||
// 如果窗口宽度大于800像素,设置对话框宽度为30%,否则设置为100%
|
||||
return windowWidth > 600 ? '30%' : '100%'
|
||||
}
|
||||
|
||||
},
|
||||
mounted() {
|
||||
this.led = this.lastItem.led_status !== 'OFF'
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.text-success {
|
||||
color: #67C23A
|
||||
}
|
||||
.text-danger {
|
||||
color: #F56C6C
|
||||
}
|
||||
.base-wrapper {
|
||||
overflow: auto;
|
||||
.device-base {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
min-width: 350px;
|
||||
.item {
|
||||
width: 300px;
|
||||
margin: 0 0 5px 0;
|
||||
}
|
||||
.keyword {
|
||||
display: inline-block;
|
||||
width: 100px;
|
||||
font-size: 0.9em;
|
||||
}
|
||||
}
|
||||
}
|
||||
.screen-wrapper {
|
||||
background: #F2F6FC;
|
||||
.device-screen {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
table {
|
||||
font-size: 1.2rem;
|
||||
font-family: 'Courier New', Courier, monospace;
|
||||
border: 1px solid #666;
|
||||
border-collapse: collapse;
|
||||
text-align: center;
|
||||
margin: 2rem 0 2rem 0;
|
||||
td {
|
||||
border: 1px solid #666;
|
||||
width: 1rem;
|
||||
height: 1.5rem;
|
||||
line-height: 1.5rem;
|
||||
font-weight: 600;
|
||||
padding: .2rem;
|
||||
}
|
||||
}
|
||||
}
|
||||
.device-status {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
margin: -2rem 0 1rem 0;
|
||||
ul {
|
||||
padding: 0;
|
||||
li {
|
||||
font-size: .85rem;
|
||||
list-style-type: none;
|
||||
display: inline-block;
|
||||
}
|
||||
.signal {
|
||||
margin: 0 2rem 0 2rem
|
||||
}
|
||||
}
|
||||
}
|
||||
@media only screen and (max-width: 768px) {
|
||||
.device-screen {
|
||||
table {
|
||||
margin: 1rem 0 1rem 0;
|
||||
td {
|
||||
font-size: 1rem;
|
||||
}
|
||||
}
|
||||
}
|
||||
.device-status {
|
||||
margin: -1rem 0 1.5rem 0;
|
||||
font-size: 1rem;
|
||||
}
|
||||
.signal {
|
||||
margin: 0 1rem 0 1rem
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
|
@ -1,12 +1,14 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<p class="warn-content">设备设置</p>
|
||||
<p class="warn-content">
|
||||
只能模块消息推送列表
|
||||
</p>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'deviceSetting'
|
||||
name: 'count'
|
||||
}
|
||||
</script>
|
||||
|
|
@ -1,392 +0,0 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<el-tabs v-model="activeName" @tab-click="handleTabClick">
|
||||
<el-tab-pane :label="$t('counter.screen')" name="screen">
|
||||
<transition>
|
||||
<screen
|
||||
:deviceID="this.$store.getters.deviceID"
|
||||
:lastItem="lastItem"
|
||||
@countClear="countClear"
|
||||
v-if="flag"
|
||||
>
|
||||
</screen>
|
||||
</transition>
|
||||
</el-tab-pane>
|
||||
<el-tab-pane :label="$t('counter.trendChart')" name="chart">
|
||||
<el-row style="background:#fff;padding:16px 16px 0;margin-bottom:32px;">
|
||||
<chart
|
||||
:chart-data="lineChartData.total"
|
||||
:showChart="showChart"
|
||||
>
|
||||
</chart>
|
||||
</el-row>
|
||||
</el-tab-pane>
|
||||
<!-- <el-tab-pane :label="$t('counter.humitureChart')" name="humiture">
|
||||
<el-row style="background:#fff;padding:16px 16px 0;margin-bottom:32px;">
|
||||
<humiture
|
||||
:humiture-data="HumitureData.total"
|
||||
:showHumiture="showHumiture"
|
||||
>
|
||||
</humiture>
|
||||
</el-row>
|
||||
</el-tab-pane> -->
|
||||
</el-tabs>
|
||||
|
||||
<div class="filter-container">
|
||||
<div class="date-selector filter-item">
|
||||
<el-date-picker
|
||||
v-model="dateRange"
|
||||
size="small"
|
||||
type="daterange"
|
||||
align="right"
|
||||
:range-separator="$t('counter.to')"
|
||||
:start-placeholder="$t('counter.start_date')"
|
||||
:end-placeholder="$t('counter.end_date')"
|
||||
:picker-options="pickerOptions"
|
||||
value-format="yyyy-MM-dd"
|
||||
@change="handleDateSelect"
|
||||
/>
|
||||
</div>
|
||||
<el-button class="filter-item" size="small" type="primary" v-waves icon="el-icon-search" @click="handleFilter">{{$t('table.search')}}</el-button>
|
||||
</div>
|
||||
|
||||
<el-table
|
||||
v-show="!showHumiture"
|
||||
v-loading="listLoading"
|
||||
:data="deviceLogs"
|
||||
style="width: 100%">
|
||||
<el-table-column
|
||||
type="index"
|
||||
:label="$t('counter.sn')"
|
||||
width="50">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="device_id"
|
||||
:label="$t('counter.device')"
|
||||
min-width="150">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="total"
|
||||
:label="$t('counter.count')"
|
||||
min-width="80">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="date"
|
||||
:label="$t('counter.date')"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<div v-show="!showHumiture" class="pagination-container">
|
||||
<el-pagination background
|
||||
:current-page="1"
|
||||
:page-sizes="[10,20,30,50]"
|
||||
:page-size="deviceHistoryListQuery.limit"
|
||||
layout="total, sizes, prev, pager, next, jumper"
|
||||
:total="logsTotal" @size-change="handleSizeChange" @current-change="handleCurrentChange" />
|
||||
</div>
|
||||
|
||||
<!-- humiture table -->
|
||||
<el-table
|
||||
v-show="showHumiture"
|
||||
v-loading="tempLoading"
|
||||
:data="deviceTempTableLogs"
|
||||
style="width: 100%">
|
||||
<el-table-column
|
||||
prop="create_time"
|
||||
:label="$t('counter.date')"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="temperature"
|
||||
:label="$t('counter.temperature')"
|
||||
min-width="80">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="humidity"
|
||||
:label="$t('counter.humidity')"
|
||||
min-width="80">
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<!-- humiture paging -->
|
||||
<div v-show="showHumiture" class="pagination-container">
|
||||
<el-pagination background
|
||||
:current-page="1"
|
||||
:page-sizes="[10,20,30,50]"
|
||||
:page-size="deviceTempListQuery.limit"
|
||||
layout="total, sizes, prev, pager, next, jumper"
|
||||
:total="tempTotal" @size-change="handleTempSizeChange" @current-change="handleTempCurrentChange" />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import waves from '@/directive/waves' // 水波纹指令
|
||||
import { fetchDeviceList, fetchDeviceLogsHistory, fetchDeviceTempLog } from '@/api/counter'
|
||||
import Screen from './components/screen'
|
||||
import Chart from './components/chart'
|
||||
import Humiture from './components/humiture'
|
||||
|
||||
export default {
|
||||
name: 'deviceDetail',
|
||||
components: {
|
||||
Screen,
|
||||
Chart,
|
||||
Humiture
|
||||
},
|
||||
directives: {
|
||||
waves
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
lineChartData: {
|
||||
total: {
|
||||
historyData: [],
|
||||
xAxis: [],
|
||||
title: 'Trend'
|
||||
}
|
||||
},
|
||||
HumitureData: {
|
||||
total: {
|
||||
historyData: {
|
||||
temperature: [],
|
||||
humidity: []
|
||||
},
|
||||
xAxis: [],
|
||||
title: ['temperature', 'humidity']
|
||||
}
|
||||
},
|
||||
deviceTempListQuery: {
|
||||
device_id: undefined,
|
||||
page: 1,
|
||||
limit: 20,
|
||||
start: undefined,
|
||||
end: undefined,
|
||||
ordering: '-create_time'
|
||||
},
|
||||
deviceHistoryListQuery: {
|
||||
page: 1,
|
||||
limit: 20,
|
||||
device_id: undefined,
|
||||
start: undefined,
|
||||
end: undefined
|
||||
},
|
||||
listLoading: true,
|
||||
tempLoading: true,
|
||||
device_id: undefined,
|
||||
deviceLogs: [],
|
||||
deviceTempLogs: [],
|
||||
deviceTempTableLogs: [],
|
||||
activeName: 'screen',
|
||||
logsTotal: 0,
|
||||
tempTotal: 0,
|
||||
lastItem: {},
|
||||
showScreen: true,
|
||||
showChart: false,
|
||||
showHumiture: false,
|
||||
flag: false,
|
||||
pickerOptions: null,
|
||||
dateRange: undefined
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
activeName(val) {
|
||||
if (val === 'chart') {
|
||||
this.showChart = true
|
||||
}
|
||||
if (val === 'humiture') {
|
||||
this.showHumiture = true
|
||||
}
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.timer = setInterval(() => {
|
||||
this.getDevices({ device_id: this.device_id })
|
||||
}, 30 * 1000)
|
||||
},
|
||||
methods: {
|
||||
getDeviceLogsHistory(params) {
|
||||
fetchDeviceLogsHistory(params).then(response => {
|
||||
const dateList = []
|
||||
this.deviceLogs = response.data.results
|
||||
this.deviceLogs.forEach((item, index) => {
|
||||
this.lineChartData.total.historyData.push(item.total)
|
||||
dateList.push(item.date.substr(5))
|
||||
})
|
||||
this.lineChartData.total.historyData = this.lineChartData.total.historyData.reverse()
|
||||
this.lineChartData.total.xAxis = dateList.reverse()
|
||||
this.logsTotal = response.data.count
|
||||
this.listLoading = false
|
||||
})
|
||||
},
|
||||
countClear() {
|
||||
this.getDevices({ device_id: this.device_id })
|
||||
},
|
||||
// getDeviceLogsTableHistory(params) {
|
||||
// fetchDeviceLogsHistory(params).then(response => {
|
||||
// this.deviceLogs = response.data.results
|
||||
// this.logsTotal = response.data.count
|
||||
// this.listLoading = false
|
||||
// })
|
||||
// },
|
||||
getDeviceTempLog(params) {
|
||||
fetchDeviceTempLog(params).then(response => {
|
||||
const dateList = []
|
||||
this.deviceTempLogs = response.data.results
|
||||
this.deviceTempLogs.forEach((item, index) => {
|
||||
if (index % 2 === 0) {
|
||||
this.HumitureData.total.historyData.temperature.push(item.temperature)
|
||||
this.HumitureData.total.historyData.humidity.push(item.humidity)
|
||||
dateList.push(item.last_time.substr(11, 5))
|
||||
}
|
||||
})
|
||||
this.HumitureData.total.xAxis = dateList
|
||||
this.tempTotal = response.data.count
|
||||
this.tempLoading = false
|
||||
})
|
||||
},
|
||||
getDeviceTempTableLog(params) {
|
||||
fetchDeviceTempLog(params).then(response => {
|
||||
this.deviceTempTableLogs = response.data.results
|
||||
this.tempTotal = response.data.count
|
||||
this.tempLoading = false
|
||||
})
|
||||
},
|
||||
getDevices(params) {
|
||||
let device_id = params.device_id
|
||||
fetchDeviceList(params).then(response => {
|
||||
this.deviceList = response.data.results
|
||||
this.lastItem = this.deviceList[0]
|
||||
if (!device_id) {
|
||||
device_id = this.lastItem.device_id
|
||||
this.$store.dispatch('changeDeviceID', device_id)
|
||||
console.log(device_id)
|
||||
}
|
||||
this.getDeviceLogsHistory({ device_id, limit: 20 })
|
||||
if (typeof (this.lastItem.count) === 'number') {
|
||||
this.lastItem.count = this.lastItem.count.toString()
|
||||
}
|
||||
this.flag = true
|
||||
})
|
||||
},
|
||||
coordinate(row, column) {
|
||||
return row.longitude + ', ' + row.latitude
|
||||
},
|
||||
handleDateSelect(value) {
|
||||
if (value === null) {
|
||||
this.deviceHistoryListQuery.start = undefined
|
||||
this.deviceHistoryListQuery.end = undefined
|
||||
} else {
|
||||
const [start, end] = value
|
||||
this.deviceHistoryListQuery.start = start
|
||||
this.deviceHistoryListQuery.end = end
|
||||
this.deviceTempListQuery.start = start
|
||||
this.deviceTempListQuery.end = end
|
||||
}
|
||||
},
|
||||
handleFilter() {
|
||||
this.deviceHistoryListQuery.page = 1
|
||||
this.deviceTempListQuery.page = 1
|
||||
this.getDeviceLogsHistory(this.deviceHistoryListQuery)
|
||||
this.getDeviceTempTableLog(this.deviceTempListQuery)
|
||||
},
|
||||
handleCurrentChange(page) {
|
||||
this.listLoading = true
|
||||
this.deviceHistoryListQuery.device_id = this.device_id
|
||||
this.deviceHistoryListQuery.page = page
|
||||
// this.getDeviceLogsTableHistory(this.deviceHistoryListQuery)
|
||||
this.getDeviceLogsHistory(this.deviceHistoryListQuery)
|
||||
},
|
||||
handleSizeChange(val) {
|
||||
this.listLoading = true
|
||||
this.deviceHistoryListQuery.device_id = this.device_id
|
||||
this.deviceHistoryListQuery.limit = val
|
||||
// this.getDeviceLogsTableHistory(this.deviceHistoryListQuery)
|
||||
this.getDeviceLogsHistory(this.deviceHistoryListQuery)
|
||||
},
|
||||
handleTempCurrentChange(page) {
|
||||
this.tempLoading = true
|
||||
this.deviceTempListQuery.page = page
|
||||
this.deviceTempListQuery.device_id = this.device_id
|
||||
this.getDeviceTempLog(this.deviceTempListQuery)
|
||||
},
|
||||
handleTempSizeChange(val) {
|
||||
this.tempLoading = true
|
||||
this.deviceTempListQuery.limit = val
|
||||
this.deviceTempListQuery.device_id = device_id
|
||||
const device_id = this.$store.getters.deviceID
|
||||
this.getDeviceTempLog(this.deviceTempListQuery)
|
||||
},
|
||||
handleTabClick(tab, event) {
|
||||
// console.log(tab, event)
|
||||
// 解决siderbar变化,disactiveTab没有resize
|
||||
if (tab.name === 'chart') {
|
||||
this.showHumiture = false
|
||||
}
|
||||
if (tab.name === 'humiture') {
|
||||
this.showChart = false
|
||||
}
|
||||
if (tab.name === 'screen') {
|
||||
this.showHumiture = false
|
||||
}
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.device_id = this.$store.getters.deviceID
|
||||
this.deviceHistoryListQuery.device_id = this.device_id
|
||||
this.deviceTempListQuery.device_id = this.device_id
|
||||
this.getDevices({ device_id: this.device_id })
|
||||
// this.getDeviceLogsTableHistory({ device_id: this.device_id, limit: 20 })
|
||||
this.getDeviceTempLog({ device_id: this.device_id, last_day: 1, limit: 30 })
|
||||
this.getDeviceTempTableLog(this.deviceTempListQuery)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.date-selector {
|
||||
margin-left: 10px;
|
||||
}
|
||||
.date-selector /deep/ .el-date-editor .el-range-separator {
|
||||
margin-right: 10px !important;
|
||||
}
|
||||
@media only screen and (max-width: 768px) {
|
||||
.filter-container {
|
||||
display: block;
|
||||
.filter-item {
|
||||
display: block;
|
||||
float: left;
|
||||
margin: 0 0 15px 10px;
|
||||
}
|
||||
.date-selector {
|
||||
margin-left: 0;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.time-selector {
|
||||
margin-left: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
<style lang="scss">
|
||||
@media only screen and (max-width: 500px) {
|
||||
.el-date-range-picker {
|
||||
width: 100% !important;
|
||||
}
|
||||
.el-date-range-picker__content {
|
||||
float: none;
|
||||
width: 80%;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
<style lang="scss">
|
||||
.v-enter, .v-leave-to {
|
||||
opacity: 0;
|
||||
}
|
||||
.v-enter-active, .v-leave-active {
|
||||
transition: opacity 1s
|
||||
}
|
||||
</style>
|
|
@ -1,133 +1,43 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<el-form :inline="true" :model="DeviceSearchForm" @submit.native.prevent>
|
||||
<el-form-item
|
||||
prop="device_id"
|
||||
>
|
||||
<el-input
|
||||
size="mini"
|
||||
type="text"
|
||||
v-model="DeviceSearchForm.device_id"
|
||||
style="width: 10rem"
|
||||
auto-complete="off"
|
||||
@keyup.enter.native="onSubmit"
|
||||
:placeholder="$t('counter.inputDeviceID')"
|
||||
></el-input>
|
||||
</el-form-item>
|
||||
<el-form-item>
|
||||
<el-select size="mini"
|
||||
style="width: 5.5rem"
|
||||
v-model="DeviceSearchForm.status"
|
||||
:placeholder="$t('counter.inputStatus')"
|
||||
>
|
||||
<el-option :label="$t('counter.all')" value=""></el-option>
|
||||
<el-option :label="$t('counter.online')" value="1"></el-option>
|
||||
<el-option :label="$t('counter.offline')" value="0"></el-option>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item>
|
||||
<el-button type="primary" size="mini" @click="onSubmit">{{$t('counter.search')}}</el-button>
|
||||
<el-button size="mini" @click="resetSearch">{{$t('counter.reset')}}</el-button>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
|
||||
<!-- table -->
|
||||
<p class="warn-content">
|
||||
无线智能设备信息表
|
||||
</p>
|
||||
<el-table
|
||||
v-loading="listLoading"
|
||||
:data="deviceList"
|
||||
style="width: 100%">
|
||||
<el-table-column
|
||||
fixed="left"
|
||||
type="index"
|
||||
:label="$t('counter.sn')">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
fixed="left"
|
||||
prop="device_id"
|
||||
:label="$t('counter.device')"
|
||||
min-width="120">
|
||||
<template slot-scope="scope">
|
||||
<span>{{ scope.row.device_id }} <el-tag v-if="scope.row.chip_type === 'AIR-V2'" type="success" size="mini">V2</el-tag></span>
|
||||
</template>
|
||||
label="设备ID"
|
||||
min-width="180">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="device_name"
|
||||
:label="$t('counter.deviceName')"
|
||||
min-width="150">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="status"
|
||||
:label="$t('counter.status')"
|
||||
min-width="80">
|
||||
<template slot-scope="scope">
|
||||
<span v-if="scope.row.status==0" style="color: #F56C6C" ><i class="el-icon-error"></i> {{$t('counter.offline')}}</span>
|
||||
<span v-if="scope.row.status==1" style="color: #67C23A" ><i class="el-icon-success"></i> {{$t('counter.online')}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="count"
|
||||
:label="$t('counter.count')"
|
||||
min-width="80">
|
||||
<template slot-scope="scope">
|
||||
<span ><i class="el-icon-alimosquito"></i> {{scope.row.count}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="signal"
|
||||
:label="$t('counter.signal')"
|
||||
min-width="80">
|
||||
<template slot-scope="scope">
|
||||
<span v-if="scope.row.signal>=24" style="color: #67C23A" ><i class="el-icon-alisignal-4"></i></span>
|
||||
<span v-if="scope.row.signal>=16 && scope.row.signal<24" style="color: #67C23A" ><i class="el-icon-alisignal-3"></i></span>
|
||||
<span v-if="scope.row.signal>=8 && scope.row.signal<16" style="color: #FF9B21" ><i class="el-icon-alisignal-2"></i></span>
|
||||
<span v-if="scope.row.signal>=0 && scope.row.signal<8" style="color: #F56C6C" ><i class="el-icon-alisignal-1"></i></span>
|
||||
</template>
|
||||
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="energy"
|
||||
:label="$t('counter.energy')"
|
||||
min-width="100">
|
||||
<template slot-scope="scope">
|
||||
<span v-if="scope.row.energy.replace('%','') >= 90" style="color: #67C23A" ><i class="el-icon-alipower_9"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 80 && scope.row.energy.replace('%','') < 90" style="color: #67C23A" ><i class="el-icon-alipower_8" size="small"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 70 && scope.row.energy.replace('%','') < 80" style="color: #67C23A" ><i class="el-icon-alipower_7"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 60 && scope.row.energy.replace('%','') < 70" style="color: #67C23A" ><i class="el-icon-alipower_6"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 50 && scope.row.energy.replace('%','') < 60" style="color: #67C23A" ><i class="el-icon-alipower_5"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 40 && scope.row.energy.replace('%','') < 50" style="color: #FF9B21" ><i class="el-icon-alipower_4"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 30 && scope.row.energy.replace('%','') < 40" style="color: #FF9B21" ><i class="el-icon-alipower_3" ></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 20 && scope.row.energy.replace('%','') < 30" style="color: #FF9B21" ><i class="el-icon-alipower_2"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 10 && scope.row.energy.replace('%','') < 20" style="color: #F56C6C" ><i class="el-icon-alipower_1"></i> {{scope.row.energy.replace('%','')}}%</span>
|
||||
<span v-if="scope.row.energy.replace('%','') >= 0 && scope.row.energy.replace('%','') < 10" style="color: #F56C6C" ><i class="el-icon-alipower_"></i> <{{'10.0%'}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="time"
|
||||
:label="$t('counter.time')"
|
||||
label="设备名称"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
fixed="right"
|
||||
:label="$t('counter.action')"
|
||||
min-width="85">
|
||||
<template slot-scope="scope">
|
||||
<el-button type="text" title="Detail"
|
||||
@click="handleDetailClick(scope.row.device_id)" ><i class="el-icon-alixiangqing"></i>
|
||||
</el-button>
|
||||
<el-button type="text" title="Map"
|
||||
@click="handleMapClick(scope.row.device_id)" ><i class="el-icon-alimap"></i>
|
||||
</el-button>
|
||||
</template>
|
||||
prop="chip_type"
|
||||
label="芯片类型"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="chip_id"
|
||||
label="芯片ID"
|
||||
min-width="180">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="last_connect"
|
||||
label="上次连接时间"
|
||||
min-width="180">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="last_offline_time"
|
||||
label="上次离线时间"
|
||||
min-width="180">
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
<el-pagination
|
||||
class="pagination"
|
||||
background
|
||||
layout="total, prev, pager, next, jumper"
|
||||
@current-change="handleCurrentChange"
|
||||
@size-change="handleSizeChange"
|
||||
:total="total">
|
||||
</el-pagination>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
|
@ -138,71 +48,23 @@ export default {
|
|||
data() {
|
||||
return {
|
||||
deviceList: [],
|
||||
listLoading: true,
|
||||
DeviceSearchForm: {
|
||||
device_id: null,
|
||||
status: null
|
||||
},
|
||||
total: 0
|
||||
listLoading: true
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
getDevices(params) {
|
||||
fetchDeviceList(params).then(response => {
|
||||
getDevices() {
|
||||
fetchDeviceList().then(response => {
|
||||
this.deviceList = response.data.results
|
||||
this.total = response.data.count
|
||||
this.listLoading = false
|
||||
})
|
||||
},
|
||||
onSubmit() {
|
||||
const device_id = this.DeviceSearchForm.device_id
|
||||
const status = this.DeviceSearchForm.status
|
||||
this.getDevices({ device_id, status })
|
||||
},
|
||||
resetSearch() {
|
||||
this.DeviceSearchForm.device_id = ''
|
||||
this.DeviceSearchForm.status = ''
|
||||
this.getDevices()
|
||||
},
|
||||
handleCurrentChange(page) {
|
||||
this.listLoading = true
|
||||
this.getDevices({ page })
|
||||
},
|
||||
handleSizeChange(page) {
|
||||
this.listLoading = true
|
||||
this.getDevices({ page })
|
||||
},
|
||||
handleDetailClick(deviceID) {
|
||||
// console.log(deviceID)
|
||||
this.$store.dispatch('changeDeviceID', deviceID).then(() => {
|
||||
this.$router.push('/counter/detail')
|
||||
}).catch(() => {
|
||||
console.log('Err: get device_id failed in device page')
|
||||
})
|
||||
},
|
||||
handleMapClick(deviceID) {
|
||||
// console.log(deviceID)
|
||||
this.$store.dispatch('changeMapClick', true).then(() => {
|
||||
console.log('go to map')
|
||||
}).catch(() => {
|
||||
console.log('Err: click map failed')
|
||||
})
|
||||
this.$store.dispatch('changeDeviceID', deviceID).then(() => {
|
||||
this.$router.push({ path: '/counter/map', query: { device_id: deviceID }})
|
||||
}).catch(() => {
|
||||
console.log('Err: get device_id failed in device page')
|
||||
})
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getDevices()
|
||||
},
|
||||
deactivated() {
|
||||
this.$destroy(true)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
|
||||
|
||||
</style>
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<p class="warn-content">
|
||||
这里是首页
|
||||
灭蚊侠,提供健康环境,你值得拥有。
|
||||
</p>
|
||||
</div>
|
||||
</template>
|
||||
|
|
|
@ -1,252 +0,0 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<div class="filter-container">
|
||||
<el-input
|
||||
@keyup.enter.native="handleFilter"
|
||||
@keyup.esc.native="handleEsc"
|
||||
size="small" style="width: 220px;"
|
||||
class="filter-item"
|
||||
:placeholder="$t('counter.logSeachContent')" v-model="logsListQuery.device">
|
||||
</el-input>
|
||||
<div class="date-selector filter-item">
|
||||
<el-date-picker
|
||||
v-model="dateRange"
|
||||
size="small"
|
||||
type="daterange"
|
||||
align="right"
|
||||
:range-separator="$t('counter.to')"
|
||||
:start-placeholder="$t('counter.start_date')"
|
||||
:end-placeholder="$t('counter.end_date')"
|
||||
:picker-options="pickerOptions"
|
||||
value-format="yyyy-MM-dd"
|
||||
@change="handleDateSelect"
|
||||
/>
|
||||
</div>
|
||||
<el-button class="filter-item" size="small" type="primary" v-waves icon="el-icon-search" @click="handleFilter">{{$t('table.search')}}</el-button>
|
||||
<el-button :disabled="downloadDisabled" class="filter-item export" :loading="downloadLoading" size="small"
|
||||
type="primary" icon="el-icon-document" @click="handleDownload">{{ $t('table.export') }}</el-button>
|
||||
</div>
|
||||
<el-table
|
||||
v-loading="listLoading"
|
||||
:data="logList"
|
||||
style="width: 100%"
|
||||
:default-sort = "{prop: 'calc_time', order: 'descending'}"
|
||||
>
|
||||
<el-table-column
|
||||
type="index"
|
||||
:label="$t('counter.sn')">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="device_id"
|
||||
:label="$t('counter.device')"
|
||||
sortable
|
||||
min-width="150">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="device_name"
|
||||
:label="$t('counter.deviceName')"
|
||||
sortable
|
||||
min-width="150">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="signal"
|
||||
:label="$t('counter.signal')"
|
||||
min-width="80">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
sortable
|
||||
prop="mosq_count"
|
||||
:label="$t('counter.count')"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="energy"
|
||||
:label="$t('counter.energy')"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="coordinate"
|
||||
:label="$t('counter.coordinate')"
|
||||
min-width="280px"
|
||||
:formatter="coordinate">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="calc_time"
|
||||
:label="$t('counter.time')"
|
||||
min-width="150">
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
<div class="pagination-container">
|
||||
<el-pagination background
|
||||
:current-page="1"
|
||||
:page-sizes="[10,20,30,50]"
|
||||
:page-size="logsListQuery.limit"
|
||||
layout="total, sizes, prev, pager, next, jumper"
|
||||
:total="total" @size-change="handleSizeChange" @current-change="handleCurrentChange" />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchDeviceLogs } from '@/api/counter'
|
||||
import waves from '@/directive/waves' // 水波纹指令
|
||||
import { parseTime } from '@/utils'
|
||||
export default {
|
||||
name: 'count',
|
||||
directives: {
|
||||
waves
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
logList: [],
|
||||
logExportList: [],
|
||||
listLoading: true,
|
||||
total: 0,
|
||||
logsListQuery: {
|
||||
device: undefined,
|
||||
limit: 10,
|
||||
page: 1,
|
||||
start: undefined,
|
||||
end: undefined
|
||||
},
|
||||
pickerOptions: null,
|
||||
dateRange: undefined,
|
||||
downloadLoading: false,
|
||||
downloadDisabled: false,
|
||||
filename: undefined
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
async getDeviceLogs(params, type = 'table') {
|
||||
await fetchDeviceLogs(params).then(response => {
|
||||
if (type === 'table') {
|
||||
this.logList = response.data.results
|
||||
}
|
||||
if (type === 'export') {
|
||||
this.logExportList = response.data.results
|
||||
}
|
||||
this.total = response.data.count
|
||||
this.listLoading = false
|
||||
})
|
||||
},
|
||||
coordinate(row, column) {
|
||||
return row.longitude + ', ' + row.latitude
|
||||
},
|
||||
handleCurrentChange(page) {
|
||||
// console.log(page)
|
||||
this.listLoading = true
|
||||
this.logsListQuery.page = page
|
||||
this.getDeviceLogs(this.logsListQuery)
|
||||
},
|
||||
handleSizeChange(val) {
|
||||
this.logsListQuery.limit = val
|
||||
this.getDeviceLogs(this.logsListQuery)
|
||||
},
|
||||
handleFilter() {
|
||||
this.logsListQuery.page = 1
|
||||
this.getDeviceLogs(this.logsListQuery)
|
||||
},
|
||||
handleEsc() {
|
||||
this.logsListQuery.page = 1
|
||||
this.logsListQuery.device = undefined
|
||||
this.getDeviceLogs(this.logsListQuery)
|
||||
},
|
||||
handleDateSelect(value) {
|
||||
if (value === null) {
|
||||
this.logsListQuery.start = undefined
|
||||
this.logsListQuery.end = undefined
|
||||
} else {
|
||||
const [start, end] = value
|
||||
this.logsListQuery.start = start
|
||||
this.logsListQuery.end = end
|
||||
}
|
||||
// this.getDeviceLogs(this.logsListQuery)
|
||||
},
|
||||
async handleDownload() {
|
||||
const start = this.logsListQuery.start
|
||||
const end = this.logsListQuery.end
|
||||
if (!start || !end) {
|
||||
this.$message({
|
||||
message: 'Please select the start/end date',
|
||||
type: 'warning'
|
||||
})
|
||||
return
|
||||
}
|
||||
this.downloadLoading = true
|
||||
const exportQuery = Object.assign({}, this.logsListQuery)
|
||||
exportQuery.limit = 5000
|
||||
await this.getDeviceLogs(exportQuery, 'export')
|
||||
this.filename = 'Device Log List ' + String(start).replace(/-/g, '') + '_' + String(end).replace(/-/g, '') + '.xlsx'
|
||||
|
||||
import('@/vendor/Export2Excel').then(excel => {
|
||||
const tHeader = ['Id', 'Time', 'Device ID', 'Device Name', 'Signal', 'Count', 'Energy', 'Coordinate']
|
||||
const filterVal = ['id', 'calc_time', 'device_id', 'device_name', 'signal', 'mosq_count', 'energy', 'coordinate']
|
||||
const list = this.logExportList
|
||||
const data = this.formatJson(filterVal, list)
|
||||
excel.export_json_to_excel({
|
||||
header: tHeader,
|
||||
data,
|
||||
filename: this.filename,
|
||||
autoWidth: this.autoWidth,
|
||||
bookType: this.bookType
|
||||
})
|
||||
this.downloadLoading = false
|
||||
this.logsListQuery.limit = 10
|
||||
})
|
||||
},
|
||||
formatJson(filterVal, jsonData) {
|
||||
return jsonData.map(v => filterVal.map(j => {
|
||||
if (j === 'timestamp') {
|
||||
return parseTime(v[j])
|
||||
} else {
|
||||
return v[j]
|
||||
}
|
||||
}))
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getDeviceLogs(this.logsListQuery)
|
||||
},
|
||||
deactivated() {
|
||||
this.$destroy(true)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.date-selector {
|
||||
margin-left: 10px;
|
||||
}
|
||||
.date-selector /deep/ .el-date-editor .el-range-separator {
|
||||
margin-right: 10px !important;
|
||||
}
|
||||
@media only screen and (max-width: 768px) {
|
||||
.filter-container {
|
||||
display: block;
|
||||
.filter-item {
|
||||
display: block;
|
||||
float: left;
|
||||
margin: 0 0 15px 10px;
|
||||
}
|
||||
.date-selector {
|
||||
margin-left: 0;
|
||||
margin-bottom: 0;
|
||||
}
|
||||
.time-selector {
|
||||
margin-left: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
<style lang="scss">
|
||||
@media only screen and (max-width: 500px) {
|
||||
.el-date-range-picker {
|
||||
width: 100% !important;
|
||||
}
|
||||
.el-date-range-picker__content {
|
||||
float: none;
|
||||
width: 80%;
|
||||
}
|
||||
}
|
||||
</style>
|
|
@ -1,156 +0,0 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<div class="amap-wrapper">
|
||||
<el-amap v-if="flag" :zoom="zoom" :center="center" :plugin="plugin" class="amap-box" :vid="'amap-vue'">
|
||||
<el-amap-marker
|
||||
v-for="(marker, index) in markers"
|
||||
:key="index"
|
||||
:position="marker.position"
|
||||
:events="marker.events"
|
||||
:visible="marker.visible" :draggable="marker.draggable" :vid="index"
|
||||
>
|
||||
</el-amap-marker>
|
||||
</el-amap>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchDeviceList } from '@/api/counter'
|
||||
const defaultEvents = {
|
||||
click: () => {
|
||||
alert('click marker')
|
||||
},
|
||||
dragend: (e) => {
|
||||
console.log('---event---: dragend')
|
||||
this.markers[0].position = [e.lnglat.lng, e.lnglat.lat]
|
||||
}
|
||||
}
|
||||
export default {
|
||||
name: 'amap',
|
||||
data() {
|
||||
const self = this
|
||||
return {
|
||||
flag: false,
|
||||
defaultPositions: [
|
||||
{
|
||||
name: '海洋公园',
|
||||
position: [114.186739, 22.250872]
|
||||
},
|
||||
{
|
||||
name: '香港大学',
|
||||
position: [114.143472, 22.284105]
|
||||
},
|
||||
{
|
||||
name: '南丫北容村',
|
||||
position: [114.126261, 22.22863]
|
||||
},
|
||||
{
|
||||
name: '大帽山',
|
||||
position: [114.124105, 22.401088]
|
||||
},
|
||||
{
|
||||
name: '恒生管理学院',
|
||||
position: [114.223565, 22.380771]
|
||||
},
|
||||
{
|
||||
name: '盐田',
|
||||
position: [114.223565, 22.380771]
|
||||
},
|
||||
{
|
||||
name: '清水',
|
||||
position: [114.312821, 22.301076]
|
||||
}
|
||||
],
|
||||
zoom: 16,
|
||||
center: [],
|
||||
markers: [],
|
||||
plugin: ['ToolBar', {
|
||||
pName: 'Geolocation',
|
||||
events: {
|
||||
init(o) {
|
||||
// o 是高德地图定位插件实例
|
||||
o.getCurrentPosition((status, result) => {
|
||||
if (result && result.position) {
|
||||
const lng = result.position.lng
|
||||
const lat = result.position.lat
|
||||
self.center = [lng, lat]
|
||||
// self.loaded = true
|
||||
self.$nextTick()
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
pName: 'Driving',
|
||||
policy: 'AMap.DrivingPolicy.LEAST_TIME',
|
||||
events: {
|
||||
init(o) {
|
||||
o.search(self.center, [113.276316, 23.112071], (status, result) => {
|
||||
console.log(status, result)
|
||||
})
|
||||
}
|
||||
}
|
||||
}]
|
||||
}
|
||||
},
|
||||
// beforeRouteEnter(to, from, next) {
|
||||
// next(vm => {
|
||||
// vm.url = from.path
|
||||
// console.log(from.path)
|
||||
// })
|
||||
// },
|
||||
methods: {
|
||||
getDevices(params) {
|
||||
fetchDeviceList(params).then(response => {
|
||||
this.deviceList = response.data.results
|
||||
// console.log(this.deviceList)
|
||||
this.coordinate = this.deviceList[0].coordinate
|
||||
if (this.coordinate === null) {
|
||||
this.coordinate = [113.203460828994, 22.64902452257]
|
||||
}
|
||||
// console.log(this.coordinate)
|
||||
const marker = []
|
||||
marker.position = this.coordinate
|
||||
marker.visible = true
|
||||
marker.dragend = false
|
||||
marker.events = defaultEvents
|
||||
this.markers.push(marker)
|
||||
// this.center = this.coordinate
|
||||
this.flag = true
|
||||
})
|
||||
}
|
||||
},
|
||||
created() {
|
||||
const mapClick = this.$store.getters.mapClick
|
||||
if (mapClick) {
|
||||
const device_id = this.$store.getters.deviceID
|
||||
console.log(device_id)
|
||||
this.getDevices({ device_id })
|
||||
} else {
|
||||
this.defaultPositions.forEach((item, index) => {
|
||||
const entry = {}
|
||||
entry.position = item.position
|
||||
entry.events = defaultEvents
|
||||
entry.visible = true
|
||||
entry.draggable = false
|
||||
this.markers.push(entry)
|
||||
})
|
||||
this.zoom = 11
|
||||
this.center = [114.186739, 22.250872]
|
||||
this.flag = true
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.amap-wrapper {
|
||||
width: 100%;
|
||||
height: 80%;
|
||||
overflow: hidden;
|
||||
position: absolute;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -1,399 +0,0 @@
|
|||
<template>
|
||||
<div class="map-wrapper">
|
||||
<div id="map-container" tabindex="0"></div>
|
||||
<div v-show="flag" id="geo-tip"></div>
|
||||
<div v-show="flag" id="panel"></div>
|
||||
<div v-show="mapClick && flag" id='bt-wrapper'>
|
||||
<div id='bt'>点击去高德地图</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import AMap from 'AMap'
|
||||
import moment from 'moment'
|
||||
import { fetchDeviceList } from '@/api/counter'
|
||||
export default {
|
||||
name: 'map2',
|
||||
data() {
|
||||
return {
|
||||
geo_map: null,
|
||||
map: null,
|
||||
flag: false,
|
||||
mapClick: false,
|
||||
geo: [],
|
||||
deviceList: [],
|
||||
deviceListQuery: {
|
||||
page: 1,
|
||||
limit: 100
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
sleep(time) {
|
||||
for (var temp = Date.now(); Date.now() - temp <= time;);
|
||||
},
|
||||
async getDevices(params) {
|
||||
await fetchDeviceList(params).then(response => {
|
||||
this.deviceList = response.data.results
|
||||
})
|
||||
},
|
||||
gotoDriving() {
|
||||
this.$confirm('此操作将跳转到路线规划, 是否继续?', '提示', {
|
||||
confirmButtonText: '确定',
|
||||
cancelButtonText: '取消',
|
||||
type: 'warning'
|
||||
}).then(() => {
|
||||
this.map.clearMap()
|
||||
this.handleDrivingClick()
|
||||
this.flag = true
|
||||
this.$message({
|
||||
type: 'success',
|
||||
message: '跳转成功!'
|
||||
})
|
||||
}).catch(() => {
|
||||
document.getElementById('map-container').removeEventListener
|
||||
this.$message({
|
||||
type: 'info',
|
||||
message: '已取消跳转'
|
||||
})
|
||||
})
|
||||
},
|
||||
async initMap() {
|
||||
this.map = new AMap.Map('map-container', {
|
||||
center: [114.143472, 22.284105],
|
||||
resizeEnable: true,
|
||||
zoom: 10
|
||||
})
|
||||
// 标记点测试数据
|
||||
await this.getDevices(this.deviceListQuery)
|
||||
const markers = []
|
||||
this.deviceList.forEach((item, index) => {
|
||||
console.log(item)
|
||||
const marker = new AMap.Marker({
|
||||
position: item.coordinate,
|
||||
zIndex: 10,
|
||||
title: item.device_name,
|
||||
map: this.map
|
||||
})
|
||||
const infoWindow = this.instantiateInforWindow(item)
|
||||
AMap.event.addListener(marker, 'click', () => {
|
||||
infoWindow.open(this.map, marker.getPosition())
|
||||
})
|
||||
markers.push(marker)
|
||||
})
|
||||
AMap.plugin(['AMap.ToolBar', 'AMap.Scale'], () => {
|
||||
this.map.addControl(new AMap.ToolBar())
|
||||
this.map.addControl(new AMap.Scale())
|
||||
})
|
||||
},
|
||||
createInfoWindow(title, content) {
|
||||
const info = document.createElement('div')
|
||||
info.className = 'info'
|
||||
info.setAttribute('id', 'info')
|
||||
|
||||
// 可以通过下面的方式修改自定义窗体的宽高
|
||||
// info.style.width = "400px"
|
||||
// 定义顶部标题
|
||||
const top = document.createElement('div')
|
||||
const titleD = document.createElement('div')
|
||||
titleD.className = 'title'
|
||||
const closeX = document.createElement('img')
|
||||
top.className = 'info-top'
|
||||
titleD.innerHTML = title
|
||||
closeX.src = 'https://webapi.amap.com/images/close2.gif'
|
||||
closeX.onclick = this.closeInfoWindow
|
||||
|
||||
top.appendChild(titleD)
|
||||
top.appendChild(closeX)
|
||||
info.appendChild(top)
|
||||
|
||||
// 定义中部内容
|
||||
const middle = document.createElement('div')
|
||||
middle.className = 'info-middle'
|
||||
middle.innerHTML = content
|
||||
info.appendChild(middle)
|
||||
|
||||
// 定义底部内容
|
||||
const bottom = document.createElement('div')
|
||||
bottom.className = 'info-bottom'
|
||||
bottom.style.position = 'relative'
|
||||
bottom.style.top = '0px'
|
||||
bottom.style.margin = '0 auto'
|
||||
const sharp = document.createElement('img')
|
||||
sharp.src = 'https://webapi.amap.com/images/sharp.png'
|
||||
bottom.appendChild(sharp)
|
||||
info.appendChild(bottom)
|
||||
// console.log(info)
|
||||
return info
|
||||
},
|
||||
instantiateInforWindow(item, drivingButton = false) {
|
||||
const content = []
|
||||
const curTime = moment().format('YYYY-MM-DD HH:mm:ss')
|
||||
content.push('<div class="count">' + item.count + '</div>')
|
||||
content.push('<div class="time">Time: ' + curTime + '</div>')
|
||||
content.push('<div><span>Signal: ' + item.signal + '</span><span class="energy">Energy: ' + item.energy + '</span></div>')
|
||||
content.push('<div><span>TEMP: ' + '30.3℃' + '</span><span class="humidity">HUM: ' + '69%' + '</span></div>')
|
||||
|
||||
// content.push('<div>区域:尖沙咀</div>\n')
|
||||
// if (drivingButton) {
|
||||
// content.push('<button id="btn" class="btn">驾车规划</button>')
|
||||
// }
|
||||
const infoWindow = new AMap.InfoWindow({
|
||||
isCustom: true,
|
||||
closeWhenClickMap: true,
|
||||
content: this.createInfoWindow(item.device_name, content.join('\n')),
|
||||
offset: new AMap.Pixel(16, -45)
|
||||
})
|
||||
return infoWindow
|
||||
},
|
||||
closeInfoWindow() {
|
||||
this.map.clearInfoWindow()
|
||||
},
|
||||
onComplete(data) {
|
||||
var str = ['定位成功']
|
||||
this.geo = [data.position.getLng(), data.position.getLat()]
|
||||
str.push(data.position.getLng())
|
||||
str.push(data.position.getLat())
|
||||
console.log(this.geo)
|
||||
if (data.accuracy) {
|
||||
str.push('精度:' + data.accuracy + ' 米')
|
||||
}
|
||||
str.push('是否经过偏移:' + (data.isConverted ? '是' : '否'))
|
||||
document.getElementById('geo-tip').innerHTML = str.join('<br>')
|
||||
const drivingOptions = {
|
||||
map: this.geo_map,
|
||||
panel: 'panel'
|
||||
}
|
||||
// 驾车路径规划
|
||||
const driving = new AMap.Driving(drivingOptions)
|
||||
const button = document.getElementById('bt')
|
||||
driving.search(new AMap.LngLat(data.position.getLng(), data.position.getLat()), new AMap.LngLat(113.203460828994, 22.64902452257), (status, result) => {
|
||||
button.onclick = () => {
|
||||
driving.searchOnAMAP({
|
||||
origin: result.origin,
|
||||
destination: result.destination
|
||||
})
|
||||
}
|
||||
})
|
||||
},
|
||||
onError() {
|
||||
document.getElementById('geo-tip').innerHTML = '定位失败'
|
||||
},
|
||||
handleDrivingClick() {
|
||||
const geo_map = new AMap.Map('map-container')
|
||||
this.geo_map = geo_map
|
||||
AMap.plugin(['AMap.ToolBar', 'AMap.Scale', 'AMap.Driving', 'AMap.Geolocation'], () => {
|
||||
geo_map.addControl(new AMap.ToolBar())
|
||||
geo_map.addControl(new AMap.Scale())
|
||||
const geolocation = new AMap.Geolocation({
|
||||
enableHighAccuracy: true,
|
||||
timeout: 10000,
|
||||
buttonOffset: new AMap.Pixel(10, 20),
|
||||
zoomToAccuracy: true,
|
||||
panToLocation: false,
|
||||
buttonPosition: 'RB'
|
||||
})
|
||||
geo_map.addControl(geolocation)
|
||||
geolocation.getCurrentPosition()
|
||||
// 返回定位信息
|
||||
AMap.event.addListener(geolocation, 'complete', this.onComplete)
|
||||
// 返回定位出错信息
|
||||
AMap.event.addListener(geolocation, 'error', this.onError)
|
||||
})
|
||||
},
|
||||
gotoDrivingEvent(e) {
|
||||
const event = e || window.event
|
||||
const target = event.target || event.srcElement
|
||||
if (target.nodeName.toLocaleLowerCase() === 'button') {
|
||||
console.log('the content is: ', target.innerHTML)
|
||||
this.gotoDriving()
|
||||
}
|
||||
},
|
||||
getDevicesInitMap(params) {
|
||||
fetchDeviceList(params).then(response => {
|
||||
this.deviceList = response.data.results
|
||||
const item = this.deviceList[0]
|
||||
this.coordinate = item.coordinate
|
||||
if (!this.coordinate) {
|
||||
this.coordinate = [113.203460828994, 22.64902452257]
|
||||
}
|
||||
this.map = new AMap.Map('map-container', {
|
||||
center: this.coordinate,
|
||||
resizeEnable: true,
|
||||
zoom: 15
|
||||
})
|
||||
const marker = new AMap.Marker({
|
||||
position: this.coordinate,
|
||||
zIndex: 10,
|
||||
map: this.map
|
||||
})
|
||||
item.title = item.device_name
|
||||
const infoWindow = this.instantiateInforWindow(item, true)
|
||||
AMap.event.addListener(marker, 'click', () => {
|
||||
infoWindow.open(this.map, marker.getPosition())
|
||||
})
|
||||
// this.handleDrivingClick()
|
||||
// this.flag = true
|
||||
// if (AMap.UA.mobile) {
|
||||
// document.getElementById('panel').style.display = 'none'
|
||||
// // document.getElementById('bt-wrapper').style.display = 'normal'
|
||||
// }
|
||||
})
|
||||
const mapContainer = document.getElementById('map-container')
|
||||
mapContainer.addEventListener('click', this.gotoDrivingEvent)
|
||||
}
|
||||
},
|
||||
created() {
|
||||
// this.mapClick = this.$store.getters.mapClick
|
||||
},
|
||||
async mounted() {
|
||||
const device_id = this.$route.query.device_id
|
||||
if (device_id) {
|
||||
// const device_id = this.$store.getters.deviceID
|
||||
// this.sleep(2000)
|
||||
this.getDevicesInitMap({ device_id })
|
||||
} else {
|
||||
await this.initMap()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="css">
|
||||
#map-container {
|
||||
width: 100%;
|
||||
height: 90%;
|
||||
overflow: hidden;
|
||||
position: absolute;
|
||||
}
|
||||
.info {
|
||||
border: solid 1px silver;
|
||||
}
|
||||
div.info-top {
|
||||
position: relative;
|
||||
background: none repeat scroll 0 0 #F9F9F9;
|
||||
border-bottom: 1px solid #CCC;
|
||||
border-radius: 5px 5px 0 0;
|
||||
}
|
||||
div.info-top .title {
|
||||
display: inline-block;
|
||||
color: rgb(236, 110, 37);
|
||||
font-size: 14px;
|
||||
font-weight: bold;
|
||||
line-height: 31px;
|
||||
padding: 0 10px;
|
||||
}
|
||||
div.info-top img {
|
||||
position: absolute;
|
||||
top: 10px;
|
||||
right: 10px;
|
||||
transition-duration: 0.25s;
|
||||
}
|
||||
div.info-top img:hover {
|
||||
box-shadow: 0px 0px 5px #000;
|
||||
}
|
||||
div.info-middle {
|
||||
font-size: 12px;
|
||||
padding: .4rem .8rem .5rem .5rem;
|
||||
line-height: 20px;
|
||||
background-color: white;
|
||||
}
|
||||
.info-middle .count {
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
font-size: 1.5rem;
|
||||
font-weight: bold;
|
||||
color: #666;
|
||||
margin: 0 0 .4rem 0;
|
||||
}
|
||||
.info-middle span.energy {
|
||||
margin-left: 2.4rem;
|
||||
}
|
||||
.info-middle span.humidity {
|
||||
margin-left: 1.0rem;
|
||||
}
|
||||
div.info-bottom {
|
||||
height: 0px;
|
||||
width: 100%;
|
||||
clear: both;
|
||||
text-align: center;
|
||||
}
|
||||
div.info-bottom img {
|
||||
position: relative;
|
||||
z-index: 104;
|
||||
}
|
||||
#panel {
|
||||
position: absolute;
|
||||
background-color: white;
|
||||
max-height: 80%;
|
||||
overflow-y: auto;
|
||||
top: 10px;
|
||||
right: 10px;
|
||||
width: 250px;
|
||||
border: solid 1px silver;
|
||||
margin-top: 100px;
|
||||
}
|
||||
@media only screen and (max-width: 768px) {
|
||||
#panel {
|
||||
display: none;
|
||||
}
|
||||
.el-message-box {
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
#geo-tip {
|
||||
font-size: .8rem;
|
||||
position: absolute;
|
||||
padding: 5px;
|
||||
color: white;
|
||||
background-color:goldenrod;
|
||||
width: 150px;
|
||||
top: 15%;
|
||||
left: 10%;
|
||||
border-radius: 5px;
|
||||
text-align: center;
|
||||
}
|
||||
#bt-wrapper {
|
||||
position: absolute;
|
||||
width: 2rem;
|
||||
bottom: 15%;
|
||||
right: 10rem;
|
||||
}
|
||||
#bt {
|
||||
font-size: .8rem;
|
||||
text-align: center;
|
||||
cursor: pointer;
|
||||
border-radius: 5px;
|
||||
background-color: #0D9BF2;
|
||||
padding: 6px;
|
||||
width: 160px;
|
||||
color: white;
|
||||
margin: 0 auto;
|
||||
}
|
||||
#btn {
|
||||
display: inline-block;
|
||||
line-height: 1;
|
||||
white-space: nowrap;
|
||||
cursor: pointer;
|
||||
background: #fff;
|
||||
border: 1px solid #dcdfe6;
|
||||
border-color: #dcdfe6;
|
||||
color: #606266;
|
||||
-webkit-appearance: none;
|
||||
text-align: center;
|
||||
box-sizing: border-box;
|
||||
outline: none;
|
||||
margin: 0;
|
||||
transition: .1s;
|
||||
font-weight: 500;
|
||||
padding: 5px 5px;
|
||||
font-size: 12px;
|
||||
border-radius: 2px;
|
||||
}
|
||||
#btn:focus, #btn:hover {
|
||||
color: #409eff;
|
||||
border-color: #c6e2ff;
|
||||
background-color: #ecf5ff;
|
||||
}
|
||||
</style>
|
|
@ -67,22 +67,16 @@ export default {
|
|||
chartData: {
|
||||
deep: true,
|
||||
handler(val) {
|
||||
this.chart.resize()
|
||||
this.setOptions(val)
|
||||
// setTimeout(() => { this.chart.resize() }, 3000)
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
setOptions({ historyData, xAxis, title } = {}) {
|
||||
setOptions({ expectedData, actualData } = {}) {
|
||||
this.chart.setOption({
|
||||
xAxis: {
|
||||
// data: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'],
|
||||
data: xAxis,
|
||||
data: ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'],
|
||||
boundaryGap: false,
|
||||
axisLabel: {
|
||||
interval: 0
|
||||
},
|
||||
axisTick: {
|
||||
show: false
|
||||
}
|
||||
|
@ -107,10 +101,10 @@ export default {
|
|||
}
|
||||
},
|
||||
legend: {
|
||||
data: [title]
|
||||
data: ['expected', 'actual']
|
||||
},
|
||||
series: [{
|
||||
name: title, itemStyle: {
|
||||
name: 'expected', itemStyle: {
|
||||
normal: {
|
||||
color: '#FF005A',
|
||||
lineStyle: {
|
||||
|
@ -121,16 +115,35 @@ export default {
|
|||
},
|
||||
smooth: true,
|
||||
type: 'line',
|
||||
data: historyData,
|
||||
data: expectedData,
|
||||
animationDuration: 2800,
|
||||
animationEasing: 'cubicInOut'
|
||||
},
|
||||
{
|
||||
name: 'actual',
|
||||
smooth: true,
|
||||
type: 'line',
|
||||
itemStyle: {
|
||||
normal: {
|
||||
color: '#3888fa',
|
||||
lineStyle: {
|
||||
color: '#3888fa',
|
||||
width: 2
|
||||
},
|
||||
areaStyle: {
|
||||
color: '#f3f8ff'
|
||||
}
|
||||
}
|
||||
},
|
||||
data: actualData,
|
||||
animationDuration: 2800,
|
||||
animationEasing: 'quadraticOut'
|
||||
}]
|
||||
})
|
||||
},
|
||||
initChart() {
|
||||
this.chart = echarts.init(this.$el, 'macarons')
|
||||
console.log(this.chartData)
|
||||
// this.setOptions(this.chartData)
|
||||
this.setOptions(this.chartData)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,54 +0,0 @@
|
|||
<template>
|
||||
<div>
|
||||
<el-table
|
||||
v-loading="listLoading"
|
||||
:data="historyList"
|
||||
style="width: 100%">
|
||||
<el-table-column
|
||||
type="index"
|
||||
label="序号">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="date"
|
||||
label="日期"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
prop="increment"
|
||||
label="数量"
|
||||
min-width="100">
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchLogStatisticHistory } from '@/api/counter'
|
||||
export default {
|
||||
name: 'LogHistoryTable',
|
||||
data() {
|
||||
return {
|
||||
listLoading: true,
|
||||
historyList: []
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
getLogStatisticHistory() {
|
||||
fetchLogStatisticHistory().then(response => {
|
||||
this.historyList = response.data.results
|
||||
this.historyList.forEach((item, index) => {
|
||||
})
|
||||
this.listLoading = false
|
||||
this.$emit('history', this.historyList)
|
||||
})
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getLogStatisticHistory()
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style rel="stylesheet/scss" lang="scss">
|
||||
|
||||
</style>
|
|
@ -1,46 +1,46 @@
|
|||
<template>
|
||||
<el-row class="panel-group" :gutter="40">
|
||||
<el-col :xs="12" :sm="12" :lg="6" class="card-panel-col">
|
||||
<div class='card-panel' @click="handleSetLineChartData('total')">
|
||||
<div class="card-panel-icon-wrapper icon-plus">
|
||||
<svg-icon icon-class="plus" class-name="card-panel-icon" />
|
||||
<div class='card-panel' @click="handleSetLineChartData('newVisitis')">
|
||||
<div class="card-panel-icon-wrapper icon-people">
|
||||
<svg-icon icon-class="peoples" class-name="card-panel-icon" />
|
||||
</div>
|
||||
<div class="card-panel-description">
|
||||
<div class="card-panel-text">Monthly Mosquito</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="curMonthCount" :duration="2600"></count-to>
|
||||
<div class="card-panel-text">New Visits</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="102400" :duration="2600"></count-to>
|
||||
</div>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :xs="12" :sm="12" :lg="6" class="card-panel-col">
|
||||
<div class="card-panel" @click="handleSetLineChartData('increment')">
|
||||
<div class="card-panel-icon-wrapper icon-rise">
|
||||
<svg-icon icon-class="rise" class-name="card-panel-icon" />
|
||||
<div class="card-panel" @click="handleSetLineChartData('messages')">
|
||||
<div class="card-panel-icon-wrapper icon-message">
|
||||
<svg-icon icon-class="message" class-name="card-panel-icon" />
|
||||
</div>
|
||||
<div class="card-panel-description">
|
||||
<div class="card-panel-text">Daily Mosquito</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="dailyCount" :duration="3000"></count-to>
|
||||
<div class="card-panel-text">Messages</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="81212" :duration="3000"></count-to>
|
||||
</div>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :xs="12" :sm="12" :lg="6" class="card-panel-col">
|
||||
<div class="card-panel">
|
||||
<div class="card-panel-icon-wrapper icon-online">
|
||||
<svg-icon icon-class="online" class-name="card-panel-icon" />
|
||||
<div class="card-panel" @click="handleSetLineChartData('purchases')">
|
||||
<div class="card-panel-icon-wrapper icon-money">
|
||||
<svg-icon icon-class="money" class-name="card-panel-icon" />
|
||||
</div>
|
||||
<div class="card-panel-description">
|
||||
<div class="card-panel-text">Online Device</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="onlineCount" :duration="3200"></count-to>
|
||||
<div class="card-panel-text">Purchases</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="9280" :duration="3200"></count-to>
|
||||
</div>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :xs="12" :sm="12" :lg="6" class="card-panel-col">
|
||||
<div class="card-panel">
|
||||
<div class="card-panel-icon-wrapper icon-offline">
|
||||
<svg-icon icon-class="offline" class-name="card-panel-icon" />
|
||||
<div class="card-panel" @click="handleSetLineChartData('shoppings')">
|
||||
<div class="card-panel-icon-wrapper icon-shoppingCard">
|
||||
<svg-icon icon-class="shoppingCard" class-name="card-panel-icon" />
|
||||
</div>
|
||||
<div class="card-panel-description">
|
||||
<div class="card-panel-text">Offline Device</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="offlineCount" :duration="3600"></count-to>
|
||||
<div class="card-panel-text">Shoppings</div>
|
||||
<count-to class="card-panel-num" :startVal="0" :endVal="13600" :duration="3600"></count-to>
|
||||
</div>
|
||||
</div>
|
||||
</el-col>
|
||||
|
@ -51,12 +51,6 @@
|
|||
import CountTo from 'vue-count-to'
|
||||
|
||||
export default {
|
||||
props: {
|
||||
curMonthCount: Number,
|
||||
dailyCount: Number,
|
||||
onlineCount: Number,
|
||||
offlineCount: Number
|
||||
},
|
||||
components: {
|
||||
CountTo
|
||||
},
|
||||
|
@ -88,30 +82,30 @@ export default {
|
|||
.card-panel-icon-wrapper {
|
||||
color: #fff;
|
||||
}
|
||||
.icon-plus {
|
||||
.icon-people {
|
||||
background: #40c9c6;
|
||||
}
|
||||
.icon-message {
|
||||
background: #36a3f7;
|
||||
}
|
||||
.icon-rise {
|
||||
background: #40c9c6;
|
||||
.icon-money {
|
||||
background: #f4516c;
|
||||
}
|
||||
.icon-online {
|
||||
background: #5be496;
|
||||
}
|
||||
.icon-offline {
|
||||
background: #f4516c
|
||||
.icon-shoppingCard {
|
||||
background: #34bfa3
|
||||
}
|
||||
}
|
||||
.icon-plus {
|
||||
color: #36a3f7;
|
||||
}
|
||||
.icon-rise {
|
||||
.icon-people {
|
||||
color: #40c9c6;
|
||||
}
|
||||
.icon-online {
|
||||
color: #5be496;
|
||||
.icon-message {
|
||||
color: #36a3f7;
|
||||
}
|
||||
.icon-offline {
|
||||
color: #f4516c
|
||||
.icon-money {
|
||||
color: #f4516c;
|
||||
}
|
||||
.icon-shoppingCard {
|
||||
color: #34bfa3
|
||||
}
|
||||
.card-panel-icon-wrapper {
|
||||
float: left;
|
||||
|
@ -125,10 +119,10 @@ export default {
|
|||
font-size: 48px;
|
||||
}
|
||||
.card-panel-description {
|
||||
// float: right;
|
||||
float: right;
|
||||
font-weight: bold;
|
||||
margin: 26px;
|
||||
margin-left: 120px;
|
||||
margin-left: 0px;
|
||||
.card-panel-text {
|
||||
line-height: 18px;
|
||||
color: rgba(0, 0, 0, 0.45);
|
||||
|
@ -140,30 +134,5 @@ export default {
|
|||
}
|
||||
}
|
||||
}
|
||||
@media only screen and (max-width: 768px) {
|
||||
.card-panel-icon-wrapper {
|
||||
float: none!important;
|
||||
text-align: center;
|
||||
margin: 0!important;
|
||||
border-radius: 0!important;
|
||||
padding: 1rem 0 1rem 0!important;
|
||||
}
|
||||
.card-panel-icon {
|
||||
float: none!important;
|
||||
font-size: 2.2rem!important;
|
||||
}
|
||||
.card-panel-description {
|
||||
float: none!important;
|
||||
font-weight: bold;
|
||||
text-align: center;
|
||||
margin: .5rem 0 0 0!important;
|
||||
.card-panel-text {
|
||||
display: none;
|
||||
}
|
||||
.card-panel-num {
|
||||
font-size: 1rem!important;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
|
@ -1,109 +1,98 @@
|
|||
<template>
|
||||
<div class="dashboard-editor-container">
|
||||
<!-- <github-corner></github-corner> -->
|
||||
<github-corner></github-corner>
|
||||
|
||||
<panel-group
|
||||
@handleSetLineChartData="handleSetLineChartData"
|
||||
:curMonthCount="curMonthCount"
|
||||
:dailyCount="dailyCount"
|
||||
:onlineCount="onlineCount"
|
||||
:offlineCount="offlineCount"
|
||||
>
|
||||
</panel-group>
|
||||
<panel-group @handleSetLineChartData="handleSetLineChartData"></panel-group>
|
||||
|
||||
<el-row style="background:#fff;padding:16px 16px 0;margin-bottom:32px;">
|
||||
<line-chart :chart-data="lineChartData"></line-chart>
|
||||
</el-row>
|
||||
|
||||
<el-row>
|
||||
<log-history-table
|
||||
@history="handleHistoryLine"
|
||||
></log-history-table>
|
||||
<el-row :gutter="32">
|
||||
<el-col :xs="24" :sm="24" :lg="8">
|
||||
<div class="chart-wrapper">
|
||||
<raddar-chart></raddar-chart>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :xs="24" :sm="24" :lg="8">
|
||||
<div class="chart-wrapper">
|
||||
<pie-chart></pie-chart>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :xs="24" :sm="24" :lg="8">
|
||||
<div class="chart-wrapper">
|
||||
<bar-chart></bar-chart>
|
||||
</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
|
||||
<el-row :gutter="8">
|
||||
<!-- <el-col :xs="{span: 24}" :sm="{span: 24}" :md="{span: 24}" :lg="{span: 12}" :xl="{span: 12}" style="padding-right:8px;margin-bottom:30px;">
|
||||
<transaction-table></transaction-table>
|
||||
</el-col> -->
|
||||
<el-col :xs="{span: 24}" :sm="{span: 12}" :md="{span: 12}" :lg="{span: 6}" :xl="{span: 5}" style="margin-bottom:30px;">
|
||||
<todo-list></todo-list>
|
||||
</el-col>
|
||||
<el-col :xs="{span: 24}" :sm="{span: 12}" :md="{span: 12}" :lg="{span: 6}" :xl="{span: 5}" style="margin-bottom:30px;" >
|
||||
<box-card></box-card>
|
||||
</el-col>
|
||||
</el-row>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import GithubCorner from '@/components/GithubCorner'
|
||||
import PanelGroup from './components/PanelGroup'
|
||||
import LineChart from './components/LineChart'
|
||||
import LogHistoryTable from './components/LogHistoryTable'
|
||||
import RaddarChart from './components/RaddarChart'
|
||||
import PieChart from './components/PieChart'
|
||||
import BarChart from './components/BarChart'
|
||||
import TransactionTable from './components/TransactionTable'
|
||||
import
|
||||
{
|
||||
fetchDeviceLogStatistic,
|
||||
fetchDeviceInfoStatistic
|
||||
// fetchLogStatisticHistory
|
||||
} from '@/api/counter'
|
||||
import TodoList from './components/TodoList'
|
||||
import BoxCard from './components/BoxCard'
|
||||
|
||||
const lineChartData = {
|
||||
total: {
|
||||
historyData: [],
|
||||
xAxis: [],
|
||||
title: 'Total'
|
||||
newVisitis: {
|
||||
expectedData: [100, 120, 161, 134, 105, 160, 165],
|
||||
actualData: [120, 82, 91, 154, 162, 140, 145]
|
||||
},
|
||||
increment: {
|
||||
historyData: [],
|
||||
xAxis: [],
|
||||
title: 'Increment'
|
||||
messages: {
|
||||
expectedData: [200, 192, 120, 144, 160, 130, 140],
|
||||
actualData: [180, 160, 151, 106, 145, 150, 130]
|
||||
},
|
||||
purchases: {
|
||||
expectedData: [80, 100, 121, 104, 105, 90, 100],
|
||||
actualData: [120, 90, 100, 138, 142, 130, 130]
|
||||
},
|
||||
shoppings: {
|
||||
expectedData: [130, 140, 141, 142, 145, 150, 160],
|
||||
actualData: [120, 82, 91, 154, 162, 140, 130]
|
||||
}
|
||||
}
|
||||
|
||||
export default {
|
||||
name: 'dashboard-admin',
|
||||
components: {
|
||||
GithubCorner,
|
||||
PanelGroup,
|
||||
LineChart,
|
||||
LogHistoryTable,
|
||||
TransactionTable
|
||||
RaddarChart,
|
||||
PieChart,
|
||||
BarChart,
|
||||
TransactionTable,
|
||||
TodoList,
|
||||
BoxCard
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
lineChartData: lineChartData.total,
|
||||
curMonthCount: 0,
|
||||
dailyCount: 0,
|
||||
onlineCount: 0,
|
||||
offlineCount: 0,
|
||||
historyList: []
|
||||
lineChartData: lineChartData.newVisitis
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
handleSetLineChartData(type) {
|
||||
this.lineChartData = lineChartData[type]
|
||||
},
|
||||
getDeviceInfoStatistic() {
|
||||
fetchDeviceInfoStatistic().then(response => {
|
||||
const infoData = response.data
|
||||
this.onlineCount = infoData['online_count']
|
||||
this.offlineCount = infoData['offline_count']
|
||||
})
|
||||
},
|
||||
getDeviceLogStatistic() {
|
||||
fetchDeviceLogStatistic().then(response => {
|
||||
const data = response.data
|
||||
this.curMonthCount = data['cur_month_count']
|
||||
this.dailyCount = data['daily_count']
|
||||
})
|
||||
},
|
||||
handleHistoryLine(historyList) {
|
||||
const totalList = []
|
||||
const incrementList = []
|
||||
const dateList = []
|
||||
console.log(historyList)
|
||||
historyList.forEach((item, index) => {
|
||||
totalList.push(item.total)
|
||||
incrementList.push(item.increment)
|
||||
dateList.push(item.date.substr(5))
|
||||
})
|
||||
lineChartData.total.historyData = totalList.reverse()
|
||||
lineChartData.increment.historyData = incrementList.reverse()
|
||||
lineChartData.total.xAxis = dateList.reverse()
|
||||
lineChartData.increment.xAxis = dateList
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getDeviceInfoStatistic()
|
||||
this.getDeviceLogStatistic()
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
|
@ -23,11 +23,7 @@ export default {
|
|||
])
|
||||
},
|
||||
created() {
|
||||
const adminDashboardRoles = new Set(['manager', 'admin', 'staff'])
|
||||
const userRoles = new Set(this.roles)
|
||||
const intersection = new Set([...userRoles].filter(role => adminDashboardRoles.has(role)))
|
||||
console.log(intersection.size)
|
||||
if (intersection.size === 0) {
|
||||
if (!this.roles.includes('admin')) {
|
||||
this.currentRole = 'editorDashboard'
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,47 @@
|
|||
<template>
|
||||
<div class="app-container documentation-container">
|
||||
<a class="document-btn" target='_blank' href="https://panjiachen.github.io/vue-element-admin-site/">{{$t('documentation.documentation')}}</a>
|
||||
<a class="document-btn" target='_blank' href="https://github.com/PanJiaChen/vue-element-admin/">{{$t('documentation.github')}}</a>
|
||||
<dropdown-menu style="float:left;margin-left:50px;" title='系列文章' :items='articleList'></dropdown-menu>
|
||||
</div>
|
||||
</template>
|
||||
<script>
|
||||
import DropdownMenu from '@/components/Share/dropdownMenu'
|
||||
|
||||
export default {
|
||||
name: 'documentation',
|
||||
components: { DropdownMenu },
|
||||
data() {
|
||||
return {
|
||||
articleList: [
|
||||
{ title: '基础篇', href: 'https://segmentfault.com/a/1190000009275424' },
|
||||
{ title: '登录权限篇', href: 'https://segmentfault.com/a/1190000009506097' },
|
||||
{ title: '实战篇', href: 'https://segmentfault.com/a/1190000009762198' },
|
||||
{ title: 'vueAdmin-template 篇', href: 'https://segmentfault.com/a/1190000010043013' },
|
||||
{ title: '自行封装 component', href: 'https://segmentfault.com/a/1190000009090836' },
|
||||
{ title: '优雅的使用 icon', href: 'https://segmentfault.com/a/1190000012213278' }
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style rel="stylesheet/scss" lang="scss" scoped>
|
||||
.documentation-container {
|
||||
margin: 50px;
|
||||
.document-btn {
|
||||
float: left;
|
||||
margin-left: 50px;
|
||||
vertical-align: middle;
|
||||
display: block;
|
||||
cursor: pointer;
|
||||
background: black;
|
||||
color: white;
|
||||
height: 60px;
|
||||
width: 200px;
|
||||
line-height: 60px;
|
||||
font-size: 20px;
|
||||
text-align: center;
|
||||
}
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,253 @@
|
|||
<template>
|
||||
<div class="createPost-container">
|
||||
<el-form class="form-container" :model="postForm" :rules="rules" ref="postForm">
|
||||
|
||||
<sticky :className="'sub-navbar '+postForm.status">
|
||||
<CommentDropdown v-model="postForm.comment_disabled" />
|
||||
<PlatformDropdown v-model="postForm.platforms" />
|
||||
<SourceUrlDropdown v-model="postForm.source_uri" />
|
||||
<el-button v-loading="loading" style="margin-left: 10px;" type="success" @click="submitForm">发布
|
||||
</el-button>
|
||||
<el-button v-loading="loading" type="warning" @click="draftForm">草稿</el-button>
|
||||
</sticky>
|
||||
|
||||
<div class="createPost-main-container">
|
||||
<el-row>
|
||||
|
||||
<Warning />
|
||||
|
||||
<el-col :span="21">
|
||||
<el-form-item style="margin-bottom: 40px;" prop="title">
|
||||
<MDinput name="name" v-model="postForm.title" required :maxlength="100">
|
||||
标题
|
||||
</MDinput>
|
||||
</el-form-item>
|
||||
|
||||
<div class="postInfo-container">
|
||||
<el-row>
|
||||
<el-col :span="8">
|
||||
<el-form-item label-width="45px" label="作者:" class="postInfo-container-item">
|
||||
<el-select v-model="postForm.author" filterable remote placeholder="搜索用户" :remote-method="getRemoteUserList">
|
||||
<el-option v-for="(item,index) in userListOptions" :key="item+index" :label="item" :value="item">
|
||||
</el-option>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
</el-col>
|
||||
|
||||
<el-col :span="8">
|
||||
<el-form-item label-width="80px" label="发布时间:" class="postInfo-container-item">
|
||||
<el-date-picker v-model="postForm.display_time" type="datetime" format="yyyy-MM-dd HH:mm:ss" placeholder="选择日期时间">
|
||||
</el-date-picker>
|
||||
</el-form-item>
|
||||
</el-col>
|
||||
|
||||
<el-col :span="8">
|
||||
<el-form-item label-width="60px" label="重要性:" class="postInfo-container-item">
|
||||
<el-rate style="margin-top:8px;" v-model="postForm.importance" :max='3' :colors="['#99A9BF', '#F7BA2A', '#FF9900']" :low-threshold="1"
|
||||
:high-threshold="3">
|
||||
</el-rate>
|
||||
</el-form-item>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
|
||||
<el-form-item style="margin-bottom: 40px;" label-width="45px" label="摘要:">
|
||||
<el-input type="textarea" class="article-textarea" :rows="1" autosize placeholder="请输入内容" v-model="postForm.content_short">
|
||||
</el-input>
|
||||
<span class="word-counter" v-show="contentShortLength">{{contentShortLength}}字</span>
|
||||
</el-form-item>
|
||||
|
||||
<div class="editor-container">
|
||||
<Tinymce :height=400 ref="editor" v-model="postForm.content" />
|
||||
</div>
|
||||
|
||||
<div style="margin-bottom: 20px;">
|
||||
<Upload v-model="postForm.image_uri" />
|
||||
</div>
|
||||
</div>
|
||||
</el-form>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Tinymce from '@/components/Tinymce'
|
||||
import Upload from '@/components/Upload/singleImage3'
|
||||
import MDinput from '@/components/MDinput'
|
||||
import Multiselect from 'vue-multiselect'// 使用的一个多选框组件,element-ui的select不能满足所有需求
|
||||
import 'vue-multiselect/dist/vue-multiselect.min.css'// 多选框组件css
|
||||
import Sticky from '@/components/Sticky' // 粘性header组件
|
||||
import { validateURL } from '@/utils/validate'
|
||||
import { fetchArticle } from '@/api/article'
|
||||
import { userSearch } from '@/api/remoteSearch'
|
||||
import Warning from './Warning'
|
||||
import { CommentDropdown, PlatformDropdown, SourceUrlDropdown } from './Dropdown'
|
||||
|
||||
const defaultForm = {
|
||||
status: 'draft',
|
||||
title: '', // 文章题目
|
||||
content: '', // 文章内容
|
||||
content_short: '', // 文章摘要
|
||||
source_uri: '', // 文章外链
|
||||
image_uri: '', // 文章图片
|
||||
display_time: undefined, // 前台展示时间
|
||||
id: undefined,
|
||||
platforms: ['a-platform'],
|
||||
comment_disabled: false,
|
||||
importance: 0
|
||||
}
|
||||
|
||||
export default {
|
||||
name: 'articleDetail',
|
||||
components: { Tinymce, MDinput, Upload, Multiselect, Sticky, Warning, CommentDropdown, PlatformDropdown, SourceUrlDropdown },
|
||||
props: {
|
||||
isEdit: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
},
|
||||
data() {
|
||||
const validateRequire = (rule, value, callback) => {
|
||||
if (value === '') {
|
||||
this.$message({
|
||||
message: rule.field + '为必传项',
|
||||
type: 'error'
|
||||
})
|
||||
callback(null)
|
||||
} else {
|
||||
callback()
|
||||
}
|
||||
}
|
||||
const validateSourceUri = (rule, value, callback) => {
|
||||
if (value) {
|
||||
if (validateURL(value)) {
|
||||
callback()
|
||||
} else {
|
||||
this.$message({
|
||||
message: '外链url填写不正确',
|
||||
type: 'error'
|
||||
})
|
||||
callback(null)
|
||||
}
|
||||
} else {
|
||||
callback()
|
||||
}
|
||||
}
|
||||
return {
|
||||
postForm: Object.assign({}, defaultForm),
|
||||
loading: false,
|
||||
userListOptions: [],
|
||||
rules: {
|
||||
image_uri: [{ validator: validateRequire }],
|
||||
title: [{ validator: validateRequire }],
|
||||
content: [{ validator: validateRequire }],
|
||||
source_uri: [{ validator: validateSourceUri, trigger: 'blur' }]
|
||||
}
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
contentShortLength() {
|
||||
return this.postForm.content_short.length
|
||||
}
|
||||
},
|
||||
created() {
|
||||
if (this.isEdit) {
|
||||
const id = this.$route.params && this.$route.params.id
|
||||
this.fetchData(id)
|
||||
} else {
|
||||
this.postForm = Object.assign({}, defaultForm)
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
fetchData(id) {
|
||||
fetchArticle(id).then(response => {
|
||||
this.postForm = response.data
|
||||
// Just for test
|
||||
this.postForm.title += ` Article Id:${this.postForm.id}`
|
||||
this.postForm.content_short += ` Article Id:${this.postForm.id}`
|
||||
}).catch(err => {
|
||||
console.log(err)
|
||||
})
|
||||
},
|
||||
submitForm() {
|
||||
this.postForm.display_time = parseInt(this.display_time / 1000)
|
||||
console.log(this.postForm)
|
||||
this.$refs.postForm.validate(valid => {
|
||||
if (valid) {
|
||||
this.loading = true
|
||||
this.$notify({
|
||||
title: '成功',
|
||||
message: '发布文章成功',
|
||||
type: 'success',
|
||||
duration: 2000
|
||||
})
|
||||
this.postForm.status = 'published'
|
||||
this.loading = false
|
||||
} else {
|
||||
console.log('error submit!!')
|
||||
return false
|
||||
}
|
||||
})
|
||||
},
|
||||
draftForm() {
|
||||
if (this.postForm.content.length === 0 || this.postForm.title.length === 0) {
|
||||
this.$message({
|
||||
message: '请填写必要的标题和内容',
|
||||
type: 'warning'
|
||||
})
|
||||
return
|
||||
}
|
||||
this.$message({
|
||||
message: '保存成功',
|
||||
type: 'success',
|
||||
showClose: true,
|
||||
duration: 1000
|
||||
})
|
||||
this.postForm.status = 'draft'
|
||||
},
|
||||
getRemoteUserList(query) {
|
||||
userSearch(query).then(response => {
|
||||
if (!response.data.items) return
|
||||
this.userListOptions = response.data.items.map(v => v.name)
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style rel="stylesheet/scss" lang="scss" scoped>
|
||||
@import "src/styles/mixin.scss";
|
||||
.createPost-container {
|
||||
position: relative;
|
||||
.createPost-main-container {
|
||||
padding: 40px 45px 20px 50px;
|
||||
.postInfo-container {
|
||||
position: relative;
|
||||
@include clearfix;
|
||||
margin-bottom: 10px;
|
||||
.postInfo-container-item {
|
||||
float: left;
|
||||
}
|
||||
}
|
||||
.editor-container {
|
||||
min-height: 500px;
|
||||
margin: 0 0 30px;
|
||||
.editor-upload-btn-container {
|
||||
text-align: right;
|
||||
margin-right: 10px;
|
||||
.editor-upload-btn {
|
||||
display: inline-block;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.word-counter {
|
||||
width: 40px;
|
||||
position: absolute;
|
||||
right: -10px;
|
||||
top: 0px;
|
||||
}
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,31 @@
|
|||
<template>
|
||||
<el-dropdown trigger="click" :show-timeout="100">
|
||||
<el-button plain>{{!comment_disabled?'评论已打开':'评论已关闭'}}
|
||||
<i class="el-icon-caret-bottom el-icon--right"></i>
|
||||
</el-button>
|
||||
<el-dropdown-menu class="no-padding" slot="dropdown">
|
||||
<el-dropdown-item>
|
||||
<el-radio-group style="padding: 10px;" v-model="comment_disabled">
|
||||
<el-radio :label="true">关闭评论</el-radio>
|
||||
<el-radio :label="false">打开评论</el-radio>
|
||||
</el-radio-group>
|
||||
</el-dropdown-item>
|
||||
</el-dropdown-menu>
|
||||
</el-dropdown>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
props: ['value'],
|
||||
computed: {
|
||||
comment_disabled: {
|
||||
get() {
|
||||
return this.value
|
||||
},
|
||||
set(val) {
|
||||
this.$emit('input', val)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,40 @@
|
|||
<template>
|
||||
<el-dropdown :hide-on-click="false" :show-timeout="100" trigger="click">
|
||||
<el-button plain>
|
||||
平台({{platforms.length}})
|
||||
<i class="el-icon-caret-bottom el-icon--right"></i>
|
||||
</el-button>
|
||||
<el-dropdown-menu class="no-border" slot="dropdown">
|
||||
<el-checkbox-group v-model="platforms" style="padding: 5px 15px;">
|
||||
<el-checkbox v-for="item in platformsOptions" :label="item.key" :key="item.key">
|
||||
{{item.name}}
|
||||
</el-checkbox>
|
||||
</el-checkbox-group>
|
||||
</el-dropdown-menu>
|
||||
</el-dropdown>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
props: ['value'],
|
||||
data() {
|
||||
return {
|
||||
platformsOptions: [
|
||||
{ key: 'a-platform', name: 'a-platform' },
|
||||
{ key: 'b-platform', name: 'b-platform' },
|
||||
{ key: 'c-platform', name: 'c-platform' }
|
||||
]
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
platforms: {
|
||||
get() {
|
||||
return this.value
|
||||
},
|
||||
set(val) {
|
||||
this.$emit('input', val)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,31 @@
|
|||
<template>
|
||||
<el-dropdown :show-timeout="100" trigger="click">
|
||||
<el-button plain>
|
||||
外链
|
||||
<i class="el-icon-caret-bottom el-icon--right"></i>
|
||||
</el-button>
|
||||
<el-dropdown-menu class="no-padding no-border" style="width:400px" slot="dropdown">
|
||||
<el-form-item label-width="0px" style="margin-bottom: 0px" prop="source_uri">
|
||||
<el-input placeholder="请输入内容" v-model="source_uri">
|
||||
<template slot="prepend">填写url</template>
|
||||
</el-input>
|
||||
</el-form-item>
|
||||
</el-dropdown-menu>
|
||||
</el-dropdown>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
props: ['value'],
|
||||
computed: {
|
||||
source_uri: {
|
||||
get() {
|
||||
return this.value
|
||||
},
|
||||
set(val) {
|
||||
this.$emit('input', val)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,3 @@
|
|||
export { default as CommentDropdown } from './Comment'
|
||||
export { default as PlatformDropdown } from './Platform'
|
||||
export { default as SourceUrlDropdown } from './SourceUrl'
|
|
@ -0,0 +1,9 @@
|
|||
<template>
|
||||
<p class="warn-content">
|
||||
创建和编辑页面是不能被keep-alive 缓存的,因为keep-alive 的include 目前不支持根据路由来缓存,所以目前都是基于component name 来缓存的,如果你想要实现缓存的效果,可以使用localstorage 等游览器缓存方案。或者不要使用keep-alive
|
||||
的include,直接缓存所有页面。详情见
|
||||
<a href="https://panjiachen.github.io/vue-element-admin-site/guide/essentials/tags-view.html"
|
||||
target="_blank">文档</a>
|
||||
</p>
|
||||
</template>
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
<template>
|
||||
<article-detail :is-edit='false'></article-detail>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import ArticleDetail from './components/ArticleDetail'
|
||||
|
||||
export default {
|
||||
name: 'createForm',
|
||||
components: { ArticleDetail }
|
||||
}
|
||||
</script>
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
<template>
|
||||
<article-detail :is-edit='true'></article-detail>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import ArticleDetail from './components/ArticleDetail'
|
||||
|
||||
export default {
|
||||
name: 'editForm',
|
||||
components: { ArticleDetail }
|
||||
}
|
||||
</script>
|
||||
|
|
@ -0,0 +1,121 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
|
||||
<el-table :data="list" v-loading.body="listLoading" border fit highlight-current-row style="width: 100%">
|
||||
<el-table-column align="center" label="ID" width="80">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.id}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="180px" align="center" label="Date">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.timestamp | parseTime('{y}-{m}-{d} {h}:{i}')}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="120px" align="center" label="Author">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.author}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="100px" label="Importance">
|
||||
<template slot-scope="scope">
|
||||
<svg-icon v-for="n in +scope.row.importance" icon-class="star" class="meta-item__icon" :key="n"></svg-icon>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column class-name="status-col" label="Status" width="110">
|
||||
<template slot-scope="scope">
|
||||
<el-tag :type="scope.row.status | statusFilter">{{scope.row.status}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column min-width="300px" label="Title">
|
||||
<template slot-scope="scope">
|
||||
|
||||
<router-link class="link-type" :to="'/example/edit/'+scope.row.id">
|
||||
<span>{{ scope.row.title }}</span>
|
||||
</router-link>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column align="center" label="Actions" width="120">
|
||||
<template slot-scope="scope">
|
||||
<router-link :to="'/example/edit/'+scope.row.id">
|
||||
<el-button type="primary" size="small" icon="el-icon-edit">Edit</el-button>
|
||||
</router-link>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<div class="pagination-container">
|
||||
<el-pagination background @size-change="handleSizeChange" @current-change="handleCurrentChange" :current-page="listQuery.page"
|
||||
:page-sizes="[10,20,30, 50]" :page-size="listQuery.limit" layout="total, sizes, prev, pager, next, jumper" :total="total">
|
||||
</el-pagination>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchList } from '@/api/article'
|
||||
|
||||
export default {
|
||||
name: 'articleList',
|
||||
data() {
|
||||
return {
|
||||
list: null,
|
||||
total: 0,
|
||||
listLoading: true,
|
||||
listQuery: {
|
||||
page: 1,
|
||||
limit: 10
|
||||
}
|
||||
}
|
||||
},
|
||||
filters: {
|
||||
statusFilter(status) {
|
||||
const statusMap = {
|
||||
published: 'success',
|
||||
draft: 'info',
|
||||
deleted: 'danger'
|
||||
}
|
||||
return statusMap[status]
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getList()
|
||||
},
|
||||
methods: {
|
||||
getList() {
|
||||
this.listLoading = true
|
||||
fetchList(this.listQuery).then(response => {
|
||||
this.list = response.data.items
|
||||
this.total = response.data.total
|
||||
this.listLoading = false
|
||||
})
|
||||
},
|
||||
handleSizeChange(val) {
|
||||
this.listQuery.limit = val
|
||||
this.getList()
|
||||
},
|
||||
handleCurrentChange(val) {
|
||||
this.listQuery.page = val
|
||||
this.getList()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.edit-input {
|
||||
padding-right: 100px;
|
||||
}
|
||||
.cancel-btn {
|
||||
position: absolute;
|
||||
right: 15px;
|
||||
top: 10px;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,108 @@
|
|||
<template>
|
||||
<!-- $t is vue-i18n global function to translate lang -->
|
||||
<div class="app-container">
|
||||
|
||||
<label class="radio-label" style="padding-left:0;">Filename: </label>
|
||||
<el-input style='width:340px;' :placeholder="$t('excel.placeholder')" prefix-icon="el-icon-document" v-model="filename"></el-input>
|
||||
<label class="radio-label">Cell Auto Width: </label>
|
||||
<el-radio-group v-model="autoWidth">
|
||||
<el-radio :label="true" border>True</el-radio>
|
||||
<el-radio :label="false" border>False</el-radio>
|
||||
</el-radio-group>
|
||||
<el-button style='margin:0 0 20px 20px;' type="primary" icon="document" @click="handleDownload" :loading="downloadLoading">{{$t('excel.export')}} excel</el-button>
|
||||
|
||||
<el-table :data="list" v-loading="listLoading" element-loading-text="拼命加载中" border fit highlight-current-row>
|
||||
<el-table-column align="center" label='Id' width="95">
|
||||
<template slot-scope="scope">
|
||||
{{scope.$index}}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="Title">
|
||||
<template slot-scope="scope">
|
||||
{{scope.row.title}}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="Author" width="110" align="center">
|
||||
<template slot-scope="scope">
|
||||
<el-tag>{{scope.row.author}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="Readings" width="115" align="center">
|
||||
<template slot-scope="scope">
|
||||
{{scope.row.pageviews}}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column align="center" label="Date" width="220">
|
||||
<template slot-scope="scope">
|
||||
<i class="el-icon-time"></i>
|
||||
<span>{{scope.row.timestamp | parseTime('{y}-{m}-{d} {h}:{i}')}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchList } from '@/api/article'
|
||||
import { parseTime } from '@/utils'
|
||||
|
||||
export default {
|
||||
name: 'exportExcel',
|
||||
data() {
|
||||
return {
|
||||
list: null,
|
||||
listLoading: true,
|
||||
downloadLoading: false,
|
||||
filename: '',
|
||||
autoWidth: true
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.fetchData()
|
||||
},
|
||||
methods: {
|
||||
fetchData() {
|
||||
this.listLoading = true
|
||||
fetchList().then(response => {
|
||||
this.list = response.data.items
|
||||
this.listLoading = false
|
||||
})
|
||||
},
|
||||
handleDownload() {
|
||||
this.downloadLoading = true
|
||||
import('@/vendor/Export2Excel').then(excel => {
|
||||
const tHeader = ['Id', 'Title', 'Author', 'Readings', 'Date']
|
||||
const filterVal = ['id', 'title', 'author', 'pageviews', 'display_time']
|
||||
const list = this.list
|
||||
const data = this.formatJson(filterVal, list)
|
||||
excel.export_json_to_excel({
|
||||
header: tHeader,
|
||||
data,
|
||||
filename: this.filename,
|
||||
autoWidth: this.autoWidth
|
||||
})
|
||||
this.downloadLoading = false
|
||||
})
|
||||
},
|
||||
formatJson(filterVal, jsonData) {
|
||||
return jsonData.map(v => filterVal.map(j => {
|
||||
if (j === 'timestamp') {
|
||||
return parseTime(v[j])
|
||||
} else {
|
||||
return v[j]
|
||||
}
|
||||
}))
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
.radio-label {
|
||||
font-size: 14px;
|
||||
color: #606266;
|
||||
line-height: 40px;
|
||||
padding: 0 12px 0 30px;
|
||||
}
|
||||
</style>
|
||||
|
|
@ -0,0 +1,95 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<!-- $t is vue-i18n global function to translate lang -->
|
||||
<el-input style='width:340px;' :placeholder="$t('excel.placeholder')" prefix-icon="el-icon-document" v-model="filename"></el-input>
|
||||
<el-button style='margin-bottom:20px' type="primary" icon="document" @click="handleDownload" :loading="downloadLoading">{{$t('excel.selectedExport')}}</el-button>
|
||||
<el-table :data="list" v-loading="listLoading" element-loading-text="拼命加载中" border fit highlight-current-row @selection-change="handleSelectionChange"
|
||||
ref="multipleTable">
|
||||
<el-table-column type="selection" align="center"></el-table-column>
|
||||
<el-table-column align="center" label='Id' width="95">
|
||||
<template slot-scope="scope">
|
||||
{{scope.$index}}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="Title">
|
||||
<template slot-scope="scope">
|
||||
{{scope.row.title}}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="Author" width="110" align="center">
|
||||
<template slot-scope="scope">
|
||||
<el-tag>{{scope.row.author}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column label="Readings" width="115" align="center">
|
||||
<template slot-scope="scope">
|
||||
{{scope.row.pageviews}}
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column align="center" label="PDate" width="220">
|
||||
<template slot-scope="scope">
|
||||
<i class="el-icon-time"></i>
|
||||
<span>{{scope.row.display_time}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchList } from '@/api/article'
|
||||
|
||||
export default {
|
||||
name: 'selectExcel',
|
||||
data() {
|
||||
return {
|
||||
list: null,
|
||||
listLoading: true,
|
||||
multipleSelection: [],
|
||||
downloadLoading: false,
|
||||
filename: ''
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.fetchData()
|
||||
},
|
||||
methods: {
|
||||
fetchData() {
|
||||
this.listLoading = true
|
||||
fetchList(this.listQuery).then(response => {
|
||||
this.list = response.data.items
|
||||
this.listLoading = false
|
||||
})
|
||||
},
|
||||
handleSelectionChange(val) {
|
||||
this.multipleSelection = val
|
||||
},
|
||||
handleDownload() {
|
||||
if (this.multipleSelection.length) {
|
||||
this.downloadLoading = true
|
||||
import('@/vendor/Export2Excel').then(excel => {
|
||||
const tHeader = ['Id', 'Title', 'Author', 'Readings', 'Date']
|
||||
const filterVal = ['id', 'title', 'author', 'pageviews', 'display_time']
|
||||
const list = this.multipleSelection
|
||||
const data = this.formatJson(filterVal, list)
|
||||
excel.export_json_to_excel({
|
||||
header: tHeader,
|
||||
data,
|
||||
filename: this.filename
|
||||
})
|
||||
this.$refs.multipleTable.clearSelection()
|
||||
this.downloadLoading = false
|
||||
})
|
||||
} else {
|
||||
this.$message({
|
||||
message: 'Please select at least one item',
|
||||
type: 'warning'
|
||||
})
|
||||
}
|
||||
},
|
||||
formatJson(filterVal, jsonData) {
|
||||
return jsonData.map(v => filterVal.map(j => v[j]))
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,43 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<upload-excel-component :on-success='handleSuccess' :before-upload="beforeUpload"></upload-excel-component>
|
||||
<el-table :data="tableData" border highlight-current-row style="width: 100%;margin-top:20px;">
|
||||
<el-table-column v-for='item of tableHeader' :prop="item" :label="item" :key='item'>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import UploadExcelComponent from '@/components/UploadExcel/index.vue'
|
||||
|
||||
export default {
|
||||
name: 'uploadExcel',
|
||||
components: { UploadExcelComponent },
|
||||
data() {
|
||||
return {
|
||||
tableData: [],
|
||||
tableHeader: []
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
beforeUpload(file) {
|
||||
const isLt1M = file.size / 1024 / 1024 < 1
|
||||
|
||||
if (isLt1M) {
|
||||
return true
|
||||
}
|
||||
|
||||
this.$message({
|
||||
message: 'Please do not upload files larger than 1m in size.',
|
||||
type: 'warning'
|
||||
})
|
||||
return false
|
||||
},
|
||||
handleSuccess({ results, header }) {
|
||||
this.tableData = results
|
||||
this.tableHeader = header
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,52 @@
|
|||
const steps = [
|
||||
{
|
||||
element: '.hamburger-container',
|
||||
popover: {
|
||||
title: 'Hamburger',
|
||||
description: 'Open && Close sidebar',
|
||||
position: 'bottom'
|
||||
}
|
||||
},
|
||||
{
|
||||
element: '.breadcrumb-container',
|
||||
popover: {
|
||||
title: 'Breadcrumb',
|
||||
description: 'Indicate the current page location',
|
||||
position: 'bottom'
|
||||
}
|
||||
},
|
||||
{
|
||||
element: '.screenfull',
|
||||
popover: {
|
||||
title: 'Screenfull',
|
||||
description: 'Bring the page into fullscreen',
|
||||
position: 'left'
|
||||
}
|
||||
},
|
||||
{
|
||||
element: '.international-icon',
|
||||
popover: {
|
||||
title: 'Switch language',
|
||||
description: 'Switch the system language',
|
||||
position: 'left'
|
||||
}
|
||||
},
|
||||
{
|
||||
element: '.theme-switch',
|
||||
popover: {
|
||||
title: 'Theme Switch',
|
||||
description: 'Custom switch system theme',
|
||||
position: 'left'
|
||||
}
|
||||
},
|
||||
{
|
||||
element: '.tags-view-container',
|
||||
popover: {
|
||||
title: 'Tags view',
|
||||
description: 'The history of the page you visited',
|
||||
position: 'bottom'
|
||||
}
|
||||
}
|
||||
]
|
||||
|
||||
export default steps
|
|
@ -0,0 +1,34 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<p class="warn-content">
|
||||
{{$t('guide.description')}}
|
||||
<a href="https://github.com/kamranahmedse/driver.js" target="_blank">driver.js.
|
||||
</a>
|
||||
</p>
|
||||
<el-button icon='el-icon-question' type="primary" @click.prevent.stop="guide">{{$t('guide.button')}}</el-button>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import * as Driver from 'driver.js' // import driver.js
|
||||
import 'driver.js/dist/driver.min.css' // import driver.js css
|
||||
import steps from './defineSteps'
|
||||
|
||||
export default {
|
||||
name: 'guide',
|
||||
data() {
|
||||
return {
|
||||
driver: null
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.driver = new Driver()
|
||||
},
|
||||
methods: {
|
||||
guide() {
|
||||
this.driver.defineSteps(steps)
|
||||
this.driver.start()
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,111 @@
|
|||
<template>
|
||||
<div>
|
||||
<el-card class="box-card" style="margin-top:40px;">
|
||||
<div slot="header" class="clearfix">
|
||||
<svg-icon icon-class="international" />
|
||||
<span style='margin-left:10px;'>{{$t('i18nView.title')}}</span>
|
||||
</div>
|
||||
<div>
|
||||
<el-radio-group v-model="lang" size="small">
|
||||
<el-radio label="zh" border>简体中文</el-radio>
|
||||
<el-radio label="en" border>English</el-radio>
|
||||
</el-radio-group>
|
||||
<el-tag style='margin-top:15px;display:block;' type="info">{{$t('i18nView.note')}}</el-tag>
|
||||
</div>
|
||||
</el-card>
|
||||
|
||||
<el-row :gutter="20" style="margin:100px 15px 50px;">
|
||||
<el-col :span="12">
|
||||
<div class="block">
|
||||
<el-date-picker v-model="date" type="date" :placeholder="$t('i18nView.datePlaceholder')"></el-date-picker>
|
||||
</div>
|
||||
<div class="block">
|
||||
<el-pagination background :current-page="currentPage" :page-sizes="[100, 200, 300, 400]" :page-size="100" layout="total, sizes, prev, pager, next"
|
||||
:total="400">
|
||||
</el-pagination>
|
||||
</div>
|
||||
<div class="block">
|
||||
<el-button class="item-btn" size="small">{{$t('i18nView.default')}}</el-button>
|
||||
<el-button class="item-btn" size="small" type="primary">{{$t('i18nView.primary')}}</el-button>
|
||||
<el-button class="item-btn" size="small" type="success">{{$t('i18nView.success')}}</el-button>
|
||||
<el-button class="item-btn" size="small" type="info">{{$t('i18nView.info')}}</el-button>
|
||||
<el-button class="item-btn" size="small" type="warning">{{$t('i18nView.warning')}}</el-button>
|
||||
<el-button class="item-btn" size="small" type="danger">{{$t('i18nView.danger')}}</el-button>
|
||||
</div>
|
||||
</el-col>
|
||||
<el-col :span="12">
|
||||
<el-table :data="tableData" fit highlight-current-row border style="width: 100%">
|
||||
<el-table-column prop="name" :label="$t('i18nView.tableName')" width="100" align="center"></el-table-column>
|
||||
<el-table-column prop="date" :label="$t('i18nView.tableDate')" width="120" align="center"></el-table-column>
|
||||
<el-table-column prop="address" :label="$t('i18nView.tableAddress')"></el-table-column>
|
||||
</el-table>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import local from './local'
|
||||
const viewName = 'i18nView'
|
||||
|
||||
export default {
|
||||
name: 'i18n',
|
||||
data() {
|
||||
return {
|
||||
date: '',
|
||||
currentPage: 5,
|
||||
tableData: [{
|
||||
date: '2016-05-03',
|
||||
name: 'Tom',
|
||||
address: 'No. 189, Grove St, Los Angeles'
|
||||
},
|
||||
{
|
||||
date: '2016-05-02',
|
||||
name: 'Tom',
|
||||
address: 'No. 189, Grove St, Los Angeles'
|
||||
},
|
||||
{
|
||||
date: '2016-05-04',
|
||||
name: 'Tom',
|
||||
address: 'No. 189, Grove St, Los Angeles'
|
||||
},
|
||||
{
|
||||
date: '2016-05-01',
|
||||
name: 'Tom',
|
||||
address: 'No. 189, Grove St, Los Angeles'
|
||||
}]
|
||||
}
|
||||
},
|
||||
created() {
|
||||
if (!this.$i18n.getLocaleMessage('en')[viewName]) {
|
||||
this.$i18n.mergeLocaleMessage('en', local.en)
|
||||
this.$i18n.mergeLocaleMessage('zh', local.zh)
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
lang: {
|
||||
get() {
|
||||
return this.$store.state.app.language
|
||||
},
|
||||
set(lang) {
|
||||
this.$i18n.locale = lang
|
||||
this.$store.dispatch('setLanguage', lang)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.box-card {
|
||||
width: 600px;
|
||||
margin: 20px auto;
|
||||
}
|
||||
.item-btn{
|
||||
margin-bottom: 15px;
|
||||
margin-left: 0px;
|
||||
}
|
||||
.block {
|
||||
padding: 25px;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,36 @@
|
|||
|
||||
export default {
|
||||
zh: {
|
||||
i18nView: {
|
||||
title: '切换语言',
|
||||
note: '目前只翻译了当前页面和侧边栏和导航,未完待续,敬请期待...',
|
||||
datePlaceholder: '请选择日期',
|
||||
tableDate: '日期',
|
||||
tableName: '姓名',
|
||||
tableAddress: '地址',
|
||||
default: '默认按钮',
|
||||
primary: '主要按钮',
|
||||
success: '成功按钮',
|
||||
info: '信息按钮',
|
||||
warning: '警告按钮',
|
||||
danger: '危险按钮'
|
||||
}
|
||||
|
||||
},
|
||||
en: {
|
||||
i18nView: {
|
||||
title: 'Switch Language',
|
||||
note: 'Currently only translated the i18n page and the sidebar and levelbar, please look forword to...',
|
||||
datePlaceholder: 'Pick a day',
|
||||
tableDate: 'tableDate',
|
||||
tableName: 'tableName',
|
||||
tableAddress: 'tableAddress',
|
||||
default: 'default:',
|
||||
primary: 'primary',
|
||||
success: 'success',
|
||||
info: 'info',
|
||||
warning: 'warning',
|
||||
danger: 'danger'
|
||||
}
|
||||
}
|
||||
}
|
|
@ -13,29 +13,26 @@
|
|||
|
||||
<lang-select class="international right-menu-item"></lang-select>
|
||||
|
||||
<!-- <el-tooltip effect="dark" :content="$t('navbar.theme')" placement="bottom">
|
||||
<el-tooltip effect="dark" :content="$t('navbar.theme')" placement="bottom">
|
||||
<theme-picker class="theme-switch right-menu-item"></theme-picker>
|
||||
</el-tooltip> -->
|
||||
</el-tooltip>
|
||||
|
||||
<el-dropdown class="avatar-container right-menu-item" trigger="click">
|
||||
<div class="avatar-wrapper">
|
||||
<img class="user-avatar" :src="avatar+'?x-oss-process=image/resize,m_fixed,h_80,w_80'">
|
||||
<img class="user-avatar" :src="avatar+'?imageView2/1/w/80/h/80'">
|
||||
<i class="el-icon-caret-bottom"></i>
|
||||
</div>
|
||||
<el-dropdown-menu slot="dropdown">
|
||||
<el-dropdown-item disabled>
|
||||
<span style="color: #999;">{{$store.getters.name}}</span>
|
||||
</el-dropdown-item>
|
||||
<router-link to="/">
|
||||
<el-dropdown-item divided>
|
||||
<el-dropdown-item>
|
||||
{{$t('navbar.dashboard')}}
|
||||
</el-dropdown-item>
|
||||
</router-link>
|
||||
<!-- <a target='_blank' href="https://github.com/PanJiaChen/vue-element-admin/">
|
||||
<a target='_blank' href="https://github.com/PanJiaChen/vue-element-admin/">
|
||||
<el-dropdown-item>
|
||||
{{$t('navbar.github')}}
|
||||
</el-dropdown-item>
|
||||
</a> -->
|
||||
</a>
|
||||
<el-dropdown-item divided>
|
||||
<span @click="logout" style="display:block;">{{$t('navbar.logOut')}}</span>
|
||||
</el-dropdown-item>
|
||||
|
@ -52,7 +49,7 @@ import Hamburger from '@/components/Hamburger'
|
|||
import ErrorLog from '@/components/ErrorLog'
|
||||
import Screenfull from '@/components/Screenfull'
|
||||
import LangSelect from '@/components/LangSelect'
|
||||
// import ThemePicker from '@/components/ThemePicker'
|
||||
import ThemePicker from '@/components/ThemePicker'
|
||||
|
||||
export default {
|
||||
components: {
|
||||
|
@ -60,8 +57,8 @@ export default {
|
|||
Hamburger,
|
||||
ErrorLog,
|
||||
Screenfull,
|
||||
LangSelect
|
||||
// ThemePicker
|
||||
LangSelect,
|
||||
ThemePicker
|
||||
},
|
||||
computed: {
|
||||
...mapGetters([
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<code>Parent View: Bar</code>
|
||||
<img src="https://wpimg.wallstcn.com/be29a7d2-5ccf-4a2b-888d-8a6c2bbb7aac.png">
|
||||
<router-view></router-view>
|
||||
</div>
|
||||
</template>
|
|
@ -0,0 +1,6 @@
|
|||
<template>
|
||||
<div style="margin-top:30px;">
|
||||
<el-alert title="Children: Posts" type="warning" :closable="false">
|
||||
</el-alert>
|
||||
</div>
|
||||
</template>
|
|
@ -0,0 +1,6 @@
|
|||
<template>
|
||||
<div style="margin-top:30px;">
|
||||
<el-alert title="Children: Profile" type="success" :closable="false">
|
||||
</el-alert>
|
||||
</div>
|
||||
</template>
|
|
@ -0,0 +1,30 @@
|
|||
<template>
|
||||
<div>
|
||||
<div style="margin-bottom:15px;">{{$t('permission.roles')}}: {{roles}}</div>
|
||||
{{$t('permission.switchRoles')}}:
|
||||
<el-radio-group v-model="switchRoles">
|
||||
<el-radio-button label="editor"></el-radio-button>
|
||||
<el-radio-button label="admin"></el-radio-button>
|
||||
</el-radio-group>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
computed: {
|
||||
roles() {
|
||||
return this.$store.getters.roles
|
||||
},
|
||||
switchRoles: {
|
||||
get() {
|
||||
return this.roles[0]
|
||||
},
|
||||
set(val) {
|
||||
this.$store.dispatch('ChangeRoles', val).then(() => {
|
||||
this.$emit('change')
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,72 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<switch-roles @change="handleRolesChange" />
|
||||
<div :key="key" style="margin-top:30px;">
|
||||
<span v-permission="['admin']" class="permission-alert">
|
||||
Only
|
||||
<el-tag class="permission-tag" size="small">admin</el-tag> can see this
|
||||
</span>
|
||||
<span v-permission="['editor']" class="permission-alert">
|
||||
Only
|
||||
<el-tag class="permission-tag" size="small">editor</el-tag> can see this
|
||||
</span>
|
||||
<span v-permission="['admin','editor']" class="permission-alert">
|
||||
Both
|
||||
<el-tag class="permission-tag" size="small">admin</el-tag> and
|
||||
<el-tag class="permission-tag" size="small">editor</el-tag> can see this
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<div style="margin-top:30px;" :key="'checkPermission'+key">
|
||||
<code>In some cases it is not suitable to use v-permission, such as element Tab component which can only be achieved by manually setting the v-if.
|
||||
<br> e.g.
|
||||
</code>
|
||||
<el-tabs type="border-card" style="width:500px;">
|
||||
<el-tab-pane v-if="checkPermission(['admin'])" label="Admin">Admin can see this</el-tab-pane>
|
||||
<el-tab-pane v-if="checkPermission(['editor'])" label="Editor">Editor can see this</el-tab-pane>
|
||||
<el-tab-pane v-if="checkPermission(['admin','editor'])" label="Admin-OR-Editor">Both admin or editor can see this</el-tab-pane>
|
||||
</el-tabs>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import permission from '@/directive/permission/index.js' // 权限判断指令
|
||||
import checkPermission from '@/utils/permission' // 权限判断函数
|
||||
import SwitchRoles from './components/SwitchRoles'
|
||||
|
||||
export default{
|
||||
name: 'directivePermission',
|
||||
components: { SwitchRoles },
|
||||
directives: { permission },
|
||||
data() {
|
||||
return {
|
||||
key: 1 // 为了能每次切换权限的时候重新初始化指令
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
checkPermission,
|
||||
handleRolesChange() {
|
||||
this.key++
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style rel="stylesheet/scss" lang="scss" scoped>
|
||||
.app-container {
|
||||
/deep/ .permission-alert {
|
||||
width: 320px;
|
||||
margin-top: 30px;
|
||||
background-color: #f0f9eb;
|
||||
color: #67c23a;
|
||||
padding: 8px 16px;
|
||||
border-radius: 4px;
|
||||
display: block;
|
||||
}
|
||||
/deep/ .permission-tag{
|
||||
background-color: #ecf5ff;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<switch-roles @change="handleRolesChange" />
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import SwitchRoles from './components/SwitchRoles'
|
||||
|
||||
export default{
|
||||
name: 'pagePermission',
|
||||
components: { SwitchRoles },
|
||||
methods: {
|
||||
handleRolesChange() {
|
||||
this.$router.push({ path: '/permission/index?' + +new Date() })
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,40 @@
|
|||
<template>
|
||||
<el-upload action="https://upload.qbox.me" :data="dataObj" drag :multiple="true" :before-upload="beforeUpload">
|
||||
<i class="el-icon-upload"></i>
|
||||
<div class="el-upload__text">将文件拖到此处,或<em>点击上传</em></div>
|
||||
</el-upload>
|
||||
</template>
|
||||
|
||||
|
||||
<script>
|
||||
import { getToken } from '@/api/qiniu'
|
||||
// 获取七牛token 后端通过Access Key,Secret Key,bucket等生成token
|
||||
// 七牛官方sdk https://developer.qiniu.com/sdk#official-sdk
|
||||
|
||||
export default{
|
||||
data() {
|
||||
return {
|
||||
dataObj: { token: '', key: '' },
|
||||
image_uri: [],
|
||||
fileList: []
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
beforeUpload() {
|
||||
const _self = this
|
||||
return new Promise((resolve, reject) => {
|
||||
getToken().then(response => {
|
||||
const key = response.data.qiniu_key
|
||||
const token = response.data.qiniu_token
|
||||
_self._data.dataObj.token = token
|
||||
_self._data.dataObj.key = key
|
||||
resolve(true)
|
||||
}).catch(err => {
|
||||
console.log(err)
|
||||
reject(false)
|
||||
})
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -1,15 +0,0 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<p class="warn-content">系统设置</p>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'systemSetting'
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
|
||||
</style>
|
|
@ -0,0 +1,98 @@
|
|||
<template>
|
||||
<el-table :data="list" border fit highlight-current-row style="width: 100%">
|
||||
|
||||
<el-table-column align="center" label="ID" width="65" v-loading="loading"
|
||||
element-loading-text="请给我点时间!">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.id}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="180px" align="center" label="Date">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.timestamp | parseTime('{y}-{m}-{d} {h}:{i}')}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column min-width="300px" label="Title">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.title}}</span>
|
||||
<el-tag>{{scope.row.type}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="110px" align="center" label="Author">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.author}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="120px" label="Importance">
|
||||
<template slot-scope="scope">
|
||||
<svg-icon v-for="n in +scope.row.importance" icon-class="star" :key="n"></svg-icon>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column align="center" label="Readings" width="95">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.pageviews}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column class-name="status-col" label="Status" width="110">
|
||||
<template slot-scope="scope">
|
||||
<el-tag :type="scope.row.status | statusFilter">{{scope.row.status}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
</el-table>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchList } from '@/api/article'
|
||||
|
||||
export default {
|
||||
props: {
|
||||
type: {
|
||||
type: String,
|
||||
default: 'CN'
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
list: null,
|
||||
listQuery: {
|
||||
page: 1,
|
||||
limit: 5,
|
||||
type: this.type,
|
||||
sort: '+id'
|
||||
},
|
||||
loading: false
|
||||
}
|
||||
},
|
||||
filters: {
|
||||
statusFilter(status) {
|
||||
const statusMap = {
|
||||
published: 'success',
|
||||
draft: 'info',
|
||||
deleted: 'danger'
|
||||
}
|
||||
return statusMap[status]
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getList()
|
||||
},
|
||||
methods: {
|
||||
getList() {
|
||||
this.loading = true
|
||||
this.$emit('create') // for test
|
||||
fetchList(this.listQuery).then(response => {
|
||||
this.list = response.data.items
|
||||
this.loading = false
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
<template>
|
||||
<div class="tab-container">
|
||||
<el-tag>mounted times :{{createdTimes}}</el-tag>
|
||||
<el-alert style="width:200px;display:inline-block;vertical-align: middle;margin-left:30px;" title="Tab with keep-alive" type="success" :closable="false">
|
||||
</el-alert>
|
||||
<el-tabs style='margin-top:15px;' v-model="activeName" type="border-card">
|
||||
<el-tab-pane v-for="item in tabMapOptions" :label="item.label" :key='item.key' :name="item.key">
|
||||
<keep-alive>
|
||||
<tab-pane v-if='activeName==item.key' :type='item.key' @create='showCreatedTimes'></tab-pane>
|
||||
</keep-alive>
|
||||
</el-tab-pane>
|
||||
</el-tabs>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import tabPane from './components/tabPane'
|
||||
|
||||
export default {
|
||||
name: 'tab',
|
||||
components: { tabPane },
|
||||
data() {
|
||||
return {
|
||||
tabMapOptions: [
|
||||
{ label: 'China', key: 'CN' },
|
||||
{ label: 'USA', key: 'US' },
|
||||
{ label: 'Japan', key: 'JP' },
|
||||
{ label: 'Eurozone', key: 'EU' }
|
||||
],
|
||||
activeName: 'CN',
|
||||
createdTimes: 0
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
showCreatedTimes() {
|
||||
this.createdTimes = this.createdTimes + 1
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.tab-container{
|
||||
margin: 30px;
|
||||
}
|
||||
</style>
|
|
@ -0,0 +1,361 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<div class="filter-container">
|
||||
<el-input @keyup.enter.native="handleFilter" style="width: 200px;" class="filter-item" :placeholder="$t('table.title')" v-model="listQuery.title">
|
||||
</el-input>
|
||||
<el-select clearable style="width: 90px" class="filter-item" v-model="listQuery.importance" :placeholder="$t('table.importance')">
|
||||
<el-option v-for="item in importanceOptions" :key="item" :label="item" :value="item">
|
||||
</el-option>
|
||||
</el-select>
|
||||
<el-select clearable class="filter-item" style="width: 130px" v-model="listQuery.type" :placeholder="$t('table.type')">
|
||||
<el-option v-for="item in calendarTypeOptions" :key="item.key" :label="item.display_name+'('+item.key+')'" :value="item.key">
|
||||
</el-option>
|
||||
</el-select>
|
||||
<el-select @change='handleFilter' style="width: 140px" class="filter-item" v-model="listQuery.sort">
|
||||
<el-option v-for="item in sortOptions" :key="item.key" :label="item.label" :value="item.key">
|
||||
</el-option>
|
||||
</el-select>
|
||||
<el-button class="filter-item" type="primary" v-waves icon="el-icon-search" @click="handleFilter">{{$t('table.search')}}</el-button>
|
||||
<el-button class="filter-item" style="margin-left: 10px;" @click="handleCreate" type="primary" icon="el-icon-edit">{{$t('table.add')}}</el-button>
|
||||
<el-button class="filter-item" type="primary" :loading="downloadLoading" v-waves icon="el-icon-download" @click="handleDownload">{{$t('table.export')}}</el-button>
|
||||
<el-checkbox class="filter-item" style='margin-left:15px;' @change='tableKey=tableKey+1' v-model="showReviewer">{{$t('table.reviewer')}}</el-checkbox>
|
||||
</div>
|
||||
|
||||
<el-table :key='tableKey' :data="list" v-loading="listLoading" border fit highlight-current-row
|
||||
style="width: 100%;min-height:1000px;">
|
||||
<el-table-column align="center" :label="$t('table.id')" width="65">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.id}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column width="150px" align="center" :label="$t('table.date')">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.timestamp | parseTime('{y}-{m}-{d} {h}:{i}')}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column min-width="150px" :label="$t('table.title')">
|
||||
<template slot-scope="scope">
|
||||
<span class="link-type" @click="handleUpdate(scope.row)">{{scope.row.title}}</span>
|
||||
<el-tag>{{scope.row.type | typeFilter}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column width="110px" align="center" :label="$t('table.author')">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.author}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column width="110px" v-if='showReviewer' align="center" :label="$t('table.reviewer')">
|
||||
<template slot-scope="scope">
|
||||
<span style='color:red;'>{{scope.row.reviewer}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column width="80px" :label="$t('table.importance')">
|
||||
<template slot-scope="scope">
|
||||
<svg-icon v-for="n in +scope.row.importance" icon-class="star" class="meta-item__icon" :key="n"></svg-icon>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column align="center" :label="$t('table.readings')" width="95">
|
||||
<template slot-scope="scope">
|
||||
<span v-if="scope.row.pageviews" class="link-type" @click='handleFetchPv(scope.row.pageviews)'>{{scope.row.pageviews}}</span>
|
||||
<span v-else>0</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column class-name="status-col" :label="$t('table.status')" width="100">
|
||||
<template slot-scope="scope">
|
||||
<el-tag :type="scope.row.status | statusFilter">{{scope.row.status}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column align="center" :label="$t('table.actions')" width="230" class-name="small-padding fixed-width">
|
||||
<template slot-scope="scope">
|
||||
<el-button type="primary" size="mini" @click="handleUpdate(scope.row)">{{$t('table.edit')}}</el-button>
|
||||
<el-button v-if="scope.row.status!='published'" size="mini" type="success" @click="handleModifyStatus(scope.row,'published')">{{$t('table.publish')}}
|
||||
</el-button>
|
||||
<el-button v-if="scope.row.status!='draft'" size="mini" @click="handleModifyStatus(scope.row,'draft')">{{$t('table.draft')}}
|
||||
</el-button>
|
||||
<el-button v-if="scope.row.status!='deleted'" size="mini" type="danger" @click="handleModifyStatus(scope.row,'deleted')">{{$t('table.delete')}}
|
||||
</el-button>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
|
||||
<div class="pagination-container">
|
||||
<el-pagination background @size-change="handleSizeChange" @current-change="handleCurrentChange" :current-page="listQuery.page" :page-sizes="[10,20,30, 50]" :page-size="listQuery.limit" layout="total, sizes, prev, pager, next, jumper" :total="total">
|
||||
</el-pagination>
|
||||
</div>
|
||||
|
||||
<el-dialog :title="textMap[dialogStatus]" :visible.sync="dialogFormVisible">
|
||||
<el-form :rules="rules" ref="dataForm" :model="temp" label-position="left" label-width="70px" style='width: 400px; margin-left:50px;'>
|
||||
<el-form-item :label="$t('table.type')" prop="type">
|
||||
<el-select class="filter-item" v-model="temp.type" placeholder="Please select">
|
||||
<el-option v-for="item in calendarTypeOptions" :key="item.key" :label="item.display_name" :value="item.key">
|
||||
</el-option>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('table.date')" prop="timestamp">
|
||||
<el-date-picker v-model="temp.timestamp" type="datetime" placeholder="Please pick a date">
|
||||
</el-date-picker>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('table.title')" prop="title">
|
||||
<el-input v-model="temp.title"></el-input>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('table.status')">
|
||||
<el-select class="filter-item" v-model="temp.status" placeholder="Please select">
|
||||
<el-option v-for="item in statusOptions" :key="item" :label="item" :value="item">
|
||||
</el-option>
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('table.importance')">
|
||||
<el-rate style="margin-top:8px;" v-model="temp.importance" :colors="['#99A9BF', '#F7BA2A', '#FF9900']" :max='3'></el-rate>
|
||||
</el-form-item>
|
||||
<el-form-item :label="$t('table.remark')">
|
||||
<el-input type="textarea" :autosize="{ minRows: 2, maxRows: 4}" placeholder="Please input" v-model="temp.remark">
|
||||
</el-input>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
<div slot="footer" class="dialog-footer">
|
||||
<el-button @click="dialogFormVisible = false">{{$t('table.cancel')}}</el-button>
|
||||
<el-button v-if="dialogStatus=='create'" type="primary" @click="createData">{{$t('table.confirm')}}</el-button>
|
||||
<el-button v-else type="primary" @click="updateData">{{$t('table.confirm')}}</el-button>
|
||||
</div>
|
||||
</el-dialog>
|
||||
|
||||
<el-dialog title="Reading statistics" :visible.sync="dialogPvVisible">
|
||||
<el-table :data="pvData" border fit highlight-current-row style="width: 100%">
|
||||
<el-table-column prop="key" label="Channel"> </el-table-column>
|
||||
<el-table-column prop="pv" label="Pv"> </el-table-column>
|
||||
</el-table>
|
||||
<span slot="footer" class="dialog-footer">
|
||||
<el-button type="primary" @click="dialogPvVisible = false">{{$t('table.confirm')}}</el-button>
|
||||
</span>
|
||||
</el-dialog>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchList, fetchPv, createArticle, updateArticle } from '@/api/article'
|
||||
import waves from '@/directive/waves' // 水波纹指令
|
||||
import { parseTime } from '@/utils'
|
||||
|
||||
const calendarTypeOptions = [
|
||||
{ key: 'CN', display_name: 'China' },
|
||||
{ key: 'US', display_name: 'USA' },
|
||||
{ key: 'JP', display_name: 'Japan' },
|
||||
{ key: 'EU', display_name: 'Eurozone' }
|
||||
]
|
||||
|
||||
// arr to obj ,such as { CN : "China", US : "USA" }
|
||||
const calendarTypeKeyValue = calendarTypeOptions.reduce((acc, cur) => {
|
||||
acc[cur.key] = cur.display_name
|
||||
return acc
|
||||
}, {})
|
||||
|
||||
export default {
|
||||
name: 'complexTable',
|
||||
directives: {
|
||||
waves
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
tableKey: 0,
|
||||
list: null,
|
||||
total: null,
|
||||
listLoading: true,
|
||||
listQuery: {
|
||||
page: 1,
|
||||
limit: 20,
|
||||
importance: undefined,
|
||||
title: undefined,
|
||||
type: undefined,
|
||||
sort: '+id'
|
||||
},
|
||||
importanceOptions: [1, 2, 3],
|
||||
calendarTypeOptions,
|
||||
sortOptions: [{ label: 'ID Ascending', key: '+id' }, { label: 'ID Descending', key: '-id' }],
|
||||
statusOptions: ['published', 'draft', 'deleted'],
|
||||
showReviewer: false,
|
||||
temp: {
|
||||
id: undefined,
|
||||
importance: 1,
|
||||
remark: '',
|
||||
timestamp: new Date(),
|
||||
title: '',
|
||||
type: '',
|
||||
status: 'published'
|
||||
},
|
||||
dialogFormVisible: false,
|
||||
dialogStatus: '',
|
||||
textMap: {
|
||||
update: 'Edit',
|
||||
create: 'Create'
|
||||
},
|
||||
dialogPvVisible: false,
|
||||
pvData: [],
|
||||
rules: {
|
||||
type: [{ required: true, message: 'type is required', trigger: 'change' }],
|
||||
timestamp: [{ type: 'date', required: true, message: 'timestamp is required', trigger: 'change' }],
|
||||
title: [{ required: true, message: 'title is required', trigger: 'blur' }]
|
||||
},
|
||||
downloadLoading: false
|
||||
}
|
||||
},
|
||||
filters: {
|
||||
statusFilter(status) {
|
||||
const statusMap = {
|
||||
published: 'success',
|
||||
draft: 'info',
|
||||
deleted: 'danger'
|
||||
}
|
||||
return statusMap[status]
|
||||
},
|
||||
typeFilter(type) {
|
||||
return calendarTypeKeyValue[type]
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getList()
|
||||
},
|
||||
methods: {
|
||||
getList() {
|
||||
this.listLoading = true
|
||||
fetchList(this.listQuery).then(response => {
|
||||
this.list = response.data.items
|
||||
this.total = response.data.total
|
||||
|
||||
// Just to simulate the time of the request
|
||||
setTimeout(() => {
|
||||
this.listLoading = false
|
||||
}, 1.5 * 1000)
|
||||
})
|
||||
},
|
||||
handleFilter() {
|
||||
this.listQuery.page = 1
|
||||
this.getList()
|
||||
},
|
||||
handleSizeChange(val) {
|
||||
this.listQuery.limit = val
|
||||
this.getList()
|
||||
},
|
||||
handleCurrentChange(val) {
|
||||
this.listQuery.page = val
|
||||
this.getList()
|
||||
},
|
||||
handleModifyStatus(row, status) {
|
||||
this.$message({
|
||||
message: '操作成功',
|
||||
type: 'success'
|
||||
})
|
||||
row.status = status
|
||||
},
|
||||
resetTemp() {
|
||||
this.temp = {
|
||||
id: undefined,
|
||||
importance: 1,
|
||||
remark: '',
|
||||
timestamp: new Date(),
|
||||
title: '',
|
||||
status: 'published',
|
||||
type: ''
|
||||
}
|
||||
},
|
||||
handleCreate() {
|
||||
this.resetTemp()
|
||||
this.dialogStatus = 'create'
|
||||
this.dialogFormVisible = true
|
||||
this.$nextTick(() => {
|
||||
this.$refs['dataForm'].clearValidate()
|
||||
})
|
||||
},
|
||||
createData() {
|
||||
this.$refs['dataForm'].validate((valid) => {
|
||||
if (valid) {
|
||||
this.temp.id = parseInt(Math.random() * 100) + 1024 // mock a id
|
||||
this.temp.author = 'vue-element-admin'
|
||||
createArticle(this.temp).then(() => {
|
||||
this.list.unshift(this.temp)
|
||||
this.dialogFormVisible = false
|
||||
this.$notify({
|
||||
title: '成功',
|
||||
message: '创建成功',
|
||||
type: 'success',
|
||||
duration: 2000
|
||||
})
|
||||
})
|
||||
}
|
||||
})
|
||||
},
|
||||
handleUpdate(row) {
|
||||
this.temp = Object.assign({}, row) // copy obj
|
||||
this.temp.timestamp = new Date(this.temp.timestamp)
|
||||
this.dialogStatus = 'update'
|
||||
this.dialogFormVisible = true
|
||||
this.$nextTick(() => {
|
||||
this.$refs['dataForm'].clearValidate()
|
||||
})
|
||||
},
|
||||
updateData() {
|
||||
this.$refs['dataForm'].validate((valid) => {
|
||||
if (valid) {
|
||||
const tempData = Object.assign({}, this.temp)
|
||||
tempData.timestamp = +new Date(tempData.timestamp) // change Thu Nov 30 2017 16:41:05 GMT+0800 (CST) to 1512031311464
|
||||
updateArticle(tempData).then(() => {
|
||||
for (const v of this.list) {
|
||||
if (v.id === this.temp.id) {
|
||||
const index = this.list.indexOf(v)
|
||||
this.list.splice(index, 1, this.temp)
|
||||
break
|
||||
}
|
||||
}
|
||||
this.dialogFormVisible = false
|
||||
this.$notify({
|
||||
title: '成功',
|
||||
message: '更新成功',
|
||||
type: 'success',
|
||||
duration: 2000
|
||||
})
|
||||
})
|
||||
}
|
||||
})
|
||||
},
|
||||
handleDelete(row) {
|
||||
this.$notify({
|
||||
title: '成功',
|
||||
message: '删除成功',
|
||||
type: 'success',
|
||||
duration: 2000
|
||||
})
|
||||
const index = this.list.indexOf(row)
|
||||
this.list.splice(index, 1)
|
||||
},
|
||||
handleFetchPv(pv) {
|
||||
fetchPv(pv).then(response => {
|
||||
this.pvData = response.data.pvData
|
||||
this.dialogPvVisible = true
|
||||
})
|
||||
},
|
||||
handleDownload() {
|
||||
this.downloadLoading = true
|
||||
import('@/vendor/Export2Excel').then(excel => {
|
||||
const tHeader = ['timestamp', 'title', 'type', 'importance', 'status']
|
||||
const filterVal = ['timestamp', 'title', 'type', 'importance', 'status']
|
||||
const data = this.formatJson(filterVal, this.list)
|
||||
excel.export_json_to_excel({
|
||||
header: tHeader,
|
||||
data,
|
||||
filename: 'table-list'
|
||||
})
|
||||
this.downloadLoading = false
|
||||
})
|
||||
},
|
||||
formatJson(filterVal, jsonData) {
|
||||
return jsonData.map(v => filterVal.map(j => {
|
||||
if (j === 'timestamp') {
|
||||
return parseTime(v[j])
|
||||
} else {
|
||||
return v[j]
|
||||
}
|
||||
}))
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
|
@ -0,0 +1,152 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<!-- Note that row-key is necessary to get a correct row order. -->
|
||||
<el-table :data="list" row-key="id" v-loading="listLoading" border fit highlight-current-row style="width: 100%">
|
||||
|
||||
<el-table-column align="center" label="ID" width="65">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.id}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="180px" align="center" label="Date">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.timestamp | parseTime('{y}-{m}-{d} {h}:{i}')}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column min-width="300px" label="Title">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.title}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="110px" align="center" label="Author">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.author}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column width="100px" label="Importance">
|
||||
<template slot-scope="scope">
|
||||
<svg-icon v-for="n in +scope.row.importance" icon-class="star" class="icon-star" :key="n"></svg-icon>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column align="center" label="Readings" width="95">
|
||||
<template slot-scope="scope">
|
||||
<span>{{scope.row.pageviews}}</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column class-name="status-col" label="Status" width="110">
|
||||
<template slot-scope="scope">
|
||||
<el-tag :type="scope.row.status | statusFilter">{{scope.row.status}}</el-tag>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column align="center" label="Drag" width="80">
|
||||
<template slot-scope="scope">
|
||||
<svg-icon class='drag-handler' icon-class="drag"></svg-icon>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
</el-table>
|
||||
<!-- $t is vue-i18n global function to translate lang (lang in @/lang) -->
|
||||
<div class='show-d'>{{$t('table.dragTips1')}} : {{ oldList}}</div>
|
||||
<div class='show-d'>{{$t('table.dragTips2')}} : {{newList}}</div>
|
||||
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { fetchList } from '@/api/article'
|
||||
import Sortable from 'sortablejs'
|
||||
|
||||
export default {
|
||||
name: 'dragTable',
|
||||
data() {
|
||||
return {
|
||||
list: null,
|
||||
total: null,
|
||||
listLoading: true,
|
||||
listQuery: {
|
||||
page: 1,
|
||||
limit: 10
|
||||
},
|
||||
sortable: null,
|
||||
oldList: [],
|
||||
newList: []
|
||||
}
|
||||
},
|
||||
filters: {
|
||||
statusFilter(status) {
|
||||
const statusMap = {
|
||||
published: 'success',
|
||||
draft: 'info',
|
||||
deleted: 'danger'
|
||||
}
|
||||
return statusMap[status]
|
||||
}
|
||||
},
|
||||
created() {
|
||||
this.getList()
|
||||
},
|
||||
methods: {
|
||||
getList() {
|
||||
this.listLoading = true
|
||||
fetchList(this.listQuery).then(response => {
|
||||
this.list = response.data.items
|
||||
this.total = response.data.total
|
||||
this.listLoading = false
|
||||
this.oldList = this.list.map(v => v.id)
|
||||
this.newList = this.oldList.slice()
|
||||
this.$nextTick(() => {
|
||||
this.setSort()
|
||||
})
|
||||
})
|
||||
},
|
||||
setSort() {
|
||||
const el = document.querySelectorAll('.el-table__body-wrapper > table > tbody')[0]
|
||||
this.sortable = Sortable.create(el, {
|
||||
ghostClass: 'sortable-ghost', // Class name for the drop placeholder,
|
||||
setData: function(dataTransfer) {
|
||||
dataTransfer.setData('Text', '')
|
||||
// to avoid Firefox bug
|
||||
// Detail see : https://github.com/RubaXa/Sortable/issues/1012
|
||||
},
|
||||
onEnd: evt => {
|
||||
const targetRow = this.list.splice(evt.oldIndex, 1)[0]
|
||||
this.list.splice(evt.newIndex, 0, targetRow)
|
||||
|
||||
// for show the changes, you can delete in you code
|
||||
const tempIndex = this.newList.splice(evt.oldIndex, 1)[0]
|
||||
this.newList.splice(evt.newIndex, 0, tempIndex)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
.sortable-ghost{
|
||||
opacity: .8;
|
||||
color: #fff!important;
|
||||
background: #42b983!important;
|
||||
}
|
||||
</style>
|
||||
|
||||
<style scoped>
|
||||
.icon-star{
|
||||
margin-right:2px;
|
||||
}
|
||||
.drag-handler{
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
cursor: pointer;
|
||||
}
|
||||
.show-d{
|
||||
margin-top: 15px;
|
||||
}
|
||||
</style>
|