优化高德地图,修改首页图片,修改事件处理视频
This commit is contained in:
parent
7babd0fec6
commit
220d8ffb5e
23
config.js
23
config.js
@ -1,23 +0,0 @@
|
||||
const BASE_API = {
|
||||
// SERVER_IP: 'http://www.linxyun.com',
|
||||
SERVER_IP: 'http://39.101.75.113:8088',
|
||||
// SERVER_IP: 'http://121.229.160.133:8088',
|
||||
GetFileConfigUrl: '/smartroadlamp/genFileConfig.action',
|
||||
// 部署时是否要加前缀,后端API地址需要统计加上这串,当部署不需要时,该串配置成空串就可以
|
||||
URL_PRE: '',
|
||||
// 显示的项目名称
|
||||
PROJECT_NAME: '智慧路灯',
|
||||
PROJECT_URI: '/smartroadlamp',
|
||||
ContainCustmerID: '0',
|
||||
CustomerType: 1,
|
||||
// 项目ID
|
||||
ENT_CODE: '56',
|
||||
SubSysID: '2',
|
||||
// 提示消息显示时长
|
||||
MSG_SHOW_TIME: 3000,
|
||||
IS_TEST: false,
|
||||
// 是否开启国际化
|
||||
I18N: false,
|
||||
// 管理员角色编码
|
||||
MANAGER_ROLE: '2101',
|
||||
}
|
@ -13,7 +13,7 @@
|
||||
content="vue-next-admin,基于 vue3 + CompositionAPI + typescript + vite + element plus,适配手机、平板、pc 的后台开源免费管理系统模板!vue-prev-admin,基于 vue2 + element ui,适配手机、平板、pc 的后台开源免费管理系统模板!"
|
||||
/>
|
||||
<link rel="icon" href="/favicon.ico" />
|
||||
<script src="./config.js"></script>
|
||||
<script src="./public/config.js"></script>
|
||||
<title>智慧路灯</title>
|
||||
</head>
|
||||
<body>
|
||||
|
@ -14,6 +14,7 @@
|
||||
"@element-plus/icons-vue": "^2.3.1",
|
||||
"@wangeditor/editor": "^5.1.23",
|
||||
"@wangeditor/editor-for-vue": "^5.1.12",
|
||||
"ali-oss": "^6.22.0",
|
||||
"autofit.js": "^3.2.2",
|
||||
"axios": "^1.6.8",
|
||||
"coordtransform": "^2.1.2",
|
||||
@ -27,7 +28,10 @@
|
||||
"js-cookie": "^3.0.5",
|
||||
"js-table2excel": "^1.1.2",
|
||||
"jsplumb": "^2.15.6",
|
||||
"localforage": "^1.10.0",
|
||||
"lodash-es": "^4.17.21",
|
||||
"mitt": "^3.0.1",
|
||||
"monaco-editor": "^0.52.2",
|
||||
"nprogress": "^0.2.0",
|
||||
"pinia": "^2.1.7",
|
||||
"print-js": "^1.6.0",
|
||||
@ -36,12 +40,14 @@
|
||||
"screenfull": "^6.0.2",
|
||||
"sortablejs": "^1.15.2",
|
||||
"splitpanes": "^3.1.5",
|
||||
"vant": "^4.9.15",
|
||||
"vue": "^3.4.21",
|
||||
"vue-clipboard3": "^2.0.0",
|
||||
"vue-demi": "^0.14.7",
|
||||
"vue-grid-layout": "^3.0.0-beta1",
|
||||
"vue-i18n": "^9.10.2",
|
||||
"vue-router": "^4.3.0"
|
||||
"vue-router": "^4.3.0",
|
||||
"xlsx": "^0.18.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/node": "^20.11.28",
|
||||
|
@ -1,8 +1,8 @@
|
||||
// import { Post, SyncPost } from '/@/api/linxyun/base/index.ts'
|
||||
import IFileClient from './file_client_interface.js';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
|
||||
const httpReqeust = httpReqeustApi();
|
||||
const httpReqeust = httpRequestApi();
|
||||
|
||||
export default class FileClient_Eslithe extends IFileClient {
|
||||
constructor(fileConfig) {
|
||||
@ -40,7 +40,10 @@ export default class FileClient_Eslithe extends IFileClient {
|
||||
console.log('[Debug][File][eslithe]upload file, file: ', fileName, content);
|
||||
const formData = new FormData();
|
||||
formData.append('file', content, fileName);
|
||||
let res = await httpReqeust.SyncPost(this._fileConfig.setting.uploadUrl, null, formData);
|
||||
|
||||
let res = await httpReqeust.SyncPost(this._fileConfig.setting.uploadUrl, null, formData, {
|
||||
'Content-Type': 'multipart/form-data'
|
||||
});
|
||||
console.log('yyyyyyyyyyyyyyyyyy, res: ', res);
|
||||
if (!res || !res.data || res.code !== '0000') {
|
||||
console.error('[Error][File][uploadFile][eslithe]Upload fail, res: ', res);
|
||||
|
@ -1,9 +1,9 @@
|
||||
// import { Post, SyncPost, SyncPostOutside } from '/@/api/linxyun/base/index.ts'
|
||||
import { warnTime } from './constant.js';
|
||||
import IFileClient from './file_client_interface.js';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
|
||||
const httpReqeust = httpReqeustApi();
|
||||
const httpReqeust = httpRequestApi();
|
||||
|
||||
export default class FileClient_QN extends IFileClient {
|
||||
constructor(fileConfig) {
|
||||
|
@ -2,9 +2,9 @@ import { warnTime } from './constant.js'
|
||||
// import { SyncPost } from '/@/api/linxyun/base/index.ts'
|
||||
import IFileClient from './file_client_interface.js'
|
||||
import { getGUID } from './guid.js'
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
|
||||
const httpReqeust = httpReqeustApi();
|
||||
const httpReqeust = httpRequestApi();
|
||||
|
||||
const COS = () => ({})
|
||||
|
||||
|
@ -6,9 +6,9 @@ import FileClient_Ali from './file_client_ali.js';
|
||||
// import { Message } from 'element-ui'
|
||||
import { ElMessage } from 'element-plus';
|
||||
// import { SyncPost } from '/@/api/linxyun/base/index.ts'
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
|
||||
const httpReqeust = httpReqeustApi();
|
||||
const httpReqeust = httpRequestApi();
|
||||
|
||||
export default class FileIns {
|
||||
_getFileConfigUrl = 'genFileConfig';
|
||||
|
@ -8,13 +8,13 @@
|
||||
</template>
|
||||
<script lang="ts" setup name="ImportExcel">
|
||||
import uoloadExcel from './upload-excel.vue';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index.ts';
|
||||
import EnumOptions from '/@/components/Linxyun/Datas/enum_options.js';
|
||||
import Lxy_page_event_remote from '/@/components/Linxyun/custom/CustomCommon/lxy_page_event_remote.js';
|
||||
import { treeData2Optioins } from '/@/components/Linxyun/custom/CustomCommon/tools.js';
|
||||
import { getVuex } from '/@/utils/formatPrivacyData.js';
|
||||
import { ElMessage } from 'element-plus';
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
|
||||
const props = withDefaults(
|
||||
defineProps<{
|
||||
|
@ -12,7 +12,7 @@ import {
|
||||
} from '/@/utils/formatPrivacyData.js';
|
||||
import EnumOptions from '../../Datas/enum_options.js';
|
||||
import Lxy_params_mgr from '/@/components/Linxyun/custom/CustomCommon/lxy_params_mgr.js';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { createDDE_SA } from '/@/utils/stringUtil';
|
||||
import localforage from 'localforage';
|
||||
import { functions } from 'lodash';
|
||||
@ -625,7 +625,7 @@ export const getPageFuncDefine = async (pageid) => {
|
||||
// 页面函数
|
||||
const funcs = await loadFuncFromLocal(1, pageid)
|
||||
if (funcs == null) {
|
||||
const res = await httpReqeustApi().SyncPost(
|
||||
const res = await httpRequestApi().SyncPost(
|
||||
'/eslithe/queryFunctionDefineNew.action',
|
||||
{ PageID: pageid, EntCode: BASE_API.ENT_CODE, Type: 1 },
|
||||
{},
|
||||
@ -642,7 +642,7 @@ export const getPageFuncDefine = async (pageid) => {
|
||||
// 全局函数
|
||||
const glfuncs = await loadFuncFromLocal(0, -1)
|
||||
if (glfuncs == null) {
|
||||
const glres = await httpReqeustApi().SyncPost('/eslithe/queryFunctionDefineNew.action', { EntCode: BASE_API.ENT_CODE, Type: 0 }, {}, headers);
|
||||
const glres = await httpRequestApi().SyncPost('/eslithe/queryFunctionDefineNew.action', { EntCode: BASE_API.ENT_CODE, Type: 0 }, {}, headers);
|
||||
addFunction(glres, 0, -1);
|
||||
} else {
|
||||
if (glfuncs !== 'None') {
|
||||
|
@ -1,8 +1,8 @@
|
||||
// import request from '@/utils/request'
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index.ts';
|
||||
import lxy_event from './lxy_page_event.js';
|
||||
import Lxy_params_mgr from './lxy_params_mgr.js';
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
|
||||
class Lxy_page_event_emit extends lxy_event {
|
||||
constructor(e) {
|
||||
|
@ -1,8 +1,8 @@
|
||||
// import { SyncPost } from '@/api/linxyun/base/index'
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index.ts';
|
||||
import Lxy_params_mgr from './lxy_params_mgr.js';
|
||||
import lxy_event from './lxy_page_event.js';
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
// 远程调用事件;
|
||||
class Lxy_page_event_remote extends lxy_event {
|
||||
_uri = null; // 远程服务URI;
|
||||
|
@ -1,6 +1,6 @@
|
||||
import PageItem from './page_item.js';
|
||||
import localforage from 'localforage';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { getPageFuncDefine } from './lxy_expression.js';
|
||||
const httpRequest = httpReqeustApi();
|
||||
|
||||
|
@ -1,11 +1,11 @@
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index.ts';
|
||||
import { formatStr2Obj } from './tools.js';
|
||||
import EnumOptions from '/@/components/Linxyun/Datas/enum_options.js';
|
||||
import { createDDE_SA } from '/@/utils/stringUtil';
|
||||
|
||||
const DDE_SA = createDDE_SA(BASE_API.ENT_CODE || 0, 0, 0);
|
||||
const headers = { 'DDE-SA': DDE_SA, 'Content-Type': 'application/json;charset=UTF-8' };
|
||||
const httpRequest = httpReqeustApi();
|
||||
const headers = { 'DDE-SA': httpRequestApi, 'Content-Type': 'application/json;charset=UTF-8' };
|
||||
const httpRequest = httpRequestApi();
|
||||
const ColOptType_Update = 0;
|
||||
const ColOptType_Delete = 1;
|
||||
// const ColOptType_Details = 2
|
||||
|
@ -31,7 +31,7 @@ import { getComponent } from '/@/utils/componentFactory';
|
||||
import { calcFieldValue } from '/@/components/Linxyun/custom/CustomCommon/lxy_expression.js';
|
||||
import { isChinese, isEnglish } from '/@/utils/extendMethods';
|
||||
import localforage from 'localforage';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
import { createDDE_SA } from '/@/utils/stringUtil';
|
||||
const props = defineProps<{
|
||||
fieldDefines: TabFieldType[];
|
||||
@ -41,7 +41,7 @@ const props = defineProps<{
|
||||
rowParams?: Record<string, any>;
|
||||
}>();
|
||||
const formItemRefs = ref<Record<string, any>>({});
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
const { OpType, inputData, rowParams, fieldDefines } = toRefs(props);
|
||||
const formData = reactive<Record<string, any>>({});
|
||||
const located = ref('Add');
|
||||
|
@ -1,14 +1,14 @@
|
||||
import { useRouter } from 'vue-router';
|
||||
import { ElMessage, ElMessageBox, ElLoading } from 'element-plus';
|
||||
import { ButtonDefineType, DialogType, EInputDataType, EventExcuteType, TabFieldType } from '../../DataStructs/commontype';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
import exportExcel from '/@/utils/exportExcel.js';
|
||||
// import { calcFieldValue } from '/@/utils/formatPrivacyData.js';
|
||||
import { calcFieldValue } from '/@/components/Linxyun/custom/CustomCommon/lxy_expression.js';
|
||||
|
||||
import type { IStateType, IPropsType } from '../type';
|
||||
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
|
||||
export default function useBtnOperate(getData: () => void, state: IStateType, props: IPropsType) {
|
||||
const router = useRouter();
|
||||
|
@ -270,7 +270,7 @@ import {
|
||||
DialogConfigType,
|
||||
EInputType,
|
||||
} from '/@/components/Linxyun/custom/DataStructs/commontype';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
// import { TabPageItem } from '../CustomCommon/tab_page_item.js';
|
||||
import { getComponent } from '/@/utils/componentFactory';
|
||||
import { compare, getArrayIndex } from '/@/utils/extendMethods';
|
||||
@ -297,7 +297,7 @@ export interface IPropsType {
|
||||
}
|
||||
const router = useRouter();
|
||||
const route = useRoute();
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
const customTableStore = useCustomTableStore();
|
||||
|
||||
const props = withDefaults(defineProps<IPropsType>(), {
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { EInputDataType, ProcessType, TabFieldType } from '/@/components/Linxyun/custom/DataStructs/commontype';
|
||||
import { calcFieldValue } from '/@/components/linxyun/custom/CustomCommon/lxy_expression.js';
|
||||
import { calcFieldValue } from '/@/components/Linxyun/custom/CustomCommon/lxy_expression.js';
|
||||
export default function useElement(located: any, FieldItem: TabFieldType, componentVal: any, props: Record<string, any>) {
|
||||
if (FieldItem?.FieldName) {
|
||||
if (FieldItem.InputDataType == EInputDataType.FrontType) {
|
||||
|
@ -1,5 +1,6 @@
|
||||
<template>
|
||||
<el-cascader v-model="componentVal" :options="options" :key="propKey" :disabled="!activate" clearable :style="{ width: width }" @change="handleChange" />
|
||||
<el-cascader v-model="componentVal" :options="options" :key="propKey" :disabled="!activate" clearable
|
||||
:style="{ width: width }" @change="handleChange" />
|
||||
</template>
|
||||
|
||||
<script lang="ts" setup>
|
||||
@ -19,7 +20,7 @@ const props = withDefaults(
|
||||
pageData?: Record<string, any>;
|
||||
inputData?: Record<string, any>;
|
||||
}>(),
|
||||
{ located: 'table', filterIdx: -1, pageData: () => ({}), inputData: () => ({}), modelValue: () =>(''), FieldItem: null }
|
||||
{ located: 'table', filterIdx: -1, pageData: () => ({}), inputData: () => ({}), modelValue: () => (''), FieldItem: null }
|
||||
);
|
||||
/**
|
||||
* 目前的级联只支持tab_tree_data中的数据,
|
||||
@ -45,7 +46,7 @@ const propKey = ref(1);
|
||||
// } else {
|
||||
// tempVal.value = ''
|
||||
// }
|
||||
|
||||
|
||||
// },
|
||||
// {
|
||||
// immediate: true,
|
||||
@ -64,42 +65,55 @@ const init = async (item: any) => {
|
||||
const remoteEvent = new Lxy_page_event_remote(item.pageType ? item.dynamicOptions : item.InputDefine.event);
|
||||
remoteEvent.setDataSrc(props.pageData, props.inputData, null);
|
||||
const result = await remoteEvent.callEvent(null);
|
||||
|
||||
|
||||
if (!result || !result.data) {
|
||||
console.error('[Error]call remote method fail, itme: ', item.FieldName);
|
||||
// return this.$set(this.loadings, item.value, false)
|
||||
console.error('[Error]call remote method fail, item: ', item.FieldName);
|
||||
return;
|
||||
}
|
||||
treeData2Optioins(result.data.Child, options);
|
||||
console.log('cascader: ', options)
|
||||
console.log('located.value: ', located.value)
|
||||
console.log("aaaaaaaa", { options: options, tempVal: tempVal.value, })
|
||||
getCascaderDataArray(options, tempVal.value);
|
||||
if (tempVal.value) {
|
||||
tempCpnVal.value = [];
|
||||
getCascaderDataArray(options, tempVal.value);
|
||||
componentVal.value = [...tempCpnVal.value];
|
||||
}
|
||||
};
|
||||
let falg = false
|
||||
watch(() => props.modelValue,
|
||||
watch(
|
||||
() => props.modelValue,
|
||||
(newVal: string) => {
|
||||
console.log('props modelValue: ', newVal)
|
||||
tempCpnVal.value = []
|
||||
if(newVal === ''){
|
||||
console.log(11111,[...componentVal.value])
|
||||
componentVal.value = []
|
||||
// componentVal.length = 0
|
||||
}else{
|
||||
if(!falg){
|
||||
console.log(2234434)
|
||||
tempVal.value = newVal
|
||||
// init(FieldItem.value)
|
||||
if (['Add'].includes(located.value)) {
|
||||
tempCpnVal.value = []
|
||||
}
|
||||
console.log('props modelValue: ', newVal);
|
||||
falg = false;
|
||||
|
||||
if (newVal === '') {
|
||||
componentVal.value = [];
|
||||
tempCpnVal.value = [];
|
||||
} else {
|
||||
tempVal.value = newVal;
|
||||
tempCpnVal.value = []; // 清空临时数组
|
||||
|
||||
// 确保options已经加载
|
||||
if (options.length > 0) {
|
||||
getCascaderDataArray(options, newVal);
|
||||
componentVal.value = [...tempCpnVal.value];
|
||||
} else {
|
||||
// 如果options还没加载,可以等待options加载完成后再次调用
|
||||
nextTick(() => {
|
||||
if (options.length > 0) {
|
||||
getCascaderDataArray(options, newVal);
|
||||
componentVal.value = [...tempCpnVal.value];
|
||||
}
|
||||
});
|
||||
}
|
||||
componentVal.value = tempCpnVal.value
|
||||
}
|
||||
},
|
||||
{
|
||||
immediate:true,
|
||||
deep:true
|
||||
})
|
||||
immediate: true,
|
||||
deep: true,
|
||||
}
|
||||
);
|
||||
const handleChange = (val: string[]) => {
|
||||
falg = true
|
||||
tempCpnVal.value = []
|
||||
@ -110,30 +124,45 @@ const handleChange = (val: string[]) => {
|
||||
} else {
|
||||
emit('update:modelValue', '');
|
||||
}
|
||||
|
||||
|
||||
};
|
||||
const setActivate = (params: any) => {
|
||||
activate.value = params.activate;
|
||||
};
|
||||
|
||||
const getCascaderDataArray = (options: any[], value: string,) => {
|
||||
if (!options || options.length === 0) {
|
||||
return;
|
||||
const getCascaderDataArray = (options: any[], value: string) => {
|
||||
if (!options || options.length === 0 || !value) {
|
||||
return false;
|
||||
}
|
||||
|
||||
console.log('getCascaderDataArray', options, value, tempCpnVal.value);
|
||||
for (let i = 0; i < options.length; i++) {
|
||||
if (value && value.indexOf(options[i].value) === 0) {
|
||||
console.log('getCascaderDataArray', options[i].value);
|
||||
tempCpnVal.value.push(options[i].value);
|
||||
if (options[i].children && options[i].children.length > 0) {
|
||||
getCascaderDataArray(options[i].children, value);
|
||||
|
||||
for (const option of options) {
|
||||
if (value === option.value) {
|
||||
// 找到完全匹配的值
|
||||
tempCpnVal.value.push(option.value);
|
||||
return true;
|
||||
}
|
||||
|
||||
if (option.children && option.children.length > 0) {
|
||||
// 先将当前级别的值加入数组
|
||||
tempCpnVal.value.push(option.value);
|
||||
|
||||
// 递归查找子级
|
||||
const found = getCascaderDataArray(option.children, value);
|
||||
|
||||
if (found) {
|
||||
// 如果在子级中找到了匹配值,返回true
|
||||
return true;
|
||||
} else {
|
||||
// 如果在当前分支没找到,需要回溯,删除刚才加入的值
|
||||
tempCpnVal.value.pop();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
};
|
||||
|
||||
if(!['Table','Detail'].includes(located.value)){
|
||||
if (!['Table', 'Detail'].includes(located.value)) {
|
||||
init(FieldItem.value);
|
||||
}
|
||||
// 绑定值发生变化时更改
|
||||
|
@ -62,7 +62,7 @@ import { ElMessage, ElMessageBox, ElLoading } from 'element-plus';
|
||||
import { DialogConfigType, DialogType, TabFieldType } from '/@/components/Linxyun/custom/DataStructs/commontype';
|
||||
import Lxy_params_mgr from '../custom/CustomCommon/lxy_params_mgr.js';
|
||||
import Lxy_expression from '../custom/CustomCommon/lxy_expression.js';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base';
|
||||
import TableForm from '../custom/TableForm/index.vue';
|
||||
import CustomTablePape from '../custom/CustomTablePape/index.vue';
|
||||
import CustomPage from '../custom/CustomizePage/index.vue';
|
||||
@ -86,7 +86,7 @@ const props = withDefaults(
|
||||
const { dialogConfig, inputData } = toRefs(props);
|
||||
const emit = defineEmits(['update:modelValue', 'getTableData', 'exportExcel', 'handleEmitEvent']);
|
||||
|
||||
const httpRequest = httpReqeustApi();
|
||||
const httpRequest = httpRequestApi();
|
||||
const showDialog = ref(false);
|
||||
|
||||
// 为后代组件提供依赖
|
||||
|
@ -5,8 +5,8 @@
|
||||
<script lang="ts" setup>
|
||||
import { TablePageType, TabFieldType, timestampType } from '/@/components/Linxyun/custom/DataStructs/commontype';
|
||||
import { ElMessage } from 'element-plus';
|
||||
import { httpReqeustApi } from '/@/api/linxyun/base/index'
|
||||
const httpRequest = httpReqeustApi()
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index'
|
||||
const httpRequest = httpRequestApi()
|
||||
import { calcFieldValue } from '/@/components/Linxyun/custom/CustomCommon/lxy_expression.js';
|
||||
import { randomLetter, randomNum, randomString, uuid } from '/@/utils/stringUtil'
|
||||
|
||||
|
@ -2,55 +2,48 @@
|
||||
<div v-if="located === 'Filter'">不支持图片过滤</div>
|
||||
<template v-else>
|
||||
<div>{{ FieldItem?.TipsText }}</div>
|
||||
<el-upload
|
||||
v-bind="attrs"
|
||||
:disabled="!activate"
|
||||
:file-list="fileList"
|
||||
:before-upload="handleBeforeUpload"
|
||||
:on-remove="handleRemove"
|
||||
:on-preview="handlePreview"
|
||||
:on-exceed="handleExceed"
|
||||
:on-change="handleChange"
|
||||
:http-request="handleUploadRequest"
|
||||
class="upload"
|
||||
>
|
||||
<el-icon><Plus /></el-icon>
|
||||
<template #file="{ file }" v-if="FieldItem?.InputType === 'video' || FieldItem?.InputDefine?.fileType === '2'">
|
||||
<el-upload v-bind="attrs" :disabled="!activate" :file-list="fileList" :before-upload="handleBeforeUpload"
|
||||
:on-remove="handleRemove" :on-preview="handlePreview" :on-exceed="handleExceed" :on-change="handleChange"
|
||||
:http-request="handleUploadRequest" class="upload">
|
||||
<el-icon>
|
||||
<Plus />
|
||||
</el-icon>
|
||||
<template #file="{ file }"
|
||||
v-if="FieldItem?.InputType === 'video' || FieldItem?.InputDefine?.fileType === '2'">
|
||||
<video :src="file.url" controls height="148" width="148"></video>
|
||||
<el-icon v-if="located !== 'Detail'" class="delete" :size="20" @click="handleRemove(file)"><DeleteFilled /></el-icon>
|
||||
<el-icon v-if="located !== 'Detail'" class="delete" :size="20" @click="handleRemove(file)">
|
||||
<DeleteFilled />
|
||||
</el-icon>
|
||||
</template>
|
||||
<template #file="{ file }" v-else-if="FieldItem?.InputDefine?.fileType === '1'">
|
||||
<div style="width: 100%; height: 100%; background-color: #409eff; display: flex; justify-content: center; align-items: center">
|
||||
<div
|
||||
style="width: 100%; height: 100%; background-color: #409eff; display: flex; justify-content: center; align-items: center">
|
||||
<span style="color: #fff; cursor: pointer" @click="previewFile(file.url)">预览</span>
|
||||
</div>
|
||||
|
||||
<el-icon v-if="located !== 'Detail'" class="delete" :size="20" @click="handleRemove(file)"><DeleteFilled /></el-icon>
|
||||
<el-icon v-if="located !== 'Detail'" class="delete" :size="20" @click="handleRemove(file)">
|
||||
<DeleteFilled />
|
||||
</el-icon>
|
||||
</template>
|
||||
</el-upload>
|
||||
<el-progress v-if="progress" :percentage="state.progressPercent" />
|
||||
</template>
|
||||
<el-dialog v-model="dialogVisible" destroy-on-close append-to-body>
|
||||
<img v-if="FieldItem?.InputType === 'el-img'" w-full :src="dialogImageUrl" alt="Preview Image" style="width: 100%" />
|
||||
<video v-else-if="FieldItem?.InputType === 'video' || FieldItem?.InputDefine?.fileType === '2'" :src="dialogImageUrl" controls></video>
|
||||
<img v-if="FieldItem?.InputType === 'el-img'" w-full :src="dialogImageUrl" alt="Preview Image"
|
||||
style="width: 100%" />
|
||||
<video v-else-if="FieldItem?.InputType === 'video' || FieldItem?.InputDefine?.fileType === '2'"
|
||||
:src="dialogImageUrl" controls></video>
|
||||
</el-dialog>
|
||||
|
||||
<el-dialog
|
||||
@close="endCropper ? '' : fileList.pop()"
|
||||
width="1000px"
|
||||
v-model="showCropper"
|
||||
append-to-body
|
||||
title="需要将图片剪切至规范大小"
|
||||
:close-on-click-modal="false"
|
||||
destroy-on-close
|
||||
>
|
||||
<cropper
|
||||
:imgurl="imgurl"
|
||||
@cropperClone="cropperClone"
|
||||
:config="FieldItem?.pageType === 'page' ? FieldItem.attrs.cropperCfg : FieldItem!.InputDefine.cropperCfg"
|
||||
></cropper>
|
||||
<el-dialog @close="endCropper ? '' : fileList.pop()" width="1000px" v-model="showCropper" append-to-body
|
||||
title="需要将图片剪切至规范大小" :close-on-click-modal="false" destroy-on-close>
|
||||
<cropper :imgurl="imgurl" @cropperClone="cropperClone"
|
||||
:config="FieldItem?.pageType === 'page' ? FieldItem.attrs.cropperCfg : FieldItem!.InputDefine.cropperCfg">
|
||||
</cropper>
|
||||
</el-dialog>
|
||||
</template>
|
||||
<script lang="ts" setup>
|
||||
import { reactive, toRefs, onMounted, ref, watch, nextTick, withDefaults } from 'vue';
|
||||
import { ElMessage, UploadFile, UploadFiles, UploadRawFile, UploadRequestOptions } from 'element-plus';
|
||||
import { DeleteFilled } from '@element-plus/icons-vue';
|
||||
import { TabFieldType, TablePageType } from '../custom/DataStructs/commontype';
|
||||
@ -71,12 +64,25 @@ const props = withDefaults(
|
||||
{ located: 'table', filterIdx: -1, pageData: () => ({}), inputData: () => ({}), modelValue: '', FieldItem: null }
|
||||
);
|
||||
const { FieldItem, located } = toRefs(props);
|
||||
|
||||
// 添加文件类型映射
|
||||
const fileTypeMap = {
|
||||
'0': '.jpg,.jpeg,.png,.gif', // 图片类型
|
||||
'1': '.doc,.docx,.pdf,.txt,.xls,.xlsx,.ppt,.pptx', // 文档类型
|
||||
'2': '.mp4,.avi,.mov' // 视频类型
|
||||
};
|
||||
|
||||
// 修改 attrs 的定义
|
||||
const attrs: Record<string, any> = {
|
||||
listType: FieldItem.value!.InputDefine?.listType || 'picture-card',
|
||||
drag: FieldItem.value!.InputDefine?.drag || false,
|
||||
limit: FieldItem.value!.InputDefine?.limit || 1,
|
||||
action: '#',
|
||||
autoUpload: false,
|
||||
autoUpload: true,
|
||||
// 根据 fileType 设置 accept
|
||||
accept: FieldItem.value?.InputDefine?.fileType ?
|
||||
fileTypeMap[FieldItem.value.InputDefine.fileType] :
|
||||
(FieldItem.value?.attrs?.fileType ? fileTypeMap[FieldItem.value.attrs.fileType] : undefined)
|
||||
};
|
||||
|
||||
const style = ref<Record<string, any>>({
|
||||
@ -114,6 +120,8 @@ const { activate, fileList, deleteList, dialogVisible, dialogImageUrl, videoArr,
|
||||
|
||||
const progress = ref(false);
|
||||
|
||||
const fileUrl = ref(null)
|
||||
|
||||
const fileConfig = ref();
|
||||
if (localStorage.getItem('setting')) {
|
||||
fileConfig.value = JSON.parse(localStorage.getItem('setting') as string);
|
||||
@ -127,6 +135,7 @@ if (attrs.listType === 'picture-card') {
|
||||
}
|
||||
|
||||
const init = async () => {
|
||||
console.log('初始化 upload 组件...');
|
||||
// 判断文件的类型来选择对应的上传类型
|
||||
if (FieldItem.value?.pageType === 'page') {
|
||||
FieldItem.value.InputDataType = 0;
|
||||
@ -136,9 +145,21 @@ const init = async () => {
|
||||
FieldItem.value.InputType = 'video';
|
||||
}
|
||||
}
|
||||
fileClient.value = await FileIns.instance(FieldItem.value!.InputDefine);
|
||||
|
||||
try {
|
||||
console.log('初始化 fileClient...');
|
||||
console.log('InputDefine:', FieldItem.value?.InputDefine);
|
||||
fileClient.value = await FileIns.instance(FieldItem.value!.InputDefine);
|
||||
console.log('fileClient 初始化完成:', fileClient.value);
|
||||
} catch (error) {
|
||||
console.error('fileClient 初始化失败:', error);
|
||||
}
|
||||
};
|
||||
init();
|
||||
|
||||
// 确保 init 执行
|
||||
onMounted(() => {
|
||||
init();
|
||||
});
|
||||
|
||||
const initFileList = () => {
|
||||
for (let i = 0; i < tempModelVal.value.length; i++) {
|
||||
@ -199,7 +220,20 @@ watch(
|
||||
);
|
||||
// 文件上传前调用
|
||||
const handleBeforeUpload = (file: UploadRawFile) => {
|
||||
console.log(file);
|
||||
console.log('beforeUpload:', file);
|
||||
|
||||
const fileType = FieldItem.value?.InputDefine?.fileType || FieldItem.value?.attrs?.fileType;
|
||||
if (fileType) {
|
||||
const allowedTypes = fileTypeMap[fileType].split(',');
|
||||
const fileExt = file.name.substring(file.name.lastIndexOf('.')).toLowerCase();
|
||||
|
||||
if (!allowedTypes.includes(fileExt)) {
|
||||
ElMessage.error(`只允许上传${allowedTypes.join('/')}格式的文件`);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
};
|
||||
// 文件列表移除文件时调用
|
||||
const handleRemove = (file: UploadFile) => {
|
||||
@ -226,6 +260,10 @@ const handleExceed = () => {
|
||||
};
|
||||
// 文件状态改变时的调用
|
||||
const handleChange = (file: UploadFile, files: UploadFiles) => {
|
||||
console.log('handleChange - file status:', file.status);
|
||||
console.log('handleChange - file:', file);
|
||||
console.log('handleChange - files:', files);
|
||||
|
||||
if (FieldItem?.value?.InputDefine?.cropperCfg?.isCrop || (FieldItem.value?.pageType === 'page' && FieldItem.value.attrs.cropperCfg.isCrop)) {
|
||||
imgurl.value = file.url || '';
|
||||
showCropper.value = true;
|
||||
@ -234,15 +272,37 @@ const handleChange = (file: UploadFile, files: UploadFiles) => {
|
||||
getDuration();
|
||||
};
|
||||
// 文件上传
|
||||
const handleUploadRequest = (option: UploadRequestOptions) => {
|
||||
console.log('handleUploadRequest option', option);
|
||||
const fileUrl = FileIns.instance().uploadFile();
|
||||
if (fileUrl === null) {
|
||||
const handleUploadRequest = async (option: UploadRequestOptions) => {
|
||||
console.log('开始上传文件...');
|
||||
console.log('upload options:', option);
|
||||
console.log('fileClient:', fileClient.value); // 检查 fileClient 是否正确初始化
|
||||
|
||||
try {
|
||||
if (!fileClient.value) {
|
||||
console.error('fileClient not initialized');
|
||||
onError();
|
||||
return;
|
||||
}
|
||||
|
||||
const fileUrl = await fileClient.value.uploadContent(
|
||||
option.file.name,
|
||||
option.file,
|
||||
state
|
||||
);
|
||||
|
||||
console.log('上传返回的 URL:', fileUrl);
|
||||
|
||||
if (fileUrl === null) {
|
||||
console.error('上传失败:返回的 URL 为 null');
|
||||
onError();
|
||||
return;
|
||||
}
|
||||
fileUrl.value = fileUrl;
|
||||
onSuccess(fileUrl, fileList.value);
|
||||
} catch (error) {
|
||||
console.error('上传失败:', error);
|
||||
onError();
|
||||
return;
|
||||
}
|
||||
fileList.value.push(fileUrl);
|
||||
onSuccess(fileUrl, fileList.value);
|
||||
};
|
||||
const onSuccess = (file: string, fileList: any[]) => {
|
||||
console.log('[Debug][File][Upload]success: ', file, fileList);
|
||||
@ -304,7 +364,7 @@ const uploadSubmit = async () => {
|
||||
}
|
||||
if (!fileList.value[i].raw) {
|
||||
// 已经上传了的文件,不再上传
|
||||
item = { name: fileList.value[i].name, url: fileList.value[i].url };
|
||||
item = { name: fileList.value[i].name, url: fileList.value[i].url };
|
||||
resList.push(item);
|
||||
continue;
|
||||
}
|
||||
@ -359,16 +419,18 @@ defineExpose({
|
||||
:deep(.el-upload-dragger) {
|
||||
padding: v-bind('style.padding');
|
||||
}
|
||||
|
||||
:deep(.el-upload.is-drag) {
|
||||
display: v-bind('style.display');
|
||||
}
|
||||
|
||||
.delete {
|
||||
position: absolute;
|
||||
right: 5px;
|
||||
top: 5px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
// .upload:deep(.el-upload .el-upload--picture-card .is-drag .el-list-move) {
|
||||
// display: v-bind('displayStyle');
|
||||
// }
|
||||
</style>
|
||||
// }</style>
|
||||
|
@ -1,8 +1,10 @@
|
||||
<template>
|
||||
<div id="map-container">
|
||||
<Transition>
|
||||
<Component :is="popCom" :data="clickData" :visible="visible" @close="close" />
|
||||
</Transition>
|
||||
<div class="map-container">
|
||||
<div id="map-container">
|
||||
<Transition>
|
||||
<Component :is="popCom" :data="clickData" :visible="visible" @close="close" />
|
||||
</Transition>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<script setup>
|
||||
@ -14,6 +16,7 @@ import BroadcastPopUp from '/@/components/broadcastPopUp/index.vue';
|
||||
import CameraPopUp from '/@/components/cameraPopUp/index.vue';
|
||||
import { useCommon } from "/@/stores/common";
|
||||
import { storeToRefs } from "pinia";
|
||||
import { debounce } from 'lodash-es'
|
||||
|
||||
const commonStore = useCommon()
|
||||
const { markerData, deviceType } = storeToRefs(commonStore)
|
||||
@ -52,17 +55,19 @@ import screenImage from '/@/assets/icon-screen.png';
|
||||
import broadcastImage from '/@/assets/icon-broadcast.png';
|
||||
const markerMap = new Map();
|
||||
const currentHighlightMarker = ref(null)
|
||||
const markers = ref([])
|
||||
|
||||
// 监听markerData是否有变化,深度监听
|
||||
watch(() => markerData.value, () => {
|
||||
console.log('markerData.records 发生变化')
|
||||
watch(() => markerData.value, debounce(() => {
|
||||
console.log('markerData 发生变化')
|
||||
initMarkerData()
|
||||
}, { deep: true })
|
||||
}, 200), { deep: true })
|
||||
// 监听center是否有变化,直接设置地图中心点
|
||||
watch(center, () => {
|
||||
console.log('map center 发生变化')
|
||||
map?.setCenter(center.value, false, 200)
|
||||
})
|
||||
watch(center, debounce(() => {
|
||||
if (map && center.value) {
|
||||
map.setZoomAndCenter( 15, center.value, false, 500)
|
||||
}
|
||||
}, 200))
|
||||
const close = () => {
|
||||
visible.value = false
|
||||
}
|
||||
@ -125,58 +130,63 @@ const clickScreen = (event) => {
|
||||
|
||||
|
||||
const initMarkerData = async () => {
|
||||
if (!map) return;
|
||||
if (!markerData.value) {
|
||||
console.error('markerData 不存在');
|
||||
return;
|
||||
}
|
||||
if (!map || !markerData.value) return;
|
||||
|
||||
// 清除旧的标记物
|
||||
markers.value.forEach(marker => {
|
||||
marker.off('click') // 移除事件监听
|
||||
map.remove(marker) // 从地图移除
|
||||
})
|
||||
markers.value = [] // 清空数组
|
||||
markerMap.clear() // 清空 Map
|
||||
|
||||
map.clearMap(); // 清空地图
|
||||
// 批量创建新的标记物
|
||||
const newMarkers = markerData.value.map(item => {
|
||||
if (!item.Lng || !item.Lat) return null;
|
||||
|
||||
// 使用 Promise.all 来确保异步操作完成
|
||||
await Promise.all(markerData.value.map(async (item) => {
|
||||
if (!item.Lng || !item.Lat) {
|
||||
console.warn('经纬度不存在', item);
|
||||
return;
|
||||
}
|
||||
|
||||
let marker = new AMap.Marker({
|
||||
const marker = new AMap.Marker({
|
||||
position: new AMap.LngLat(parseFloat(item.Lng), parseFloat(item.Lat)),
|
||||
offset: new AMap.Pixel(0, 0), // 以 icon 的 [center bottom] 为原点
|
||||
anchor: "bottom-center", // 设置锚点方位
|
||||
offset: new AMap.Pixel(0, 0),
|
||||
anchor: "bottom-center",
|
||||
icon: new AMap.Icon({
|
||||
size: new AMap.Size(50, 50),
|
||||
image: getIcon(),
|
||||
imageSize: new AMap.Size(50, 50)
|
||||
})
|
||||
});
|
||||
|
||||
var icon = new AMap.Icon({
|
||||
size: new AMap.Size(50, 50),
|
||||
image: getIcon(),
|
||||
imageSize: new AMap.Size(50, 50)
|
||||
});
|
||||
// 根据设备类型绑定对应的点击事件
|
||||
const clickHandler = {
|
||||
'lamp': clickLamp,
|
||||
'camera': clickCamera,
|
||||
'screen': clickScreen,
|
||||
'broadcast': clickBroadcast
|
||||
}[deviceType.value];
|
||||
|
||||
marker.setIcon(icon);
|
||||
|
||||
// 事件处理
|
||||
if (deviceType.value === 'lamp') {
|
||||
marker.on('click', clickLamp);
|
||||
markerMap.set(item.LampID, marker);
|
||||
} else if (deviceType.value === 'camera') {
|
||||
marker.on('click', clickCamera);
|
||||
markerMap.set(item.CameraID, marker);
|
||||
} else if (deviceType.value === 'screen') {
|
||||
marker.on('click', clickScreen);
|
||||
markerMap.set(item.DiaplayID, marker);
|
||||
} else if (deviceType.value === 'broadcast') {
|
||||
marker.on('click', clickBroadcast);
|
||||
markerMap.set(item.BreakerID, marker);
|
||||
if (clickHandler) {
|
||||
marker.on('click', clickHandler);
|
||||
}
|
||||
|
||||
marker.setExtData(item);
|
||||
|
||||
// 异步添加到地图
|
||||
await new Promise((resolve) => {
|
||||
map?.add(marker);
|
||||
resolve();
|
||||
});
|
||||
}));
|
||||
// 存储标记物ID
|
||||
const markerId = item[{
|
||||
'lamp': 'LampID',
|
||||
'camera': 'CameraID',
|
||||
'screen': 'DiaplayID',
|
||||
'broadcast': 'BreakerID'
|
||||
}[deviceType.value]];
|
||||
|
||||
if (markerId) {
|
||||
markerMap.set(markerId, marker);
|
||||
}
|
||||
|
||||
return marker;
|
||||
}).filter(Boolean); // 过滤掉无效的标记物
|
||||
|
||||
// 批量添加标记物到地图
|
||||
map.add(newMarkers);
|
||||
markers.value = newMarkers;
|
||||
}
|
||||
|
||||
defineExpose({
|
||||
@ -209,8 +219,22 @@ onMounted(() => {
|
||||
});
|
||||
|
||||
onUnmounted(() => {
|
||||
map?.destroy();
|
||||
});
|
||||
// 清理所有标记物的事件监听
|
||||
markers.value.forEach(marker => {
|
||||
marker.off('click')
|
||||
})
|
||||
|
||||
// 清空数组和Map
|
||||
markers.value = []
|
||||
markerMap.clear()
|
||||
|
||||
// 销毁地图实例
|
||||
if (map) {
|
||||
map.clearMap()
|
||||
map.destroy()
|
||||
map = null
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
@ -232,6 +256,12 @@ onUnmounted(() => {
|
||||
.v-leave-to {
|
||||
opacity: 0;
|
||||
}
|
||||
.map-container {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
width: 100%;
|
||||
background-color: #000000;
|
||||
}
|
||||
|
||||
#map-container {
|
||||
width: 100%;
|
||||
|
@ -4,7 +4,8 @@
|
||||
<el-icon class="close-btn" style="font-size: 30px; color: #006CFF;" @click="close">
|
||||
<Close />
|
||||
</el-icon>
|
||||
<video src="https://sample-videos.com/video321/mp4/720/big_buck_bunny_720p_20mb.mp4"></video>
|
||||
<!-- <video src="https://sample-videos.com/video321/mp4/720/big_buck_bunny_720p_20mb.mp4"></video> -->
|
||||
<img src="https://th.bing.com/th/id/R.ca3fe924bfbac323d488b382f6fbb83b?rik=vNQ3wuFYrb2zsQ&riu=http%3a%2f%2fzcgjjsjt.com%2f_20191212%2f1449129436.jpg&ehk=%2fnTSEckavCq%2fAq59QI3G00zDyJH1w9y0C4b8EgFEr%2fY%3d&risl=&pid=ImgRaw&r=0" alt="">
|
||||
<div class="control">
|
||||
<div class="setting-box">
|
||||
<div class="top">
|
||||
@ -95,7 +96,7 @@ const close = () => {
|
||||
transform: translate(-50%, -50%);
|
||||
|
||||
.content {
|
||||
padding: 0 50px;
|
||||
padding: 0 40px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 30px;
|
||||
@ -113,7 +114,7 @@ const close = () => {
|
||||
}
|
||||
}
|
||||
|
||||
video {
|
||||
video, img {
|
||||
width: 252px;
|
||||
height: 158px;
|
||||
}
|
||||
|
@ -40,7 +40,7 @@ const videoRef = ref(null);
|
||||
const videoUrl = ref(null);
|
||||
const flvPlayer = ref(null);
|
||||
var sdk = null;
|
||||
var apiUrl = "http://127.0.0.1:9999"
|
||||
var apiUrl = BASE_API.STREAM_URL
|
||||
|
||||
const getStream = async (camera_id, type) => {
|
||||
try {
|
||||
|
@ -12,7 +12,7 @@
|
||||
</div>
|
||||
</div>
|
||||
<div class="right">
|
||||
<button>返回</button>
|
||||
<button @click="router.push('/home')">返回</button>
|
||||
<el-icon color="#fff" size="24">
|
||||
<Close />
|
||||
</el-icon>
|
||||
@ -25,8 +25,8 @@
|
||||
<div>丈八东路监控</div>
|
||||
<div>2023.10.12 14:00:00</div>
|
||||
</div>
|
||||
<video controls autoplay
|
||||
src="https://sample-videos.com/video321/mp4/720/big_buck_bunny_720p_1mb.mp4"></video>
|
||||
<video controls autoplay loop muted
|
||||
src="/src/assets/video/test.mp4"></video>
|
||||
</div>
|
||||
</div>
|
||||
<div class="other-box">
|
||||
@ -63,7 +63,7 @@
|
||||
<div class="handle-box">
|
||||
<div class="internal-handle">
|
||||
<div class="label">
|
||||
内部处理
|
||||
内部处置
|
||||
</div>
|
||||
<div class="left-icon">
|
||||
<div class="content yellow">
|
||||
@ -156,7 +156,7 @@
|
||||
</div>
|
||||
<div class="external-linkage">
|
||||
<div class="label">
|
||||
内部处理
|
||||
外部联动
|
||||
</div>
|
||||
<div class="left-icon">
|
||||
<div class="content yellow">
|
||||
@ -242,15 +242,18 @@ onMounted(() => {
|
||||
<style scoped lang="scss">
|
||||
.visualization-container {
|
||||
position: relative;
|
||||
min-height: 1080px;
|
||||
padding: 119px 27.5px 94px 27.5px;
|
||||
height: 1080px;
|
||||
overflow-y: hidden;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
padding: 90px 27.5px;
|
||||
background: linear-gradient(90deg, #272E42 0%, #304E7E 49%, #272E42 100%);
|
||||
|
||||
.data-show {
|
||||
width: 1862px;
|
||||
height: 934px;
|
||||
border: 1px solid #0989d3;
|
||||
padding: 24px 17px 34px 17px;
|
||||
padding: 30px 25px;
|
||||
position: relative;
|
||||
|
||||
.header {
|
||||
@ -309,16 +312,22 @@ onMounted(() => {
|
||||
height: 34px;
|
||||
border: 2px solid #0670AC;
|
||||
background: transparent;
|
||||
transition: all 0.2s ease-in-out;
|
||||
}
|
||||
button:hover {
|
||||
background: #0b5f8f;
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.monitoring-box {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
gap: 35px;
|
||||
|
||||
.monitoring {
|
||||
width: 430px;
|
||||
max-width: 422px;
|
||||
height: 227px;
|
||||
position: relative;
|
||||
|
||||
@ -326,7 +335,6 @@ onMounted(() => {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
z-index: 1;
|
||||
background-image: url('/@/assets/monitoring-frame.png');
|
||||
background-size: 100% 100%;
|
||||
}
|
||||
@ -336,7 +344,10 @@ onMounted(() => {
|
||||
font-size: 15.28px;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
left: 50%;
|
||||
// 剧中
|
||||
transform: translate(-50%);
|
||||
|
||||
height: 34.4px;
|
||||
width: 100%;
|
||||
color: #fff;
|
||||
@ -357,7 +368,7 @@ onMounted(() => {
|
||||
.other-box {
|
||||
display: flex;
|
||||
gap: 60px;
|
||||
margin-top: 8px;
|
||||
margin-top: 20px;
|
||||
|
||||
.monitoring-search {
|
||||
width: 367px;
|
||||
|
@ -93,7 +93,7 @@ import { NextLoading } from '/@/utils/loading';
|
||||
import PullDown from '/@/components/pullDown/index.vue';
|
||||
import EnumOptions from '/@/components/Linxyun/Datas/enum_options.js';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base'
|
||||
import { formatDateTimeStr, formatStrByDate } from '/@/utils/formatTime';
|
||||
import { formatDateTimeStr, formatStrByDate } from '/@/utils/formatTime.ts';
|
||||
import { Close } from '@element-plus/icons-vue'
|
||||
const http = httpRequestApi()
|
||||
const SourceTypes = EnumOptions.instance().getOptions('SourceType')
|
||||
|
@ -62,7 +62,9 @@
|
||||
<span class="sub-title">在线</span>
|
||||
</div>
|
||||
<div class="content">
|
||||
<img class="screen-img" src="https://www.yumus.cn/api/?target=img&brand=bing&ua=m" alt="">
|
||||
<img class="screen-img"
|
||||
src="https://bpic.588ku.com/back_origin_min_pic/20/12/01/37f1aca822d87db9356238a1571aed1b.jpg"
|
||||
alt="">
|
||||
<div class="control">
|
||||
<div class="control-title">{{ currentScreen.content }}</div>
|
||||
<div class="play">
|
||||
@ -158,11 +160,12 @@ import { CirclePlus, Remove } from '@element-plus/icons-vue';
|
||||
import { httpRequestApi } from '/@/api/linxyun/base/index';
|
||||
import { getAllData } from '/@/api/linxyun/common';
|
||||
import { ElMessage } from 'element-plus';
|
||||
import { formatDateTimeStr } from '/@/utils/formatTime';
|
||||
import { formatDateTimeStr } from '/@/utils/formatTime.ts';
|
||||
import EnumOptions from '/@/components/Linxyun/Datas/enum_options.js';
|
||||
import { storeToRefs } from 'pinia'
|
||||
import { useCommon } from '/@/stores/common';
|
||||
import StreamVideo from '/@/components/streamVideo/index.vue'
|
||||
|
||||
const EventTypes = EnumOptions.instance().getOptions('EventType')
|
||||
const commonStore = useCommon()
|
||||
const { deviceType, markerData, lampData, screenData, broadcastData, cameraData } = storeToRefs(commonStore)
|
||||
|
Loading…
Reference in New Issue
Block a user