add plc manage page & configuration development page
|
@ -0,0 +1,25 @@
|
|||
import request from '@/utils/request'
|
||||
|
||||
export function getList(data) {
|
||||
return request({
|
||||
url: '/protocolProduct/selectAll',
|
||||
method: 'get',
|
||||
params: data || {}
|
||||
})
|
||||
}
|
||||
|
||||
export function add(data) {
|
||||
return request({
|
||||
url: '/protocolProduct/add',
|
||||
method: 'post',
|
||||
data
|
||||
})
|
||||
}
|
||||
|
||||
export function remove(data) {
|
||||
return request({
|
||||
url: '/protocolProduct/delete',
|
||||
method: 'post',
|
||||
data
|
||||
})
|
||||
}
|
After Width: | Height: | Size: 428 B |
After Width: | Height: | Size: 378 B |
After Width: | Height: | Size: 328 B |
After Width: | Height: | Size: 322 B |
After Width: | Height: | Size: 404 B |
After Width: | Height: | Size: 1.5 KiB |
After Width: | Height: | Size: 2.3 KiB |
After Width: | Height: | Size: 1.5 KiB |
After Width: | Height: | Size: 1.3 KiB |
After Width: | Height: | Size: 774 B |
After Width: | Height: | Size: 1.9 KiB |
After Width: | Height: | Size: 1.2 KiB |
After Width: | Height: | Size: 126 B |
After Width: | Height: | Size: 1.3 KiB |
After Width: | Height: | Size: 1.5 KiB |
|
@ -0,0 +1 @@
|
|||
<?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="1663643854683" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1388" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M95.658667 461.354667a71.637333 71.637333 0 0 0 0 101.290666l365.696 365.696a71.637333 71.637333 0 0 0 101.290666 0l365.696-365.696a71.637333 71.637333 0 1 0-101.248-101.290666L512 776.448l-315.093333-315.093333a71.594667 71.594667 0 0 0-101.248 0z" p-id="1389"></path><path d="M95.658667 95.658667a71.637333 71.637333 0 0 0 0 101.248l365.696 365.738666a71.594667 71.594667 0 0 0 101.290666 0l365.696-365.738666a71.637333 71.637333 0 0 0-101.248-101.248L512 410.709333 196.906667 95.658667a71.637333 71.637333 0 0 0-101.248 0z" p-id="1390"></path></svg>
|
After Width: | Height: | Size: 886 B |
|
@ -0,0 +1 @@
|
|||
<?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="1663643850119" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1233" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><path d="M95.658667 562.645333a71.637333 71.637333 0 0 1 0-101.290666l365.696-365.696a71.637333 71.637333 0 0 1 101.290666 0l365.696 365.696a71.637333 71.637333 0 1 1-101.248 101.290666L512 247.552l-315.093333 315.093333a71.594667 71.594667 0 0 1-101.248 0z" p-id="1234"></path><path d="M95.658667 928.341333a71.637333 71.637333 0 0 1 0-101.248l365.696-365.738666a71.594667 71.594667 0 0 1 101.290666 0l365.696 365.696a71.637333 71.637333 0 0 1-101.248 101.290666L512 613.290667l-315.093333 315.050666a71.637333 71.637333 0 0 1-101.248 0z" p-id="1235"></path></svg>
|
After Width: | Height: | Size: 889 B |
|
@ -0,0 +1,17 @@
|
|||
<svg id="Layer_2" data-name="Layer 2" xmlns="http://www.w3.org/2000/svg" width="45" height="47" viewBox="0 0 45 47">
|
||||
<defs>
|
||||
<style>
|
||||
.cls-1, .cls-2 {
|
||||
fill: currentColor;
|
||||
}
|
||||
|
||||
.cls-1 {
|
||||
opacity: 0;
|
||||
}
|
||||
</style>
|
||||
</defs>
|
||||
<g id="shopping-bag" transform="translate(0 0)">
|
||||
<rect id="矩形_569" data-name="矩形 569" class="cls-1" width="45" height="47"/>
|
||||
<path id="路径_1372" data-name="路径 1372" class="cls-2" d="M34.8,9.89,29.54,4.634A5.572,5.572,0,0,0,25.6,3H13.828A5.572,5.572,0,0,0,9.89,4.634L4.634,9.89A5.572,5.572,0,0,0,3,13.828V30.859a5.572,5.572,0,0,0,5.572,5.572H30.859a5.572,5.572,0,0,0,5.572-5.572V13.828A5.572,5.572,0,0,0,34.8,9.89ZM19.715,27.144a7.429,7.429,0,0,1-7.429-7.429,1.857,1.857,0,1,1,3.715,0,3.715,3.715,0,0,0,7.429,0,1.857,1.857,0,1,1,3.715,0A7.429,7.429,0,0,1,19.715,27.144ZM9.333,10.429l3.176-3.176a1.95,1.95,0,0,1,1.319-.539H25.6a1.95,1.95,0,0,1,1.319.539L30.1,10.429Z" transform="translate(3.153 3.567)"/>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 1006 B |
|
@ -0,0 +1,12 @@
|
|||
<svg id="组_31575" data-name="组 31575" xmlns="http://www.w3.org/2000/svg" width="46.772" height="41.22" viewBox="0 0 46.772 41.22">
|
||||
<defs>
|
||||
<style>
|
||||
.cls-1 {
|
||||
fill: currentColor;
|
||||
}
|
||||
</style>
|
||||
</defs>
|
||||
<path id="路径_30830" data-name="路径 30830" class="cls-1" d="M-20667.859-1920.7l-7.064,11.746,7.064,11.354,6.9-11.354Z" transform="translate(20691.354 1920.697)"/>
|
||||
<path id="路径_30831" data-name="路径 30831" class="cls-1" d="M7.065,0,0,11.746,7.065,23.1l6.9-11.354Z" transform="translate(20.005 16.898) rotate(60)"/>
|
||||
<path id="路径_30832" data-name="路径 30832" class="cls-1" d="M7.065,0,0,11.746,7.065,23.1l6.9-11.354Z" transform="matrix(0.53, -0.848, 0.848, 0.53, 19.781, 28.979)"/>
|
||||
</svg>
|
After Width: | Height: | Size: 742 B |
|
@ -0,0 +1,14 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" width="38" height="53" viewBox="0 0 38 53">
|
||||
<defs>
|
||||
<style>
|
||||
.cls-1 {
|
||||
fill: currentColor;
|
||||
font-size: 53px;
|
||||
font-family: MyriadHebrew-BoldIt, Myriad Hebrew;
|
||||
font-weight: 700;
|
||||
font-style: italic;
|
||||
}
|
||||
</style>
|
||||
</defs>
|
||||
<text id="O" class="cls-1" transform="translate(-10 45)"><tspan x="0" y="0">O</tspan></text>
|
||||
</svg>
|
After Width: | Height: | Size: 417 B |
|
@ -0,0 +1,14 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" width="28" height="53" viewBox="0 0 28 53">
|
||||
<defs>
|
||||
<style>
|
||||
.cls-1 {
|
||||
fill: currentColor;
|
||||
font-size: 53px;
|
||||
font-family: MyriadHebrew-BoldIt, Myriad Hebrew;
|
||||
font-weight: 700;
|
||||
font-style: italic;
|
||||
}
|
||||
</style>
|
||||
</defs>
|
||||
<text id="S" class="cls-1" transform="translate(-10 45)"><tspan x="0" y="0">S</tspan></text>
|
||||
</svg>
|
After Width: | Height: | Size: 417 B |
|
@ -48,7 +48,7 @@ export default {
|
|||
}
|
||||
},
|
||||
showBreadcrumb() {
|
||||
const whiteList = ['overview', 'terminal/add', 'data/value', 'configuration/development']
|
||||
const whiteList = ['overview', 'terminal/add', 'terminal/plc', 'data/value', 'configuration/development']
|
||||
return whiteList.every((item) => this.$route.path.indexOf(item) === -1)
|
||||
}
|
||||
},
|
||||
|
|
|
@ -130,12 +130,14 @@ export const constantRoutes = [
|
|||
{
|
||||
path: 'alarm',
|
||||
name: 'Alarm',
|
||||
component: () => import('@/views/terminal/alarm/index'),
|
||||
meta: { title: '设备告警', disabled: true }
|
||||
},
|
||||
{
|
||||
path: 'plc',
|
||||
name: 'PLC',
|
||||
meta: { title: 'PLC管理', disabled: true }
|
||||
component: () => import('@/views/terminal/PLC/index'),
|
||||
meta: { title: 'PLC管理' }
|
||||
},
|
||||
{
|
||||
path: 'ota',
|
||||
|
|
|
@ -154,7 +154,7 @@ export default {
|
|||
}
|
||||
}
|
||||
</script>
|
||||
<style lang="scss" scoped>
|
||||
<style lang="scss">
|
||||
.home {
|
||||
height: calc(100vh - 50px);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,988 @@
|
|||
<template>
|
||||
<div class="app-container" style="min-height: calc(100vh - 50px)">
|
||||
<el-row
|
||||
type="flex"
|
||||
justify="space-between"
|
||||
style="align-items: baseline; margin-bottom: 30px"
|
||||
>
|
||||
<div class="header">
|
||||
<h1 class="title">大胜达PLC管理</h1>
|
||||
<span class="date">{{ date }}</span>
|
||||
</div>
|
||||
</el-row>
|
||||
<el-card style="min-height: 60vh; padding-bottom: 40px">
|
||||
<el-row>
|
||||
<el-col
|
||||
v-for="(formula, index) in formulaList"
|
||||
ref="formula"
|
||||
:key="index"
|
||||
:span="4"
|
||||
:style="index % 5 === 0 ? 'clear:both' : ''"
|
||||
:offset="index % 5 === 0 ? 0 : 1"
|
||||
:class="{ active: formula.active }"
|
||||
style="margin-top: 50px"
|
||||
>
|
||||
<div class="formula-container fadeIn" :class="formula.brand">
|
||||
<div class="dot">
|
||||
<img :src="formula.url">
|
||||
</div>
|
||||
<div class="remove_icon" @click="remove(index,formula.productName)">x</div>
|
||||
<p class="formula_name">{{ formula.productName }}</p>
|
||||
<p class="brand">{{ formula.brandName }}</p>
|
||||
<p class="protocol_name">{{ formula.protocolType }}</p>
|
||||
<el-collapse-transition>
|
||||
<div v-show="formula.active" class="addition">
|
||||
<p>{{ '工业设备ID:' + formula.deviceId }}</p>
|
||||
<p>{{ '工业设备名称:' + formula.deviceName }}</p>
|
||||
<p>{{ '扫描间隔:' + formula.readPeriod + 'ms' }}</p>
|
||||
</div>
|
||||
</el-collapse-transition>
|
||||
<div class="button-container">
|
||||
<el-button
|
||||
type="primary"
|
||||
class="button"
|
||||
@click="showDetail(index)"
|
||||
>配方查看</el-button>
|
||||
</div>
|
||||
<svg-icon
|
||||
:icon-class="formula.active ? 'arrow_up' : 'arrow_down'"
|
||||
class="detail_arrow"
|
||||
@click="formula.active = !formula.active"
|
||||
/>
|
||||
</div>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</el-card>
|
||||
<el-card class="btn_group">
|
||||
<el-col :offset="2" :span="4">
|
||||
<div class="add_btn omron_btn" @click="addFormula('omron', 'FINS')">
|
||||
<img src="@/assets/images/plus.png">
|
||||
</div>
|
||||
<span>欧姆龙FINS</span>
|
||||
</el-col>
|
||||
<el-col :offset="1" :span="4">
|
||||
<div class="add_btn mufg_btn" @click="addFormula('mufg', 'MC')">
|
||||
<img src="@/assets/images/plus.png">
|
||||
</div>
|
||||
<span>三菱MC</span>
|
||||
</el-col>
|
||||
<el-col :offset="1" :span="4">
|
||||
<div class="add_btn siemens_btn" @click="addFormula('siemens', 'S7')">
|
||||
<img src="@/assets/images/plus.png">
|
||||
</div>
|
||||
<span>西门子S7</span>
|
||||
</el-col>
|
||||
<el-col :offset="1" :span="6">
|
||||
<div
|
||||
class="add_btn general_btn"
|
||||
@click="addFormula('general', 'Modbus')"
|
||||
>
|
||||
<img src="@/assets/images/plus.png">
|
||||
</div>
|
||||
<span>通用协议Modbus</span>
|
||||
</el-col>
|
||||
</el-card>
|
||||
|
||||
<!-- PLC设置弹窗 -->
|
||||
<div v-show="visible" class="dialog_wrapper">
|
||||
<div class="dialog-container">
|
||||
<div class="dot">
|
||||
<svg-icon
|
||||
:icon-class="form.brand ? form.brand : ''"
|
||||
class="dialog_icon"
|
||||
/>
|
||||
</div>
|
||||
<div class="remove_icon" @click="close">X</div>
|
||||
<h2>{{ dialogTitle }}</h2>
|
||||
<div class="content-container">
|
||||
<el-steps
|
||||
class="test"
|
||||
:active="active"
|
||||
finish-status="success"
|
||||
align-center
|
||||
style="padding: 20px 0 40px"
|
||||
>
|
||||
<el-step title="PLC基本设置" />
|
||||
<el-step title="读取数据设置" />
|
||||
<el-step title="配方保存" />
|
||||
</el-steps>
|
||||
<div v-show="active === 0" class="content">
|
||||
<div class="step1_tab">
|
||||
<div class="line" />
|
||||
<img src="@/assets/images/pie-chart.png" width="80px">
|
||||
<p class="active">PLC基本设置</p>
|
||||
<p
|
||||
:class="{ active: step1_active === 1 }"
|
||||
@click="step1_active = 1"
|
||||
>
|
||||
通用
|
||||
</p>
|
||||
<p
|
||||
v-if="form.brand === 'mufg'"
|
||||
:class="{ active: step1_active === 2 }"
|
||||
@click="step1_active = 2"
|
||||
>
|
||||
串口
|
||||
</p>
|
||||
<p
|
||||
:class="{ active: step1_active === 3 }"
|
||||
@click="step1_active = 3"
|
||||
>
|
||||
网口
|
||||
</p>
|
||||
</div>
|
||||
<div v-if="step1_active === 1" class="step1_form">
|
||||
<el-form
|
||||
ref="form"
|
||||
:model="form"
|
||||
label-position="right"
|
||||
label-width="130px"
|
||||
>
|
||||
<el-form-item label="通信协议:">
|
||||
<span>{{ form.protocolType }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="工业设备ID:">
|
||||
<el-input v-if="add" v-model="form.deviceId" />
|
||||
<span v-else>{{ form.deviceId }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="工业设备名称:">
|
||||
<el-input v-if="add" v-model="form.deviceName" />
|
||||
<span v-else>{{ form.deviceName }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="扫描间隔:">
|
||||
<el-input v-if="add" v-model="form.readPeriod">
|
||||
<template slot="suffix">ms</template>
|
||||
</el-input>
|
||||
<span v-else>{{ form.readPeriod + 'ms' }}</span>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</div>
|
||||
<div v-if="step1_active === 2" class="step1_form">
|
||||
<el-form
|
||||
ref="form"
|
||||
:model="form"
|
||||
label-position="right"
|
||||
label-width="130px"
|
||||
>
|
||||
<el-form-item label="波特率:">
|
||||
<el-select v-if="add" v-model="form.socketConfig.baud_rate">
|
||||
<el-option
|
||||
v-for="(item, index) in baudRateList"
|
||||
:key="index"
|
||||
:value="item"
|
||||
/>
|
||||
</el-select>
|
||||
<span v-else>{{ form.baud_rate }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="校验位:">
|
||||
<el-select v-if="add" v-model="form.socketConfig.check_mode">
|
||||
<el-option
|
||||
v-for="(item, index) in checkModeList"
|
||||
:key="index"
|
||||
:value="item"
|
||||
/>
|
||||
</el-select>
|
||||
<span v-else>{{ form.check_mode }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="停止位:">
|
||||
<el-select v-if="add" v-model="form.socketConfig.stop_bits">
|
||||
<el-option
|
||||
v-for="(item, index) in stopBitsList"
|
||||
:key="index"
|
||||
:value="item"
|
||||
/>
|
||||
</el-select>
|
||||
<span v-else>{{ form.stop_bits }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="数位号:">
|
||||
<el-select v-if="add" v-model="form.socketConfig.data_bits">
|
||||
<el-option
|
||||
v-for="(item, index) in dataBitsList"
|
||||
:key="index"
|
||||
:value="item"
|
||||
/>
|
||||
</el-select>
|
||||
<span v-else>{{ form.data_bits }}</span>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</div>
|
||||
<div v-if="step1_active === 3" class="step1_form">
|
||||
<el-form
|
||||
ref="form"
|
||||
:model="form"
|
||||
label-position="right"
|
||||
label-width="130px"
|
||||
>
|
||||
<el-form-item label="远程IP:">
|
||||
<el-input v-if="add" v-model="form.socketConfig.plc_ip" />
|
||||
<span v-else>{{ form.socketConfig.plc_ip }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="端口号:">
|
||||
<el-input v-if="add" v-model="form.socketConfig.port" />
|
||||
<span v-else>{{ form.socketConfig.port }}</span>
|
||||
</el-form-item>
|
||||
<el-form-item label="本机IP:">
|
||||
<el-input v-if="add" v-model="form.socketConfig.local_ip" />
|
||||
<span v-else>{{ form.socketConfig.local_ip }}</span>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="active === 1" class="content" style="width:100%">
|
||||
<div class="step2_tab">
|
||||
<img src="@/assets/images/pie-chart.png" width="80px">
|
||||
<p class="active">读取数据设置</p>
|
||||
</div>
|
||||
<div v-if="add" class="step2_params">
|
||||
<div class="line" />
|
||||
<el-form :model="paramForm" label-position="left" label-width="80px">
|
||||
<el-form-item label="变量名">
|
||||
<el-input v-model="paramForm.value_name" />
|
||||
</el-form-item>
|
||||
<el-form-item label="数据类型">
|
||||
<el-select v-model="paramForm.value_type" placeholder="">
|
||||
<el-option v-for="(item,index) in valueTypeList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'omron'" label="访问形式">
|
||||
<el-select v-model="paramForm.data_type" placeholder="">
|
||||
<el-option v-for="(item,index) in finsDataTypeList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'siemens'" label="访问形式">
|
||||
<el-select v-model="paramForm.data_type" placeholder="">
|
||||
<el-option v-for="(item,index) in s7DataTypeList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'general'" label="命令码">
|
||||
<el-select v-model="paramForm.function_code" placeholder="">
|
||||
<el-option v-for="(item,index) in functionCodeList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'omron'" label="存储区域">
|
||||
<el-select v-model="paramForm.area_char" placeholder="">
|
||||
<el-option v-for="(item,index) in finsAreaCharList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'siemens'" label="存储区域">
|
||||
<el-select v-model="paramForm.area_char" placeholder="">
|
||||
<el-option v-for="(item,index) in s7AreaCharList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'mufg'" label="存储区域">
|
||||
<el-select v-model="paramForm.area_char" placeholder="">
|
||||
<el-option v-for="(item,index) in mcAreaCharList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item label="起始地址">
|
||||
<el-input v-model="paramForm.start_address" />
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'omron'" label="位地址">
|
||||
<el-input v-model="paramForm.bit_address" />
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'siemens'" label="DB号">
|
||||
<el-input v-model="paramForm.db_number" />
|
||||
</el-form-item>
|
||||
<el-form-item label="数据长度">
|
||||
<el-input v-model="paramForm.data_length" />
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'mufg'" label="命令类型">
|
||||
<el-select v-model="paramForm.command_type" placeholder="">
|
||||
<el-option v-for="(item,index) in commandTypeList" :key="index" :value="item" />
|
||||
</el-select>
|
||||
</el-form-item>
|
||||
<el-form-item v-if="form.brand === 'mufg'" label="监控时间">
|
||||
<el-input v-model="paramForm.monitoring_timer" />
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</div>
|
||||
<div class="step2_table">
|
||||
<el-table :data="form.readItemList" height="330px" highlight-current-row fit :header-row-style="{'color':'#FF4E00'}" @row-click="handleSelect">
|
||||
<el-table-column align="center" label="变量名" prop="value_name" />
|
||||
<el-table-column align="center" label="数据类型" prop="value_type" />
|
||||
<el-table-column v-if="form.brand === 'omron' || form.brand === 'siemens'" align="center" label="访问形式" prop="data_type" />
|
||||
<el-table-column v-if="form.brand === 'general'" align="center" label="命令码" prop="function_code" />
|
||||
<el-table-column v-if="form.brand !== 'general'" align="center" label="存储区域" prop="area_char" />
|
||||
<el-table-column align="center" label="起始地址" prop="start_address" />
|
||||
<el-table-column v-if="form.brand === 'omron'" align="center" label="位地址" prop="bit_address" />
|
||||
<el-table-column v-if="form.brand === 'siemens'" align="center" label="DB号" prop="db_number" />
|
||||
<el-table-column align="center" label="数据长度" prop="data_length" />
|
||||
<el-table-column v-if="form.brand === 'mufg'" align="center" label="命令类型" prop="command_type" />
|
||||
<el-table-column v-if="form.brand === 'mufg'" align="center" label="监控时间" prop="monitoring_timer" />
|
||||
</el-table>
|
||||
<el-row v-if="add" type="flex" justify="space-between" style="width:60%;margin: 20px auto 0;">
|
||||
<div>
|
||||
<img src="@/assets/images/plus_orange.png" width="35px" @click="addParam">
|
||||
<p>添加</p>
|
||||
</div>
|
||||
<div>
|
||||
<img src="@/assets/images/minus_orange.png" width="35px" @click="removeParam">
|
||||
<p>删除</p>
|
||||
</div>
|
||||
<div>
|
||||
<img src="@/assets/images/remove_orange.png" width="35px" @click="removeAllParam">
|
||||
<p>清空</p>
|
||||
</div>
|
||||
<!-- <div>
|
||||
<img src="@/assets/images/import_orange.png" width="35px">
|
||||
<p>导入</p>
|
||||
</div>
|
||||
<div>
|
||||
<img src="@/assets/images/download_orange.png" width="35px">
|
||||
<p>导出</p>
|
||||
</div> -->
|
||||
</el-row>
|
||||
</div>
|
||||
</div>
|
||||
<div v-show="active === 2" class="content">
|
||||
<div class="step3_tab">
|
||||
<div class="line" />
|
||||
<img src="@/assets/images/pie-chart.png" width="80px">
|
||||
<p class="active">配方保存</p>
|
||||
</div>
|
||||
<div class="step3_form">
|
||||
<el-form
|
||||
ref="form"
|
||||
:model="form"
|
||||
label-position="right"
|
||||
label-width="130px"
|
||||
>
|
||||
<el-form-item label="配方名称:">
|
||||
<el-input v-if="add" v-model="form.productName" />
|
||||
<span v-else>{{ form.productName }}</span>
|
||||
</el-form-item>
|
||||
</el-form>
|
||||
</div>
|
||||
</div>
|
||||
<el-row style="text-align: center; margin-top: 20px">
|
||||
<el-button
|
||||
v-show="active !== 0"
|
||||
class="dialog_btn"
|
||||
@click="lastStep"
|
||||
>上一步</el-button>
|
||||
<el-button class="dialog_btn primary" @click="nextStep">{{
|
||||
active === 2 ? '保存' : '下一步'
|
||||
}}</el-button>
|
||||
</el-row>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getList, add, remove } from '@/api/terminal/plc'
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
visible: false,
|
||||
date: '',
|
||||
formulaList: [],
|
||||
form: {
|
||||
deviceId: '',
|
||||
deviceName: '',
|
||||
readPeriod: '',
|
||||
socketConfig: {
|
||||
baud_rate: '',
|
||||
check_mode: '',
|
||||
stop_bits: '',
|
||||
data_bits: '',
|
||||
plc_ip: '',
|
||||
port: '',
|
||||
local_ip: ''
|
||||
},
|
||||
readItemList: []
|
||||
},
|
||||
initForm: {
|
||||
deviceId: '',
|
||||
deviceName: '',
|
||||
readPeriod: '',
|
||||
socketConfig: {
|
||||
baud_rate: '',
|
||||
check_mode: '',
|
||||
stop_bits: '',
|
||||
data_bits: '',
|
||||
plc_ip: '',
|
||||
port: '',
|
||||
local_ip: ''
|
||||
},
|
||||
readItemList: []
|
||||
},
|
||||
active: 0,
|
||||
step1_active: 1,
|
||||
dialogTitle: '配方设置',
|
||||
baudRateList: [
|
||||
2400, 4800, 9600, 19200, 38400, 57600, 115200, 230400, 460800, 921600,
|
||||
2000000, 3000000
|
||||
],
|
||||
paramForm: {
|
||||
value_name: '',
|
||||
value_type: '',
|
||||
data_type: '',
|
||||
function_code: '',
|
||||
area_char: '',
|
||||
start_address: '',
|
||||
bit_address: '',
|
||||
db_number: '',
|
||||
data_length: '',
|
||||
command_type: '',
|
||||
monitoring_timer: ''
|
||||
},
|
||||
checkModeList: ['NONE', 'ODD', 'EVEN'],
|
||||
stopBitsList: [1, 2, 3, 4],
|
||||
dataBitsList: [5, 6, 7, 8, 9],
|
||||
valueTypeList: ['BOOL', 'INT8', 'INT16', 'INT32', 'UINT8', 'UINT16', 'UINT32', 'DOUBLE', 'FLOAT'],
|
||||
finsDataTypeList: ['位', '字'],
|
||||
finsAreaCharList: ['W', 'H', 'D'],
|
||||
s7DataTypeList: ['Bit', 'Byte', 'Word', 'DWord', 'Real'],
|
||||
s7AreaCharList: ['V', 'M', 'I', 'Q', 'DB'],
|
||||
mcAreaCharList: ['M', 'D', 'B', 'W'],
|
||||
functionCodeList: ['01', '02', '03'],
|
||||
commandTypeList: ['位读', '位写', '字读', '字写'],
|
||||
add: true,
|
||||
currentIndex: -1
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.date = new Date().toLocaleDateString()
|
||||
this.getList()
|
||||
},
|
||||
methods: {
|
||||
getList() {
|
||||
getList().then((res) => {
|
||||
this.formulaList = res.data.map((item) => {
|
||||
const active = false
|
||||
let url, brandName, brand
|
||||
switch (item.protocolType) {
|
||||
case 'FINS':
|
||||
brandName = '欧姆龙'
|
||||
brand = 'omron'
|
||||
url = require('@/assets/images/O.png')
|
||||
break
|
||||
case 'S7':
|
||||
brandName = '西门子'
|
||||
brand = 'siemens'
|
||||
url = require('@/assets/images/S.png')
|
||||
break
|
||||
case 'MC':
|
||||
brandName = '三菱'
|
||||
brand = 'mufg'
|
||||
url = require('@/assets/images/mufg.png')
|
||||
break
|
||||
case 'Modbus':
|
||||
brandName = '通用协议'
|
||||
brand = 'general'
|
||||
url = require('@/assets/images/basket.png')
|
||||
break
|
||||
}
|
||||
return { ...item, url, brandName, brand, active }
|
||||
})
|
||||
})
|
||||
},
|
||||
remove(index, productName) {
|
||||
remove({ productName }).then(res => {
|
||||
if (res.code === '200000') {
|
||||
const dom = document.getElementsByClassName('formula-container')[index]
|
||||
dom.classList.add('fadeOut')
|
||||
setTimeout(() => {
|
||||
this.formulaList.splice(index, 1)
|
||||
}, 400)
|
||||
}
|
||||
})
|
||||
},
|
||||
showDetail(index) {
|
||||
this.add = false
|
||||
this.form = this.formulaList[index]
|
||||
this.visible = true
|
||||
this.dialogTitle = '配方查看'
|
||||
},
|
||||
addFormula(brand, protocolType) {
|
||||
this.add = true
|
||||
this.form = _.cloneDeep(this.initForm)
|
||||
this.form.brand = brand
|
||||
this.form.protocolType = protocolType
|
||||
this.visible = true
|
||||
this.dialogTitle = '配方设置'
|
||||
},
|
||||
lastStep() {
|
||||
this.active -= 1
|
||||
},
|
||||
nextStep() {
|
||||
if (this.active === 2) {
|
||||
add(this.form).then(res => {
|
||||
if (res.code === '200000') {
|
||||
this.getList()
|
||||
this.$message.success('配方设置成功')
|
||||
this.visible = false
|
||||
this.form = _.cloneDeep(this.initForm)
|
||||
this.active = 0
|
||||
this.step1_active = 1
|
||||
}
|
||||
})
|
||||
} else {
|
||||
this.active += 1
|
||||
}
|
||||
},
|
||||
close() {
|
||||
this.visible = false
|
||||
this.form = _.cloneDeep(this.initForm)
|
||||
this.active = 0
|
||||
this.step1_active = 1
|
||||
},
|
||||
handleSelect(row, col, event) {
|
||||
this.currentIndex = this.form.readItemList.findIndex(item => item.value_name === row.value_name)
|
||||
},
|
||||
addParam() {
|
||||
this.form.readItemList.push(this.paramForm)
|
||||
this.paramForm = {}
|
||||
},
|
||||
removeParam() {
|
||||
this.form.readItemList.splice(this.currentIndex, 1)
|
||||
},
|
||||
removeAllParam() {
|
||||
this.form.readItemList = []
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.is-success {
|
||||
color: #ff4e00 !important;
|
||||
border-color: #ff4e00 !important;
|
||||
.el-step__line {
|
||||
background-color: #ff4e00;
|
||||
}
|
||||
}
|
||||
.is-process {
|
||||
color: #ff4e00 !important;
|
||||
border-color: #ff4e00 !important;
|
||||
.el-step__icon.is-text {
|
||||
border: 2px dashed;
|
||||
}
|
||||
}
|
||||
.el-form-item__label {
|
||||
font-weight: normal;
|
||||
font-size: 16px !important;
|
||||
line-height: 3;
|
||||
font-family: PingFangSC-Regular;
|
||||
color: rgba(0, 0, 0, 0.85);
|
||||
}
|
||||
.el-form-item__content {
|
||||
font-weight: normal;
|
||||
font-size: 16px !important;
|
||||
line-height: 3;
|
||||
font-family: PingFangSC-Regular;
|
||||
color: rgba(0, 0, 0, 0.85);
|
||||
}
|
||||
.el-input {
|
||||
line-height: 4;
|
||||
}
|
||||
.el-button:hover,.el-button:focus {
|
||||
background-color: #fff;
|
||||
}
|
||||
.step2_params{
|
||||
.el-form-item__label{
|
||||
color: #ff4e00;
|
||||
}
|
||||
.el-input__inner{
|
||||
border-color: #ff4e00;
|
||||
}
|
||||
.el-select .el-input .el-select__caret{
|
||||
color: #ff4e00;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
<style lang="scss" scoped>
|
||||
.header {
|
||||
font-family: Lato;
|
||||
.title {
|
||||
color: #174a84;
|
||||
}
|
||||
.date {
|
||||
color: #a5c9ff;
|
||||
}
|
||||
}
|
||||
.formula-container {
|
||||
max-width: 220px;
|
||||
margin: auto;
|
||||
padding-bottom: 10px;
|
||||
position: relative;
|
||||
border-radius: 0 0 20px 20px;
|
||||
.dot {
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -100%);
|
||||
width: 60px;
|
||||
height: 30px;
|
||||
border-radius: 50px 50px 0 0;
|
||||
text-align: center;
|
||||
img {
|
||||
margin-top: 10px;
|
||||
}
|
||||
}
|
||||
p {
|
||||
text-align: center;
|
||||
font-size: 20px;
|
||||
font-family: Microsoft YaHei;
|
||||
font-weight: bold;
|
||||
margin: 10px;
|
||||
}
|
||||
.remove_icon {
|
||||
font-size: 18px;
|
||||
text-align: end;
|
||||
padding-right: 15px;
|
||||
padding-top: 10px;
|
||||
cursor: pointer;
|
||||
}
|
||||
.button-container {
|
||||
text-align: center;
|
||||
margin-bottom: 10px;
|
||||
.button {
|
||||
color:#fff;
|
||||
border-radius: 39px;
|
||||
border: none;
|
||||
width: 70%;
|
||||
transform: scaleY(0.9);
|
||||
}
|
||||
}
|
||||
.detail_arrow {
|
||||
cursor: pointer;
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
height: 30px;
|
||||
width: 30px;
|
||||
transform: translate(-50%, -20%);
|
||||
z-index: 2;
|
||||
}
|
||||
.addition {
|
||||
margin-top: 20px;
|
||||
p {
|
||||
font-size: 15px;
|
||||
text-align: left;
|
||||
font-weight: 500;
|
||||
margin-left: 15%;
|
||||
}
|
||||
}
|
||||
}
|
||||
.omron {
|
||||
background: #d6edff;
|
||||
color: #00ccf2;
|
||||
|
||||
.dot {
|
||||
background: #d6edff;
|
||||
}
|
||||
.button {
|
||||
background-color: #00ccf2;
|
||||
}
|
||||
}
|
||||
.active .omron {
|
||||
border: 1px solid #00ccf2;
|
||||
&::after {
|
||||
content: '';
|
||||
width: 50px;
|
||||
height: 1px;
|
||||
position: absolute;
|
||||
border-bottom: 1px solid #d6edff;
|
||||
bottom: -1px;
|
||||
left: 50%;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
.dot {
|
||||
border: 1px solid #00ccf2;
|
||||
border-bottom: none;
|
||||
}
|
||||
}
|
||||
.siemens {
|
||||
background: #dfd7fc;
|
||||
color: #724fe8;
|
||||
|
||||
.dot {
|
||||
background: #dfd7fc;
|
||||
}
|
||||
.button {
|
||||
background-color: #724fe8;
|
||||
}
|
||||
}
|
||||
.active .siemens {
|
||||
border: 1px solid #724fe8;
|
||||
&::after {
|
||||
content: '';
|
||||
width: 50px;
|
||||
height: 1px;
|
||||
position: absolute;
|
||||
border-bottom: 1px solid #dfd7fc;
|
||||
bottom: -1px;
|
||||
left: 50%;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
.dot {
|
||||
border: 1px solid #724fe8;
|
||||
border-bottom: none;
|
||||
}
|
||||
}
|
||||
.mufg {
|
||||
background: #fce1c9;
|
||||
color: #ff4e00;
|
||||
|
||||
.dot {
|
||||
background: #fce1c9;
|
||||
}
|
||||
.button {
|
||||
background-color: #ff4e00;
|
||||
}
|
||||
}
|
||||
.active .mufg {
|
||||
border: 1px solid #ff4e00;
|
||||
&::after {
|
||||
content: '';
|
||||
width: 50px;
|
||||
height: 1px;
|
||||
position: absolute;
|
||||
border-bottom: 1px solid #fce1c9;
|
||||
bottom: -1px;
|
||||
left: 50%;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
.dot {
|
||||
border: 1px solid #ff4e00;
|
||||
border-bottom: none;
|
||||
}
|
||||
}
|
||||
.general {
|
||||
background: #e0fcd7;
|
||||
color: #20be0b;
|
||||
|
||||
.dot {
|
||||
background: #e0fcd7;
|
||||
}
|
||||
.button {
|
||||
background-color: #20be0b;
|
||||
}
|
||||
}
|
||||
.active .general {
|
||||
border: 1px solid #20be0b;
|
||||
&::after {
|
||||
content: '';
|
||||
width: 50px;
|
||||
height: 1px;
|
||||
position: absolute;
|
||||
border-bottom: 1px solid #e0fcd7;
|
||||
bottom: -1px;
|
||||
left: 50%;
|
||||
transform: translateX(-50%);
|
||||
}
|
||||
.dot {
|
||||
border: 1px solid #20be0b;
|
||||
border-bottom: none;
|
||||
}
|
||||
}
|
||||
.btn_group {
|
||||
padding-bottom: 20px;
|
||||
font-size: 20px;
|
||||
font-family: Microsoft YaHei;
|
||||
font-weight: bold;
|
||||
.add_btn {
|
||||
width: 50px;
|
||||
height: 50px;
|
||||
border-radius: 50px;
|
||||
text-align: center;
|
||||
vertical-align: middle;
|
||||
display: inline-block;
|
||||
cursor: pointer;
|
||||
}
|
||||
.omron_btn {
|
||||
background-color: #00ccf2;
|
||||
img {
|
||||
margin-top: 5px;
|
||||
}
|
||||
& + span {
|
||||
color: #00ccf2;
|
||||
margin-left: 20px;
|
||||
}
|
||||
}
|
||||
.mufg_btn {
|
||||
background-color: #ff4e00;
|
||||
img {
|
||||
margin-top: 5px;
|
||||
}
|
||||
& + span {
|
||||
color: #ff4e00;
|
||||
margin-left: 20px;
|
||||
}
|
||||
}
|
||||
.siemens_btn {
|
||||
background-color: #724fe8;
|
||||
img {
|
||||
margin-top: 5px;
|
||||
}
|
||||
& + span {
|
||||
color: #724fe8;
|
||||
margin-left: 20px;
|
||||
}
|
||||
}
|
||||
.general_btn {
|
||||
background-color: #20be0b;
|
||||
img {
|
||||
margin-top: 5px;
|
||||
}
|
||||
& + span {
|
||||
color: #20be0b;
|
||||
margin-left: 20px;
|
||||
}
|
||||
}
|
||||
}
|
||||
@keyframes in {
|
||||
from {
|
||||
opacity: 0;
|
||||
}
|
||||
to {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
@keyframes out {
|
||||
from {
|
||||
opacity: 1;
|
||||
}
|
||||
to {
|
||||
opacity: 0;
|
||||
}
|
||||
}
|
||||
.fadeIn {
|
||||
animation: 1s in;
|
||||
}
|
||||
.fadeOut {
|
||||
animation: 0.5s out;
|
||||
}
|
||||
.dialog_wrapper {
|
||||
z-index: 99;
|
||||
position: fixed;
|
||||
left: 230px;
|
||||
right: 0;
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
margin: 0;
|
||||
.dialog-container {
|
||||
width: 1100px;
|
||||
transform: none;
|
||||
margin: 15vh auto;
|
||||
padding: 10px;
|
||||
position: relative;
|
||||
border-radius: 20px;
|
||||
background-color: #fce1c9;
|
||||
}
|
||||
.dot {
|
||||
width: 60px;
|
||||
height: 30px;
|
||||
border-radius: 50px 50px 0 0;
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -100%);
|
||||
text-align: center;
|
||||
background-color: #fce1c9;
|
||||
.dialog_icon {
|
||||
color: #ff4e00;
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
margin-top: 10px;
|
||||
}
|
||||
}
|
||||
.remove_icon {
|
||||
cursor: pointer;
|
||||
position: absolute;
|
||||
color: #ff4e00;
|
||||
right: 20px;
|
||||
top: 20px;
|
||||
font-size: 20px;
|
||||
}
|
||||
h2 {
|
||||
text-align: center;
|
||||
color: #ff4e00;
|
||||
padding-top: 10px;
|
||||
}
|
||||
.content-container {
|
||||
background: #fff;
|
||||
margin: 0 20px 20px;
|
||||
padding: 20px;
|
||||
.content {
|
||||
display: flex;
|
||||
width: 80%;
|
||||
margin: auto;
|
||||
align-items: center;
|
||||
}
|
||||
.line {
|
||||
position: absolute;
|
||||
right: 40px;
|
||||
top: 20%;
|
||||
height: 60%;
|
||||
width: 2px;
|
||||
background-image: linear-gradient(
|
||||
to bottom,
|
||||
#ff4e00 0%,
|
||||
#ff4e00 50%,
|
||||
transparent 50%
|
||||
);
|
||||
background-size: 100% 18px;
|
||||
background-repeat: repeat-y;
|
||||
}
|
||||
p {
|
||||
cursor: pointer;
|
||||
font-size: 18px;
|
||||
color: #fce1c9;
|
||||
font-family: Microsoft YaHei;
|
||||
}
|
||||
.active {
|
||||
font-weight: bold;
|
||||
color: #ff4e00;
|
||||
}
|
||||
.step1_tab {
|
||||
position: relative;
|
||||
text-align: center;
|
||||
flex: 1;
|
||||
}
|
||||
.step1_form {
|
||||
flex: 1;
|
||||
}
|
||||
.step2_tab{
|
||||
text-align: center;
|
||||
flex: 1;
|
||||
}
|
||||
.step2_params{
|
||||
width: 250px;
|
||||
position: relative;
|
||||
.line{
|
||||
right: 10px;
|
||||
height: 62%;
|
||||
}
|
||||
}
|
||||
.step2_table{
|
||||
flex: 3;
|
||||
p{
|
||||
color:#FF4E00;
|
||||
font-size: 16px;
|
||||
font-family: PingFangSC-Regular;
|
||||
margin: 0;
|
||||
}
|
||||
}
|
||||
.step3_tab {
|
||||
position: relative;
|
||||
text-align: center;
|
||||
flex: 1;
|
||||
}
|
||||
.step3_form {
|
||||
flex: 1;
|
||||
}
|
||||
.dialog_btn {
|
||||
width: 100px;
|
||||
border-radius: 40px;
|
||||
border-color: #ff4e00;
|
||||
color: #ff4e00;
|
||||
}
|
||||
.primary {
|
||||
background-color: #ff4e00;
|
||||
color: #fff;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
|
@ -202,6 +202,7 @@ export default {
|
|||
remove(device, index) {
|
||||
remove({ no: device.no }).then(res => {
|
||||
if (res.code === '200000') {
|
||||
console.log('activatedDevice', this.$refs.activatedDevice[index])
|
||||
this.$refs.activatedDevice[index].classList.add('fadeOut')
|
||||
setTimeout(() => {
|
||||
this.activeList.splice(index, 1)
|
||||
|
|
|
@ -0,0 +1,64 @@
|
|||
<template>
|
||||
<div class="app-container">
|
||||
<el-card>
|
||||
<div class="header">
|
||||
<div class="header_left">
|
||||
<div class="chart" />
|
||||
<div class="data">
|
||||
<p class="desc">告警数(7日)</p>
|
||||
<h1 class="num">17</h1>
|
||||
</div>
|
||||
<div class="data">
|
||||
<p class="desc">未处理告警数(7日)</p>
|
||||
<h1 class="num">8</h1>
|
||||
</div>
|
||||
</div>
|
||||
<div class="header_right">
|
||||
<div class="data">
|
||||
<p class="level">紧急</p>
|
||||
<h1 class="num emergency">6</h1>
|
||||
</div>
|
||||
<div class="data">
|
||||
<p class="level">重要</p>
|
||||
<h1 class="num important">1</h1>
|
||||
</div>
|
||||
<div class="data">
|
||||
<p class="level">次要</p>
|
||||
<h1 class="num minor">8</h1>
|
||||
</div>
|
||||
<div class="data">
|
||||
<p class="level">提示</p>
|
||||
<h1 class="num info">1</h1>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</el-card>
|
||||
<el-col v-for="(alarm,index) in alarmList" :key="index" :span="12">
|
||||
<div class="alarm-container">
|
||||
<div class="img-box">
|
||||
<img src="">
|
||||
</div>
|
||||
<div class="content">
|
||||
<p>{{ '设备序列号:test1' }}</p>
|
||||
<p>{{ '报警时间:2022/08/18' }}</p>
|
||||
<p>状态:<span>未处理</span>报警名称:<span>{{ '文本文本文本文本' }}</span></p>
|
||||
<p><span>内核序列号: 1234567890</span><span>设备类型:gateway</span></p>
|
||||
</div>
|
||||
<div class="button">
|
||||
<el-button>处理</el-button>
|
||||
</div>
|
||||
<img src="" class="status"></img>
|
||||
</div>
|
||||
</el-col>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
|
||||
</style>
|