顶部导航
This commit is contained in:
parent
370d0f0aa8
commit
0db37fa82c
@ -12,7 +12,7 @@ export const useWrapComponents = (Component, route) => {
|
||||
wrapper = {
|
||||
name: wrapperName,
|
||||
render() {
|
||||
return h('div', { className: 'layout' }, Component);
|
||||
return h('div', { className: 'layout-main' }, Component);
|
||||
},
|
||||
};
|
||||
wrapperMap.set(wrapperName, wrapper);
|
||||
|
44
main/src/layouts/Link.vue
Normal file
44
main/src/layouts/Link.vue
Normal file
@ -0,0 +1,44 @@
|
||||
<!--
|
||||
* @Description:
|
||||
* @Author: zenghua.wang
|
||||
* @Date: 2023-06-20 14:29:45
|
||||
* @LastEditors: zenghua.wang
|
||||
* @LastEditTime: 2024-01-27 09:29:36
|
||||
-->
|
||||
<template>
|
||||
<component :is="type" v-bind="linkProps(to)">
|
||||
<slot />
|
||||
</component>
|
||||
</template>
|
||||
|
||||
<script setup name="app-link">
|
||||
import { computed } from 'vue';
|
||||
import { isExternal } from '@/utils/validate';
|
||||
|
||||
const props = defineProps({
|
||||
to: {
|
||||
type: String,
|
||||
required: true,
|
||||
},
|
||||
});
|
||||
|
||||
const type = computed(() => {
|
||||
if (isExternal(props.to)) {
|
||||
return 'a';
|
||||
}
|
||||
return 'router-link';
|
||||
});
|
||||
|
||||
const linkProps = (to) => {
|
||||
if (isExternal(to)) {
|
||||
return {
|
||||
href: to,
|
||||
target: '_blank',
|
||||
rel: 'noopener',
|
||||
};
|
||||
}
|
||||
return {
|
||||
to: to,
|
||||
};
|
||||
};
|
||||
</script>
|
1
main/src/layouts/base64img.js
Normal file
1
main/src/layouts/base64img.js
Normal file
File diff suppressed because one or more lines are too long
@ -9,22 +9,100 @@
|
||||
<router-view v-slot="{ Component, route }">
|
||||
<transition name="fade-slide" mode="out-in" appear>
|
||||
<keep-alive v-if="isReload" :include="cacheRoutes">
|
||||
<component :is="useWrapComponents(Component, route)" :key="route.path" />
|
||||
<div class="layout">
|
||||
<div class="layout-header">
|
||||
<div class="layout-header-top">
|
||||
<div class="layout-header-top-left">
|
||||
<span>您好,欢迎来到农业产业服务平台</span>
|
||||
<el-tag>运营大屏</el-tag>
|
||||
<el-tag>产业服务APP</el-tag>
|
||||
<el-tag>产业运营管理</el-tag>
|
||||
</div>
|
||||
<div class="layout-header-top-right">
|
||||
<span>商家中心</span>
|
||||
<span>个人中心</span>
|
||||
<span>返回首页</span>
|
||||
</div>
|
||||
</div>
|
||||
<div class="layout-header-bottom">
|
||||
<div class="layout-header-bottom-left">
|
||||
<div class="layout-header-bottom-search">
|
||||
<div class="title">农业产业服务平台</div>
|
||||
<el-input v-model="keyword" placeholder="请输入关键词进行搜索"></el-input>
|
||||
<el-button type="primary" @click="Search">搜索</el-button>
|
||||
</div>
|
||||
<el-menu ellipsis class="layout-header-bottom-menu" mode="horizontal">
|
||||
<app-link v-for="(item, index) in meuns" :key="index" :to="item.path">
|
||||
<el-menu-item>{{ item.label }}</el-menu-item>
|
||||
</app-link>
|
||||
</el-menu>
|
||||
</div>
|
||||
<div class="layout-header-bottom-right">
|
||||
<div class="layout-header-bottom-right-qr">
|
||||
<div class="layout-header-bottom-right-qr-img">
|
||||
<img :src="qrImg" alt="" />
|
||||
<p>下载数农App</p>
|
||||
</div>
|
||||
<div class="layout-header-bottom-right-qr-img">
|
||||
<img :src="qrImg" alt="" />
|
||||
<p>打开数农小程序</p>
|
||||
</div>
|
||||
</div>
|
||||
<p>使用数农手机服务,更方便</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<component :is="useWrapComponents(Component, route)" :key="route.path" />
|
||||
</div>
|
||||
</keep-alive>
|
||||
</transition>
|
||||
</router-view>
|
||||
</template>
|
||||
|
||||
<script setup name="layout">
|
||||
import { computed } from 'vue';
|
||||
import { computed, ref } from 'vue';
|
||||
import { useSettingStore } from '@/store/modules/setting';
|
||||
import { usePermissionStore } from '@/store/modules/permission';
|
||||
import { useWrapComponents } from '@/hooks/useWrapComponents';
|
||||
import { qrImg } from './base64img';
|
||||
import AppLink from './Link.vue';
|
||||
|
||||
const SettingStore = useSettingStore();
|
||||
const PermissionStore = usePermissionStore();
|
||||
const cacheRoutes = computed(() => PermissionStore.keepAliveRoutes);
|
||||
const isReload = computed(() => SettingStore.isReload);
|
||||
|
||||
const keyword = ref('');
|
||||
|
||||
const meuns = ref([
|
||||
{
|
||||
label: '智慧种植',
|
||||
path: '/login',
|
||||
},
|
||||
{
|
||||
label: '农事服务',
|
||||
path: '/sub-admin/',
|
||||
},
|
||||
{
|
||||
label: '涉农金融',
|
||||
},
|
||||
{
|
||||
label: '电商交易',
|
||||
},
|
||||
{
|
||||
label: '分拣包装',
|
||||
},
|
||||
{
|
||||
label: '仓储物流',
|
||||
},
|
||||
{
|
||||
label: '公共品牌运营',
|
||||
},
|
||||
]);
|
||||
|
||||
function Search() {
|
||||
console.log(keyword.value, 'search');
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
@ -32,5 +110,108 @@ const isReload = computed(() => SettingStore.isReload);
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
box-sizing: border-box;
|
||||
&-header {
|
||||
height: 206px;
|
||||
overflow: hidden;
|
||||
&-top {
|
||||
display: flex;
|
||||
height: 44px;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
background-color: #f8f8f8;
|
||||
padding: 0 32px;
|
||||
&-left {
|
||||
line-height: 36px;
|
||||
font-size: 16px;
|
||||
.el-tag {
|
||||
color: #fff;
|
||||
background-color: #a4adb3;
|
||||
margin-left: 12px;
|
||||
border-color: #a4adb3;
|
||||
cursor: pointer;
|
||||
font-size: 18px;
|
||||
}
|
||||
}
|
||||
&-right {
|
||||
span {
|
||||
color: #000;
|
||||
margin-left: 25px;
|
||||
line-height: 36px;
|
||||
font-size: 16px;
|
||||
text-align: center;
|
||||
cursor: pointer;
|
||||
&:nth-child(1) {
|
||||
margin-left: 0;
|
||||
font-weight: bold;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
&-bottom {
|
||||
display: flex;
|
||||
padding: 20px 32px 0;
|
||||
&-left {
|
||||
flex-grow: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: space-between;
|
||||
width: calc(100% - 300px);
|
||||
.layout-header-bottom-search {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.title {
|
||||
font-size: 45px;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.el-input {
|
||||
flex-grow: 1;
|
||||
max-width: 460px;
|
||||
margin-left: 40px;
|
||||
height: 50px;
|
||||
font-size: 18px;
|
||||
}
|
||||
.el-button {
|
||||
margin-left: 40px;
|
||||
font-size: 18px;
|
||||
height: 45px;
|
||||
padding: 8px 24px;
|
||||
}
|
||||
}
|
||||
.layout-header-bottom-menu {
|
||||
justify-content: space-around;
|
||||
border: none;
|
||||
.el-menu-item {
|
||||
font-size: 24px;
|
||||
}
|
||||
}
|
||||
}
|
||||
&-right {
|
||||
margin-top: -10px;
|
||||
width: 240px;
|
||||
padding-left: 20px;
|
||||
p {
|
||||
text-align: center;
|
||||
}
|
||||
&-qr {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
&-img {
|
||||
img {
|
||||
width: 110px;
|
||||
height: 110px;
|
||||
}
|
||||
p {
|
||||
text-align: center;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
&-main {
|
||||
width: 100%;
|
||||
height: calc(100% - 206px);
|
||||
background-color: #f8f8f8;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
116
main/src/utils/validate.js
Normal file
116
main/src/utils/validate.js
Normal file
@ -0,0 +1,116 @@
|
||||
/**
|
||||
* 路径匹配器
|
||||
* @param {string} pattern
|
||||
* @param {string} path
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function isPathMatch(pattern, path) {
|
||||
const regexPattern = pattern.replace(/\//g, '\\/').replace(/\*\*/g, '.*').replace(/\*/g, '[^\\/]*');
|
||||
const regex = new RegExp(`^${regexPattern}$`);
|
||||
return regex.test(path);
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断value字符串是否为空
|
||||
* @param {string} value
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function isEmpty(value) {
|
||||
if (value == null || value == '' || value == undefined || value == 'undefined') {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断url是否是http或https
|
||||
* @param {string} url
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function isHttp(url) {
|
||||
return url.indexOf('http://') !== -1 || url.indexOf('https://') !== -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断path是否为外链
|
||||
* @param {string} path
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function isExternal(path) {
|
||||
return /^(https?:|mailto:|tel:)/.test(path);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} str
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function validUsername(str) {
|
||||
const valid_map = ['admin', 'editor'];
|
||||
return valid_map.indexOf(str.trim()) >= 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} url
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function validURL(url) {
|
||||
const reg =
|
||||
/^(https?|ftp):\/\/([a-zA-Z0-9.-]+(:[a-zA-Z0-9.&%$-]+)*@)*((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]?)(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}|([a-zA-Z0-9-]+\.)*[a-zA-Z0-9-]+\.(com|edu|gov|int|mil|net|org|biz|arpa|info|name|pro|aero|coop|museum|[a-zA-Z]{2}))(:[0-9]+)*(\/($|[a-zA-Z0-9.,?'\\+&%$#=~_-]+))*$/;
|
||||
return reg.test(url);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} str
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function validLowerCase(str) {
|
||||
const reg = /^[a-z]+$/;
|
||||
return reg.test(str);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} str
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function validUpperCase(str) {
|
||||
const reg = /^[A-Z]+$/;
|
||||
return reg.test(str);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} str
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function validAlphabets(str) {
|
||||
const reg = /^[A-Za-z]+$/;
|
||||
return reg.test(str);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} email
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function validEmail(email) {
|
||||
const reg =
|
||||
/^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
|
||||
return reg.test(email);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} str
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function isString(str) {
|
||||
return typeof str === 'string' || str instanceof String;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {Array} arg
|
||||
* @returns {Boolean}
|
||||
*/
|
||||
export function isArray(arg) {
|
||||
if (typeof Array.isArray === 'undefined') {
|
||||
return Object.prototype.toString.call(arg) === '[object Array]';
|
||||
}
|
||||
return Array.isArray(arg);
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user