fzq #31

Closed
fanzhiqin wants to merge 215 commits from fzq into test
Showing only changes of commit 399589bb3b - Show all commits

View File

@ -4,13 +4,15 @@
<el-form :inline="true" :model="dataForm" @keyup.enter.native="getDataList()">
<!-- 产线 -->
<el-form-item>
<el-select v-model="dataForm.productlines" :placeholder="'产线'" clearable />
<el-select v-model="dataForm.productlines" :placeholder="'产线'" @change="handleProductLineChange" clearable>
<el-option v-for="productLine in productLineList" :key="productLine.id" :value="productLine.id" :label="productLine.name" />
</el-select>
</el-form-item>
<!-- 工序 -->
<el-form-item>
<!-- <el-select v-model="dataForm.factoryId" :placeholder="$t('eq.name') + ' / ' + $t('eq.code')" clearable></el-select> -->
<el-select v-model="dataForm.ftId" :placeholder="'工序'" clearable>
<el-option v-for="factory in factoryList" :key="factory.id" :value="factory.id" :label="factory.name" />
<el-select v-model="dataForm.wsId" :placeholder="'工序'" clearable>
<el-option v-for="ws in wsList" :key="ws.id" :value="ws.id" :label="ws.name" />
</el-select>
</el-form-item>
<!-- 日期选择 -->
@ -24,107 +26,168 @@
</el-form-item>
</el-form>
<base-table :data="dataList" :table-head-configs="tableConfigs" :max-height="calcMaxHeight(8)" @operate-event="handleOperations" @refreshDataList="getDataList" />
<el-pagination
@size-change="sizeChangeHandle"
@current-change="currentChangeHandle"
:current-page="pageIndex"
:page-sizes="[10, 20, 50, 100]"
:page-size="pageSize"
:total="totalPage"
layout="total, sizes, prev, pager, next, jumper"
></el-pagination>
<div class="time-chart" style="margin-top: 10px;">
<div
v-show="equipmentCount > 0"
id="time-chart__inner"
ref="time-chart__inner"
class="time-chart__inner"
style="width: 100%; min-height: 50vh;"
:style="{ height: autoHeight + 'px' }"
/>
<div v-show="equipmentCount === 0">请先查询数据</div>
<!-- <div v-show="equipmentCount === 0">{{ $t('module.basicData.visual.hints.searchFirst') }}</div> -->
</div>
</div>
</template>
<script>
import i18n from '@/i18n'
import * as echarts from 'echarts'
// import i18n from '@/i18n'
import BaseTable from '@/components/base-table'
import TableOperateComponent from '@/components/base-table/components/operationComponent'
import TableTextComponent from '@/components/base-table/components/detailComponent'
import { calcMaxHeight } from '@/utils'
import { timeFilter } from '@/utils/filters'
import moment from 'moment'
// import TableOperateComponent from '@/components/base-table/components/operationComponent'
// import TableTextComponent from '@/components/base-table/components/detailComponent'
// import { timeFilter } from '@/utils/filters'
const tableConfigs = [
{
type: 'index',
name: i18n.t('index')
},
{
// name: i18n.t('createTime'),
prop: 'factoryName',
name: '工厂'
},
{ prop: 'pdName', name: '产线' },
{ prop: 'wsName', name: '工段' },
{ prop: 'eqName', name: '设备' },
{
name: '有效时间(h)',
children: [
{ prop: 'workTime', name: '工作时长(h)', width: 120, filter: val => `${val} 小时` },
{ prop: 'workRate', name: '工作时长比率', width: 120, filter: val => (val * 100).toFixed(2) + '%' }
]
},
{
name: '关机时间(h)',
children: [
{ prop: 'stopTime', name: '停机时长(h)', width: 120, filter: val => `${val} 小时` },
{ prop: 'stopRate', name: '停机比率', width: 120, filter: val => (val * 100).toFixed(2) + '%' }
]
},
{
name: '中断损失',
children: [
{ prop: 'downTime', name: '故障时长(h)', width: 120, filter: val => `${val} 小时` },
{ prop: 'downRate', name: '故障比率', width: 120, filter: val => (val * 100).toFixed(2) + '%' },
{ prop: 'timeEfficiency', name: '时间开动率', width: 120, filter: val => (val * 100).toFixed(2) + '%' }
]
},
{
name: '速度损失',
children: [
{ prop: 'realYield', name: '实际加工速度', width: 120, filter: val => `${val} 小时` },
{ prop: 'designYield', name: '理论加工速度', width: 120, filter: val => `${val} 小时` },
{ prop: 'peEfficiency', name: '速度开动率', width: 120, filter: val => (val * 100).toFixed(2) + '%' }
]
},
{
name: 'OEE',
prop: 'oee',
filter: val => (val * 100).toFixed(2) + '%'
},
{
name: 'TEEP',
prop: 'teep',
filter: val => (val * 100).toFixed(2) + '%'
},
{
prop: 'operations',
name: i18n.t('handle'),
fixed: 'right',
width: 180,
subcomponent: TableOperateComponent,
// options: ['edit', 'delete']
options: ['view-trend'] //
function renderItem(params, api) {
var categoryIndex = api.value(0)
var start = api.coord([api.value(1), categoryIndex])
var end = api.coord([api.value(2), categoryIndex])
var height = 32
return {
type: 'rect',
shape: echarts.graphic.clipRectByRect(
{
x: start[0],
y: start[1] - height / 2,
width: end[0] - start[0],
height: height
},
{
x: params.coordSys.x,
y: params.coordSys.y,
width: params.coordSys.width,
height: params.coordSys.height
}
),
style: api.style()
}
]
}
class ChartOption {
constructor() {
this.color = ['#4caf50', '#ffb300', '#e53935']
this.legend = {
data: [
// i18n.t('module.basicData.visual.echartLegends.working'),
'正常',
'停机',
'故障'
],
bottom: '0%',
selectedMode: false,
textStyle: {
color: '#000'
}
}
this.tooltip = {
formatter: function(params) {
return moment(params.value[1]).format('YYYY-MM-DD HH:mm:ss') + ' - ' + moment(params.value[2]).format('YYYY-MM-DD HH:mm:ss') + ' : ' + params.name
}
}
this.title = {
// text: i18n.t('module.basicData.visual.echartTitles.eqStatus'),
text: '设备状态时序图',
left: 'center'
}
this.xAxis = {
type: 'time',
// min: +new Date().setHours(0, 0, 0, 0),
splitNumber: 24,
interval: 3600 * 1000,
axisTick: {
show: true,
alignWithLabel: true
},
axisLine: {
show: true
},
axisLabel: {
formatter: function(val) {
const time = new Date(val)
const hour = time.getHours()
const minute = time.getMinutes()
const hours = hour >= 10 ? hour + '' : '0' + hour
const minutes = minute >= 10 ? minute + '' : '0' + minute
return hours + ':' + minutes
}
}
}
this.yAxis = {
// data: Object.keys(eqData).map(item => eqData[item].name)
data: []
}
this.series = [
{ name: /** i18n.t('module.basicData.visual.echartLegends.working') */ '正常', type: 'bar', data: [] },
{ name: '停机', type: 'bar', data: [] },
{ name: '故障', type: 'bar', data: [] },
{
type: 'custom',
renderItem: renderItem,
itemStyle: {
opacity: 0.8
},
encode: {
x: [1, 2],
y: 0
},
data: []
}
]
}
setTitle(title) {
this.title.text = title
}
// date:
setXAxis(date) {
// this.xAxis.min = +new Date(date).setHours(0)
this.xAxis.min = +new Date(date).setHours(0, 0, 0, 0)
this.xAxis.max = this.xAxis.min + 3600 * 1000 * 24
}
setYAxis(data) {
this.yAxis.data = data
}
setData(data) {
this.series[3].data = data
}
}
export default {
data() {
return {
/** hfxny part */
factoryList: [],
wsList: [],
productLineList: [],
/** */
chart: null,
chartOption: new ChartOption(),
equipments: {},
state: ['正常', '停机', '故障'],
colors: ['#4caf50', '#ffb300', '#e53935'],
queryBuffer: {},
// tableConfigs,
calcMaxHeight,
tableConfigs,
timeType: 'range',
rawTime: null, // [] or datetime
currentLine: null,
rawTime: null,
dataForm: {
type: 1,
ftId: null,
wsId: null,
productlines: [],
startTime: null,
entTime: null
@ -139,10 +202,18 @@ export default {
components: {
BaseTable
},
computed: {
autoHeight: function() {
return Object.keys(this.equipments).length * 100 || 500
},
equipmentCount: function() {
return Object.keys(this.equipments).length
}
},
created() {
this.getFactoryList()
this.getProductLineList()
this.getProductLineList().then(() => {
this.getWorksetionList()
})
},
watch: {
timeType() {
@ -151,27 +222,14 @@ export default {
}
},
methods: {
//
getFactoryList() {
this.$http({
url: this.$http.adornUrl('/monitoring/factory/page'),
method: 'get'
}).then(({ data }) => {
if (data && data.code === 0) {
this.factoryList = data.data.list
/** set default */
if (this.factoryList.length) {
this.dataForm.ftId = this.factoryList[0].id
}
} else {
this.factoryList = []
this.dataForm.ftId = null
}
})
initChart() {
if (!this.chart) {
this.chart = echarts.init(this.$refs['time-chart__inner'])
}
},
// 线
getProductLineList() {
this.$http({
return this.$http({
url: this.$http.adornUrl('/monitoring/productionLine/page'),
method: 'get'
}).then(({ data }) => {
@ -179,7 +237,7 @@ export default {
this.productLineList = data.data.list
/** set default */
if (this.productLineList.length) {
this.dataForm.productlines = [this.productLineList[0].id]
this.dataForm.productlines = this.productLineList[0].id
}
} else {
this.productLineList = []
@ -187,55 +245,116 @@ export default {
})
},
//
getTimeRange() {
let startTime
let endTime
if (this.rawTime instanceof Array) {
startTime = this.rawTime[0] ? moment(this.rawTime[0]).format('YYYY-MM-DDTHH:mm:ss') : '' // axios使
endTime = this.rawTime[1] ? moment(this.rawTime[1]).format('YYYY-MM-DDTHH:mm:ss') : ''
} else {
if (this.rawTime) {
startTime = moment(this.rawTime).format('YYYY-MM-DDTHH:mm:ss')
endTime = moment(startTime)
.add(1, 'd')
.format('YYYY-MM-DDTHH:mm:ss')
//
getWorksetionList() {
// 线
this.$http({
// url: this.$http.adornUrl('/monitoring/workshopSection/list'),
url: this.$http.adornUrl('/monitoring/workshopSection/page'),
method: 'get',
params: this.$http.adornParams({
limit: 99999,
page: 1,
lineId: this.dataForm.productlines ?? ''
})
}).then(({ data: res }) => {
if (res && res.code === 0) {
this.wsList = res.data.list
/** set default */
if (this.wsList.length) {
this.dataForm.wsId = this.wsList[0].id
}
} else {
startTime = ''
endTime = ''
this.wsList.splice(0)
this.dataForm.wsId = '' // <== ...
}
}
return { startTime, endTime }
})
},
//
transformDataToEquipments(dataList) {
console.log('transformDataToEquipments() datalist: ', dataList)
const equipments = {}
dataList.map(item => {
if (equipments[item.eqId]) {
//
equipments[item.eqId].name = item.eqName
equipments[item.eqId].status.push({
startTime: +new Date(item.startTime),
endTime: +new Date(item.endTime),
status: this.state[item.status] // 0 1 2
})
} else {
equipments[item.eqId] = {
name: item.eqName,
status: [
{
startTime: +new Date(item.startTime),
endTime: +new Date(item.endTime),
status: this.state[item.status] // 0 1 2
}
]
}
}
})
// console.log('items --- ', equipments)
return equipments
},
// echartsseries
transformEquipmentsToSeries(equipments) {
const seriesData = []
Object.entries(equipments).map(([key, item], index) => {
item.status.forEach(status => {
seriesData.push({
name: status.status,
value: [index, status.startTime, status.endTime],
itemStyle: {
normal: {
color: status.status === '正常' ? '#4caf50' : status.status === '停机' ? '#ffb300' : status.status === '故障' ? '#e53935' : null
}
}
})
})
})
return seriesData
},
//
getDataList() {
const { startTime, endTime } = this.getTimeRange()
let startTime = this.rawTime
? moment(this.rawTime)
.set({ date: 1, hour: 0, minute: 0, second: 0, millisecond: 0 })
.format('YYYY-MM-DDTHH:mm:ss')
: ''
let endTime = startTime
? moment(startTime)
.add(1, 'M')
.format('YYYY-MM-DDTHH:mm:ss')
: ''
this.dataListLoading = true
this.$http({
url: this.$http.adornUrl('/monitoring/eqAnalysis/oee'),
url: this.$http.adornUrl('/monitoring/eqAnalysis/timeAndStatus'),
method: 'post',
data: {
startTime,
endTime,
ftId: this.dataForm.ftId,
productlines: this.dataForm.productlines,
limit: this.pageIndex,
page: this.pageSize,
type: 1
productlines: [this.dataForm.productlines],
wsId: this.dataForm.wsId
}
}).then(({ data: res }) => {
console.log('oee data:', res)
if (res.length) {
this.dataList = res
this.totalPage = res.length
} else {
if (res.code === 500) {
this.dataList.splice(0)
this.totalPage = 0
this.$message.error(res.msg)
} else {
this.dataList = res.data
}
})
},
handleProductLineChange(val) {
console.log('handleProductLineChange', this.dataForm.productlines)
this.getWorksetionList()
},
//
sizeChangeHandle(val) {
this.pageSize = val