Compare commits
11 Commits
afe2d7e7f8
...
master
Author | SHA1 | Date | |
---|---|---|---|
04a8c08904 | |||
ef313b9399 | |||
162ef0ef26 | |||
2b8797a1ac | |||
01ea333978 | |||
e37d0e4112 | |||
d022e33da9 | |||
a93b95e814 | |||
d64dc3c4d6 | |||
09db3c322f | |||
54d1b52fb8 |
246
App.vue
@ -3,7 +3,10 @@
|
||||
onLaunch: function() {
|
||||
console.warn('当前组件仅支持 uni_modules 目录结构 ,请升级 HBuilderX 到 3.1.0 版本以上!')
|
||||
console.log('App Launch')
|
||||
// plus.navigator.setFullscreen(true);//隐藏状态栏
|
||||
// #ifndef MP-WEIXIN
|
||||
uni.hideTabBar();
|
||||
// #endif
|
||||
|
||||
},
|
||||
onShow: function() {
|
||||
console.log('App Show')
|
||||
@ -15,35 +18,238 @@
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
/*每个页面公共css */
|
||||
/* 每个页面公共css */
|
||||
@import '@/uni_modules/uni-scss/index.scss';
|
||||
/* #ifndef APP-NVUE */
|
||||
@import '@/static/customicons.css';
|
||||
// 设置整个项目的背景色
|
||||
page {
|
||||
background-color: #060B26;
|
||||
color: #fff;
|
||||
}
|
||||
@import 'uni.scss';
|
||||
/* #endif */
|
||||
|
||||
/* 设置整个项目的背景色 */
|
||||
page {
|
||||
background-color: $uni-bg-color-default !important;
|
||||
color: $uni-text-color-inverse;
|
||||
}
|
||||
.example-info {
|
||||
font-size: 14px;
|
||||
color: #333;
|
||||
color: $uni-text-color;
|
||||
padding: 10px;
|
||||
}
|
||||
.pagepaddings{padding: 14px;}
|
||||
//内容框
|
||||
.contentboxsty{border-radius: 8px;background: #1C2755;}
|
||||
//没有底部边框
|
||||
.page_padding{padding: 14px;}
|
||||
.page_content{padding: 0 12px 10px;}
|
||||
/* 内容框 */
|
||||
.contentboxsty{border-radius: 8px;background: $uni-bg-color-primary;}
|
||||
/* 没有底部边框 */
|
||||
.noborbot{border-bottom:none !important}
|
||||
|
||||
.t-icon{background-repeat: no-repeat;}
|
||||
.icon22{width: 22px;height: 22px;}
|
||||
.paddrigth5{padding-right: 5px;}
|
||||
//字体大小
|
||||
.font12{font-size: $uni-font-size-sm;}
|
||||
.font13{font-size:13px;}
|
||||
.font14{font-size: $uni-font-size-base;}
|
||||
.font_bold{font-weight: bold;}
|
||||
//文字颜色
|
||||
.text_color_black{color: #000;}
|
||||
|
||||
/* 字体大小 */
|
||||
.font12{font-size: 12px;}
|
||||
.font13{font-size: 13px;}
|
||||
.font14{font-size: 14px;}
|
||||
.font15{font-size: 15px;}
|
||||
.font18{font-size: 18px;}
|
||||
.font20{font-size: 20px;}
|
||||
.font22{font-size: 22px;}
|
||||
.font24{font-size: 24px;}
|
||||
.font35{font-size: 35px;}
|
||||
.font_bold{font-weight: bold;}
|
||||
|
||||
/* 文字颜色 */
|
||||
.text_color_black{color: $uni-text-color-default;}
|
||||
.theme_color{color: $uni-text-color-primary } //主题绿
|
||||
/* 按钮颜色 */
|
||||
.but_color{background: $uni-color-primary !important;}
|
||||
|
||||
/* 布局 */
|
||||
.flex_layout{display: flex;}
|
||||
.flex1{flex: 1;}
|
||||
.comView{flex: 1;overflow: hidden;}
|
||||
/* paddind */
|
||||
.padd_rigth5{padding-right: 5px;}
|
||||
.padd_bot6{padding-bottom: 6px;}
|
||||
.padd_top12{padding-top:12px;}
|
||||
.padd_rigth12{padding-right: 12px;}
|
||||
.padd_bot12{padding-bottom: 12px;}
|
||||
.padd_left12{padding-left:12px;}
|
||||
.padd12{padding: 12px;}
|
||||
/* margin */
|
||||
.mar_top12{margin-top: 12px;}
|
||||
.mar_bot12{margin-bottom: 12px;}
|
||||
.page_list{margin-bottom: 12px;padding:0 12px;}
|
||||
|
||||
/* 有详情的列表 */
|
||||
.detail_list{
|
||||
margin-bottom: 12px;
|
||||
.list_top{
|
||||
display: flex;
|
||||
padding:12px;
|
||||
font-size: 14px;
|
||||
border-radius: 8px 8px 0px 0px;
|
||||
background: linear-gradient(90deg, rgba(61, 84, 176, 0.70) 5.83%, rgba(58, 77, 158, 0.00) 73.76%);
|
||||
.top_left{flex: 1;display: flex;align-items: center; font-weight: bold;}
|
||||
.top_right{display: flex;align-items: center;font-weight: bold;}
|
||||
.top_right .arrow{margin-left: 5px;font-weight: normal;}
|
||||
}
|
||||
.list_content{padding:12px;position: relative;}
|
||||
.list_content .card_right{position: absolute;top: 12px;right: 12px;}
|
||||
}
|
||||
|
||||
.page_list .card_right, .detail_list .card_right{
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
.status{
|
||||
background: $uni-bg-color-success-dark;
|
||||
color: $uni-text-color-success;
|
||||
padding: 3px 10px;
|
||||
border-radius: 4px;
|
||||
font-size: 12px;
|
||||
}
|
||||
.success{
|
||||
background: $uni-bg-color-success-dark;
|
||||
color: $uni-text-color-success;
|
||||
padding: 3px 10px;
|
||||
border-radius: 4px;
|
||||
font-size: 12px;
|
||||
}
|
||||
.warning{
|
||||
background: $uni-bg-color-warning-dark;
|
||||
color: $uni-text-color-warning;
|
||||
padding: 3px 10px;
|
||||
border-radius: 4px;
|
||||
font-size: 12px;
|
||||
}
|
||||
.error{
|
||||
background: $uni-bg-color-error-dark;
|
||||
color: $uni-text-color-danger;
|
||||
padding: 3px 10px;
|
||||
border-radius: 4px;
|
||||
font-size: 12px;
|
||||
}
|
||||
}
|
||||
.flexBox .detail_list:first-child{
|
||||
margin-top: 2px;
|
||||
}
|
||||
/* 检索固定 */
|
||||
.headerViewFixed{
|
||||
background: $uni-bg-color-default;
|
||||
}
|
||||
/* 页面固定按钮 */
|
||||
.bottom_but{
|
||||
width: 100%;
|
||||
position: fixed;
|
||||
bottom: 0px;
|
||||
z-index: 90;
|
||||
background-color: #060B26;
|
||||
border-top: 1px solid #2E3249;
|
||||
height: 80px;
|
||||
view{width: 50%;text-align: center;margin: 0 20px;border-radius: 19px;background: #DDD;line-height: 38px;height: 38px;margin-top: 6px;}
|
||||
}
|
||||
/* 底部固定添加按钮 */
|
||||
.page_bottom_button{
|
||||
width: 100%;position: fixed;bottom: 0px;background-color: #060B26;border-top: 1px solid #2E3249;height: 80px;
|
||||
.page_add{display:flex;justify-content:center;align-items: center;margin: 7px 20px;border-radius: 17.5px;background: #1C2755;height: 38px;}
|
||||
.page_add .icon{margin-right: 4px;}
|
||||
}
|
||||
.bot_padding{padding-bottom: 100px;}
|
||||
|
||||
.placeholderStyle{
|
||||
color: $uni-text-color-placeholder;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
/* 圆形进度条 */
|
||||
.progressBg{
|
||||
position: absolute;
|
||||
left: 2px;
|
||||
top: 2px;
|
||||
z-index: 20;
|
||||
background: $uni-bg-color-primary;
|
||||
width: 98px;
|
||||
height: 98px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
box-sizing: border-box;
|
||||
border-radius: 50%;
|
||||
}
|
||||
.progressBox{
|
||||
background: $uni-bg-color-default-dark;
|
||||
width: 90px;
|
||||
height: 90px;
|
||||
border-radius: 50%;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
.circle-progress {
|
||||
width: 102px;
|
||||
height: 102px;
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
border-radius: 50%;
|
||||
background: $uni-bg-color-primary;
|
||||
}
|
||||
|
||||
.circle-progress__bar {
|
||||
position: absolute;
|
||||
z-index: 10;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%, -50%);
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
border-radius: 50%;
|
||||
background-image: conic-gradient($uni-color-primary 0%, $uni-color-primary var(--progress), transparent 0);
|
||||
}
|
||||
|
||||
/* 选择日期时间颜色的配置 */
|
||||
.input_date .uni-date-x .uni-date__x-input{
|
||||
color: $uni-text-color-tip;
|
||||
}
|
||||
.haveTime .uni-date-x .uni-date__x-input{
|
||||
color: $uni-text-color-inverse;
|
||||
}
|
||||
|
||||
/* 修改 日期时间选择组件 */
|
||||
.input_date ::v-deep .uni-date-changed .uni-datetime-picker--btn{
|
||||
background: $uni-color-primary !important;
|
||||
}
|
||||
.input_date ::v-deep .uni-calendar-item--checked{
|
||||
background: $uni-color-primary !important;
|
||||
}
|
||||
|
||||
/* 自定义 复选框-背景颜色 */
|
||||
checkbox.checkbox-custom[checked] .wx-checkbox-input , checkbox.checkbox-custom.checked .uni-checkbox-input{
|
||||
background-color: $uni-color-primary;
|
||||
border-color: $uni-color-primary;
|
||||
color: $uni-text-color-inverse;
|
||||
}
|
||||
::v-deep .checkbox_indeterminate::before{
|
||||
content: '';
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: calc(50% - 2px);
|
||||
z-index: 80;
|
||||
transform: translate(-50%,-50%);
|
||||
width: 12px;
|
||||
height: 2px;
|
||||
border-radius: 4px;
|
||||
background: $uni-bg-color-whith;
|
||||
}
|
||||
::v-deep .checkbox_indeterminate::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
z-index: 10;
|
||||
width: calc(100% - 5px);
|
||||
height: 100%;
|
||||
border-radius: 3px;
|
||||
background-color: $uni-color-primary;
|
||||
}
|
||||
</style>
|
||||
|
BIN
__MACOSX/components/._.DS_Store
Normal file
BIN
__MACOSX/components/chocolate-progress-bar/._.DS_Store
Normal file
BIN
components/.DS_Store
vendored
Normal file
400
components/calendar/index.vue
Normal file
@ -0,0 +1,400 @@
|
||||
<template>
|
||||
<view class="calendarBox">
|
||||
<view class="content-top">
|
||||
<view class="content-left" @click="prveClick">
|
||||
<text class="iconfont icon-gengduo more_icon"></text>
|
||||
</view>
|
||||
<view class="content-scroll">
|
||||
<view class="center-cut-menu">
|
||||
<scroll-view scroll-x="true" show-scrollbar="false" scroll-with-animation="true" :scroll-left="scrollLeft" class="scroll-view horizontalScrollView" :class="{'monthScroll':params.date!=='day'}" >
|
||||
<view class="scroll-item" :style="'width:'+itemWidth+'px'" v-for="(item, index) in titleList" :key="index" @click="changeMenu(index)">
|
||||
<view class="viewItem" :class="{'active':curIndex == index,'monthViewItem':params.date !=='day','todoayView':item.todoay}">
|
||||
<text class="item-text">{{item.name}}</text>
|
||||
<text class="item-date" v-if="params.date == 'day'">{{item.text}}</text>
|
||||
<text class="todoay" v-if="item.todoay">今</text>
|
||||
</view>
|
||||
</view>
|
||||
</scroll-view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content-right" @click="nextClick">
|
||||
<text class="iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<swiper v-if="params.date!='day'" class="swiper-box-list" circular="true" easing-function="linear" :current="curIndex" @change="swiperChange" :style="'height:'+swiperHeight+'px'">
|
||||
<swiper-item class="swiper-topic-list" v-for="(item,index) in titleList" :key="index">
|
||||
<view :style="'height:'+swiperHeight+'px'" v-if="curIndex == index">
|
||||
<view class="swiper-item padd_top12 font14">
|
||||
<view class="device_row" v-for="(em,inde) in item.data" :key="inde">
|
||||
<view class="rowView" :class="{'active':inde==0,'todoayView':em.todoay}">
|
||||
<text class="name font_bold">{{em.text}}</text>
|
||||
<text class="text">{{em.name}}</text>
|
||||
<text v-if="em.todoay" class="todoay">今</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</swiper-item>
|
||||
</swiper>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default{
|
||||
data(){
|
||||
return{
|
||||
params:this.params,
|
||||
|
||||
curIndex:0,
|
||||
scrollLeft:0,
|
||||
swiperHeight:0,
|
||||
itemWidth:53,
|
||||
itemColumn:5,
|
||||
|
||||
titleList:[
|
||||
{name:'日',date:11,text:''},
|
||||
{name:'一',date:12,text:''},
|
||||
{name:'二',date:13,text:''},
|
||||
{name:'三',date:14,text:''},
|
||||
{name:'四',date:15,text:''},
|
||||
{name:'五',date:16,text:''},
|
||||
{name:'六',date:17,text:''},
|
||||
],
|
||||
}
|
||||
},
|
||||
inject:['params','changeDateText'],
|
||||
watch:{
|
||||
'params.date':{
|
||||
handler(val){
|
||||
this.params.date = val;
|
||||
this.itemColumn = val=='day'?5:4
|
||||
this.setTitle();
|
||||
this.getScrollW();
|
||||
this.getSwiperH();
|
||||
},
|
||||
immediate:false,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.setTitle();
|
||||
},
|
||||
methods:{
|
||||
getScrollW() {
|
||||
let itemWidth = 0;
|
||||
let query = uni.createSelectorQuery().in(this);
|
||||
query.select('.scroll-view').boundingClientRect(data => {
|
||||
this.itemWidth = (data.width/this.itemColumn).toFixed(0);
|
||||
itemWidth = (data.width/this.itemColumn).toFixed(0);
|
||||
this.getItemWidth(itemWidth);
|
||||
}).exec();
|
||||
},
|
||||
getSwiperH(){
|
||||
if(this.params.date!='day'){
|
||||
setTimeout(()=>{
|
||||
let query = uni.createSelectorQuery().in(this);
|
||||
query.select('.swiper-item').boundingClientRect(data => {
|
||||
if(data){
|
||||
this.swiperHeight = data.height;
|
||||
}else{
|
||||
this.getSwiperH();
|
||||
}
|
||||
}).exec();
|
||||
},100)
|
||||
}
|
||||
},
|
||||
getItemWidth(num){
|
||||
let query = uni.createSelectorQuery().in(this);
|
||||
query.selectAll('.scroll-item').boundingClientRect(data => {
|
||||
let dataLen = data.length;
|
||||
for (let i = 0; i < dataLen; i++) {
|
||||
this.titleList[i].width = Number(num);
|
||||
this.titleList[i].left = Number(num) + Number(data[i].left);
|
||||
}
|
||||
}).exec();
|
||||
},
|
||||
|
||||
// 获取数据
|
||||
setTitle(){
|
||||
if(this.params.date == 'day'){
|
||||
let list = this.$wf.getDatesOfWeek();
|
||||
let todoay = this.$wf.getToday();
|
||||
list.forEach(item=>{
|
||||
if(item.date == todoay){
|
||||
item.todoay = true;
|
||||
}
|
||||
item.text = item.date.split('-')[2];
|
||||
})
|
||||
if(this.curIndex >= list.length){
|
||||
this.curIndex = list.length - 1;
|
||||
}
|
||||
this.titleList = list;
|
||||
}
|
||||
if(this.params.date == 'week'){
|
||||
let list = [];
|
||||
let arr = this.$wf.getWeeksOfMonth();
|
||||
|
||||
arr.forEach((item,index)=>{
|
||||
let date = item.find(em=> em!==null && em!==undefined);
|
||||
let todoay = this.$wf.getToday();
|
||||
item.forEach(em=>{
|
||||
if(em){
|
||||
if(em.date == todoay){
|
||||
em.todoay = true;
|
||||
}
|
||||
em.text = em.date.split('-')[2];
|
||||
em.name = '星期'+em.name;
|
||||
}
|
||||
})
|
||||
list.push({
|
||||
name:'第'+this.$wf.numberToChineseLower(Number(index+1))+'周',
|
||||
date:date.date,
|
||||
data:item.filter(em=> em!==null),
|
||||
})
|
||||
})
|
||||
if(this.curIndex >= list.length){
|
||||
this.curIndex = list.length - 1;
|
||||
}
|
||||
this.titleList = list;
|
||||
}
|
||||
if(this.params.date == 'month'){
|
||||
let list = [];
|
||||
let arr = this.$wf.getCurrentYearData();
|
||||
arr.forEach((item,index)=>{
|
||||
let weeks = [];
|
||||
item.weeks.forEach((em,ind)=>{
|
||||
let dateList = em.filter(em=> em!==null);
|
||||
weeks.push({
|
||||
data:dateList,
|
||||
text:dateList[0].date.split('-')[2],
|
||||
name:'第'+Number(ind+1)+'周',
|
||||
date:dateList[0].date,
|
||||
})
|
||||
})
|
||||
list.push({
|
||||
name:this.$wf.numberToChineseLower(Number(item.month))+'月',
|
||||
date:weeks[0].date,
|
||||
data:weeks,
|
||||
})
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
|
||||
this.getScrollW();
|
||||
this.changeDate();
|
||||
},
|
||||
|
||||
// 选择标题
|
||||
changeMenu(index) {
|
||||
this.curIndex = index;
|
||||
this.scrollLeft = 0;
|
||||
for (let i = 0; i < index - 1; i++) {
|
||||
this.scrollLeft += this.titleList[i].width;
|
||||
};
|
||||
this.changeDate(this.titleList[index].date);
|
||||
|
||||
if(this.params.date!='day'){
|
||||
this.getSwiperH();
|
||||
}
|
||||
},
|
||||
swiperChange(e) {
|
||||
let index = e.detail.current;
|
||||
this.changeMenu(index);
|
||||
},
|
||||
prveClick(){
|
||||
if(this.params.date == 'day'){
|
||||
let date = String(this.titleList[0].date);
|
||||
let list = this.$wf.getPreviousWeekDatesWithDays(date);
|
||||
list.forEach(item=>{
|
||||
item.text = item.date.split('-')[2];
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
if(this.params.date == 'week'){
|
||||
// 获取本月的选中周日期
|
||||
let date = this.titleList[this.curIndex];
|
||||
let countNum = this.$wf.getPreviousMonthWeekCount(String(date.date));
|
||||
if(this.curIndex >= countNum){
|
||||
this.curIndex = countNum-1;
|
||||
}
|
||||
let list = [];
|
||||
let arr = this.$wf.getPreviousMonthGroupedByWeek(String(date.date));
|
||||
arr.forEach((item,index)=>{
|
||||
let date = item.find(em=> em!==null && em!==undefined);
|
||||
item.forEach(em=>{
|
||||
if(em){
|
||||
em.text = em.date.split('-')[2];
|
||||
em.name = '星期'+em.name;
|
||||
}
|
||||
})
|
||||
list.push({
|
||||
name:'第'+this.$wf.numberToChineseLower(Number(index+1))+'周',
|
||||
date:date.date,
|
||||
data:item.filter(em=> em!==null),
|
||||
})
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
if(this.params.date == 'month'){
|
||||
// 获取本年的选中周日期
|
||||
let date = this.titleList[this.curIndex];
|
||||
let list = [];
|
||||
let arr = this.$wf.getPreviousYearData(String(date.date));
|
||||
arr.forEach((item,index)=>{
|
||||
let weeks = [];
|
||||
item.weeks.forEach((em,ind)=>{
|
||||
let dateList = em.filter(em=> em!==null);
|
||||
weeks.push({
|
||||
data:dateList,
|
||||
text:dateList[0].date.split('-')[2],
|
||||
name:'第'+Number(ind+1)+'周',
|
||||
date:dateList[0].date,
|
||||
})
|
||||
})
|
||||
list.push({
|
||||
name:this.$wf.numberToChineseLower(Number(item.month))+'月',
|
||||
date:weeks[0].date,
|
||||
data:weeks,
|
||||
})
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
|
||||
this.getScrollW();
|
||||
this.changeDate();
|
||||
|
||||
if(this.params.date!='day'){
|
||||
this.getSwiperH();
|
||||
}
|
||||
},
|
||||
nextClick(){
|
||||
if(this.params.date == 'day'){
|
||||
let date = String(this.titleList[this.titleList.length -1].date);
|
||||
let list = this.$wf.getNextWeekDatesWithDays(date);
|
||||
list.forEach(item=>{
|
||||
item.text = item.date.split('-')[2];
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
// 获取下一个月所有周
|
||||
if(this.params.date == 'week'){
|
||||
// 获取本月的选中周日期
|
||||
let date = this.titleList[this.curIndex];
|
||||
let countNum = this.$wf.getNextMonthWeekCount(String(date.date));
|
||||
if(this.curIndex >= countNum){
|
||||
this.curIndex = countNum-1;
|
||||
}
|
||||
let list = [];
|
||||
let arr = this.$wf.getNextMonthGroupedByWeek(String(date.date));
|
||||
arr.forEach((item,index)=>{
|
||||
let date = item.find(em=> em!==null && em!==undefined);
|
||||
item.forEach(em=>{
|
||||
if(em){
|
||||
em.text = em.date.split('-')[2];
|
||||
em.name = '星期'+em.name;
|
||||
}
|
||||
})
|
||||
list.push({
|
||||
name:'第'+this.$wf.numberToChineseLower(Number(index+1))+'周',
|
||||
date:date.date,
|
||||
data:item.filter(em=> em!==null),
|
||||
})
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
// 获取下一年的日期
|
||||
if(this.params.date == 'month'){
|
||||
let date = this.titleList[this.curIndex];
|
||||
let list = [];
|
||||
let arr = this.$wf.getNextYearData(String(date.date));
|
||||
arr.forEach((item,index)=>{
|
||||
let weeks = [];
|
||||
item.weeks.forEach((em,ind)=>{
|
||||
let dateList = em.filter(em=> em!==null);
|
||||
weeks.push({
|
||||
data:dateList,
|
||||
text:dateList[0].date.split('-')[2],
|
||||
name:'第'+Number(ind+1)+'周',
|
||||
date:dateList[0].date,
|
||||
})
|
||||
})
|
||||
list.push({
|
||||
name:this.$wf.numberToChineseLower(Number(item.month))+'月',
|
||||
date:weeks[0].date,
|
||||
data:weeks,
|
||||
})
|
||||
})
|
||||
this.titleList = list;
|
||||
}
|
||||
|
||||
this.getScrollW();
|
||||
this.changeDate();
|
||||
|
||||
if(this.params.date!='day'){
|
||||
this.getSwiperH();
|
||||
}
|
||||
},
|
||||
|
||||
// 修改时间的阶段
|
||||
changeDate(item){
|
||||
let text = null;
|
||||
if(this.titleList[this.curIndex] == undefined){
|
||||
text = this.titleList[this.titleList.length -1].date;
|
||||
this.current = this.titleList.length -1;
|
||||
}else{
|
||||
text = this.titleList[this.curIndex].date;
|
||||
}
|
||||
if(item){
|
||||
text = item
|
||||
}
|
||||
let month = text.split('-')[0] + '-' + text.split('-')[1]
|
||||
this.changeDateText(month);
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.content-top{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.content-left{flex-basis: 30px;text-align: center;
|
||||
.more_icon{display: inline-block;transform: scaleX(-1);}
|
||||
}
|
||||
.content-scroll{flex: 1;overflow: hidden;}
|
||||
.center-cut-menu {width: 100%;height: 50px;display: flex;align-items: center;
|
||||
.scroll-view {height: 50px;white-space: nowrap;
|
||||
.scroll-item {height: 100%;padding: 0 5px;display: inline-block;text-align: center;box-sizing: border-box;
|
||||
.viewItem{
|
||||
position: relative;
|
||||
font-size: 14px;height: 100%;display: flex;flex-direction: column;align-items: center;justify-content: center;
|
||||
border: 1px solid $uni-color-primary;box-sizing: border-box;border-radius: 8px;
|
||||
}
|
||||
.monthViewItem{
|
||||
border: none;
|
||||
border-radius: 40px;
|
||||
}
|
||||
.active {
|
||||
background: $uni-color-primary;
|
||||
}
|
||||
.todoay{
|
||||
display: flex;align-items: center;justify-content: center;background: $uni-bg-color-success;
|
||||
position: absolute;top: 2px;right: 2px;z-index: 20;
|
||||
border-radius: 2px;width: 12px;height: 12px;font-size: 8px;
|
||||
}
|
||||
}
|
||||
}
|
||||
.monthScroll{height: 27px;}
|
||||
}
|
||||
.content-right{flex-basis: 30px;text-align: center;}
|
||||
}
|
||||
.swiper-box-list{height: 240px;padding:0 12px;
|
||||
.swiper-item{display: flex;flex-direction: row;flex-wrap: wrap;}
|
||||
.device_row{display: flex;flex-direction: column;width: 33%;justify-content: center;align-items: center;margin-bottom: 12px;height: 70px;box-sizing: border-box;padding: 0 8px;position: relative;
|
||||
.name{margin-bottom: 6px;}
|
||||
.rowView{display: flex;flex-direction: column;justify-content: center;align-items: center;height: 100%;width: 100%;padding: 12px 0;box-sizing: border-box;position: relative;}
|
||||
.todoayView{padding: 0 8px; background: $uni-bg-color-default-dark; box-sizing: border-box;border-radius: 8px;}
|
||||
.active{background: $uni-bg-color-info;border-radius: 8px;}
|
||||
.todoay{position: absolute;top: -5px;right: -5px;z-index: 20;display: flex;align-items: center;justify-content: center;background: $uni-bg-color-success;width: 16px;height: 16px;border-radius: 3px;font-size: 10px;}
|
||||
}
|
||||
}
|
||||
</style>
|
BIN
components/chocolate-progress-bar/.DS_Store
vendored
Normal file
123
components/chocolate-progress-bar/chocolate-progress-bar.vue
Normal file
@ -0,0 +1,123 @@
|
||||
<template>
|
||||
<view class="progress_box">
|
||||
<canvas class="progress_bg" canvas-id="cpbg"></canvas>
|
||||
<canvas class="progress_bar" canvas-id="cpbar"></canvas>
|
||||
<view class="progress_txt">
|
||||
<view class="progress_info">{{ progress_txt }}%</view>
|
||||
<text class="progress_title">{{title}}</text>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
props:{
|
||||
progress_txt:{
|
||||
type: Number,
|
||||
default:0
|
||||
},
|
||||
title:{
|
||||
type:String,
|
||||
default: ''
|
||||
},
|
||||
width:{
|
||||
type:Number,
|
||||
defauit:''
|
||||
},
|
||||
height:{
|
||||
type:Number,
|
||||
defauit:''
|
||||
}
|
||||
},
|
||||
mounted: function() {
|
||||
this.drawProgressbg();
|
||||
this.drawCircle(this.progress_txt); //参数为1-100
|
||||
this.style(this.width,this.height);
|
||||
},
|
||||
methods: {
|
||||
style:function(width,height){
|
||||
// console.log(width,height)
|
||||
// document.getElementById("cpbg").style.width = width+"px";
|
||||
// cpbgA.style.width = width+"px";
|
||||
// cpbgA.style.height = height+"px";
|
||||
// var cpbarA = document.getElementById("cpbar");
|
||||
// cpbarA.style.width = width+"px";
|
||||
// cpbarA.style.height = height+"px";
|
||||
},
|
||||
drawProgressbg: function() {
|
||||
// 自定义组件实例 this ,表示在这个自定义组件下查找拥有 canvas-id 的 <canvas/>
|
||||
var ctx = uni.createCanvasContext('cpbg', this);
|
||||
ctx.setLineWidth(6); // 设置圆环的宽度
|
||||
ctx.setStrokeStyle('#E9E9E9'); // 设置圆环的颜色
|
||||
ctx.setLineCap('round'); // 设置圆环端点的形状
|
||||
ctx.beginPath(); //开始一个新的路径
|
||||
ctx.arc(110, 110, 70, 0.75 * Math.PI, 0.25 * Math.PI, false);
|
||||
//设置一个原点(110,110),半径为100的圆的路径到当前路径
|
||||
ctx.stroke(); //对当前路径进行描边
|
||||
ctx.draw();
|
||||
},
|
||||
drawCircle: function(step) {
|
||||
var ctx = uni.createCanvasContext('cpbar', this);
|
||||
// 进度条的渐变(中心x坐标-半径-边宽,中心Y坐标,中心x坐标+半径+边宽,中心Y坐标)
|
||||
var gradient = ctx.createLinearGradient(28, 55, 192, 55);
|
||||
gradient.addColorStop('0', '#009688');
|
||||
// gradient.addColorStop('1.0', '#FF3B1D');
|
||||
ctx.setLineWidth(6);
|
||||
ctx.setStrokeStyle(gradient);
|
||||
ctx.setLineCap('round');
|
||||
ctx.beginPath();
|
||||
// 参数step 为绘制的百分比
|
||||
step = 0.015 * step + 0.75;
|
||||
if (step >= 2) {
|
||||
step = step % 2;
|
||||
}
|
||||
ctx.arc(110, 110, 70, 0.75 * Math.PI, step * Math.PI, false);
|
||||
ctx.stroke();
|
||||
ctx.draw();
|
||||
},
|
||||
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
.progress_box {
|
||||
position: relative;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
text-align: center;
|
||||
}
|
||||
.progress_bg {
|
||||
position: absolute;
|
||||
width: 220px;
|
||||
height: 220px;
|
||||
}
|
||||
.progress_bar {
|
||||
width: 220px;
|
||||
height: 220px;
|
||||
}
|
||||
.progress_txt {
|
||||
position: absolute;
|
||||
font-size: 28upx;
|
||||
color: #999999;
|
||||
}
|
||||
.progress_info {
|
||||
font-size: 36upx;
|
||||
padding-left: 16upx;
|
||||
letter-spacing: 2upx;
|
||||
font-size: 52upx;
|
||||
color: #fff;
|
||||
}
|
||||
.progress_titleP{
|
||||
color: #BFBFBF;
|
||||
}
|
||||
.progress_dot {
|
||||
width: 16upx;
|
||||
height: 16upx;
|
||||
border-radius: 50%;
|
||||
background-color: #fb9126;
|
||||
}
|
||||
</style>
|
@ -4,7 +4,7 @@
|
||||
<!-- 针对中间的导航栏 通过true来判断控制类名和样式 -->
|
||||
<view class="tabbar-item" v-for="(item, index) in tabbarList" :class="[item.centerItem ? 'center-item' : '']" @click="changeItem(item)" :key="index">
|
||||
<view class="item-top">
|
||||
<image :src="currentItem == item.id ? item.selectIcon : item.icon"></image>
|
||||
<image class="img" :src="currentItem == item.id ? item.selectIcon:item.icon"></image>
|
||||
</view>
|
||||
<!-- 通过三元判断控制类名 达到控制选中和未选中的样式 -->
|
||||
<view class="item-bottom" :class="[currentItem == item.id ? 'item-active' : '']">
|
||||
@ -31,25 +31,25 @@ export default {
|
||||
{
|
||||
id: 0,
|
||||
path: '/pages/index/index',
|
||||
// icon: '/static/template.png',
|
||||
// selectIcon: '/static/templateHL.png',
|
||||
icon: '/static/indexA.png',
|
||||
selectIcon: '/static/indexB.png',
|
||||
text: '首页',
|
||||
centerItem: false
|
||||
},
|
||||
{
|
||||
id: 1,
|
||||
path: '/pages/midell/index',
|
||||
// icon: '/static/api.png',
|
||||
// selectIcon: '/static/apiHL.png',
|
||||
text: '中间',
|
||||
path: '',
|
||||
icon: '/static/sweep.png',
|
||||
selectIcon: '',
|
||||
text: '扫一扫',
|
||||
// 通过类名class控制样式大小
|
||||
centerItem: true
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
path: '/pages/mine/index',
|
||||
// icon: '/static/component.png',
|
||||
// selectIcon: '/static/componentHL.png',
|
||||
path: '/pages/person/person',
|
||||
icon: '/static/personB.png',
|
||||
selectIcon: '/static/personA.png',
|
||||
text: '我的',
|
||||
centerItem: false
|
||||
}
|
||||
@ -58,37 +58,70 @@ export default {
|
||||
},
|
||||
mounted () {
|
||||
this.currentItem = this.currentPage
|
||||
// 隐藏原来的tabBar导航栏
|
||||
uni.hideTabBar()
|
||||
},
|
||||
methods: {
|
||||
changeItem (item) {
|
||||
let _this = this
|
||||
//_this.currentItem = item.id;
|
||||
if(item.centerItem){
|
||||
this.scanQRCode();
|
||||
return
|
||||
}
|
||||
uni.switchTab({
|
||||
url: item.path
|
||||
})
|
||||
},
|
||||
scanQRCode(){
|
||||
uni.scanCode({
|
||||
success: (res) => {
|
||||
console.log('扫码结果:' + res.result);
|
||||
uni.showModal({
|
||||
title: '扫码结果',
|
||||
content: res.result,
|
||||
showCancel: false
|
||||
});
|
||||
},
|
||||
fail: (err) => {
|
||||
console.error('扫码失败:' + err);
|
||||
uni.showToast({
|
||||
title: '扫码失败',
|
||||
icon: 'none'
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
<style lang="less" scope>
|
||||
<style lang="scss" scope>
|
||||
view {
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
.tabbar-container::before{
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 10%;
|
||||
top: 0;
|
||||
z-index: 10;
|
||||
height: 1px;
|
||||
width: 80%;
|
||||
background-image: linear-gradient(90deg, $uni-border-color-default, $uni-color-primary 50%, $uni-border-color-default);
|
||||
background-size: 100% 1px;
|
||||
background-repeat:no-repeat;
|
||||
z-index: 1;
|
||||
}
|
||||
.tabbar-container {
|
||||
position: fixed;
|
||||
bottom: 0rpx;
|
||||
left: 0rpx;
|
||||
width: 100%;
|
||||
height: 110rpx;
|
||||
box-shadow: 0 0 5px #999;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding: 5rpx 0;
|
||||
color: #999999;
|
||||
color: $uni-text-color-grey;
|
||||
background: $uni-border-color-default;
|
||||
box-shadow: 0 2px 4px $uni-border-shadow-color-default;
|
||||
|
||||
/* 针对tabbar的统一处理 */
|
||||
.tabbar-item {
|
||||
@ -110,12 +143,12 @@ view {
|
||||
}
|
||||
// 未被选中的导航栏字体
|
||||
.item-bottom {
|
||||
font-size: 28rpx;
|
||||
font-size: 12px;
|
||||
width: 100%;
|
||||
}
|
||||
// 被选中的导航栏字体
|
||||
.item-active {
|
||||
color: #f00;
|
||||
color: $uni-text-color-inverse;
|
||||
}
|
||||
}
|
||||
|
||||
@ -123,16 +156,26 @@ view {
|
||||
.center-item {
|
||||
display: block;
|
||||
position: relative;
|
||||
z-index: 20;
|
||||
.item-top {
|
||||
flex-shrink: 0;
|
||||
width: 100rpx;
|
||||
height: 100rpx;
|
||||
position: absolute;
|
||||
top: -50rpx;
|
||||
top: -60rpx;
|
||||
left: calc(50% - 50rpx);
|
||||
border-radius: 50%;
|
||||
box-shadow: 0 0 5px #999;
|
||||
background-color: rgb(240, 63, 131);
|
||||
box-shadow: 0 2px 4px $uni-border-shadow-color-default;
|
||||
padding: 0;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
border: 2px solid $uni-text-color-inverse;
|
||||
.img{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
border-radius: 50%;
|
||||
}
|
||||
}
|
||||
.item-bottom {
|
||||
position: absolute;
|
||||
@ -141,7 +184,7 @@ view {
|
||||
.item-active {
|
||||
position: absolute;
|
||||
bottom: 5rpx;
|
||||
color: #1fff;
|
||||
color: $uni-text-color-inverse;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,86 +0,0 @@
|
||||
<template>
|
||||
<view class="tab-bar">
|
||||
<view class="content">
|
||||
<view class="one-tab" v-for="(item, index) in tabBarList" :key="index" @click="selectTabBar(item.pagePath)">
|
||||
<view>
|
||||
<view class="tab-img">
|
||||
<image v-if="routePath === item.pagePath" class="img" :src="item.selectedIconPath"></image>
|
||||
<image v-else class="img" :src="item.iconPath"></image>
|
||||
</view>
|
||||
</view>
|
||||
<view v-if="routePath === item.pagePath" class="tit selectTexts">{{ item.text }}</view>
|
||||
<view v-else class="tit texts">{{ item.text }}</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
props: {
|
||||
// 底部导航栏数据
|
||||
tabBarList: {
|
||||
type: Array,
|
||||
required: true
|
||||
},
|
||||
// 当前页面路径
|
||||
routePath: {
|
||||
type: String,
|
||||
required: true
|
||||
}
|
||||
},
|
||||
data() {
|
||||
return {};
|
||||
},
|
||||
methods: {
|
||||
selectTabBar(path) {
|
||||
this.$emit('onTabBar', path)
|
||||
}
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.tab-bar {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
width: 100vw;
|
||||
padding-top: 10rpx;
|
||||
padding-bottom: calc(10rpx + constant(safe-area-inset-bottom));
|
||||
padding-bottom: calc(10rpx + env(safe-area-inset-bottom));
|
||||
background-color: #fff;
|
||||
|
||||
.content {
|
||||
display: flex;
|
||||
|
||||
.one-tab {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
width: 50%;
|
||||
|
||||
.tab-img {
|
||||
width: 50rpx;
|
||||
height: 50rpx;
|
||||
|
||||
.img {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
.tit {
|
||||
font-size: 30rpx;
|
||||
transform: scale(0.7);
|
||||
}
|
||||
.selectTexts{
|
||||
color:#1890e1;
|
||||
}
|
||||
.texts{
|
||||
color: block;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
70
components/loadMore/index.vue
Normal file
@ -0,0 +1,70 @@
|
||||
<template>
|
||||
<view class="loadMore">
|
||||
<!-- 无数据 -->
|
||||
<view class="noData" v-if="noData">
|
||||
<view class="imgView">
|
||||
<image class="img" src="https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/noData.png" lazy-load="true"></image>
|
||||
</view>
|
||||
<view class="text font14">暂无数据...</view>
|
||||
</view>
|
||||
<view class="loadView" v-if="loading">
|
||||
<view class="loadBox">
|
||||
<text class="icon iconfont icon-loading"></text>
|
||||
<text class="text font14">加载中...</text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="loadCompleted" v-if="loadEnd && !loading">
|
||||
<view class="loadBox">
|
||||
<text class="iconfont icon-meiyougengduo"></text>
|
||||
<text class="text font14">没有更多数据了!</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
|
||||
}
|
||||
},
|
||||
props: {
|
||||
noData:{
|
||||
type:[Boolean],
|
||||
default(){
|
||||
return false
|
||||
}
|
||||
},
|
||||
loading:{
|
||||
type:[Boolean],
|
||||
default(){
|
||||
return false
|
||||
}
|
||||
},
|
||||
loadEnd:{
|
||||
type:[Boolean],
|
||||
default(){
|
||||
return false
|
||||
}
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.noData{
|
||||
.text{
|
||||
color: $uni-text-color-grey;
|
||||
}
|
||||
}
|
||||
.loadBox{
|
||||
color: $uni-text-color-loading;
|
||||
}
|
||||
</style>
|
128
components/pickerSelect/index.vue
Normal file
@ -0,0 +1,128 @@
|
||||
<template>
|
||||
<view class="selectView">
|
||||
<picker mode="selector" @change="bindPickerChange" @cancel="pickerHide" :value="value" range-key="name" :range="list" >
|
||||
<view class="pickerBom" @click="pickerClick">
|
||||
<input class="input" type="text" :value="text" :placeholder="placeholder" disabled />
|
||||
<text class="iconfont icon-gengduo" :class="selectShow?'selectOpen':'selectHide'"></text>
|
||||
</view>
|
||||
</picker>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
selectShow:false,
|
||||
value:'',
|
||||
text:'',
|
||||
id:this.id,
|
||||
array:this.list,
|
||||
}
|
||||
},
|
||||
props: {
|
||||
placeholder:{
|
||||
type:[String],
|
||||
default:'请选择'
|
||||
},
|
||||
list:{
|
||||
type:[Array],
|
||||
default:[]
|
||||
},
|
||||
id:{
|
||||
type:[String,Number],
|
||||
default:''
|
||||
}
|
||||
},
|
||||
watch:{
|
||||
id:{
|
||||
handler(val){
|
||||
if(val){
|
||||
this.array.forEach((item,index)=>{
|
||||
if(item.value == val){
|
||||
this.value = index;
|
||||
this.text = item.name;
|
||||
this.id = val;
|
||||
}
|
||||
})
|
||||
}else{
|
||||
this.value = '';
|
||||
this.text = '';
|
||||
this.id = '';
|
||||
}
|
||||
},
|
||||
immediate:true,
|
||||
deep:true
|
||||
},
|
||||
list:{
|
||||
handler(val){
|
||||
this.array = val;
|
||||
this.array.forEach((item,index)=>{
|
||||
if(item.value == this.id){
|
||||
this.value = index;
|
||||
this.text = item.name;
|
||||
this.id = item.value;
|
||||
}
|
||||
})
|
||||
},
|
||||
immediate:true,
|
||||
deep:true
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
|
||||
},
|
||||
methods: {
|
||||
pickerClick(){
|
||||
this.selectShow = true;
|
||||
},
|
||||
bindPickerChange(e){
|
||||
this.value = e.detail.value;
|
||||
this.text = this.array[e.detail.value].name;
|
||||
this.id = this.array[e.detail.value].value;
|
||||
this.selectShow = false;
|
||||
|
||||
this.$emit('change',{name:this.array[e.detail.value].name,value:this.array[e.detail.value].value,item:this.array[e.detail.value]});
|
||||
},
|
||||
pickerHide(){
|
||||
this.selectShow = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.selectView{
|
||||
width: 100%;
|
||||
}
|
||||
.pickerBom{
|
||||
width: 100%;
|
||||
.input{
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
.selectOpen{
|
||||
animation: rotate 0.6s;
|
||||
animation-fill-mode: forwards;
|
||||
}
|
||||
.selectHide{
|
||||
animation: rotate180 0.6s ;
|
||||
animation-fill-mode: forwards;
|
||||
}
|
||||
@keyframes rotate {
|
||||
from {
|
||||
transform: rotate(0deg);
|
||||
}
|
||||
to {
|
||||
transform: rotate(90deg);
|
||||
}
|
||||
}
|
||||
@keyframes rotate180 {
|
||||
from {
|
||||
transform: rotate(90deg);
|
||||
}
|
||||
to {
|
||||
transform: rotate(0deg);
|
||||
}
|
||||
}
|
||||
</style>
|
91
components/progressBar.vue
Normal file
@ -0,0 +1,91 @@
|
||||
<template>
|
||||
<view>
|
||||
<view class="line-total" :style="'width: ' + (val / total * 100) + '%'">
|
||||
<text class="line-data">
|
||||
{{val}}%
|
||||
</text>
|
||||
</view>
|
||||
<view style="position: relative;bottom: 13px;">
|
||||
<view class="line-base"></view>
|
||||
<view class="line-blue" :style="'width: ' + (val / total * 100) + '%'"></view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'progressBar',
|
||||
data() {
|
||||
return {
|
||||
}
|
||||
},
|
||||
props: {
|
||||
// 标题
|
||||
title: {
|
||||
type: [String, Number],
|
||||
default: ''
|
||||
},
|
||||
total: {
|
||||
type: [Number],
|
||||
default: 0
|
||||
},
|
||||
val: {
|
||||
type: [Number],
|
||||
default: 0
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.line-total {
|
||||
color: #67C23A;
|
||||
text-align: right;
|
||||
font-size: 25rpx;
|
||||
font-style: normal;
|
||||
font-weight: 700;
|
||||
line-height: normal;
|
||||
position: relative;
|
||||
z-index: 99;
|
||||
|
||||
}
|
||||
.line-data{
|
||||
color: $uni-text-color-inverse;
|
||||
padding: 1px 5px;
|
||||
border-radius: 9px;
|
||||
border: 1px solid $uni-text-color-inverse;
|
||||
background: var(--color-warning, #67C23A);
|
||||
width: 30px;
|
||||
display: inline-block;
|
||||
text-align: center;
|
||||
font-size: 11px;
|
||||
}
|
||||
.line-base {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 6px;
|
||||
border-radius: 8px;
|
||||
background: rgba(128, 136, 142, 0.40);
|
||||
}
|
||||
.line-blue {
|
||||
position: absolute;
|
||||
width: 50%;
|
||||
height: 6px;
|
||||
border-radius: 10px;
|
||||
background: #67C23A;
|
||||
}
|
||||
.line-val {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
color: #7e7e7e;
|
||||
font-size: 25rpx;
|
||||
font-weight: 50px;
|
||||
margin-top: 12rpx;
|
||||
}
|
||||
</style>
|
40
components/searchView/index.vue
Normal file
@ -0,0 +1,40 @@
|
||||
<template>
|
||||
<view class="searchBox">
|
||||
<view class="searchView">
|
||||
<view class="searchInput">
|
||||
<input class="input font14" confirm-type="search" placeholder-class="placeholderStyle placeholderClass iconfont icon-a-Vector6-copy" :placeholder="placeholder" />
|
||||
<view class="filter">
|
||||
<text class="iconfont icon-a-shaixuan2 font22"></text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
|
||||
}
|
||||
},
|
||||
props: {
|
||||
placeholder:{
|
||||
type:[String],
|
||||
default:' 请输入关键字'
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.searchBox .searchInput .input{
|
||||
background: $uni-bg-color-primary;
|
||||
}
|
||||
</style>
|
20
components/switchDefine.vue
Normal file
@ -0,0 +1,20 @@
|
||||
<template>
|
||||
<view>
|
||||
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name:"switchDefine",
|
||||
data() {
|
||||
return {
|
||||
|
||||
};
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
|
||||
</style>
|
245
components/upload/uploadImg.vue
Normal file
@ -0,0 +1,245 @@
|
||||
<template>
|
||||
<view class="uploadImgView">
|
||||
<view class="uploadTitle" v-if="name && name!=''">
|
||||
<view class="name font_bold">{{name}}</view>
|
||||
<view class="limit">{{newList.length}}/{{limit}}</view>
|
||||
</view>
|
||||
<view class="imgList">
|
||||
<view class="uploadFlex itemBox" v-for="(item,index) in newList" :key="index">
|
||||
<view class="imgItem">
|
||||
<view class="itemImg">
|
||||
<image class="img" :src="item" mode="scaleToFill"></image>
|
||||
</view>
|
||||
<view class="deleteBox" @click="deleteImg(index)">
|
||||
<text class="icon iconfont icon-a-shanchu21"></text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="uploadFlex itemBox" v-for="(item,index) in uploadList" :key="index">
|
||||
<view class="imgItem">
|
||||
<view class="itemImg">
|
||||
<image class="img" :src="item.path" mode="scaleToFill"></image>
|
||||
</view>
|
||||
<view class="progressView">
|
||||
<view class="progressWidth" :style="'width:'+item.progress+'%'"></view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="uploadBut itemBox" @click="upload()" v-if="newList.length<limit">
|
||||
<view class="img_but">
|
||||
<view class="icon iconfont icon-a-shangchuanzhaopian2 font35"></view>
|
||||
<view class="text font12">
|
||||
上传图片
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default{
|
||||
data(){
|
||||
return{
|
||||
newList:this.list,
|
||||
uploadList:[],
|
||||
|
||||
oss:{},
|
||||
}
|
||||
},
|
||||
props:{
|
||||
name:{
|
||||
type:[String],
|
||||
default:''
|
||||
},
|
||||
limit:{
|
||||
type:[Number,String],
|
||||
default:1
|
||||
},
|
||||
list:{
|
||||
type:[Array,Object],
|
||||
default: () => []
|
||||
},
|
||||
},
|
||||
watch:{
|
||||
list:{
|
||||
handler(val){
|
||||
this.newList = val;
|
||||
},
|
||||
immediate:true,
|
||||
deep:true
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.getOss();
|
||||
},
|
||||
onShow() {
|
||||
|
||||
},
|
||||
methods:{
|
||||
// 获取图片oss 服务地址
|
||||
getOss(){
|
||||
this.$api.getOss('/oss.sign',{dir:'mes'}).then(res=>{
|
||||
this.oss = res.data;
|
||||
}).catch(err=>{})
|
||||
},
|
||||
deleteImg(num){
|
||||
this.newList.forEach((item,index)=>{
|
||||
if(num == index){
|
||||
this.newList.splice(index,1);
|
||||
}
|
||||
})
|
||||
this.$emit('input',this.newList);
|
||||
},
|
||||
upload(){
|
||||
uni.chooseImage({
|
||||
count:9,
|
||||
success: (chooseImageRes) => {
|
||||
const tempFilePaths = chooseImageRes.tempFilePaths;
|
||||
tempFilePaths.forEach((item,index)=>{
|
||||
let num = item.length;
|
||||
let nameStr = item.toString();
|
||||
let name = Date.parse(new Date())+'/'+nameStr.substring(nameStr-8);
|
||||
let fileName = this.oss.dir+'/'+ name;
|
||||
let text = Date.parse(new Date())+'_'+index;
|
||||
|
||||
let obj = {
|
||||
path:nameStr,
|
||||
text:text,
|
||||
progress:0,
|
||||
}
|
||||
this.uploadList.push(obj)
|
||||
|
||||
this.uploadOss(item,name,fileName,text);
|
||||
})
|
||||
},
|
||||
fail:(errUpload)=> {
|
||||
|
||||
}
|
||||
});
|
||||
},
|
||||
uploadOss(url,name,fileName,text){
|
||||
const uploadTask = uni.uploadFile({
|
||||
url:this.oss.host,
|
||||
header:{
|
||||
'Content-Type':'application/x-www-form-urlencoded',
|
||||
},
|
||||
filePath: url,
|
||||
name: 'file',
|
||||
formData: {
|
||||
'name':name,
|
||||
'key': fileName,
|
||||
'policy': this.oss.policy,
|
||||
'OSSAccessKeyId': this.oss.accessid,
|
||||
'success_action_status':200,
|
||||
'Signature': this.oss.signature,
|
||||
},
|
||||
success: (uploadFileRes)=>{
|
||||
this.newList.push(this.oss.host+fileName);
|
||||
this.uploadList = [];
|
||||
this.$emit('input',this.newList);
|
||||
},
|
||||
fail:(err)=>{
|
||||
uni.showModal({
|
||||
content: err.errMsg,
|
||||
showCancel: false
|
||||
});
|
||||
}
|
||||
});
|
||||
uploadTask.onProgressUpdate((res) => {
|
||||
this.uploadList.forEach((item,index)=>{
|
||||
if(item.text == text){
|
||||
item.progress = res.progress;
|
||||
}
|
||||
})
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.uploadTitle{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
margin-bottom: 6px;
|
||||
.limit{
|
||||
color: $uni-text-color-info;
|
||||
}
|
||||
}
|
||||
.imgList{
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
.uploadFlex{
|
||||
display: flex;
|
||||
}
|
||||
.itemBox{
|
||||
width: 32%;
|
||||
height: 100px;
|
||||
margin-right: 2%;
|
||||
padding: 7px 0 0 0;
|
||||
box-sizing: border-box;
|
||||
.imgItem{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: relative;
|
||||
.itemImg{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
.img{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
border-radius: 4px;
|
||||
}
|
||||
.deleteBox{
|
||||
position: absolute;
|
||||
top: 3px;
|
||||
right: 3px;
|
||||
z-index: 20;
|
||||
width: 26px;
|
||||
height: 26px;
|
||||
border-radius: 50%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background: $uni-bg-color-delete;
|
||||
.icon{font-size: 14px;}
|
||||
}
|
||||
}
|
||||
}
|
||||
.itemBox:nth-child(3n){
|
||||
margin-right: 0;
|
||||
}
|
||||
.uploadBut{
|
||||
height: 93px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
background: $uni-bg-color-placeholder;
|
||||
border-radius: 4px;
|
||||
margin: 7px 0 0 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
}
|
||||
|
||||
.img_but{
|
||||
display: flex;flex-direction: column;align-items: center;
|
||||
.icon{color: $uni-text-color-inverse;}
|
||||
.text{margin-top: 5px;}
|
||||
}
|
||||
|
||||
.progressView{
|
||||
position: absolute;bottom: 0;left: 0;z-index: 2;
|
||||
width: 100%;height: 6px;background: $uni-bg-color-placeholder;border-radius: 8px;
|
||||
.progressWidth{
|
||||
height: 6px;background: $uni-color-primary;
|
||||
border-radius: 8px;
|
||||
}
|
||||
}
|
||||
</style>
|
21
env.js
Normal file
@ -0,0 +1,21 @@
|
||||
// 不同的环境变量配置
|
||||
const development = {
|
||||
requestBaseUrl: 'http://development',
|
||||
appid: '',
|
||||
}
|
||||
|
||||
const test = {
|
||||
requestBaseUrl: 'https://api.dev.dwoodauto.com/api',
|
||||
appid: 'wxd5xxxxee0fce1c81',
|
||||
}
|
||||
|
||||
const production = {
|
||||
requestBaseUrl: 'http://production',
|
||||
appid: 'wx3xxxx1ce403cab3',
|
||||
}
|
||||
|
||||
export default {
|
||||
development,
|
||||
test,
|
||||
production
|
||||
}
|
33
main.js
@ -1,12 +1,28 @@
|
||||
|
||||
import "./static/iconfont/iconfont.css"
|
||||
import './static/css/app.css';
|
||||
import "./static/iconfont/iconfont-weapp/iconfont-weapp-icon.css"
|
||||
|
||||
|
||||
// 全局组件
|
||||
import searchView from './components/searchView/index'
|
||||
import loadMore from './components/loadMore/index'
|
||||
import progressBar from './components/progressBar'
|
||||
import pickerSelect from './components/pickerSelect/index'
|
||||
import calendar from './components/calendar/index'
|
||||
import uploadImg from './components/upload/uploadImg'
|
||||
// #ifndef VUE3
|
||||
import Vue from 'vue'
|
||||
import App from './App'
|
||||
import svg from './static/iconfont/svg.js'
|
||||
|
||||
Vue.component('search-view', searchView);
|
||||
Vue.component('load-more', loadMore);
|
||||
Vue.component('progress-bar', progressBar);
|
||||
Vue.component('picker-select', pickerSelect);
|
||||
Vue.component('calendar', calendar);
|
||||
Vue.component('upload-img', uploadImg);
|
||||
|
||||
|
||||
Vue.use(svg);
|
||||
|
||||
Vue.config.productionTip = false;
|
||||
@ -21,10 +37,25 @@ app.$mount()
|
||||
// #ifdef VUE3
|
||||
import { createSSRApp } from 'vue'
|
||||
import App from './App.vue'
|
||||
import request from "./utils/api.js"
|
||||
import publicMethods from "./utils/public.js"
|
||||
|
||||
export function createApp() {
|
||||
const app = createSSRApp(App)
|
||||
|
||||
// 全局注册组件
|
||||
app.component('searchView', searchView);
|
||||
app.component('loadMore', loadMore);
|
||||
app.component('progressBar', progressBar);
|
||||
app.component('pickerSelect', pickerSelect);
|
||||
app.component('calendar', calendar);
|
||||
app.component('uploadImg', uploadImg);
|
||||
|
||||
app.config.globalProperties.$api = request;
|
||||
app.config.globalProperties.$wf = publicMethods;
|
||||
return {
|
||||
app
|
||||
}
|
||||
}
|
||||
// #endif
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
{
|
||||
"name" : "mes-mobile01",
|
||||
"name" : "mes-mobile",
|
||||
"appid" : "__UNI__41DB0F2",
|
||||
"description" : "",
|
||||
"versionName" : "1.0.0",
|
||||
@ -50,11 +50,16 @@
|
||||
/* 快应用特有相关 */
|
||||
"mp-weixin" : {
|
||||
/* 小程序特有相关 */
|
||||
"appid" : "wx62bd7b72516b9017",
|
||||
"appid" : "wx38dc81b0eef130a3",
|
||||
"setting" : {
|
||||
"urlCheck" : false
|
||||
"urlCheck" : false,
|
||||
"postcss" : true,
|
||||
"es6" : true,
|
||||
"minified" : true
|
||||
},
|
||||
"usingComponents" : true
|
||||
"usingComponents" : true,
|
||||
"libVersion":"latest"
|
||||
},
|
||||
"vueVersion" : "3"
|
||||
"vueVersion" : "3",
|
||||
"locale" : "zh-Hans"
|
||||
}
|
||||
|
30
package.json
@ -1,16 +1,22 @@
|
||||
{
|
||||
"name": "mes_mobile",
|
||||
"version": "1.0.0",
|
||||
"description": "",
|
||||
"main": "main.js",
|
||||
"uni-app": {
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
"dev": {
|
||||
"title": "微信小程序——开发版",
|
||||
"env": {
|
||||
"ENV_TYPE": "dev",
|
||||
"UNI_PLATFORM": "mp-weixin",
|
||||
"VITE_BASE_API": "https://api.dev.dwoodauto.com"
|
||||
}
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://git.tool.dwoodauto.com/long/mes_mobile.git"
|
||||
},
|
||||
"keywords": [],
|
||||
"author": "",
|
||||
"license": "ISC"
|
||||
"pro": {
|
||||
"title": "微信小程序——正式版",
|
||||
"env": {
|
||||
"ENV_TYPE": "pro",
|
||||
"UNI_PLATFORM": "mp-weixin",
|
||||
"VITE_BASE_API": "http://pro.domain/"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
167
pages.json
@ -35,16 +35,169 @@
|
||||
"path" : "pages/login/login",
|
||||
"style" :
|
||||
{
|
||||
// "navigationBarTitleText" : "登录",
|
||||
"enablePullDownRefresh" : false,
|
||||
"navigationStyle": "custom"
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/index/productionOrder",
|
||||
"path" : "pages/production/productionOrder",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "生产工单管理",
|
||||
"enablePullDownRefresh" : true,
|
||||
"pullToRefresh":{
|
||||
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/schedul/list",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "工单排程",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/index/schedule",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "工单进度",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/index/materialYield",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "工单出材率",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/equipmentManage/equipmentManage",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备管理",
|
||||
"enablePullDownRefresh" : true
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/equipmentManage/editDevice",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "添加设备",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/equipmentManage/bindingDevice",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备管理",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/production/productionDetail",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "工单详情",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/deviceRepair/deviceRepair",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "硬件设备报修",
|
||||
"enablePullDownRefresh" : true
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/deviceRepair/repairReport",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备报修",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path":"pages/deviceRepair/deviceDetail",
|
||||
"style" :{
|
||||
"navigationBarTitleText" : "设备报修详情",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/deviceStatus/deviceStatus",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备状态",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/equipmentManage/deviceDetail",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备信息",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/person/faceAuthentication",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "人脸认证",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/person/myAuthority",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "我的权限",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/person/alarm",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备报警",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/person/safetyAccidents",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "安全事故",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/deviceStatus/deviceCamera",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备状态",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/deviceStatus/detectionEventList",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备状态",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
},
|
||||
{
|
||||
"path" : "pages/deviceRepair/repairOrder",
|
||||
"style" :
|
||||
{
|
||||
"navigationBarTitleText" : "设备维修",
|
||||
"enablePullDownRefresh" : false
|
||||
}
|
||||
}],
|
||||
@ -52,8 +205,16 @@
|
||||
"navigationBarTextStyle": "white",
|
||||
"navigationBarTitleText": "德木自动化系统",
|
||||
"navigationBarBackgroundColor": "#060B26",
|
||||
"backgroundColor":"#060B26",
|
||||
"backgroundTextStyle":"light",
|
||||
"app-plus": {
|
||||
"background": "#efeff4"
|
||||
"background": "#060B26"
|
||||
},
|
||||
"mp-weixin":{
|
||||
"background":"#060B26",
|
||||
"pullToRefresh":{
|
||||
"color":"#060B26"
|
||||
}
|
||||
}
|
||||
},
|
||||
"condition" : { //模式配置,仅开发期间生效
|
||||
|
178
pages/deviceRepair/RepairReport.vue
Normal file
@ -0,0 +1,178 @@
|
||||
<template>
|
||||
<!-- 设备报修 -->
|
||||
<view class="page_padding">
|
||||
<view class="page_content contentboxsty font14">
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">值班工程师</view>
|
||||
<view class="flex1">
|
||||
<pickerSelect class="comView" @change="bindOperatorChange" :list="setMap.operatorList" :id="form.operator_id" placeholder="请选择工程师" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">故障时间</view>
|
||||
<view class="flex1">
|
||||
<view class='input_date' :class="[form.failure_at && form.failure_at!=''? 'haveTime' : '']">
|
||||
<uni-datetime-picker placeholder="请选择时间" type="datetime" v-model="form.failure_at" />
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">报修时间</view>
|
||||
<view class="flex1">
|
||||
<view class='input_date' :class="[form.report_at && form.report_at!=''? 'haveTime' : '']">
|
||||
<uni-datetime-picker placeholder="请选择时间" type="datetime" v-model="form.report_at" />
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">报修人</view>
|
||||
<view class="flex1">
|
||||
<pickerSelect class="comView" @change="bindRepairChange" :list="setMap.operatorList" :id="form.report_id" placeholder="请选择报修人" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">报修设备</view>
|
||||
<view class="flex1">
|
||||
<pickerSelect class="comView" @change="bindeQuipmentChange" :list="setMap.equipmentList" :id="form.equipment_id" placeholder="请选择报修设备" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="textarea_row">
|
||||
<view class="name font_bold">故障描述</view>
|
||||
<textarea class="textarea" placeholder="请输入故障描述..." v-model="form.remark" cursor-spacing="180px" :auto-blur="true" placeholder-class="placeholderStyle"/>
|
||||
</view>
|
||||
<view class="img_row">
|
||||
<uploadImg limit="3" name="故障图片" :list="form.failure_photo" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="bottom_but flex_layout">
|
||||
<view class="font13 but_color" @click="save">保存</view>
|
||||
<view class="font13" @click="cancel">取消</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
setMap:{
|
||||
operatorList:[],
|
||||
equipmentList:[],
|
||||
},
|
||||
form:{
|
||||
id:'',
|
||||
operator_id:'',
|
||||
failure_at:'',
|
||||
report_at:'',
|
||||
report_id:'',
|
||||
equipment_id:'',
|
||||
remark:'',
|
||||
failure_photo:[],
|
||||
},
|
||||
id:0,
|
||||
|
||||
oss:{},
|
||||
}
|
||||
},
|
||||
onLoad(option) {
|
||||
if(option.id != undefined){
|
||||
this.getInfo(Number(option.id));
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.userList();
|
||||
this.equipment();
|
||||
},
|
||||
methods: {
|
||||
getInfo(id){
|
||||
this.$api.request('/equipment.repair.info',{id:id}).then(res=>{
|
||||
this.form = {
|
||||
id:id,
|
||||
operator_id:res.data.operator_id,
|
||||
failure_at:res.data.failure_at,
|
||||
report_at:res.data.report_at,
|
||||
report_id:res.data.report_id,
|
||||
equipment_id:res.data.equipment_id,
|
||||
remark:res.data.remark,
|
||||
failure_photo:res.data.failure_photo,
|
||||
}
|
||||
}).catch(err=>{})
|
||||
},
|
||||
userList(){
|
||||
this.$api.request('/user.options','').then(res=>{
|
||||
res.data.forEach(item=>{
|
||||
item.value = item.id;
|
||||
})
|
||||
this.setMap['operatorList'] = res.data;
|
||||
}).catch(err=>{})
|
||||
},
|
||||
equipment(){
|
||||
this.$api.request('/device.options','').then(res=>{
|
||||
res.data.forEach(item=>{
|
||||
item.name = item.name;
|
||||
item.value = item.id;
|
||||
})
|
||||
this.setMap['equipmentList'] = res.data;
|
||||
}).catch(err=>{})
|
||||
},
|
||||
bindOperatorChange(e){
|
||||
this.form.operator_id = e.value;
|
||||
},
|
||||
bindRepairChange(e){
|
||||
this.form.report_id = e.value;
|
||||
},
|
||||
bindeQuipmentChange(e){
|
||||
this.form.equipment_id = e.value;
|
||||
},
|
||||
save(){
|
||||
this.$api.postFuncLoading('/create.repair.notice',this.form).then(res=>{
|
||||
this.parentClick();
|
||||
this.reset();
|
||||
this.$wf.toast({type:'success',text:'保存成功'});
|
||||
}).catch(err=>{})
|
||||
},
|
||||
cancel(){
|
||||
this.reset();
|
||||
},
|
||||
reset(){
|
||||
this.form = {
|
||||
id:'',
|
||||
operator_id:'',
|
||||
failure_at:'',
|
||||
report_at:'',
|
||||
report_id:'',
|
||||
equipment_id:'',
|
||||
remark:'',
|
||||
failure_photo:[],
|
||||
}
|
||||
},
|
||||
parentClick(){
|
||||
const pages = getCurrentPages();
|
||||
if (pages.length >= 2) {
|
||||
const prevPage = pages[pages.length - 2];
|
||||
prevPage.$vm.getList();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_padding{padding-bottom: 100px;}
|
||||
.page_content{padding: 0 12px 10px;}
|
||||
.content_row{display: flex;border-bottom: 1px solid #2D3A6F;height: 44px;align-items: center;
|
||||
.name{flex-basis: 96px;}
|
||||
.flex_layout{
|
||||
.contenticon{width: 20px;height: 20px;}
|
||||
.text{padding: 0 20px 0 5px;}
|
||||
}
|
||||
}
|
||||
.textarea_row{
|
||||
.name{padding: 12px 0;}
|
||||
.textarea{border-radius: 4px;background: $uni-bg-color-placeholder;padding: 10px;width: 100%;box-sizing: border-box;}
|
||||
}
|
||||
.img_row{
|
||||
padding: 12px 0 6px 0;
|
||||
height: 100%;
|
||||
}
|
||||
</style>
|
117
pages/deviceRepair/deviceDetail.vue
Normal file
@ -0,0 +1,117 @@
|
||||
<template>
|
||||
<view class="page_padding">
|
||||
<view class="padd_bot12 font14 flex_layout">
|
||||
<text>{{type==1?'硬件设备报修详情':'硬件设备维修详情'}}</text>
|
||||
</view>
|
||||
<view class="detail_list padd_top12 contentboxsty page_content font13">
|
||||
<template v-if="type==2">
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">维修工程师</view>
|
||||
<view class="text">{{info.repair_name}}</view>
|
||||
</view>
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">故障解除时间</view>
|
||||
<view class="text">{{info.repair_at_label}}</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="name font_bold">维修描述</view>
|
||||
<view class="text remarkText padd_top12">{{info.repair_remark}}</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="name font_bold">维修照片</view>
|
||||
<view class="text imgList">
|
||||
<view class="imgView" v-for="(em,ind) in info.repair_photo" :key="ind">
|
||||
<image class="img" :src="em" mode="aspectFill" @click="imgPreview(info.repair_photo,em)"></image>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<template v-if="type ==1">
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">值班工程师</view>
|
||||
<view class="text">{{info.operator_name}}</view>
|
||||
</view>
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">故障时间</view>
|
||||
<view class="text">{{info.failure_at}}</view>
|
||||
</view>
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">报修时间</view>
|
||||
<view class="text">{{info.report_at}}</view>
|
||||
</view>
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">报修人</view>
|
||||
<view class="text">{{info.repair_name}}</view>
|
||||
</view>
|
||||
<view class="row flex_layout">
|
||||
<view class="name font_bold">报修设备</view>
|
||||
<view class="text">{{info.eq_name}}</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="name font_bold">故障描述</view>
|
||||
<view class="text remarkText padd_top12">{{info.remark}}</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="name font_bold">故障照片</view>
|
||||
<view class="text imgList">
|
||||
<view class="imgView" v-for="(em,ind) in info.failure_photo" :key="ind">
|
||||
<image class="img" :src="em" mode="aspectFill" @click="imgPreview(info.failure_photo,em)"></image>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default{
|
||||
data(){
|
||||
return{
|
||||
type:1,
|
||||
id:0,
|
||||
info:{}
|
||||
}
|
||||
},
|
||||
onLoad(option) {
|
||||
this.type = option.type;
|
||||
this.id = option.id;
|
||||
},
|
||||
mounted() {
|
||||
this.getData();
|
||||
},
|
||||
methods:{
|
||||
getData(){
|
||||
this.$api.postFuncLoading('/equipment.repair.info',{id:this.id}).then(res=>{
|
||||
this.info = res.data;
|
||||
}).catch(err=>{})
|
||||
},
|
||||
imgPreview(list,url){
|
||||
uni.previewImage({
|
||||
urls: list,
|
||||
current:url,
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.row{
|
||||
padding-bottom: 12px;
|
||||
.name{flex-basis: 90px;}
|
||||
.text{flex: 1;}
|
||||
}
|
||||
.row:last-child{
|
||||
padding-bottom: 0;
|
||||
}
|
||||
.imgList{
|
||||
display: flex;flex-direction: row;flex-wrap: wrap;padding: 6px 0;
|
||||
.imgView{width: 32%;height: 100px;margin-right: 2%;box-sizing: border-box;padding: 6px 0 0 0;}
|
||||
.imgView:nth-child(3n){
|
||||
margin-right: 0;
|
||||
}
|
||||
.img{width: 100%;height: 100%;border-radius:4px;}
|
||||
}
|
||||
</style>
|
191
pages/deviceRepair/deviceRepair.vue
Normal file
@ -0,0 +1,191 @@
|
||||
<template>
|
||||
<!-- 设备报修 -->
|
||||
<view class="page_padding bot_padding">
|
||||
<view v-for="(item,index) in list" :key="index">
|
||||
<view class="page_list contentboxsty font13" @click="toDetail(item)">
|
||||
<view class="list_top flex_layout">
|
||||
<view class="top_left flex_layout">
|
||||
<view class="icon iconfont icon-daiju"></view>
|
||||
<view class="font_bold">{{item.eq_name}}</view>
|
||||
</view>
|
||||
<view class="card_right top_right">
|
||||
<text class="status error">故障中</text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_centre padd_bot12">
|
||||
<view class="row_data">
|
||||
<view class="name font_bold">值班工程师</view>
|
||||
<view class="text">{{item.operator_name}}</view>
|
||||
</view>
|
||||
<view class="row_data">
|
||||
<view class="name font_bold">故障时间</view>
|
||||
<view class="text">{{item.failure_at}}</view>
|
||||
</view>
|
||||
|
||||
<view class="row_data">
|
||||
<view class="name font_bold">报修人</view>
|
||||
<view class="text">{{item.repair_name}}</view>
|
||||
</view>
|
||||
<view class="row_data">
|
||||
<view class="name font_bold">报修时间</view>
|
||||
<view class="text">{{item.report_at}}</view>
|
||||
</view>
|
||||
<view class="row_data">
|
||||
<view class="name font_bold">处理状态</view>
|
||||
<view class="text">{{item.status_label}}</view>
|
||||
</view>
|
||||
<view class="row_data">
|
||||
<view class="name font_bold">故障解除时间</view>
|
||||
<view class="text">{{item.repair_at_label}}</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_below flex_layout">
|
||||
<view class="below_left btn" @click.stop="toRepairOrder(item)">
|
||||
<text class="icon iconfont icon-bianji font16"></text>
|
||||
维修单
|
||||
</view>
|
||||
<view class="below_right btn" @click.stop="editRepairOrder(item)">
|
||||
<text class="icon iconfont icon-bianji font16"></text>
|
||||
修改
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="page_bottom_button">
|
||||
<view class="page_add" @click="toAddRepairReport()">
|
||||
<view class="icon iconfont icon-tianjia font20"></view>
|
||||
<text class="font14">添加</text>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
params:{
|
||||
page:1,
|
||||
pageSize:10,
|
||||
},
|
||||
loadParams:{
|
||||
noData:false,
|
||||
loading:false,
|
||||
loadEnd:false
|
||||
},
|
||||
list:[],
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.getList();
|
||||
},
|
||||
// 上拉刷新
|
||||
onPullDownRefresh(){
|
||||
this.params.page = 1;
|
||||
this.loadParams = {
|
||||
noData:false,
|
||||
loading:false,
|
||||
loadEnd:false
|
||||
};
|
||||
this.getList(2);
|
||||
},
|
||||
// 加载下一页
|
||||
onReachBottom(){
|
||||
if(!(this.loadParams.loadEnd || this.loadParams.noData)){
|
||||
this.loadParams.loading = true;
|
||||
this.params.page ++;
|
||||
this.getList();
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
getList(type=1){
|
||||
if(this.params.page == 1){
|
||||
uni.showLoading({
|
||||
title: '加载中',
|
||||
mask: true
|
||||
})
|
||||
}
|
||||
this.$api.request('/equipment.repair.list',this.params).then(res=>{
|
||||
if(type ==2){
|
||||
uni.stopPullDownRefresh();
|
||||
}
|
||||
setTimeout( ()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
|
||||
this.loadParams.loading = false;
|
||||
if(res.data.rows.length ==0 && this.params.page == 1){
|
||||
this.loadParams.noData = true;
|
||||
}
|
||||
if(res.data.rows.length>0 && res.data.rows.length < this.params.pageSize){
|
||||
this.loadParams.loadEnd = true;
|
||||
}
|
||||
if(this.params.page == 1){
|
||||
this.list = res.data.rows;
|
||||
}else{
|
||||
this.list = this.list.concat(res.data.rows);
|
||||
}
|
||||
}).catch(err=>{
|
||||
setTimeout(()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
})
|
||||
},
|
||||
|
||||
//新增报修页面
|
||||
toAddRepairReport(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceRepair/repairReport'
|
||||
})
|
||||
},
|
||||
//维修页面
|
||||
toRepairOrder(item){
|
||||
// if(item.repair_id && item.repair_id>0){
|
||||
// uni.navigateTo({
|
||||
// url:'./deviceDetail?id='+item.id+'&type='+2
|
||||
// })
|
||||
// }else{
|
||||
// uni.navigateTo({
|
||||
// url:'/pages/deviceRepair/repairOrder?id='+item.id
|
||||
// })
|
||||
// }
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceRepair/repairOrder?id='+item.id
|
||||
})
|
||||
},
|
||||
editRepairOrder(item){
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceRepair/repairReport?id='+item.id
|
||||
})
|
||||
},
|
||||
toDetail(item){
|
||||
uni.navigateTo({
|
||||
url:'./deviceDetail?id='+item.id+'&type='+1
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_list{
|
||||
.list_top{height: 44px;align-items: center;border-bottom: 1px solid $uni-border-color-primary;
|
||||
.top_left{flex: 1;display: flex;align-items: center;
|
||||
.icon{margin-right: 5px;color: $uni-text-color-primary;}
|
||||
}
|
||||
}
|
||||
.list_centre{
|
||||
.row_data{
|
||||
display: flex;align-items: center;padding-top: 12px;
|
||||
.name{flex-basis: 95px;}
|
||||
.text{display: flex;display: flex;}
|
||||
}
|
||||
}
|
||||
.list_below{height: 49px;align-items: center;border-top: 1px solid $uni-border-color-primary;
|
||||
.btn{width: 50%;display: flex;align-items: center;justify-content: center;height: 100%;
|
||||
.icon{margin-right: 5px;}
|
||||
}
|
||||
.below_left{border-right: 1px solid $uni-border-color-primary;}
|
||||
}
|
||||
}
|
||||
</style>
|
135
pages/deviceRepair/repairOrder.vue
Normal file
@ -0,0 +1,135 @@
|
||||
<template>
|
||||
<!-- 维修单 -->
|
||||
<view class="page_padding">
|
||||
<view class="page_content contentboxsty font14">
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">维修工程师</view>
|
||||
<view class="flex1">
|
||||
<pickerSelect class="comView" @change="bindPickerChange" :list="setMap.operatorList" :id="form.repair_id" placeholder="请选择工程师" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">故障解除时间</view>
|
||||
<view class="flex1">
|
||||
<view class='input_date' :class="[form.repair_at && form.repair_at!=''? 'haveTime' : '']">
|
||||
<uni-datetime-picker placeholder="请选择时间" type="datetime" v-model="form.repair_at" />
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="textarea_row">
|
||||
<view class="name font_bold">维修描述</view>
|
||||
<textarea class="textarea" v-model="form.repair_remark" placeholder="请输入维修描述..." cursor-spacing="180px" :auto-blur="true" placeholder-class="placeholderStyle" />
|
||||
</view>
|
||||
<view class="img_row">
|
||||
<uploadImg limit="3" name="维修照片" :list="form.repair_photo" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="bottom_but flex_layout">
|
||||
<view class="font13 but_color" @click="save">保存</view>
|
||||
<view class="font13" @click="cancel">取消</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
setMap:{
|
||||
operatorList:[],
|
||||
},
|
||||
form:{
|
||||
id:'',
|
||||
repair_id:'',
|
||||
repair_at:'',
|
||||
repair_remark:'',
|
||||
repair_photo:[]
|
||||
},
|
||||
|
||||
array: ['中国', '美国', '巴西', '日本'],
|
||||
downtime:'',
|
||||
}
|
||||
},
|
||||
onLoad(option) {
|
||||
if(option.id !=undefined){
|
||||
// this.form.id = Number(option.id);
|
||||
this.getInfo(Number(option.id));
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.userList();
|
||||
},
|
||||
methods: {
|
||||
getInfo(id){
|
||||
this.$api.request('/equipment.repair.info',{id:id}).then(res=>{
|
||||
this.form = {
|
||||
id:id,
|
||||
repair_id:res.data.repair_id,
|
||||
repair_at:res.data.repair_at,
|
||||
repair_remark:res.data.repair_remark,
|
||||
repair_photo:res.data.repair_photo,
|
||||
}
|
||||
}).catch(err=>{})
|
||||
},
|
||||
userList(){
|
||||
this.$api.request('/user.options','').then(res=>{
|
||||
res.data.forEach(item=>{
|
||||
item.value = item.id;
|
||||
})
|
||||
this.setMap['operatorList'] = res.data;
|
||||
}).catch(err=>{})
|
||||
},
|
||||
bindPickerChange(e){
|
||||
this.form.repair_id = e.value;
|
||||
},
|
||||
save(){
|
||||
this.$api.postFuncLoading('/create.equipment.repair',this.form).then(res=>{
|
||||
this.parentClick();
|
||||
this.$wf.toast({type:'success',text:'保存成功'});
|
||||
}).catch(err=>{})
|
||||
},
|
||||
cancel(){
|
||||
this.reset();
|
||||
},
|
||||
reset(){
|
||||
this.form = {
|
||||
id:'',
|
||||
repair_id:'',
|
||||
repair_at:'',
|
||||
repair_remark:'',
|
||||
repair_photo:[]
|
||||
}
|
||||
},
|
||||
parentClick(){
|
||||
const pages = getCurrentPages();
|
||||
if (pages.length >= 2) {
|
||||
const prevPage = pages[pages.length - 2];
|
||||
prevPage.$vm.getList();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_content{padding: 0 12px 10px;}
|
||||
.content_row{display: flex;border-bottom: 1px solid #2D3A6F;height: 44px;align-items: center;
|
||||
.name{flex-basis: 100px;}
|
||||
.flex_layout{
|
||||
.contenticon{width: 20px;height: 20px;}
|
||||
.text{padding: 0 20px 0 5px;}
|
||||
}
|
||||
}
|
||||
.textarea_row{
|
||||
.name{padding: 12px 0;}
|
||||
.textarea{border-radius: 4px;background: $uni-bg-color-placeholder;padding: 10px;width: 100%;box-sizing: border-box;}
|
||||
}
|
||||
.img_row{
|
||||
padding: 12px 0 6px 0;
|
||||
.img_but{
|
||||
display: flex;flex-direction: column;align-items: center;
|
||||
.icon{color: $uni-text-color-inverse;}
|
||||
.text{margin-top: 5px;}
|
||||
}
|
||||
}
|
||||
</style>
|
49
pages/deviceStatus/detectionEventList.vue
Normal file
@ -0,0 +1,49 @@
|
||||
<template>
|
||||
<!-- 检测事件列表 -->
|
||||
<view class="page_padding">
|
||||
<view class="padd_bot12 font14">
|
||||
<text>安全生产监控设备检测事件列表</text>
|
||||
</view>
|
||||
<view class="page_list contentboxsty flex_layout">
|
||||
<view class="content_left padd_rigth12">
|
||||
<image class="img" src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/background.png" mode=""></image>
|
||||
</view>
|
||||
<view class="content_right">
|
||||
<view class="content_row font13">
|
||||
2024-01-11 19:09:56
|
||||
</view>
|
||||
<view class="content_row tip font_bold font14">
|
||||
穿越警戒线
|
||||
</view>
|
||||
<view class="content_row font12">
|
||||
(检测到指定区域内有目标越过警戒线,请注意安全)
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.page_list{padding: 12px;}
|
||||
.content_left{
|
||||
flex-basis: 126px;height: 96px;
|
||||
.img{width: 100%;height: 100%;border-radius: 8px;}
|
||||
}
|
||||
.content_right{
|
||||
flex:1;
|
||||
.tip{color: #FA3758;padding: 6px 0 5px 0;}
|
||||
}
|
||||
</style>
|
89
pages/deviceStatus/deviceCamera.vue
Normal file
@ -0,0 +1,89 @@
|
||||
<template>
|
||||
<view class="page_padding font14">
|
||||
<view class="padd_bot12 font14 flex_layout">
|
||||
<text>硬件设备状态</text>
|
||||
<view class="status font12"><text class="drop"></text>在线</view>
|
||||
</view>
|
||||
<view class="body-view contentboxsty">
|
||||
<view class="content-top flex_layout padd_bot12">
|
||||
<view class="flex1 theme_color">
|
||||
<text class="drop"></text>相机工作中
|
||||
</view>
|
||||
<view class="top_right" @click="toList()">
|
||||
更多安全事件
|
||||
<text class="iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_monitor" style="width: 100%;">
|
||||
<image style="width: 100%;" src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/background.png" mode=""></image>
|
||||
</view>
|
||||
<view class="content_data">
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">设备名称</text>
|
||||
<text class="text">安全监控相机</text>
|
||||
</view>
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">开机时间</text>
|
||||
<text class="text">2024-02-11 08:00:45</text>
|
||||
</view>
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">安全事件</text>
|
||||
<text class="text">检测到指定区域内有目标越过警戒线</text>
|
||||
</view>
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">检测时间</text>
|
||||
<text class="text">2024-01-11 19:09:56</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
toList(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceStatus/detectionEventList'
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.body-view{padding: 12px 13px;}
|
||||
.theme_color{
|
||||
display: flex;align-items: center;
|
||||
.drop{width: 4px;height: 4px;background: $uni-text-color-primary;display: inline-block;margin-right: 6px;border-radius: 50%;}
|
||||
.top_right{color: $uni-text-color-primary;}
|
||||
}
|
||||
.device_row{padding: 6px 0;display: flex;align-items: center;
|
||||
.name {flex-basis: 70px;}
|
||||
}
|
||||
.flex_layout{
|
||||
align-items: center;
|
||||
}
|
||||
.status{
|
||||
background: $uni-bg-color-success;
|
||||
margin-left: 8px;
|
||||
border-radius: 20px;
|
||||
padding: 3px 10px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.drop{
|
||||
width: 4px;
|
||||
height: 4px;
|
||||
border-radius: 50%;
|
||||
background: $uni-bg-color-whith;
|
||||
display: inline-block;
|
||||
margin-right: 6px;
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
230
pages/deviceStatus/deviceStatus.vue
Normal file
@ -0,0 +1,230 @@
|
||||
<template>
|
||||
<view class="page_padding">
|
||||
<view class="padd_bot12 font14 flex_layout">
|
||||
<text>硬件设备状态</text>
|
||||
<view class="status font12"><text class="drop"></text>在线</view>
|
||||
</view>
|
||||
<view class="body-view contentboxsty">
|
||||
<view class="content-top">
|
||||
<view class="content-left" @click="prveClick">
|
||||
<text class="iconfont icon-gengduo more_icon"></text>
|
||||
</view>
|
||||
<view class="content-scroll">
|
||||
<view class="center-cut-menu">
|
||||
<scroll-view scroll-x="true" show-scrollbar="false" scroll-with-animation="true" :scroll-left="scrollLeft" class="scroll-view horizontalScrollView" >
|
||||
<view class="scroll-item" :style="'width:'+itemWidth+'px'" v-for="(item, index) in list" :key="index" @click="changeMenu(index)">
|
||||
<text class="item-text" :class="curIndex == index? 'active' : ''">{{item.name}}</text>
|
||||
</view>
|
||||
</scroll-view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content-right" @click="nextClick">
|
||||
<text class="iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<swiper class="swiper-box-list" circular="true" easing-function="linear" :current="curIndex" @change="swiperChange">
|
||||
<swiper-item class="swiper-topic-list" v-for="item in swiperDateList" :key="item.id">
|
||||
<view class="swiper-item">
|
||||
<view class="img">
|
||||
<image style="width: 100%;height: 100%;" :src="item.img"></image>
|
||||
</view>
|
||||
<view class="font14">
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">设备名称</text>
|
||||
<text class="text">双头立锯</text>
|
||||
<view @click="toCamera()" class="videoIcon text" style="position: absolute;right: 0;">
|
||||
<text class="iconfont icon-a-shexiangtou_shiti1"></text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">开机时间</text>
|
||||
<text class="text">2024-02-11 08:00:45</text>
|
||||
</view>
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">保养到期日</text>
|
||||
<text class="text">2024-02-11 08:00:45</text>
|
||||
</view>
|
||||
<view class="device_row">
|
||||
<text class="name font_bold">今日停机</text>
|
||||
<text class="text">5次</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</swiper-item>
|
||||
</swiper>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
list: [{
|
||||
id: 1,
|
||||
name: '多片锯',
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
name: '双头带锯',
|
||||
},
|
||||
{
|
||||
id: 3,
|
||||
name: '视觉分析',
|
||||
},
|
||||
{
|
||||
id: 4,
|
||||
name: '卧锯带锯',
|
||||
},
|
||||
{
|
||||
id: 5,
|
||||
name: '上料机架',
|
||||
},
|
||||
],
|
||||
// Tab切换内容
|
||||
swiperDateList: [
|
||||
{
|
||||
id: 1,
|
||||
content: '1',
|
||||
img:'http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/duopian.png'
|
||||
},
|
||||
{
|
||||
id: 2,
|
||||
content: '2',
|
||||
img:'http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/liju.png'
|
||||
},
|
||||
{
|
||||
id: 3,
|
||||
content: '3',
|
||||
img:'http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/shijue.png'
|
||||
},
|
||||
{
|
||||
id: 4,
|
||||
content: '4',
|
||||
img:'http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/woshi.png'
|
||||
},
|
||||
{
|
||||
id: 5,
|
||||
content: '5',
|
||||
img:'http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/shang.png'
|
||||
},
|
||||
],
|
||||
itemWidth: 90,
|
||||
curIndex: 0,
|
||||
scrollLeft: 0,
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
|
||||
},
|
||||
onReady() {
|
||||
this.getScrollW();
|
||||
},
|
||||
methods: {
|
||||
toCamera(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceStatus/deviceCamera'
|
||||
})
|
||||
},
|
||||
// 区域宽度,子元素的宽度以及距离左边栏的距离
|
||||
getScrollW() {
|
||||
let itemWidth = 0;
|
||||
let query = uni.createSelectorQuery().in(this);
|
||||
query.select('.scroll-view').boundingClientRect(data => {
|
||||
this.itemWidth = (data.width/3).toFixed(0);
|
||||
itemWidth = (data.width/3).toFixed(0);
|
||||
this.getItemWidth(itemWidth);
|
||||
}).exec();
|
||||
},
|
||||
getItemWidth(num){
|
||||
let query = uni.createSelectorQuery().in(this);
|
||||
query.selectAll('.scroll-item').boundingClientRect(data => {
|
||||
let dataLen = data.length;
|
||||
for (let i = 0; i < dataLen; i++) {
|
||||
this.list[i].width = Number(num);
|
||||
this.list[i].left = Number(num) + Number(data[i].left);
|
||||
}
|
||||
}).exec()
|
||||
},
|
||||
|
||||
// 选择标题
|
||||
changeMenu(index) {
|
||||
this.curIndex = index;
|
||||
this.scrollLeft = 0;
|
||||
for (let i = 0; i < index - 1; i++) {
|
||||
this.scrollLeft += this.list[i].width;
|
||||
};
|
||||
},
|
||||
swiperChange(e) {
|
||||
let index = e.detail.current;
|
||||
this.changeMenu(index);
|
||||
},
|
||||
prveClick(){
|
||||
this.curIndex = this.curIndex==0? 0 : this.curIndex-1;
|
||||
},
|
||||
nextClick(){
|
||||
this.curIndex = this.curIndex < this.list.length-1? this.curIndex+1 : this.curIndex;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.body-view{
|
||||
height: 450px;
|
||||
.content-top{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.content-left{flex-basis: 30px;text-align: center;
|
||||
.more_icon{display: inline-block;transform: scaleX(-1);}
|
||||
}
|
||||
.content-scroll{flex: 1;overflow: hidden;}
|
||||
.center-cut-menu {width: 100%;height: 100rpx;
|
||||
.scroll-view {height: 100rpx;white-space: nowrap;
|
||||
.scroll-item {height: 100rpx;padding: 0 20rpx;display: inline-block;text-align: center;box-sizing: border-box;
|
||||
.item-text {font-size: 14px;line-height: 100rpx;
|
||||
&.active {
|
||||
font-size: 17px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.content-right{flex-basis: 30px;text-align: center;}
|
||||
}
|
||||
.swiper-box-list{height: 400px;padding:0 12px;
|
||||
.device_row:first-child{margin-top: 6px;}
|
||||
.device_row{padding: 6px 0;display: flex;
|
||||
.name{flex-basis: 82px;}
|
||||
}
|
||||
}
|
||||
}
|
||||
.flex_layout{
|
||||
align-items: center;
|
||||
}
|
||||
.swiper-item{
|
||||
.img{
|
||||
width: 100%;
|
||||
height: 250px;
|
||||
}
|
||||
.videoIcon{
|
||||
color: $uni-color-primary;
|
||||
}
|
||||
}
|
||||
.status{
|
||||
background: $uni-bg-color-success;
|
||||
margin-left: 8px;
|
||||
border-radius: 20px;
|
||||
padding: 3px 10px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
.drop{
|
||||
width: 4px;
|
||||
height: 4px;
|
||||
border-radius: 50%;
|
||||
background: $uni-bg-color-whith;
|
||||
display: inline-block;
|
||||
margin-right: 6px;
|
||||
}
|
||||
}
|
||||
</style>
|
169
pages/equipmentManage/bindingDevice.vue
Normal file
@ -0,0 +1,169 @@
|
||||
<template>
|
||||
<!-- 绑定安全生产监控相机 -->
|
||||
<view>
|
||||
<view class="page_padding">
|
||||
<view class="page_content contentboxsty font13">
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">串流推流Url</view>
|
||||
<view class="text">
|
||||
<input v-model="form.stream_url" placeholder="请输入串流推流Url" disabled/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">AppName</view>
|
||||
<view class="text">
|
||||
<input v-model="form.app_name" placeholder="请输入APP名称"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row noborbot">
|
||||
<view class="name"></view>
|
||||
<view class="tip">
|
||||
不超过256字符,支持数字、大小写字母、短划线(-)、下划线(_)、等号(=)。
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">StreamName</view>
|
||||
<view class="text">
|
||||
<input v-model="form.stream_name" placeholder="请输入StreamName"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row noborbot">
|
||||
<view class="name"></view>
|
||||
<view class="tip">
|
||||
不超过256字符,支持数字、大小写字母、短划线(-)、下划线(_)、等号(=)。
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备IP</view>
|
||||
<view class="text">
|
||||
<input v-model="form.monitor_ip" placeholder="请输入设备IP"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">端口</view>
|
||||
<view class="text">
|
||||
<input v-model="form.monitor_port" placeholder="请输入设备端口"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">用户名</view>
|
||||
<view class="text">
|
||||
<input v-model="form.monitor_account" placeholder="请输入您的用户名"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">密码</view>
|
||||
<view class="text">
|
||||
<input password type="safe-password" v-model="form.monitor_password" placeholder="请输入密码"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">监控推流权限</view>
|
||||
<view class="text flex_layout">
|
||||
<view class="switch" @click="form.stream_type=1">
|
||||
<view v-if="form.stream_type ==1" class="t-icon t-icon-qiyong1 contenticon"></view>
|
||||
<view v-else class="t-icon t-icon-jinyong1 contenticon"></view>
|
||||
<text class="text">Token验证</text>
|
||||
</view>
|
||||
<view class="switch" @click="form.stream_type=2">
|
||||
<view v-if="form.stream_type ==2" class="t-icon t-icon-qiyong1 contenticon"></view>
|
||||
<view v-else class="t-icon t-icon-jinyong1 contenticon"></view>
|
||||
<text class="text">禁用</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="bottom_but flex_layout">
|
||||
<view class="but_color font13" @click="save">保存</view>
|
||||
<view class="font13" @click="cancel">取消</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form:{
|
||||
id:'',
|
||||
stream_url:'',
|
||||
app_name:'',
|
||||
stream_name:'',
|
||||
stream_type:1,
|
||||
monitor_ip:'',
|
||||
monitor_port:'',
|
||||
monitor_account:'',
|
||||
monitor_password:''
|
||||
}
|
||||
}
|
||||
},
|
||||
onLoad(option) {
|
||||
this.form.id = option.id;
|
||||
this.getVideo(option.id);
|
||||
},
|
||||
onReady() {
|
||||
|
||||
},
|
||||
methods: {
|
||||
getVideo(id){
|
||||
this.$api.request('/get.video.config',{id:id}).then(res=>{
|
||||
this.form.stream_url = res.data.stream_url;
|
||||
if(res.data.app_name && res.data.eq_name){
|
||||
this.form.app_name = res.data.app_name;
|
||||
this.form.stream_name = res.data.stream_name;
|
||||
this.form.stream_type = res.data.stream_type;
|
||||
this.form.monitor_ip = res.data.monitor_ip;
|
||||
this.form.monitor_port = res.data.monitor_port;
|
||||
this.form.monitor_account = res.data.monitor_account;
|
||||
this.form.monitor_password = res.data.monitor_password;
|
||||
}
|
||||
}).catch(err=>{
|
||||
|
||||
})
|
||||
},
|
||||
save(){
|
||||
this.$api.postFuncLoading('/bind.video.config',this.form).then(res=>{
|
||||
this.parentClick();
|
||||
this.reset();
|
||||
this.$wf.toast({type:'success',text:'保存成功'});
|
||||
}).catch(err=>{
|
||||
|
||||
})
|
||||
},
|
||||
cancel(){
|
||||
this.reset();
|
||||
},
|
||||
reset(){
|
||||
this.form.app_name = '';
|
||||
this.form.stream_name = '';
|
||||
this.form.stream_type = 1;
|
||||
this.form.monitor_ip = '';
|
||||
this.form.monitor_port = '';
|
||||
this.form.monitor_account = '';
|
||||
this.form.monitor_password = '';
|
||||
},
|
||||
parentClick(){
|
||||
const pages = getCurrentPages();
|
||||
if (pages.length >= 2) {
|
||||
const prevPage = pages[pages.length - 2];
|
||||
prevPage.$vm.getList();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_content{padding: 0 12px;}
|
||||
.content_row{display: flex;border-bottom: 1px solid #2D3A6F;height: 44px;align-items: center;
|
||||
.name{flex-basis: 96px;}
|
||||
.text{flex: 1;}
|
||||
.tip{width: 70%;font-size: 10px;color: #666;}
|
||||
.flex_layout{
|
||||
.contenticon{width: 16px;height: 16px;}
|
||||
.text{padding: 0 20px 0 5px;}
|
||||
}
|
||||
}
|
||||
.switch{display: flex;align-items: center;}
|
||||
</style>
|
71
pages/equipmentManage/deviceDetail.vue
Normal file
@ -0,0 +1,71 @@
|
||||
<template>
|
||||
<view class="page_padding">
|
||||
<view class="detail_list contentboxsty page_content font13">
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备</view>
|
||||
<view class="text">{{form.eq_name}}</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备名称</view>
|
||||
<view class="text">{{form.name}}</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备功率</view>
|
||||
<view class="text">{{form.power}}</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备IP</view>
|
||||
<view class="text">{{form.equipment_configs.length>0? form.equipment_configs[0].ip:''}}</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">端口</view>
|
||||
<view class="text">{{form.equipment_configs.length>0? form.equipment_configs[0].port:''}}</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">状态</view>
|
||||
<view class="text">{{form.active_status==true?'启用':'禁用'}}</view>
|
||||
</view>
|
||||
<view class="textarea_row">
|
||||
<view class="name font_bold font13">备注</view>
|
||||
<view class="text textareaText">
|
||||
{{form.remark}}
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form:{
|
||||
equipment_configs:[
|
||||
{ip:'',port:''}
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
onLoad(options){
|
||||
this.getDetail(options.id);
|
||||
},
|
||||
methods: {
|
||||
getDetail(id){
|
||||
this.$api.postFuncLoading('/device.info',{id:id}).then(res=>{
|
||||
this.form = res.data
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.content_row{display: flex;align-items: center;padding-top: 17px;
|
||||
.name{flex-basis: 80px;}
|
||||
.text{flex: 1;}
|
||||
}
|
||||
.textarea_row{
|
||||
.name{padding: 17px 0;}
|
||||
.textareaText{min-height: 80px;}
|
||||
}
|
||||
</style>
|
229
pages/equipmentManage/editDevice.vue
Normal file
@ -0,0 +1,229 @@
|
||||
<template>
|
||||
<page-meta>
|
||||
<navigation-bar :title="this.form.id && this.form.id > 0?'编辑设备':'添加设备'"></navigation-bar>
|
||||
</page-meta>
|
||||
<view class="page_padding bot_padding">
|
||||
<view class="page_content contentboxsty font13">
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">选择设备</view>
|
||||
<pickerSelect class="comView" @change="equipmentChange" :list="setMap.equipment" :id="form.eq_no" placeholder="请选择设备" />
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备自定义名称</view>
|
||||
<view class="comView">
|
||||
<input v-model="form.name" placeholder="请输入设备名称"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备编号</view>
|
||||
<view class="comView">
|
||||
<input v-model="form.code" placeholder="请输入设备编号"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备功率</view>
|
||||
<view class="comView">
|
||||
<input v-model="form.power" placeholder="请输入设备功率"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">设备IP</view>
|
||||
<view class="comView">
|
||||
<input v-model="form.config[0].ip" placeholder="请输入设备IP"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">端口</view>
|
||||
<view class="comView">
|
||||
<input v-model="form.config[0].port" placeholder="请输入设备端口"/>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">型号</view>
|
||||
<view class="flex_layout comView">
|
||||
<view class="switch" @click="form.config[0].plc_model = 'H3U'">
|
||||
<view v-if="form.config[0].plc_model=='H3U'" class="t-icon t-icon-qiyong1 contenticon"></view>
|
||||
<view v-else class="t-icon t-icon-jinyong1 contenticon"></view>
|
||||
<text class="text">H3U</text>
|
||||
</view>
|
||||
<view class="switch" @click="form.config[0].plc_model = 'H5U'">
|
||||
<view v-if="form.config[0].plc_model=='H5U'" class="t-icon t-icon-qiyong1 contenticon"></view>
|
||||
<view v-else class="t-icon t-icon-jinyong1 contenticon"></view>
|
||||
<text class="text">H5U</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">逻辑控制器(PLC)</view>
|
||||
<pickerSelect class="comView" :list="setMap.plc" :id="form.plc_lj" placeholder="请选择设备" />
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<view class="name font_bold">状态</view>
|
||||
<view class="flex_layout comView">
|
||||
<view class="switch" @click="form.active_status=true">
|
||||
<view v-if="form.active_status" class="t-icon t-icon-qiyong1 contenticon"></view>
|
||||
<view v-else class="t-icon t-icon-jinyong1 contenticon"></view>
|
||||
<text class="text">启用</text>
|
||||
</view>
|
||||
<view class="switch" @click="form.active_status=false">
|
||||
<view v-if="!form.active_status" class="t-icon t-icon-qiyong1 contenticon"></view>
|
||||
<view v-else class="t-icon t-icon-jinyong1 contenticon"></view>
|
||||
<text class="text">禁用</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="textarea_row">
|
||||
<view class="name font_bold">设置备注</view>
|
||||
<view class="textarea">
|
||||
<textarea placeholder="请输入备注..." v-model="form.remark" cursor-spacing="180px" :auto-blur="true" placeholder-class="placeholderStyle" />
|
||||
</view>
|
||||
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="bottom_but flex_layout">
|
||||
<view class="font13 but_color" @click="save">保存</view>
|
||||
<view class="font13" @click="cancel">取消</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
setMap:{
|
||||
equipment:[],
|
||||
plc:[
|
||||
{name:'汇川',value:1}
|
||||
]
|
||||
},
|
||||
|
||||
form:{
|
||||
id:'',
|
||||
eq_no:'',
|
||||
name:'',
|
||||
code:'',
|
||||
power:'',
|
||||
remark:'',
|
||||
active_status:true,
|
||||
plc_lj:1,
|
||||
config:[
|
||||
{
|
||||
eq_type:'',
|
||||
ip:'',
|
||||
port:'',
|
||||
plc_model:'H3U'
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
|
||||
},
|
||||
onLoad(option) {
|
||||
this.form.id = option.id;
|
||||
if(option.id!='undefined'){
|
||||
this.getOrderInfo(option.id);
|
||||
}
|
||||
},
|
||||
onReady() {
|
||||
this.getEquipment();
|
||||
},
|
||||
methods: {
|
||||
getOrderInfo(id){
|
||||
this.$api.postFuncLoading('/device.info',{id:id}).then(res=>{
|
||||
this.form = {
|
||||
id:res.data.id,
|
||||
eq_no:res.data.eq_no,
|
||||
name:res.data.name,
|
||||
code:res.data.code,
|
||||
power:res.data.power,
|
||||
remark:res.data.remark,
|
||||
active_status:res.data.active_status,
|
||||
plc_lj:1,
|
||||
config:[
|
||||
{
|
||||
eq_type:res.data.equipment_configs[0].eq_type,
|
||||
ip:res.data.equipment_configs[0].ip,
|
||||
port:res.data.equipment_configs[0].port,
|
||||
plc_model:res.data.equipment_configs[0].plc_model
|
||||
}
|
||||
]
|
||||
}
|
||||
}).catch(err=>{
|
||||
|
||||
})
|
||||
},
|
||||
getEquipment(){
|
||||
this.$api.request('/equipment.select',{}).then(res=>{
|
||||
res.data.forEach(item=>{
|
||||
item.name = item.eq_name;
|
||||
item.value = item.eq_no;
|
||||
})
|
||||
this.setMap['equipment'] = res.data;
|
||||
})
|
||||
},
|
||||
equipmentChange(e){
|
||||
this.form.eq_no = e.value;
|
||||
this.form.name = e.name;
|
||||
},
|
||||
save(){
|
||||
if(!(this.form.id && this.form.id>0)){
|
||||
delete this.form.id
|
||||
}
|
||||
this.$api.postFuncLoading('/equipment.add',this.form).then(res=>{
|
||||
this.parentClick();
|
||||
this.reset();
|
||||
this.$wf.toast({type:'success',text:'保存成功'});
|
||||
})
|
||||
},
|
||||
cancel(){
|
||||
this.reset();
|
||||
},
|
||||
reset(){
|
||||
this.form = {
|
||||
id:'',
|
||||
eq_no:'',
|
||||
name:'',
|
||||
code:'',
|
||||
power:'',
|
||||
remark:'',
|
||||
active_status:true,
|
||||
plc_lj:1,
|
||||
config:[
|
||||
{
|
||||
eq_type:'',
|
||||
ip:'',
|
||||
port:'',
|
||||
plc_model:'H3U'
|
||||
}
|
||||
]
|
||||
};
|
||||
},
|
||||
parentClick(){
|
||||
const pages = getCurrentPages();
|
||||
if (pages.length >= 2) {
|
||||
const prevPage = pages[pages.length - 2];
|
||||
prevPage.$vm.getList();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_name{margin-bottom: 10px;}
|
||||
.page_content{padding: 0 12px 13px;}
|
||||
.content_row{display: flex;border-bottom: 1px solid #2D3A6F;height: 44px;align-items: center;
|
||||
.name{flex-basis: 110px;}
|
||||
.switch{display: flex;align-items: center;
|
||||
.contenticon{font-size: 15px;}
|
||||
.text{padding: 0 20px 0 5px;}
|
||||
}
|
||||
}
|
||||
.textarea_row{
|
||||
.name{padding: 12px 0;}
|
||||
.textarea{border-radius: 4px;background: $uni-bg-color-placeholder;padding:10px 12px;}
|
||||
}
|
||||
</style>
|
138
pages/equipmentManage/equipmentManage.vue
Normal file
@ -0,0 +1,138 @@
|
||||
<template>
|
||||
<!-- 设备管理 -->
|
||||
<view class="page_padding bot_padding columnFlex">
|
||||
<view class="flexBox">
|
||||
<view v-for="(item,index) in list" :key="index" >
|
||||
<view class="page_list contentboxsty font13" @click="toDeviceDetail(item.id)">
|
||||
<view class="list_row">
|
||||
<view class="name font_bold">设备名称</view>
|
||||
<view class="text">
|
||||
{{item.name}}
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_row padd_top12">
|
||||
<view class="name font_bold">设备IP/端口</view>
|
||||
<view class="text">{{item.equipment_monitor_config?item.equipment_monitor_config.monitor_ip+'/'+item.equipment_monitor_config.monitor_port:'-'}}</view>
|
||||
</view>
|
||||
<view class="list_row padd_top12">
|
||||
<view class="name font_bold">已绑定设备</view>
|
||||
<view class="text">
|
||||
{{item.equipment_monitor_config && item.equipment_monitor_config.eq_name?item.equipment_monitor_config.eq_name:'-'}}
|
||||
</view>
|
||||
</view>
|
||||
<view class="rightBtnView">
|
||||
<view class="iconfont icon-bianji font18" @click.stop="toAddDevice(item.id)"></view>
|
||||
<view class="iconfont icon-bangding font18" @click.stop="toBindingDevice(item.id)"></view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<loadMore :noData="loadParams.noData" :loading="loadParams.loading" :loadEnd="loadParams.loadEnd" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="page_bottom_button">
|
||||
<view class="page_add" @click="toAddDevice()">
|
||||
<view class="icon iconfont icon-tianjia font20"></view>
|
||||
<text class="font14">添加</text>
|
||||
</view>
|
||||
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
params:{
|
||||
page:1,
|
||||
pageSize:10,
|
||||
},
|
||||
loadParams:{
|
||||
noData:false,
|
||||
loading:false,
|
||||
loadEnd:false
|
||||
},
|
||||
list:[],
|
||||
}
|
||||
},
|
||||
onReady() {
|
||||
this.getList();
|
||||
},
|
||||
// 上拉刷新
|
||||
onPullDownRefresh(){
|
||||
this.params.page = 1;
|
||||
this.loadParams = {
|
||||
noData:false,
|
||||
loading:false,
|
||||
loadEnd:false
|
||||
};
|
||||
this.getList(2);
|
||||
},
|
||||
// 加载下一页
|
||||
onReachBottom(){
|
||||
if(!(this.loadParams.loadEnd || this.loadParams.noData)){
|
||||
this.loadParams.loading = true;
|
||||
this.params.page ++;
|
||||
this.getList();
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
getList(type=1){
|
||||
if(this.params.page == 1){
|
||||
uni.showLoading({
|
||||
title: '加载中',
|
||||
mask: true
|
||||
})
|
||||
}
|
||||
this.$api.request('/equipment.mag',this.params).then(res=>{
|
||||
if(type ==2){
|
||||
uni.stopPullDownRefresh();
|
||||
}
|
||||
setTimeout( ()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
|
||||
this.loadParams.loading = false;
|
||||
if(res.data.rows.length ==0 && this.params.page == 1){
|
||||
this.loadParams.noData = true;
|
||||
}
|
||||
if(res.data.rows.length>0 && res.data.rows.length < this.params.pageSize){
|
||||
this.loadParams.loadEnd = true;
|
||||
}
|
||||
if(this.params.page == 1){
|
||||
this.list = res.data.rows;
|
||||
}else{
|
||||
this.list = this.list.concat(res.data.rows);
|
||||
}
|
||||
}).catch(err=>{
|
||||
setTimeout(()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
})
|
||||
},
|
||||
//详情
|
||||
toDeviceDetail(id){
|
||||
uni.navigateTo({
|
||||
url:'/pages/equipmentManage/deviceDetail?id='+id
|
||||
})
|
||||
},
|
||||
toAddDevice(params){
|
||||
uni.navigateTo({
|
||||
url:'/pages/equipmentManage/editDevice?id='+params
|
||||
})
|
||||
},
|
||||
toBindingDevice(id){
|
||||
uni.navigateTo({
|
||||
url:'/pages/equipmentManage/bindingDevice?id='+id
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_list{padding: 12px;position: relative;}
|
||||
.list_row{display: flex;align-items: center;}
|
||||
.list_row .name{flex-basis: 84px;text-align: right;padding-right: 12px;box-sizing: border-box;}
|
||||
.list_row .text{flex: 1;display: flex;justify-content: space-between;align-items: center;}
|
||||
.rightBtnView{position: absolute;right: 12px;top: 12px;height: calc(100% - 24px);display: flex;flex-direction: column;justify-content: space-between;}
|
||||
</style>
|
@ -1,12 +1,164 @@
|
||||
<template>
|
||||
<view class="home">
|
||||
|
||||
<view class="container home">
|
||||
<view class="home_head">
|
||||
<view class="iconfont icon-chaojiguanliyuan accounticon"></view>
|
||||
<view class="name">Ykxiao 超级管理员</view>
|
||||
<view class="name" v-if="userName==''" @click="toLogin()">未登录</view>
|
||||
<view class="name" v-else>{{userName}} </view>
|
||||
<view class="iconfont icon-xiaoxitongzhi notifyicon" @click="toMessage()"></view>
|
||||
<view class="iconfont icon-shezhi setupicon"></view>
|
||||
</view>
|
||||
<view class="home_content">
|
||||
<view class="content_box">
|
||||
<view class="content_title">设备信息</view>
|
||||
<view class="device_data">
|
||||
<view class="device_module">
|
||||
<view class="module_left">
|
||||
<view class="icon_background">
|
||||
<view class="iconfont icon-WIFI_on contenticon"></view>
|
||||
</view>
|
||||
<view class="font13">
|
||||
在线设备
|
||||
</view>
|
||||
</view>
|
||||
<view class="module_right">
|
||||
<view class="top">
|
||||
▴2.89%
|
||||
</view>
|
||||
<view class="num font22">
|
||||
1,567
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="device_module">
|
||||
<view class="module_left">
|
||||
<view class="icon_background">
|
||||
<view class="iconfont icon-WIFI_off contenticon"></view>
|
||||
</view>
|
||||
<view class="font13">
|
||||
离线设备
|
||||
</view>
|
||||
</view>
|
||||
<view class="module_right">
|
||||
<view class="top">
|
||||
▴2.89%
|
||||
</view>
|
||||
<view class="num font22">
|
||||
1,567
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="device_module">
|
||||
<view class="module_left">
|
||||
<view class="icon_background">
|
||||
<view class="iconfont icon-setting contenticon"></view>
|
||||
</view>
|
||||
<view class="font13">
|
||||
维修保养
|
||||
</view>
|
||||
</view>
|
||||
<view class="module_right">
|
||||
<view class="top">
|
||||
▴2.89%
|
||||
</view>
|
||||
<view class="num font22">
|
||||
1,567
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="device_module">
|
||||
<view class="module_left">
|
||||
<view class="icon_background">
|
||||
<view class="iconfont icon-broken contenticon"></view>
|
||||
</view>
|
||||
<view class="font13">
|
||||
故障频次
|
||||
</view>
|
||||
</view>
|
||||
<view class="module_right">
|
||||
<view class="top">
|
||||
▴2.89%
|
||||
</view>
|
||||
<view class="num font22">
|
||||
1,567
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="device_module">
|
||||
<view class="module_left">
|
||||
<view class="icon_background">
|
||||
<view class="iconfont icon-brokenrate contenticon"></view>
|
||||
</view>
|
||||
<view class="font13">
|
||||
设备故障率
|
||||
</view>
|
||||
</view>
|
||||
<view class="module_right">
|
||||
<view class="top">
|
||||
▴2.89%
|
||||
</view>
|
||||
<view class="num font22">
|
||||
1,567
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="device_module">
|
||||
<view class="module_left">
|
||||
<view class="icon_background">
|
||||
<view class="iconfont icon-weixiubaoyangpinshuai contenticon"></view>
|
||||
</view>
|
||||
<view class="font13">
|
||||
维修保养频率
|
||||
</view>
|
||||
</view>
|
||||
<view class="module_right">
|
||||
<view class="top">
|
||||
▴2.89%
|
||||
</view>
|
||||
<view class="num font22">
|
||||
1,567
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_box">
|
||||
<view class="content_title">能耗信息</view>
|
||||
<view class="energy_data">
|
||||
<view class="iconfont icon-dianliang energy_icon"></view>
|
||||
<view class="energy_name">
|
||||
<view class="font13">
|
||||
用电量
|
||||
</view>
|
||||
<view class="font14">
|
||||
345.00
|
||||
</view>
|
||||
</view>
|
||||
<view class="energy_image">
|
||||
<image src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/yongdian.png" alt="" />
|
||||
</view>
|
||||
<view class="energy_number font20">
|
||||
41.443
|
||||
</view>
|
||||
</view>
|
||||
<view class="energy_data mar_top12">
|
||||
<view class="iconfont icon-yasuokongqi energy_icon"></view>
|
||||
<view class="energy_name">
|
||||
<view class="font13">
|
||||
用气量
|
||||
</view>
|
||||
<view class="font14">
|
||||
345.00
|
||||
</view>
|
||||
</view>
|
||||
<view class="energy_image">
|
||||
<image src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/yongqi.png" alt="" />
|
||||
</view>
|
||||
<view class="energy_number font20">
|
||||
41.443
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_box">
|
||||
<view class="content_title">工单管理</view>
|
||||
<view class="content_data">
|
||||
@ -14,61 +166,87 @@
|
||||
<view class="t-icon t-icon-shengchangongdan contenticon"></view>
|
||||
<view class="contentname">生产工单</view>
|
||||
</view>
|
||||
<view class="content_module">
|
||||
<view class="t-icon t-icon-gongdanjindu contenticon"></view>
|
||||
<view class="contentname">工单进度</view>
|
||||
</view>
|
||||
<view class="content_module">
|
||||
<view class="t-icon t-icon-gongdanchucaishuai contenticon"></view>
|
||||
<view class="contentname">工单出材率</view>
|
||||
</view>
|
||||
<view class="content_module">
|
||||
<view class="t-icon t-icon-shengchanbaobiao contenticon"></view>
|
||||
<view class="contentname">生产报表</view>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
</view>
|
||||
<view class="content_box">
|
||||
<view class="content_title">生产排程</view>
|
||||
<view class="content_data">
|
||||
<view class="content_module">
|
||||
<view class="content_module" @click="toSchedul()">
|
||||
<view class="t-icon t-icon-paichengguanli contenticon"></view>
|
||||
<view class="contentname">排程管理</view>
|
||||
</view>
|
||||
<view class="content_module">
|
||||
<view class="content_module" @click="toSchedule()">
|
||||
<view class="t-icon t-icon-gongdanjindu contenticon"></view>
|
||||
<view class="contentname">工单进度</view>
|
||||
</view>
|
||||
<view class="content_module" @click="toMaterialYield()">
|
||||
<view class="t-icon t-icon-gongdanchucaishuai contenticon"></view>
|
||||
<view class="contentname">工单出材率</view>
|
||||
</view>
|
||||
<!-- <view class="content_module">
|
||||
<view class="t-icon t-icon-paichengshichang contenticon"></view>
|
||||
<view class="contentname">排程时长</view>
|
||||
</view>
|
||||
</view> -->
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_box">
|
||||
<view class="content_title">设备管理</view>
|
||||
<view class="content_data">
|
||||
<view class="content_module">
|
||||
<view class="content_module" @click="toEquipmentManage()">
|
||||
<view class="t-icon t-icon-shebeiguanli contenticon"></view>
|
||||
<view class="contentname">设备设置</view>
|
||||
<view class="contentname">设备管理</view>
|
||||
</view>
|
||||
<view class="content_module">
|
||||
<view class="content_module" @click="toDeviceStatus()">
|
||||
<view class="t-icon t-icon-shebeizhuangtai contenticon"></view>
|
||||
<view class="contentname">设备状态</view>
|
||||
</view>
|
||||
<view class="content_module">
|
||||
<view class="content_module" @click="toDeviceRepair()">
|
||||
<view class="t-icon t-icon-shebeibaoxiu contenticon"></view>
|
||||
<view class="contentname">设备保修</view>
|
||||
<view class="contentname">设备报修</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
<tab-bar :current-page="0"></tab-bar>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import tabBar from "@/components/customTabBar/index"
|
||||
export default {
|
||||
components:{
|
||||
tabBar
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
userName: '',
|
||||
}
|
||||
},
|
||||
// onLoad() {
|
||||
// this.userName = uni.getStorageSync('demu_mes_user_name')
|
||||
// },
|
||||
onShow(){
|
||||
this.userName = uni.getStorageSync('demu_mes_user_name')
|
||||
},
|
||||
// created() {
|
||||
// },
|
||||
mounted() {
|
||||
this.userName = uni.getStorageSync('demu_mes_user_name')
|
||||
|
||||
},
|
||||
methods: {
|
||||
//
|
||||
toLogin(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/login/login'
|
||||
})
|
||||
},
|
||||
//跳转消息页
|
||||
toMessage(){
|
||||
uni.navigateTo({
|
||||
@ -78,58 +256,108 @@
|
||||
//跳转生产工单页
|
||||
toProductionOrder(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/index/productionOrder'
|
||||
url:'/pages/production/productionOrder'
|
||||
})
|
||||
},
|
||||
// 工单排程
|
||||
toSchedul(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/schedul/list'
|
||||
})
|
||||
},
|
||||
//跳转工单进度页
|
||||
toSchedule(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/index/schedule'
|
||||
})
|
||||
},
|
||||
//跳转工单出材率页
|
||||
toMaterialYield(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/index/materialYield'
|
||||
})
|
||||
},
|
||||
//跳转设备管理页面
|
||||
toEquipmentManage(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/equipmentManage/equipmentManage'
|
||||
})
|
||||
},
|
||||
//跳转设备报修页
|
||||
toDeviceRepair(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceRepair/deviceRepair'
|
||||
})
|
||||
},
|
||||
//跳转设备状态
|
||||
toDeviceStatus(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/deviceStatus/deviceStatus'
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
<style lang="scss">
|
||||
|
||||
/* .icon {
|
||||
width: 80upx;
|
||||
height: 80upx;
|
||||
vertical-align: -0.15em;
|
||||
fill: currentColor;
|
||||
overflow: hidden;
|
||||
} */
|
||||
.home {
|
||||
height: 100vh;
|
||||
/* background-color: #060B26; */
|
||||
padding: 0 10px;
|
||||
font-size: 14px;
|
||||
}
|
||||
.home_head{height: 40px;display: flex;position: relative;align-items: center;padding-bottom: 5px;}
|
||||
.home_head .name{flex:1;}
|
||||
.home {padding: 0 10px;font-size: 14px;
|
||||
.home_head{height: 40px;display: flex;position: relative;align-items: center;padding-bottom: 5px;
|
||||
.name{flex:1;}
|
||||
.accounticon{
|
||||
/* width: 20px;
|
||||
height: 20px; */
|
||||
margin-right: 5px;
|
||||
color: #fff;
|
||||
color: $uni-text-color-inverse;
|
||||
font-size: 20px;
|
||||
}
|
||||
.notifyicon{font-size: 20px;padding-right: 20px;}
|
||||
.setupicon{font-size: 20px;}
|
||||
.home_content{
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
.content_title{
|
||||
line-height: 25px;
|
||||
font-size: 16px;
|
||||
}
|
||||
.content_data{padding: 10px 0;display: flex;position: relative;align-items: center;text-align: center;height: 98px;}
|
||||
.content_module{
|
||||
width: 25%;
|
||||
margin: 10px 1%;
|
||||
height: 98px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
flex-direction: column;
|
||||
background-color: #009688;
|
||||
.home_content{padding-bottom: 100px;
|
||||
.content_title{line-height: 25px;font-size: 16px;padding: 15px 0;}
|
||||
.device_data{display: flex;flex-wrap: wrap;
|
||||
.device_module{
|
||||
width: calc(50% - 6px); /* 计算每个块的宽度(根据需要调整)*/
|
||||
// background-color: #ccc; /* 设置背景色(根据需要调整)*/
|
||||
background: $uni-bg-color-primary;
|
||||
margin:6px;
|
||||
padding: 10px 14px;
|
||||
border-radius: 8px;
|
||||
display: flex;
|
||||
.module_left{width: 60%;
|
||||
.icon_background{width: 32px;height: 32px;background: $uni-bg-color-info;border-radius: 8px; display: flex;align-items: center;justify-content: center;margin-bottom: 4px;}
|
||||
}
|
||||
.module_right{width: 40%;
|
||||
.top{
|
||||
display: flex;flex-direction: column; font-size: 10px;padding: 2px 4px;background: rgba(103,194,58,0.3);border-radius: 4px;color: $uni-text-color-success;
|
||||
}
|
||||
.num{
|
||||
margin-top: 6px;
|
||||
}
|
||||
}
|
||||
}
|
||||
.device_module:nth-child(even){
|
||||
margin-right: 0;
|
||||
}
|
||||
.device_module:nth-child(odd){
|
||||
margin-left: 0;
|
||||
}
|
||||
}
|
||||
.energy_data{padding: 12px; height: 64px; display: flex;align-items: center;background: $uni-bg-color-primary;border-radius: 8px;
|
||||
.energy_icon{color: $uni-text-color-primary;font-size: 24px;margin-right: 8px;}
|
||||
.energy_image{flex: 1;text-align: center;
|
||||
image{width: 86px;height: 32px;}
|
||||
}
|
||||
.energy_number{color: $uni-text-color-danger;}
|
||||
}
|
||||
.content_data{
|
||||
padding: 10px 0;display: flex;position: relative;align-items: center;justify-content:flex-start;height: 98px;
|
||||
.content_module{
|
||||
width: calc(25% - 7px);margin: 10px 4px;height: 98px;display: flex;align-items: center;justify-content: center;flex-direction: column;background-color: $uni-color-primary;border-radius: 8px;
|
||||
.contenticon{font-size: 24px;width: 32px;height: 32px;background-repeat: no-repeat;}
|
||||
.contentname{padding-top: 2px;font-size: 12px;}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
121
pages/index/materialYield.vue
Normal file
@ -0,0 +1,121 @@
|
||||
<template>
|
||||
<!-- 工单出材率 -->
|
||||
<view class="page_padding font13">
|
||||
<view v-for="(item,index) in list" :key="index" class="detail_list contentboxsty" @click="toDetail(498)">
|
||||
<view class="list_top">
|
||||
<view class="top_left">
|
||||
工单号:{{item.name}}
|
||||
</view>
|
||||
<view class="top_right">
|
||||
工单详情 <text class="arrow iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_content font13">
|
||||
<view class="list_centre">
|
||||
<view class="list_row">
|
||||
<view class="centre_left">
|
||||
<text class="name">加工规格</text>
|
||||
<text class="text">{{item.specs}}</text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_row">
|
||||
<view class="centre_left">
|
||||
<text class="name">算法出材率</text>
|
||||
<text class="text">{{item.algorithm}}%</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_below">
|
||||
<view class="below_left">
|
||||
<view class="circle-progress">
|
||||
<view class="progressBg">
|
||||
<view class="progressBox">
|
||||
<view class="percentage font22">
|
||||
{{item.algorithm}}%
|
||||
</view>
|
||||
<view class="title font12">
|
||||
出材率
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="circle-progress__bar" :style="'--progress:'+item.algorithm+'%'"></view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="card_right">
|
||||
<view class="status">生产中</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
list:[{
|
||||
name:'SO202401111004',
|
||||
algorithm:'51.5',
|
||||
reality:'81.4',
|
||||
state:'生产中',
|
||||
specs:'4*9*3.66',
|
||||
time:'jan-11 10:05',
|
||||
timeConsuming:'3.5H',
|
||||
number:'12.66m³'
|
||||
},{
|
||||
name:'SO202401111004',
|
||||
algorithm:'81.5',
|
||||
reality:'81.4',
|
||||
state:'生产中',
|
||||
specs:'4*9*3.66',
|
||||
time:'jan-11 10:05',
|
||||
timeConsuming:'3.5H',
|
||||
number:'12.66m³'
|
||||
},{
|
||||
name:'SO202401111004',
|
||||
algorithm:'61.5',
|
||||
reality:'81.4',
|
||||
state:'生产中',
|
||||
specs:'4*9*3.66',
|
||||
time:'jan-11 10:05',
|
||||
timeConsuming:'3.5H',
|
||||
number:'12.66m³'
|
||||
},{
|
||||
name:'SO202401111004',
|
||||
algorithm:'81.5',
|
||||
reality:'81.4',
|
||||
state:'生产中',
|
||||
specs:'4*9*3.66',
|
||||
time:'jan-11 10:05',
|
||||
timeConsuming:'3.5H',
|
||||
number:'12.66m³'
|
||||
}]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
toDetail(id){
|
||||
uni.navigateTo({
|
||||
url:'/pages/production/productionDetail?id='+id
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.detail_list{
|
||||
.list_centre{
|
||||
.list_row{display: flex;padding-bottom: 12px;
|
||||
.centre_left{
|
||||
flex: 1;
|
||||
.name{width:80px;display: inline-block;font-weight: bold;}
|
||||
}
|
||||
}
|
||||
}
|
||||
.list_below{display: flex;text-align: center;padding: 10px 0;
|
||||
.below_left{flex: 1;display: flex;align-items: center;justify-content: center;}
|
||||
.percentage{color: $uni-text-color-inverse;}
|
||||
}
|
||||
}
|
||||
</style>
|
@ -24,7 +24,7 @@
|
||||
</view>
|
||||
<view class="con_but">
|
||||
<view class="but_rat"><view class="t-icon t-icon-shenpizhida icon22"></view>审批</view>
|
||||
<view class="but_del"><view class="t-icon t-icon-shezhi icon22 paddrigth5"></view>删除</view>
|
||||
<view class="but_del"><view class="t-icon t-icon-shezhi icon22 padd_rigth5"></view>删除</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
|
@ -1,42 +0,0 @@
|
||||
<template>
|
||||
<!-- 生产工单 -->
|
||||
<view class="pagepaddings">
|
||||
<view v-for="(item,index) in list" :key="index" class="page_list">
|
||||
<view class="list_top">
|
||||
<view class="top_left">
|
||||
工单号:{{item.name}}
|
||||
</view>
|
||||
<view class="top_right">
|
||||
工单详情
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_centre">
|
||||
|
||||
</view>
|
||||
<view class="list_below">
|
||||
|
||||
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
list:[{
|
||||
name:'SO202401111004',
|
||||
|
||||
}]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
|
||||
</style>
|
78
pages/index/schedule.vue
Normal file
@ -0,0 +1,78 @@
|
||||
<template>
|
||||
<!-- 工单进度管理 -->
|
||||
<view class="page_padding columnFlex">
|
||||
<view class="headerView" :class="headerFixed?'headerViewFixed':''">
|
||||
<searchView placeholder=" 搜索工单" />
|
||||
</view>
|
||||
<view class="flexBox">
|
||||
<view class="detail_list contentboxsty font13" v-for="(item,index) in list" :key="index">
|
||||
<view @click="toDetail(497)">
|
||||
<view class="list_top">
|
||||
<view class="top_left">
|
||||
工单号:{{item.sn}}
|
||||
</view>
|
||||
<view class="top_right">
|
||||
工单详情<text class="arrow iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_content">
|
||||
<view class="list_row">
|
||||
<text class="name">开始时间</text>
|
||||
<text class="text">24-01-12 08:00</text>
|
||||
</view>
|
||||
<view class="list_row padd_top12">
|
||||
<text class="name">计划完成</text>
|
||||
<text class="text">24-01-12 08:00</text>
|
||||
</view>
|
||||
<view class="padd_top12">
|
||||
<progressBar :total="100" :val="item.num" title="" />
|
||||
</view>
|
||||
<view class="card_right">
|
||||
<view class="status">生产中</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
components: {
|
||||
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
list:[
|
||||
{name:'',sn:"SO20240422000002",num:20},{name:'',sn:"SO20240422000002",num:70},{name:'',sn:"SO20240422000002",num:90},
|
||||
{name:'',sn:"SO20240422000002",num:20},{name:'',sn:"SO20240422000002",num:70},{name:'',sn:"SO20240422000002",num:90}
|
||||
]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
toDetail(id){
|
||||
uni.navigateTo({
|
||||
url:'/pages/production/productionDetail?id='+id
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_padding{
|
||||
padding-top: 0;
|
||||
}
|
||||
.detail_list{
|
||||
.list_content{
|
||||
.list_row{
|
||||
.name{
|
||||
width: 65px;
|
||||
display: inline-block;
|
||||
font-weight: bold;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
@ -1,49 +1,56 @@
|
||||
<template>
|
||||
<view class="login_page ">
|
||||
<view class="iconfont icon-shouye" @click="toIndex()" style="height: 25px;position: absolute;top: 60px;width: 30px;"></view>
|
||||
<view class="login_top">
|
||||
<view class="login_logo">
|
||||
<image src="https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/meslogo.png" class="logopng"></image>
|
||||
<image src="https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/demu.png" class="demupng"></image>
|
||||
<image src="https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/loginLogo.png" class="demupng"></image>
|
||||
</view>
|
||||
<view class="">
|
||||
<view class="name">
|
||||
自动化MES管理系统
|
||||
</view>
|
||||
</view>
|
||||
<view class="login_centre">
|
||||
<view class="login_switch text_color_black font14">
|
||||
<view class="login_name font_bold" >
|
||||
<view :class="['login_name', tab==1?'font_bold':'']" @click="changeTab(1)">
|
||||
账号登录
|
||||
</view>
|
||||
<view class="login_name">
|
||||
<view :class="['login_name', tab==2?'font_bold':'']" @click="changeTab(2)">
|
||||
手机号登录
|
||||
</view>
|
||||
</view>
|
||||
<view class="font12 text_color_black" v-if="type==1">
|
||||
<view class="font12 text_color_black" v-if="tab==1">
|
||||
<view class="login_input">
|
||||
<input placeholder="请输入账号" />
|
||||
<input placeholder="请输入账号" v-model="accountValue"/>
|
||||
</view>
|
||||
<view class="login_input">
|
||||
<input password type="text" placeholder="请输入密码" />
|
||||
<input password type="text" v-model="passValue" placeholder="请输入密码" />
|
||||
</view>
|
||||
</view>
|
||||
<view class="font12" v-if="type==2">
|
||||
<view class="font12 text_color_black" v-if="tab==2">
|
||||
<view class="login_input">
|
||||
<input placeholder="请输入手机号"/>
|
||||
</view>
|
||||
<view class="">
|
||||
<input placeholder="请输入手机号"/>
|
||||
<view class="flex_layout">
|
||||
<input class="login_input login_code" placeholder="请输入验证码"/>
|
||||
<view class="getCaptcha">{{codename}}</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="" style="color: #C4C4C4;font-size: 11px; padding-top: 14px;">
|
||||
<view class="" v-if="tab==1" style="color: #C4C4C4;font-size: 12px;padding-top: 14px;">
|
||||
记住密码
|
||||
</view>
|
||||
<view class="loginbut">
|
||||
<view class="loginbut" @click="login()">
|
||||
登录
|
||||
</view>
|
||||
<button class="persontc " type="default" open-type="getPhoneNumber" @getphonenumber="getPhone">
|
||||
<view class="" style="color: #009688;text-align: center;font-size: 13px;">
|
||||
手机号一键登录
|
||||
手机号快捷登录
|
||||
</view>
|
||||
</button>
|
||||
<!-- <button class="persontc" open-type="getPhoneNumber" @getphonenumber="getPhoneNumber">
|
||||
<view class="" style="color: #009688;text-align: center;font-size: 13px;">
|
||||
手机号快捷登录
|
||||
</view>
|
||||
</button> -->
|
||||
</view>
|
||||
<view class="login_below">
|
||||
<view class="">
|
||||
@ -61,11 +68,33 @@
|
||||
data() {
|
||||
return {
|
||||
codename:'获取验证码',
|
||||
type:1,
|
||||
tab:1,
|
||||
accountValue:'long',
|
||||
passValue:'123456',
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
//切换登录方式
|
||||
changeTab(tab){
|
||||
this.$set(this,"tab",tab);
|
||||
},
|
||||
toIndex(){
|
||||
uni.reLaunch({
|
||||
url:'/pages/index/index'
|
||||
});
|
||||
},
|
||||
login(){
|
||||
this.$api.postFuncLoading('/user.login',{login_name:this.accountValue,password:this.passValue}).then(res=>{
|
||||
let obj = new Object();
|
||||
obj.mes_user_name=res.data.user.name;
|
||||
obj.mes_token=res.data.token;
|
||||
this.$wf.setLoginData(obj)
|
||||
|
||||
uni.switchTab({
|
||||
url:'/pages/index/index'
|
||||
})
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@ -74,24 +103,55 @@
|
||||
.login_page{
|
||||
padding: 0 32px;
|
||||
background: url('https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/background.png') no-repeat;
|
||||
background-position: center center;
|
||||
background-position: center;
|
||||
background-size: cover;
|
||||
height: 100vh;
|
||||
}
|
||||
|
||||
.login_top{padding-top: 160px;padding-bottom: 32px;}
|
||||
.login_top .name{letter-spacing: 1.2px;background: linear-gradient(to right, #fff, rgba(255,255,255,0.1));
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
}
|
||||
.login_logo{display: flex;align-items: center;margin-bottom: 17px;}
|
||||
.logopng{width: 53px;height: 44px;}
|
||||
.demupng{width: 60px;height: 36px;}
|
||||
.demupng{width: 117px;height: 43px;}
|
||||
.login_centre{border-radius: 16px;background: #FFF;padding: 20px 24px 40px;}
|
||||
.login_switch{display: flex;}
|
||||
.login_name{flex: 1;text-align: center;}
|
||||
.login_input{border-radius: 21.5px;background: #F3F5F9; margin-top: 12px; padding: 5px 15px;}
|
||||
.loginbut{
|
||||
background: #009688;
|
||||
text-align: center;
|
||||
margin-top: 60px;
|
||||
margin-bottom: 18px;
|
||||
padding: 9px;
|
||||
border-radius: 66rpx;}
|
||||
.login_name{flex: 1;text-align: center;
|
||||
padding-bottom: 5px;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
.login_name:focus {
|
||||
outline: none; /* 去除默认的外边框效果 */
|
||||
border-width: 3px; /* 当元素被点击或者获得焦点时,将边框宽度修改为3像素 */
|
||||
}
|
||||
.font_bold{
|
||||
position: relative;
|
||||
}
|
||||
.font_bold::after{
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: calc(50% - 15px);
|
||||
bottom: -4px;
|
||||
z-index: 10;
|
||||
width: 30px;
|
||||
border-bottom: 3px solid #009688;
|
||||
}
|
||||
.login_input{border-radius: 21.5px;background: #F3F5F9;margin-top: 12px;padding: 9px 15px;font-size: 14px;}
|
||||
.getCaptcha{border-radius: 21.5px;background: #009688;height: auto;color: white;display: flex;align-items: center;width: 40%;justify-content: center;}
|
||||
.flex_layout{display: flex;margin-top: 12px;}
|
||||
.login_code{margin-top: unset;width:60%;margin-right: 12px;}
|
||||
.loginbut{background: #009688;text-align: center;margin-top: 40px;margin-bottom: 18px;padding: 9px;border-radius: 66rpx;}
|
||||
.persontc{
|
||||
border: none;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
outline: none;
|
||||
border-radius: 0;
|
||||
background: none!important;
|
||||
line-height: normal;
|
||||
}
|
||||
.persontc::after {
|
||||
border: none;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
@ -1,16 +1,18 @@
|
||||
<template>
|
||||
<view class="person_page pagepaddings font13">
|
||||
<view class="person_page page_padding font13">
|
||||
<view class="person_dataA contentboxsty">
|
||||
<view class="content_box">
|
||||
<view class="content_box logo_box">
|
||||
<view class="data_name">头像</view>
|
||||
<view class="">
|
||||
>
|
||||
<button class="person_button" open-type="chooseAvatar" @chooseavatar='onChooseAvatar'>
|
||||
<image class="person_logo" :src="avatarUrl" mode="aspectFill"></image>
|
||||
</button>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_box">
|
||||
<view class="data_name">真实姓名</view>
|
||||
<view class="">
|
||||
>
|
||||
<text class="iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_box noborbot">
|
||||
@ -33,7 +35,9 @@
|
||||
<view class="person_dataC contentboxsty">
|
||||
<view class="content_box">
|
||||
<view class="data_name">设备故障通知</view>
|
||||
<view class=""></view>
|
||||
<view class="">
|
||||
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_box">
|
||||
<view class="data_name">出材率预警通知</view>
|
||||
@ -54,13 +58,23 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
const defaultAvatarUrl = 'https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/avatar.png';
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
|
||||
avatarUrl:defaultAvatarUrl
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
onChooseAvatar(e) {
|
||||
|
||||
uni.showToast({
|
||||
title:'成功',
|
||||
duration:1000
|
||||
})
|
||||
this.avatarUrl = e.detail.avatarUrl
|
||||
},
|
||||
//跳转更改手机号页面
|
||||
toChangPhone(){
|
||||
uni.navigateTo({
|
||||
@ -80,7 +94,15 @@
|
||||
.person_dataB{padding: 0 14px;margin-bottom: 12px;}
|
||||
.person_dataC{padding: 0 14px;margin-bottom: 12px;}
|
||||
.person_dataD{padding: 0 14px;}
|
||||
.content_box{display: flex;align-items: center;height: 44px;border-bottom: 1px solid #2D3A6F;}
|
||||
.content_box{
|
||||
display: flex;align-items: center;height: 44px;border-bottom: 1px solid #2D3A6F;
|
||||
}
|
||||
.logo_box{height: 64px;
|
||||
.person_button{width: 40px;height: 40px;border-radius: 50%;padding: 0;}
|
||||
.person_logo{width: 40px;height: 40px;}
|
||||
}
|
||||
.data_name{flex: 1;}
|
||||
}
|
||||
|
||||
|
||||
</style>
|
||||
|
60
pages/person/alarm.vue
Normal file
@ -0,0 +1,60 @@
|
||||
<template>
|
||||
<!-- 设备报警 -->
|
||||
<view class="page_padding">
|
||||
<view class="content_layout" @click="cancelLongpress">
|
||||
<view class="item_layout" v-for="(item, index) in list" :key="index">
|
||||
<view :class="islongpress?'longpress_style':''" @longpress="longpress" @click="deleteAlarm">
|
||||
<image :src="item.url" class="img_style" mode=""></image>
|
||||
</view>
|
||||
<view class="font13 flex_layout">
|
||||
<text class="flex1">{{item.name}}</text>
|
||||
<text>{{item.time}}</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
islongpress:false,
|
||||
list:[
|
||||
{name:'周边侵入警报',time:'2023-09-01',url:'../../static/logo.png'},
|
||||
{name:'周边侵入警报',time:'2023-09-01',url:'../../static/logo.png'},
|
||||
{name:'周边侵入警报',time:'2023-09-01',url:'../../static/logo.png'},
|
||||
]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
longpress(){
|
||||
console.log('长按事件')
|
||||
this.islongpress = true
|
||||
},
|
||||
//取消
|
||||
cancelLongpress(){
|
||||
this.islongpress = false
|
||||
},
|
||||
//删除警告
|
||||
deleteAlarm(){
|
||||
if(this.islongpress){
|
||||
console.log('删除')
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
/* .content_layout{display: flex;flex-flow: wrap;}
|
||||
.item_layout{width: 50%;} */
|
||||
.content_layout{
|
||||
display: grid;
|
||||
grid-template-columns: 1fr 1fr;/* 每一列占一行的一半 */
|
||||
grid-gap: 10px; /* 可选的间距 */
|
||||
}
|
||||
.img_style{height: 110px;width: 100%;}
|
||||
.longpress_style{background-color: #000;
|
||||
opacity: 0.2;}
|
||||
</style>
|
@ -1,6 +1,14 @@
|
||||
<template>
|
||||
<view>
|
||||
|
||||
<view class="page_padding font13">
|
||||
<view class="phone_page contentboxsty">
|
||||
<view class="content_row">
|
||||
<input placeholder="请输入要更换的手机号码" />
|
||||
</view>
|
||||
<view class="content_row noborbot">
|
||||
<input placeholder="请输入短信验证码" />
|
||||
<view class="theme_color">获取验证码</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
@ -18,5 +26,7 @@
|
||||
</script>
|
||||
|
||||
<style>
|
||||
|
||||
.phone_page{padding: 0 12px;}
|
||||
.content_row{display: flex;height: 49px;align-items: center;border-bottom: 1px solid #2D3A6F;}
|
||||
.content_row input{flex: 1;}
|
||||
</style>
|
||||
|
464
pages/person/faceAuthentication.vue
Normal file
@ -0,0 +1,464 @@
|
||||
<template>
|
||||
<view v-if="step==1">
|
||||
<view class="scan_box">
|
||||
<image class="avatar_frame" src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/morentouxiang.png" mode=""></image>
|
||||
<image class="scan_img" src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/saomiao.png"></image>
|
||||
|
||||
</view>
|
||||
<view class="start_view" @click="startAttestation(2)">
|
||||
<view class="start_but">
|
||||
开始认证
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="page-content" v-else-if="step==2">
|
||||
<view class="containerV">
|
||||
<view class="headerV">
|
||||
<view class="top-tips1 font15">
|
||||
<view>请把脸移入圈内保持不动</view>
|
||||
</view>
|
||||
<!-- <view class="top-tips2">
|
||||
为了便于识别认证,请拍摄本人头像
|
||||
</view> -->
|
||||
</view>
|
||||
<view class="contentV">
|
||||
<view class="mark"></view>
|
||||
<image v-if="tempImg" mode="widthFix" :src="tempImg" />
|
||||
<camera v-if='isAuthCamera' :device-position="devicePosition ?'front': 'back'" class="camera"
|
||||
flash="off" resolution='high' />
|
||||
<view v-show="!tempImg && tipsText" class="tipV">{{ tipsText }}</view>
|
||||
</view>
|
||||
<view class="footerV">
|
||||
<view style="width: 100%;">
|
||||
<view v-if="!tempImg" style="width: 100%;">
|
||||
<!-- <view class="privacyV">
|
||||
<view class="icon"></view>
|
||||
<view class="text">
|
||||
照片隐私<text @click="handleJumpSecurityClick">安全保障</text>中…
|
||||
</view>
|
||||
</view>
|
||||
<view class="bottom-tips-2">该照片仅作为你认证的凭证</view> -->
|
||||
<view class="take-photo-bgV">
|
||||
<!-- 图片上传 -->
|
||||
<!-- <view v-show="true" class="btn-change-upload" @click="handleChooseImage" ></view> -->
|
||||
<!--拍照-->
|
||||
<view class="btn-take-photo" @click="handleTakePhotoClick" ></view>
|
||||
<!-- 切换镜头 -->
|
||||
<view class="btn-change-camera" @click="handleChangeCameraClick" ></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="confirmV" v-else>
|
||||
<view class="btn-cancel" @click="handleCancelClick">
|
||||
取消
|
||||
</view>
|
||||
<view class="btn-ok" @click="handleOkClick">
|
||||
确定
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'index',
|
||||
components: {
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
step:1,
|
||||
tipsText: '', // 错误文案提示
|
||||
tempImg: '', // 本地图片路径
|
||||
// BASE_API,
|
||||
cameraEngine: null, // 相机引擎
|
||||
devicePosition: false, // 摄像头朝向
|
||||
isAuthCamera: true, // 是否拥有相机权限
|
||||
}
|
||||
},
|
||||
|
||||
onLoad(options) {
|
||||
this.initData()
|
||||
},
|
||||
mounted(){
|
||||
},
|
||||
methods: {
|
||||
//
|
||||
startAttestation(type){
|
||||
this.step=type;
|
||||
},
|
||||
// 初始化相机引擎
|
||||
initData() {
|
||||
this.handleChangeCameraClick();
|
||||
// console.log(1111)
|
||||
// const session = wx.createVKSession({
|
||||
// track: {
|
||||
// face: { mode: 1 } // mode: 1 - 使用摄像头;2 - 手动传入图像
|
||||
// },
|
||||
// })
|
||||
// console.log(222)
|
||||
// // 摄像头实时检测模式下,监测到人脸时,updateAnchors 事件会连续触发 (每帧触发一次)
|
||||
// session.on('updateAnchors', anchors => {
|
||||
// anchors.forEach(anchor => {
|
||||
// console.log('anchor.points', anchor.points)
|
||||
// console.log('anchor.origin', anchor.origin)
|
||||
// console.log('anchor.size', anchor.size)
|
||||
// console.log('anchor.angle', anchor.angle)
|
||||
// })
|
||||
// })
|
||||
// console.log(333)
|
||||
// // 当人脸从相机中离开时,会触发 removeAnchors 事件
|
||||
// session.on('removeAnchors', () => {
|
||||
// console.log('removeAnchors')
|
||||
// })
|
||||
|
||||
// // 需要调用一次 start 以启动
|
||||
// session.start(errno => {
|
||||
// if (errno) {
|
||||
// // 如果失败,将返回 errno
|
||||
// } else {
|
||||
// // 否则,返回null,表示成功
|
||||
// }
|
||||
// })
|
||||
// console.log(444)
|
||||
|
||||
|
||||
this.cameraEngine = wx.createCameraContext()
|
||||
const listener = this.cameraEngine.onCameraFrame((frame) => {
|
||||
if (this.tempImg) {
|
||||
return;
|
||||
}
|
||||
wx.createVKSession({
|
||||
track: {
|
||||
plane: {mode: 3},
|
||||
},
|
||||
version: 'v2',
|
||||
// gl, // WebGLRenderingContext
|
||||
})
|
||||
})
|
||||
|
||||
|
||||
// // #ifdef MP-WEIXIN
|
||||
// // 1、初始化人脸识别
|
||||
// wx.initFaceDetect()
|
||||
// // 2、创建 camera 上下文 CameraContext 对象
|
||||
// this.cameraEngine = wx.createCameraContext()
|
||||
// // 3、获取 Camera 实时帧数据
|
||||
// const listener = this.cameraEngine.onCameraFrame((frame) => {
|
||||
// if (this.tempImg) {
|
||||
// return;
|
||||
// }
|
||||
// // 4、人脸识别,使用前需要通过 wx.initFaceDetect 进行一次初始化,推荐使用相机接口返回的帧数据
|
||||
// wx.faceDetect({
|
||||
// frameBuffer: frame.data,
|
||||
// width: frame.width,
|
||||
// height: frame.height,
|
||||
// enablePoint: true,
|
||||
// enableConf: true,
|
||||
// enableAngle: true,
|
||||
// enableMultiFace: true,
|
||||
// success: (faceData) => {
|
||||
// let face = faceData.faceInfo[0]
|
||||
// if (faceData.x == -1 || faceData.y == -1) {
|
||||
// this.tipsText = '检测不到人'
|
||||
// }
|
||||
// if (faceData.faceInfo.length > 1) {
|
||||
// this.tipsText = '请保证只有一个人'
|
||||
// } else {
|
||||
// const {
|
||||
// pitch,
|
||||
// roll,
|
||||
// yaw
|
||||
// } = face.angleArray;
|
||||
// const standard = 0.5
|
||||
// if (Math.abs(pitch) >= standard || Math.abs(roll) >= standard ||
|
||||
// Math.abs(yaw) >= standard) {
|
||||
// this.tipsText = '请平视摄像头'
|
||||
// } else if (face.confArray.global <= 0.8 || face.confArray.leftEye <=
|
||||
// 0.8 || face.confArray.mouth <= 0.8 || face.confArray.nose <= 0.8 ||
|
||||
// face.confArray.rightEye <= 0.8) {
|
||||
// this.tipsText = '请勿遮挡五官'
|
||||
// } else {
|
||||
// this.tipsText = '请拍照'
|
||||
// // 这里可以写自己的逻辑了
|
||||
// }
|
||||
// }
|
||||
// },
|
||||
// fail: (err) => {
|
||||
// if (err.x == -1 || err.y == -1) {
|
||||
// this.tipsText = '检测不到人'
|
||||
// } else {
|
||||
// this.tipsText = err.errMsg || '网络错误,请退出页面重试'
|
||||
// }
|
||||
// },
|
||||
// })
|
||||
// })
|
||||
// 5、开始监听帧数据
|
||||
// listener.start()
|
||||
// #endif
|
||||
},
|
||||
// 切换设备镜头
|
||||
handleChangeCameraClick() {
|
||||
this.devicePosition = !this.devicePosition;
|
||||
},
|
||||
// 图片上传
|
||||
handleChooseImage() {
|
||||
uni.chooseImage({
|
||||
count: 1,
|
||||
sizeType: ['original', 'compressed'],
|
||||
sourceType: ['album','camera'],
|
||||
success: (res) => {
|
||||
console.log(res,'打印res,哈哈哈哈哈')
|
||||
if (res.errMsg === 'chooseImage:ok') {
|
||||
uni.showLoading({
|
||||
title: '照片上传中...'
|
||||
})
|
||||
const tempFilePaths = res.tempFilePaths[0]
|
||||
this.upLoad(res.tempFilePaths);
|
||||
}
|
||||
},
|
||||
fail: (res) => {
|
||||
},
|
||||
});
|
||||
},
|
||||
// 拍照点击
|
||||
handleTakePhotoClick() {
|
||||
if (this.tipsText != "" && this.tipsText != "请拍照") {
|
||||
return;
|
||||
}
|
||||
uni.getSetting({
|
||||
success: (res) => {
|
||||
if (!res.authSetting['scope.camera']) {
|
||||
this.isAuthCamera = false
|
||||
uni.openSetting({
|
||||
success: (res) => {
|
||||
if (res.authSetting['scope.camera']) {
|
||||
this.isAuthCamera = true;
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
})
|
||||
this.cameraEngine.takePhoto({
|
||||
quality: "high",
|
||||
success: ({
|
||||
tempImagePath
|
||||
}) => {
|
||||
this.tempImg = tempImagePath
|
||||
}
|
||||
})
|
||||
console.log(this.tempImg,2121)
|
||||
},
|
||||
// 点击确定上传
|
||||
handleOkClick() {
|
||||
// 这里的 this.tempImg 是经过人脸检测后 拍照拿到的路径
|
||||
this.upLoadOne(this.tempImg)
|
||||
uni.navigateBack({
|
||||
delta: 1
|
||||
});
|
||||
},
|
||||
upLoad(tempFilePaths) {
|
||||
// # 注意 这里上传图片拿到的tempFilePaths是一个数组啊
|
||||
// 图片上传
|
||||
uni.showLoading({
|
||||
title: "上传中,请稍后...",
|
||||
});
|
||||
let proAll = [];
|
||||
tempFilePaths.forEach((item) => {
|
||||
console.log(item,'打印item')
|
||||
proAll.push(this.upLoadOne(item));
|
||||
});
|
||||
Promise.all(proAll).then((res) => {
|
||||
// 上传完成
|
||||
uni.hideLoading();
|
||||
});
|
||||
},
|
||||
upLoadOne(imgPath) {
|
||||
// 然后这里imgPath 传过来的是 要上传的临时本地图片的路径
|
||||
// 具体上传方法根据自己的请求方式 请求自己的接口
|
||||
},
|
||||
// 点击 - 取消上传
|
||||
handleCancelClick() {
|
||||
this.tempImg = ''
|
||||
},
|
||||
// 点击 - 人脸安全保障按钮
|
||||
handleJumpSecurityClick() {
|
||||
uni.showToast({
|
||||
icon: "none",
|
||||
title: "假装跳转人脸安全保障",
|
||||
duration: 2000,
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.scan_box{width: 200px;height: 200px;margin: 70px auto;border: 3px solid #009688;border-radius: 50%;background-color: #EEEEEE;
|
||||
display: flex;justify-content: center;
|
||||
}
|
||||
.avatar_frame{width: 100%;height: 100%;}
|
||||
.scan_img{height: 98px;padding-top: 14px; position: absolute;width: 200px;}
|
||||
.start_view{display: flex;justify-content: center;padding-top: 20px;}
|
||||
.start_but{width: 116px;height: 34px;border-radius: 29px;background: #009688;align-items: center;justify-content: center;display: flex;}
|
||||
|
||||
.page-content {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
.containerV {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
.headerV {
|
||||
.top-tips1 {
|
||||
margin-top: 60rpx;
|
||||
color: #FFFFFF;
|
||||
font-size: 36rpx;
|
||||
text-align: center;
|
||||
}
|
||||
.top-tips2 {
|
||||
margin-top: 20rpx;
|
||||
color: #00AAFF;
|
||||
font-size: 28rpx;
|
||||
text-align: center;
|
||||
}
|
||||
}
|
||||
.contentV {
|
||||
position: relative;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
height: 400rpx;
|
||||
margin-top: 30rpx;
|
||||
.tipV {
|
||||
bottom: 30rpx;
|
||||
position: absolute;
|
||||
line-height: 90rpx;
|
||||
padding-left: 24rpx;
|
||||
padding-right: 24rpx;
|
||||
max-width: calc(100vw - 50rpx * 2);
|
||||
text-align: center;
|
||||
font-size: 30rpx;
|
||||
background: #000000;
|
||||
opacity: 0.75;
|
||||
color: #FFFFFF;
|
||||
border-radius: 16rpx;
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
text-overflow: ellipsis;
|
||||
z-index: 5;
|
||||
}
|
||||
.camera {
|
||||
width: 400upx;
|
||||
height: 400upx;
|
||||
border-radius: 50%;
|
||||
border: 3px solid #009688;
|
||||
}
|
||||
.mark {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
z-index: 2;
|
||||
width: 750rpx;
|
||||
height: 100%;
|
||||
// background:deeppink;
|
||||
background-size: 750rpx 661rpx;
|
||||
}
|
||||
image {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
z-index: 3;
|
||||
}
|
||||
}
|
||||
|
||||
.footerV {
|
||||
width: 100%;
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
.privacyV {
|
||||
padding-top: 30rpx;
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
.text {
|
||||
font-size: 30rpx;
|
||||
color: #1C1C1C;
|
||||
text-align: center;
|
||||
line-height: 42rpx;
|
||||
margin-left: 15rpx;
|
||||
text {
|
||||
font-size: 30rpx;
|
||||
color: #00AAFF;
|
||||
text-align: center;
|
||||
line-height: 42rpx;
|
||||
}
|
||||
}
|
||||
.icon {
|
||||
width: 40rpx;
|
||||
height: 47rpx;
|
||||
background:green;
|
||||
background-size: 100% auto;
|
||||
}
|
||||
}
|
||||
|
||||
.bottom-tips-2 {
|
||||
margin-top: 20rpx;
|
||||
color: #999999;
|
||||
text-align: center;
|
||||
font-size: 26rpx;
|
||||
}
|
||||
.take-photo-bgV {
|
||||
width: 100%;
|
||||
margin-top: 300rpx;
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
.btn-take-photo {
|
||||
margin: 0rpx 80rpx 0rpx 80rpx;
|
||||
width: 196rpx;
|
||||
height: 196rpx;
|
||||
background: yellow;
|
||||
background-size: 100% auto;
|
||||
}
|
||||
.btn-change-upload {
|
||||
left: 130rpx;
|
||||
width: 80rpx;
|
||||
height: 80rpx;
|
||||
background: blue;
|
||||
background-size: 100% auto;
|
||||
}
|
||||
.btn-change-camera {
|
||||
right: 130rpx;
|
||||
width: 80rpx;
|
||||
height: 80rpx;
|
||||
background:red;
|
||||
background-size: 100% auto;
|
||||
}
|
||||
}
|
||||
.confirmV {
|
||||
margin: 200rpx 100rpx 0rpx 100rpx;
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
.btn-cancel {
|
||||
font-size: 32rpx;
|
||||
color: #1C1C1C;
|
||||
}
|
||||
.btn-ok {
|
||||
font-size: 32rpx;
|
||||
color: #00AAFF;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
133
pages/person/myAuthority.vue
Normal file
@ -0,0 +1,133 @@
|
||||
<template>
|
||||
<view class="page_padding checkbox-container">
|
||||
<view class="contentboxsty" v-for="(item, index) in list" :key="index.id">
|
||||
<view class="list_name listItem">
|
||||
<checkbox-group @change="changeCheckbox">
|
||||
<label>
|
||||
<checkbox class="checkbox-custom" :class="{ 'checkbox_indeterminate': item.indeterminate }" :value="item.id" :checked="item.checked" style="transform:scale(0.6)" />
|
||||
<text class="font14">{{item.name}}</text>
|
||||
</label>
|
||||
</checkbox-group>
|
||||
</view>
|
||||
<view class="list_content listItem padd_bot12" v-for="(i, ind) in item.child" :key="ind">
|
||||
<view class="content_name">
|
||||
<checkbox-group @change="selectPath(item,i)">
|
||||
<label>
|
||||
<checkbox class="checkbox-custom" :class="{ 'checkbox_indeterminate': i.indeterminate }" :value="i.id" :checked="i.checked" style="transform:scale(0.6)" />
|
||||
<text class="font14">{{i.name}}</text>
|
||||
</label>
|
||||
</checkbox-group>
|
||||
</view>
|
||||
<view class="content_item">
|
||||
<view class="content_data" v-for="(btn, inx) in i.child" :key="inx">
|
||||
<checkbox-group @change="selectPath(item,i,inx)">
|
||||
<label>
|
||||
<checkbox class="checkbox-custom" :class="{ 'checkbox_indeterminate': btn.indeterminate }" :value="btn.id" :checked="btn.checked" style="transform:scale(0.6)" />
|
||||
<text class="font14">{{btn.name}}</text>
|
||||
</label>
|
||||
</checkbox-group>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
list:[
|
||||
{
|
||||
id:1,name:'首页',checked:true,indeterminate:true,
|
||||
child:[
|
||||
{
|
||||
id: 2,name:'控制台',checked:true,indeterminate:true,
|
||||
child:[
|
||||
{id:121,name:'设备信息',checked:true,},
|
||||
{id:122,name:'生产加工信息',checked:true,},
|
||||
{id:123,name:'设备能耗信息',},
|
||||
],
|
||||
},
|
||||
{
|
||||
id:124,name:'账号信息',
|
||||
child:[
|
||||
{id:125,name:'通知设置',},
|
||||
{id:126,name:'升级角色'},
|
||||
]
|
||||
}
|
||||
],
|
||||
},
|
||||
{
|
||||
id:11,name:'生产工单',
|
||||
child:[
|
||||
{
|
||||
id: 3,name:'待生产工单',
|
||||
child:[
|
||||
{name:'添加工单',id:31},
|
||||
{name:'审核工单',id:32},
|
||||
{name:'删除工单',id:33},
|
||||
{name:'撤回工单',id:34},
|
||||
],
|
||||
},
|
||||
{
|
||||
id:4,name:'已排产工单',
|
||||
child:[],
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
id:12,name:'生产排程',
|
||||
child:[
|
||||
{
|
||||
id: 4,name:'工单排程表',
|
||||
child:[
|
||||
{name:'创建生产计划',id:41},
|
||||
{name:'修改生产计划',id:42},
|
||||
{name:'拆分生产计划',id:43},
|
||||
{name:'删除生产计划',id:44},
|
||||
{name:'创建计划依赖',id:45},
|
||||
{name:'删除计划依赖',id:46},
|
||||
],
|
||||
},
|
||||
]
|
||||
}
|
||||
],
|
||||
arr:[]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
checkboxChange: function (e) {
|
||||
var items = this.items,
|
||||
values = e.detail.value;
|
||||
for (var i = 0, lenI = items.length; i < lenI; ++i) {
|
||||
const item = items[i]
|
||||
if(values.includes(item.value)){
|
||||
this.$set(item,'checked',true)
|
||||
}else{
|
||||
this.$set(item,'checked',false)
|
||||
}
|
||||
}
|
||||
// console.log(items)
|
||||
},
|
||||
changeCheckbox(e){
|
||||
// console.log(e)
|
||||
},
|
||||
selectPath(e,item){
|
||||
// console.log(e,item,222)
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.contentboxsty{padding: 14px 12px;margin-bottom: 12px;}
|
||||
.contentboxsty .listItem:last-child{padding-bottom: 0;}
|
||||
.list_name{display: flex;align-items: center;padding-bottom: 7px;border-bottom: 1px solid $uni-border-color-primary;}
|
||||
.content_name{padding:8px 0 ;display: flex;align-items: center;}
|
||||
.content_item{display: flex;align-items: center;flex-wrap: wrap;}
|
||||
.content_data{padding: 4px 15px 4px 0;display: flex;align-items: center;}
|
||||
|
||||
</style>
|
||||
|
||||
|
@ -1,8 +1,21 @@
|
||||
<template>
|
||||
<view class="person_page ">
|
||||
<view class="person_top">
|
||||
<view class="logo">
|
||||
|
||||
<view class="person_data">
|
||||
<view class="person_logo">
|
||||
<!-- <button class="avatar-wrapper" open-type="chooseAvatar" bind:chooseavatar="onChooseAvatar"> -->
|
||||
<image class="img" :src="avatarUrl"></image>
|
||||
<!-- </button> -->
|
||||
</view>
|
||||
<view class="person_name">
|
||||
<view class="name">
|
||||
<text class="font15">肖银奎</text>
|
||||
<image src="http://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/chaojihuiyuan.png" mode=""></image>
|
||||
</view>
|
||||
<view class="account font12">
|
||||
登录账号:ykxiao
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="person_content">
|
||||
@ -19,7 +32,7 @@
|
||||
<view class="t-icon t-icon-shengchangongdan backlogicon"></view>
|
||||
<view class="backlogname">流程审批</view>
|
||||
</view>
|
||||
<view class="backlog_module">
|
||||
<view class="backlog_module" @click="toAlarm">
|
||||
<view class="t-icon t-icon-shengchangongdan backlogicon"></view>
|
||||
<view class="backlogname">设备报警</view>
|
||||
</view>
|
||||
@ -27,7 +40,7 @@
|
||||
<view class="t-icon t-icon-shengchangongdan backlogicon"></view>
|
||||
<view class="backlogname">权限审批</view>
|
||||
</view>
|
||||
<view class="backlog_module">
|
||||
<view class="backlog_module" @click="toSafetyAccidents()">
|
||||
<view class="t-icon t-icon-shengchangongdan backlogicon"></view>
|
||||
<view class="backlogname">安全事故</view>
|
||||
</view>
|
||||
@ -38,62 +51,136 @@
|
||||
<view class="font14">账户中心</view>
|
||||
</view>
|
||||
<view class="con_data">
|
||||
<view class="con_module">
|
||||
<view class="con_module" @click="toMessage">
|
||||
<view class="t-icon t-icon-xiaoxitongzhi-gerenzhongxin personicon"></view>
|
||||
<view class="font13">消息管理</view>
|
||||
<view class=""></view>
|
||||
</view>
|
||||
<view class="con_module">
|
||||
<!-- <view class="con_module">
|
||||
<view class="t-icon t-icon-shenpizhida personicon"></view>
|
||||
<view class="font13">审批直达</view>
|
||||
<view class=""></view>
|
||||
</view>
|
||||
<view class="con_module noborbot">
|
||||
</view> -->
|
||||
<view class="con_module" @click="toMyAuthority()">
|
||||
<view class="t-icon t-icon-wodequanxian personicon"></view>
|
||||
<view class="font13">我的权限</view>
|
||||
<view class=""></view>
|
||||
</view>
|
||||
<view class="con_module noborbot" @click="toFaceAuthentication()">
|
||||
<view class="t-icon t-icon-renlianrenzheng personicon"></view>
|
||||
<view class="font13">人脸认证</view>
|
||||
<view class=""></view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="con_set">
|
||||
<view class="t-icon t-icon-xitongshezhi-gerenzhongxin personicon"></view>
|
||||
<view class="font13">系统设置</view>
|
||||
</view>
|
||||
<view class="login_out">
|
||||
<view class="font13">退出登录</view>
|
||||
</view>
|
||||
</view>
|
||||
<tab-bar :current-page="2"></tab-bar>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import tabBar from "@/components/customTabBar/index";
|
||||
const defaultAvatarUrl = 'https://dm-auto.oss-cn-shanghai.aliyuncs.com/mes_wechat/avatar.png';
|
||||
export default {
|
||||
components:{
|
||||
tabBar
|
||||
},
|
||||
|
||||
data() {
|
||||
return {
|
||||
avatarUrl:defaultAvatarUrl,
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
//跳转设备报警
|
||||
toAlarm(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/person/alarm'
|
||||
})
|
||||
},
|
||||
toSafetyAccidents(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/person/safetyAccidents'
|
||||
})
|
||||
},
|
||||
//跳转账户中心页
|
||||
toAccountCenter(){
|
||||
uni.navigateTo({
|
||||
url: '/pages/person/accountCenter'
|
||||
})
|
||||
},
|
||||
//跳转人脸认证页
|
||||
toFaceAuthentication(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/person/faceAuthentication'
|
||||
})
|
||||
},
|
||||
toMyAuthority(){
|
||||
uni.navigateTo({
|
||||
url:'/pages/person/myAuthority'
|
||||
})
|
||||
},
|
||||
//跳转消息页
|
||||
toMessage(){
|
||||
uni.navigateTo({
|
||||
url: '/pages/index/message'
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.person_page{ padding: 14px;
|
||||
.con_backlog{padding: 14px 10px 14px 15px;background: #1C2755;border-radius: 8px;margin-bottom: 12px;
|
||||
.backlog_data{display: flex; flex-wrap: wrap;
|
||||
.backlog_module{width: 93px;height: 76px;display: flex;justify-content: center;flex-direction: column;align-items: center;border-radius: 8px;
|
||||
background: #6576B7;margin: 5px 6px;}
|
||||
.person_top{margin-bottom:33px ;
|
||||
.person_data{display: flex;align-items: center;
|
||||
.person_logo{
|
||||
border-radius: 50%;width: 54px;height: 54px;margin:0 6px 0 4px;position: relative;
|
||||
.img{
|
||||
height: 100%;width: 100%;
|
||||
}
|
||||
}
|
||||
.person_logo::before{
|
||||
content: '';position: absolute;right: 2px;bottom: 1px;z-index: 10;border: 1px solid $uni-bg-color-default; background: $uni-bg-color-whith;width: 10px;height: 10px;border-radius: 50%;
|
||||
}
|
||||
.person_logo::after{
|
||||
content: '';position: absolute;right: 4px;bottom: 3px;z-index: 20;background: $uni-bg-color-success;width: 8px;height: 8px;border-radius: 50%;
|
||||
}
|
||||
|
||||
.person_name{
|
||||
.name{display: flex;align-items: center;margin-bottom: 2px;
|
||||
image{width: 50px;height: 16px;margin-left: 4px;}
|
||||
}
|
||||
.account{margin-top: 2px;}
|
||||
}
|
||||
}
|
||||
}
|
||||
.person_content{
|
||||
padding-bottom: 100px;
|
||||
.con_backlog{padding: 14px 10px;background: $uni-bg-color-primary;border-radius: 8px;margin-bottom: 12px;
|
||||
.backlog_data{
|
||||
display: flex;flex-wrap:wrap;margin-top:7px;
|
||||
.backlog_module{
|
||||
width: calc(33.33% - 12px);height: 76px;display: flex;justify-content: center;flex-direction: column;align-items: center;border-radius: 8px;
|
||||
background: $uni-color-info;margin: 5px 6px;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
.backlogicon{width: 32px;height: 32px;}
|
||||
.backlogname{
|
||||
font-size: $uni-font-size-sm;
|
||||
padding-top: 5px;}
|
||||
padding-top: 5px;
|
||||
}
|
||||
}
|
||||
}
|
||||
.con_account{
|
||||
border-radius: 8px;
|
||||
background: #1C2755;
|
||||
background: $uni-bg-color-primary;
|
||||
display: flex;
|
||||
height: 52px;
|
||||
align-items: center;
|
||||
@ -101,19 +188,33 @@
|
||||
margin-bottom: 10px;
|
||||
|
||||
}
|
||||
.personicon{width: 24px;height: 24px;padding-right: 15px;}
|
||||
.con_data{border-radius: 8px;
|
||||
background: #1C2755;
|
||||
.personicon{width: 24px;height: 24px;margin-right: 15px;}
|
||||
.con_data{
|
||||
border-radius: 8px;
|
||||
background: $uni-bg-color-primary;
|
||||
padding: 0 14px;
|
||||
margin-bottom: 12px;
|
||||
.con_module{display: flex;height: 49px;align-items: center;border-bottom: 1px solid #2D3A6F;}
|
||||
.con_module{display: flex;height: 49px;align-items: center;border-bottom: 1px solid $uni-border-color-primary;}
|
||||
}
|
||||
.con_set{border-radius: 8px;
|
||||
background: #1C2755;
|
||||
.con_set{
|
||||
border-radius: 8px;
|
||||
background: $uni-bg-color-primary;
|
||||
display: flex;
|
||||
height: 48px;
|
||||
align-items: center;
|
||||
padding: 0 14px;
|
||||
margin-bottom: 12px;
|
||||
}
|
||||
.login_out{
|
||||
border-radius: 8px;
|
||||
background: $uni-bg-color-primary;
|
||||
display: flex;
|
||||
height: 48px;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: 0 14px;
|
||||
color: $uni-text-color-danger;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
43
pages/person/safetyAccidents.vue
Normal file
@ -0,0 +1,43 @@
|
||||
<template>
|
||||
<!-- 安全事故 -->
|
||||
<view class="page_padding">
|
||||
<view class="contentboxsty font13" v-for="(item, index) in list" :key="index">
|
||||
<view class="name font_bold font14">
|
||||
{{item.name}}
|
||||
</view>
|
||||
<view class="img_style">
|
||||
<image :src="item.url"></image>
|
||||
</view>
|
||||
<view class="flex_layout padd_bot6">
|
||||
<view class="flex1">员工安全行为</view>
|
||||
<view class="">2023-09-01</view>
|
||||
</view>
|
||||
<view class="">
|
||||
事件描述事件描述事件描述事件描述事件描述事件描述
|
||||
事件描述事件描述事件描述事件描述事件描述事件描述
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
list:[
|
||||
{name:'设备一',url:'../../static/logo.png'},
|
||||
{name:'设备一',url:'../../static/logo.png'},
|
||||
]
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
.contentboxsty{padding: 14px 12px;margin-bottom: 12px;}
|
||||
.img_style{padding: 12px 0 14px 0;}
|
||||
|
||||
</style>
|
116
pages/production/productionDetail.vue
Normal file
@ -0,0 +1,116 @@
|
||||
<template>
|
||||
<view class="page_padding">
|
||||
<view class="detail_list contentboxsty">
|
||||
<view class="list_top">
|
||||
<view class="top_left">
|
||||
工单号 <text class="padd_left12">{{form.order_sn}}</text>
|
||||
</view>
|
||||
<view class="top_right font12">
|
||||
{{form.active_status_label}}
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_content">
|
||||
<view class="content_left font13">
|
||||
<view class="content_row">
|
||||
<text class="name">生产开始时间</text>
|
||||
<text class="data">{{form.time_start==''?'-':form.time_start}}</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">生产结束时间</text>
|
||||
<text class="data">{{form.time_end==''?'-':form.time_end}}</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">工单耗时</text>
|
||||
<text class="data">{{form.processing_time}}</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">加工规格</text>
|
||||
<text class="data">{{form.order_spec}}</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">规格料</text>
|
||||
<text class="data">{{form.cube}}m³</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">生产负责</text>
|
||||
<text class="data">{{form.creator_name}}</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">加工等级</text>
|
||||
<text class="data">全齐边</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">辅料</text>
|
||||
<text class="data">0.61m³</text>
|
||||
</view>
|
||||
<view class="content_row">
|
||||
<text class="name">电话</text>
|
||||
<text class="data">13712279001</text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="content_right">
|
||||
<progressBar :total="100" :val="form.progress_rate" title="" />
|
||||
</view>
|
||||
<view class="progressView">
|
||||
<view class="circle-progress">
|
||||
<view class="progressBg">
|
||||
<view class="progressBox">
|
||||
<view class="percentage font22">
|
||||
{{form.yield_rate}}%
|
||||
</view>
|
||||
<view class="title font12">
|
||||
出材率
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="circle-progress__bar" :style="'--progress:'+form.yield_rate+'%'"></view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form:{}
|
||||
}
|
||||
},
|
||||
onLoad(option){
|
||||
this.detailData(option.id)
|
||||
},
|
||||
onShow(){
|
||||
|
||||
},
|
||||
onReady() {
|
||||
|
||||
},
|
||||
methods: {
|
||||
detailData(id){
|
||||
this.$api.postFuncLoading('/order.info',{id:id}).then(res=>{
|
||||
this.form = res.data
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.list_top{
|
||||
.top_right{background: #243168;border-radius: 4px;padding: 3px 10px; text-align: center;display: inline-block;}
|
||||
}
|
||||
.list_content{
|
||||
.content_row{display: flex;padding:6px 0;
|
||||
.name{width: 90px;font-weight: bold;}
|
||||
}
|
||||
.content_right{padding: 6px 0;}
|
||||
.progressView{
|
||||
position: absolute;
|
||||
top: 12px;
|
||||
right:12px;
|
||||
z-index: 20;
|
||||
}
|
||||
}
|
||||
</style>
|
200
pages/production/productionOrder.vue
Normal file
@ -0,0 +1,200 @@
|
||||
<template>
|
||||
<!-- 生产工单 -->
|
||||
<view class="page_padding columnFlex">
|
||||
<view class="headerView" :class="headerFixed?'headerViewFixed':''">
|
||||
<searchView placeholder=" 搜索工单" />
|
||||
</view>
|
||||
<view class="flexBox">
|
||||
<view v-for="(item,index) in list" :key="index" class="detail_list contentboxsty font13">
|
||||
<view @click="toDetail(item.id)">
|
||||
<view class="list_top">
|
||||
<view class="top_left">
|
||||
工单号:{{item.order_sn}}
|
||||
</view>
|
||||
<view class="top_right">
|
||||
工单详情 <text class="arrow iconfont icon-gengduo"></text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_content font13">
|
||||
<view class="list_centre">
|
||||
<view class="centre_left">
|
||||
<view class="name font_bold">
|
||||
算法出材率
|
||||
</view>
|
||||
<view class="percentage font24">
|
||||
{{item.algorithm && item.algorithm!=''?item.algorithm+'':'0'}}%
|
||||
</view>
|
||||
</view>
|
||||
<view class="centre_left">
|
||||
<view class="name font_bold">
|
||||
实际出材率
|
||||
</view>
|
||||
<view class="percentage font24">
|
||||
{{item.reality && item.reality!=''?item.reality:'0'}}%
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="list_below">
|
||||
<view class="row">
|
||||
<view class="row_left">
|
||||
<text class="name">状态</text>
|
||||
<text class="text status">{{item.active_status_label}}</text>
|
||||
</view>
|
||||
<view class="row_right">
|
||||
<text class="name">加工规格</text>
|
||||
<text class="text">{{item.order_spec}}</text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="row_left">
|
||||
<text class="name">生产开始</text>
|
||||
<text class="text">{{item.plan_date}}</text>
|
||||
</view>
|
||||
<view class="row_right">
|
||||
<text class="name">工单耗时</text>
|
||||
<text class="text">{{item.progress_rate}}</text>
|
||||
</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="row_left">
|
||||
<text class="name">工单数量</text>
|
||||
<text class="text">{{item.order_number}}</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<loadMore :noData="loadParams.noData" :loading="loadParams.loading" :loadEnd="loadParams.loadEnd" />
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
components:{
|
||||
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
headerFixed:false,
|
||||
list:[],
|
||||
params:{
|
||||
page:1,
|
||||
pageSize:10,
|
||||
},
|
||||
loadParams:{
|
||||
noData:false,
|
||||
loading:false,
|
||||
loadEnd:false
|
||||
}
|
||||
}
|
||||
},
|
||||
onShow(){
|
||||
|
||||
},
|
||||
onReady() {
|
||||
this.listData();
|
||||
},
|
||||
onPageScroll(e){
|
||||
if(e.scrollTop>30){
|
||||
this.headerFixed = true;
|
||||
}else{
|
||||
this.headerFixed = false;
|
||||
}
|
||||
},
|
||||
// 上拉刷新
|
||||
onPullDownRefresh(){
|
||||
this.params.page = 1;
|
||||
this.loadParams = {
|
||||
noData:false,
|
||||
loading:false,
|
||||
loadEnd:false
|
||||
};
|
||||
this.listData(2);
|
||||
},
|
||||
// 加载下一页
|
||||
onReachBottom(){
|
||||
if(!(this.loadParams.loadEnd || this.loadParams.noData)){
|
||||
this.loadParams.loading = true;
|
||||
this.params.page ++;
|
||||
this.listData();
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
listData(type=1){
|
||||
if(this.params.page == 1){
|
||||
uni.showLoading({
|
||||
title: '加载中',
|
||||
mask: true
|
||||
})
|
||||
}
|
||||
this.$api.request('/order.list',this.params).then(res=>{
|
||||
if(type ==2){
|
||||
uni.stopPullDownRefresh();
|
||||
}
|
||||
setTimeout( ()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
|
||||
this.loadParams.loading = false;
|
||||
if(res.data.rows.length ==0 && this.params.page == 1){
|
||||
this.loadParams.noData = true;
|
||||
}
|
||||
if(res.data.rows.length>0 && res.data.rows.length < this.params.pageSize){
|
||||
this.loadParams.loadEnd = true;
|
||||
}
|
||||
if(this.params.page == 1){
|
||||
this.list = res.data.rows;
|
||||
}else{
|
||||
this.list = this.list.concat(res.data.rows);
|
||||
}
|
||||
}).catch(err=>{
|
||||
setTimeout( ()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
})
|
||||
},
|
||||
//跳转工单详情
|
||||
toDetail(id){
|
||||
uni.navigateTo({
|
||||
url:'/pages/production/productionDetail?id='+id
|
||||
})
|
||||
},
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.page_padding{
|
||||
padding-top: 0;
|
||||
}
|
||||
.detail_list{
|
||||
.list_centre{display: flex;text-align: center;padding-bottom: 10px;
|
||||
view{flex: 1;}
|
||||
.percentage{color: $uni-text-color-primary;margin: 10px 0 0 0;}
|
||||
}
|
||||
.list_below{padding-bottom: 12px;
|
||||
.row{display: flex;padding-top: 12px;
|
||||
.row_left{
|
||||
white-space: nowrap;overflow: hidden;text-overflow: ellipsis;
|
||||
padding-right: 4px;
|
||||
}
|
||||
.row_right{
|
||||
white-space: nowrap;overflow: hidden;text-overflow: ellipsis;
|
||||
padding-left: 4px;
|
||||
}
|
||||
view{flex: 1;}
|
||||
.row_left .name,.row_right .name{
|
||||
display: inline-block;
|
||||
width: 65px;
|
||||
font-weight: bold;
|
||||
}
|
||||
.status{
|
||||
color: $uni-text-color-warning;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
</style>
|
267
pages/schedul/list.vue
Normal file
@ -0,0 +1,267 @@
|
||||
<template>
|
||||
<view class="page_padding columnFlex">
|
||||
<view class="statistics" v-if="form.date == 'day'">
|
||||
<view class="title font14">排程日统计</view>
|
||||
<view class="boxView contentboxsty">
|
||||
<view class="item">
|
||||
<view class="name font13">待生产</view>
|
||||
<view class="font_bold">32</view>
|
||||
</view>
|
||||
<view class="item">
|
||||
<view class="name font13">生产中</view>
|
||||
<view class="font_bold">12</view>
|
||||
</view>
|
||||
<view class="item">
|
||||
<view class="name font13">生产完成</view>
|
||||
<view class="font_bold">102</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="comView font13" :class="form.date == 'day'?'padd12 contentboxsty':''">
|
||||
<view class="dateView">
|
||||
<view class="dateTitle">
|
||||
<view class="title font14">排程视图 <text class="month">{{dateText}}</text></view>
|
||||
<view class="dateSwitch">
|
||||
<div class="item" :class="form.date == item.value?'dateActive':''" @click="form.date = item.value" v-for="(item,index) in dateList" :key="index">{{item.name}}</div>
|
||||
</view>
|
||||
</view>
|
||||
<view :class="form.date !='day'?'contentboxsty mar_top12 mar_bot12 padd12':'calendarView'">
|
||||
<calendar></calendar>
|
||||
</view>
|
||||
</view>
|
||||
<view class="speedView contentboxsty" :class="form.date!='day'?'padd12':''">
|
||||
<view class="left">
|
||||
<view class="line"></view>
|
||||
</view>
|
||||
<view class="right detail_list">
|
||||
<view class="boxItem padd12" v-for="(item,index) in list" :key="index">
|
||||
<view class="time">{{item.time}}</view>
|
||||
<view class="boxView card_right" :class="item.type==1?'success':item.type==2?'warning':item.type==3?'status':item.type==4?'error':''">
|
||||
<view class="cardStatus" :class="item.type==1?'success':item.type==2?'warning':item.type==3?'status':item.type==4?'error':''">{{item.status}}</view>
|
||||
<view class="row font_bold">
|
||||
<view class="name">工单号:</view>
|
||||
<view class="text">{{item.sn}}</view>
|
||||
</view>
|
||||
<view class="row">
|
||||
<view class="name">规格:</view>
|
||||
<view class="text">4*9*63</view>
|
||||
</view>
|
||||
<view class="row rowDate">
|
||||
<view class="date">
|
||||
<text class="name">开始时间:</text>
|
||||
<text class="text color">00:00</text>
|
||||
</view>
|
||||
<view class="date">
|
||||
<text class="name">剩余时间:</text>
|
||||
<text class="text">00:30</text>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
<view class="yieldView">
|
||||
<view class="box">
|
||||
<view class="num font18 font_bold">74.3<text class="symbol font12">%</text></view>
|
||||
<view class="name">出材率</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
components: {
|
||||
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
list:[
|
||||
{name:'',sn:"SO20240426000001",num:20,status:'待生产',type:1,time:'00:00'},
|
||||
{name:'',sn:"SO20240426000001",num:70,status:'生产中',type:2,time:'00:30'},
|
||||
{name:'',sn:"SO20240426000001",num:90,status:'生产完成',type:3},
|
||||
{name:'',sn:"SO20240422000002",num:20,status:'生产暂停',type:4,time:'01:00'},
|
||||
{name:'',sn:"SO20240426000001",num:70,status:'待生产',type:1},
|
||||
{name:'',sn:"SO20240426000001",num:90,status:'待生产',type:1,time:'03:00'},
|
||||
{name:'',sn:"SO20240426000001",num:90,status:'待生产',type:1},
|
||||
],
|
||||
dateList:[
|
||||
{name:'日',id:'',value:'day'},
|
||||
{name:'周',id:'',value:'week'},
|
||||
{name:'月',id:'',value:'month'},
|
||||
],
|
||||
dateText:'',
|
||||
form:{
|
||||
date:'day'
|
||||
}
|
||||
}
|
||||
},
|
||||
provide(){
|
||||
return{
|
||||
params:this.form,
|
||||
changeDateText:this.changeDate
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
changeDate(val){
|
||||
this.dateText = val;
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.statistics{
|
||||
.boxView{
|
||||
display: flex;flex-direction: row;align-items: center;margin-top: 12px;
|
||||
.item{
|
||||
flex: 1;display: flex;align-items: center;justify-content:center;flex-direction: column;padding: 12px 0;
|
||||
.name{padding-bottom: 10px;}
|
||||
}
|
||||
}
|
||||
}
|
||||
.comView{margin-top: 12px;}
|
||||
.dateView{width: 100%;}
|
||||
.dateTitle{
|
||||
width: 100%;display: flex;align-items: center;justify-content: space-between;
|
||||
.dateSwitch{
|
||||
display: flex;align-items: center;background: $uni-bg-color-whith;border-radius: 20px;padding: 2px 3px;
|
||||
.item{
|
||||
padding: 5px 18px;
|
||||
color: $uni-text-color-default;
|
||||
}
|
||||
.dateActive{
|
||||
border-radius: 20px;
|
||||
background: $uni-color-primary;
|
||||
color: $uni-text-color-inverse;
|
||||
}
|
||||
}
|
||||
}
|
||||
.calendarView{
|
||||
margin: 20px 0;
|
||||
}
|
||||
.speedView{
|
||||
width: 100%;display: flex;box-sizing: border-box;
|
||||
.left{
|
||||
flex-basis: 45px;
|
||||
display: flex;align-items: flex-start;flex-direction: column;padding: 12px 0 12px 18px;box-sizing: border-box;
|
||||
.line{
|
||||
position: relative;width: 1px;height: 100%;background: $uni-text-color-info;
|
||||
}
|
||||
.line::after{
|
||||
content: '';
|
||||
position: absolute;
|
||||
z-index: 20;
|
||||
bottom: 0;
|
||||
left: -4px;
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
border-radius: 50%;
|
||||
background: $uni-text-color-info;
|
||||
}
|
||||
}
|
||||
.right{
|
||||
flex: 1;margin: 0;
|
||||
.boxItem:first-child{
|
||||
margin-top: 6px;
|
||||
}
|
||||
.boxItem:last-child{
|
||||
margin-bottom: 6px;
|
||||
}
|
||||
.boxItem{
|
||||
background: $uni-bg-color-schedule;
|
||||
margin: 12px 0;
|
||||
padding-left: 20px;
|
||||
border-radius: 8px;
|
||||
position: relative;
|
||||
z-index: 10;
|
||||
.boxView{
|
||||
display: block;
|
||||
}
|
||||
}
|
||||
.time{
|
||||
position: absolute;
|
||||
left: -45px;
|
||||
top: 0;
|
||||
background: $uni-bg-color-primary;
|
||||
padding: 4px 2px;
|
||||
}
|
||||
.yieldView{
|
||||
position: absolute;
|
||||
right: 12px;
|
||||
top: 12px;
|
||||
z-index: 20;
|
||||
height: calc(100% - 30px);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
.box{
|
||||
display: flex;flex-direction: column;align-items: center;
|
||||
.num{color: $uni-text-color-warning;}
|
||||
.name{color: $uni-text-color-warning;}
|
||||
}
|
||||
}
|
||||
.cardStatus{
|
||||
display: inline-block;
|
||||
}
|
||||
.row{
|
||||
display: flex;align-items: center;
|
||||
margin-top: 12px;
|
||||
.date{
|
||||
display: flex;align-items: center;
|
||||
}
|
||||
}
|
||||
.rowDate{
|
||||
justify-content: space-between;
|
||||
.color{
|
||||
color: $uni-text-color-primary;
|
||||
}
|
||||
}
|
||||
.status::after{
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
width: 12px;
|
||||
border-top-left-radius: 8px;
|
||||
border-bottom-left-radius: 8px;
|
||||
background: $uni-bg-color-success;
|
||||
}
|
||||
.success::after{
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
width: 12px;
|
||||
border-top-left-radius: 8px;
|
||||
border-bottom-left-radius: 8px;
|
||||
background: $uni-bg-color-success;
|
||||
}
|
||||
.warning::after{
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
width: 12px;
|
||||
border-top-left-radius: 8px;
|
||||
border-bottom-left-radius: 8px;
|
||||
background: $uni-bg-color-warning;
|
||||
}
|
||||
.error::after{
|
||||
content: '';
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
height: 100%;
|
||||
width: 12px;
|
||||
border-top-left-radius: 8px;
|
||||
border-bottom-left-radius: 8px;
|
||||
background: $uni-bg-color-error;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
BIN
static/.DS_Store
vendored
Normal file
117
static/css/app.css
Normal file
@ -0,0 +1,117 @@
|
||||
/* 横向滚动条 */
|
||||
.horizontalScrollView ::-webkit-scrollbar{
|
||||
display: none;
|
||||
width: 0;
|
||||
height: 0;
|
||||
}
|
||||
|
||||
/* 检索部分 */
|
||||
.columnFlex{
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
.headerView{
|
||||
padding: 10px 0;
|
||||
flex-basis: 40px;
|
||||
}
|
||||
.searchBox .searchView{
|
||||
position: relative;
|
||||
}
|
||||
.searchBox .searchInput{
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
}
|
||||
.searchBox .searchInput .input{
|
||||
border-radius: 20px;
|
||||
padding: 7px 13px 7px 13px;
|
||||
flex: 1;
|
||||
}
|
||||
.searchBox .searchInput .filter{
|
||||
flex-basis: 32px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: flex-end;
|
||||
}
|
||||
.headerViewFixed{
|
||||
position: fixed;
|
||||
left: 14px;
|
||||
top: 0;
|
||||
z-index: 100;
|
||||
width: calc(100% - 28px);
|
||||
}
|
||||
.flexBox{
|
||||
flex: 1;
|
||||
}
|
||||
.scrollView{
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
|
||||
/* 加载更多部分 */
|
||||
.noData{
|
||||
margin: 50% auto;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
.noData .imgView .img{
|
||||
width: 180px;
|
||||
height: 138px;
|
||||
}
|
||||
.noData .text{
|
||||
margin-top: 10px;
|
||||
}
|
||||
.loadBox{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
.loadBox .text{
|
||||
margin-left: 8px;
|
||||
}
|
||||
.loadBox .icon{
|
||||
animation: spin 0.6s linear infinite;
|
||||
}
|
||||
@keyframes spin {
|
||||
to {
|
||||
transform: rotate(360deg);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* picker 下拉选择 */
|
||||
.pickerBom{
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
/* 上传组件的自定义优化 */
|
||||
.img_row .file-picker__box-content{
|
||||
border: none !important;
|
||||
background: rgba(255, 255, 255, 0.5);
|
||||
border-radius: 4px !important;
|
||||
}
|
||||
.img_row .uni-file-picker__header .file-title{
|
||||
color: #fff;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
/* 选择日期时间组件自定义优化 */
|
||||
.input_date .uni-date-x--border{
|
||||
border: 0;
|
||||
}
|
||||
.input_date .uni-date-x{
|
||||
background: none;
|
||||
}
|
||||
.input_date .uni-date-x .icon-calendar{
|
||||
padding: 0;
|
||||
}
|
||||
.input_date .uni-date-x .uni-icons{
|
||||
display: none;
|
||||
}
|
BIN
static/disable.png
Normal file
After Width: | Height: | Size: 1.1 KiB |
BIN
static/enable.png
Normal file
After Width: | Height: | Size: 1.2 KiB |
BIN
static/iconfont/.DS_Store
vendored
Normal file
BIN
static/iconfont/iconfont-weapp/.DS_Store
vendored
Normal file
@ -1,17 +1,190 @@
|
||||
@font-face {
|
||||
font-family: "iconfont"; /* Project id 4403683 */
|
||||
src: url('//at.alicdn.com/t/c/font_4403683_jzx1hwbdok.woff2?t=1704766027171') format('woff2'),
|
||||
url('//at.alicdn.com/t/c/font_4403683_jzx1hwbdok.woff?t=1704766027171') format('woff'),
|
||||
url('//at.alicdn.com/t/c/font_4403683_jzx1hwbdok.ttf?t=1704766027171') format('truetype');
|
||||
src: url('//at.alicdn.com/t/c/font_4403683_vv40jcno6w9.woff2?t=1714724942805') format('woff2'),
|
||||
url('//at.alicdn.com/t/c/font_4403683_vv40jcno6w9.woff?t=1714724942805') format('woff'),
|
||||
url('//at.alicdn.com/t/c/font_4403683_vv40jcno6w9.ttf?t=1714724942805') format('truetype');
|
||||
}
|
||||
|
||||
.iconfont {
|
||||
font-family: "iconfont" !important;
|
||||
font-size: 16px;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
.icon-daiju:before {
|
||||
content: "\e63a";
|
||||
}
|
||||
|
||||
.icon-a-shexiangtou_shiti1:before {
|
||||
content: "\e639";
|
||||
}
|
||||
|
||||
.icon-meiyougengduo:before {
|
||||
content: "\e638";
|
||||
}
|
||||
|
||||
.icon-loading:before {
|
||||
content: "\e891";
|
||||
}
|
||||
|
||||
.icon-bianji1:before {
|
||||
content: "\e601";
|
||||
}
|
||||
|
||||
.icon-bangding1:before {
|
||||
content: "\e602";
|
||||
}
|
||||
|
||||
.icon-a-shaixuan2:before {
|
||||
content: "\e636";
|
||||
}
|
||||
|
||||
.icon-a-Vector6:before {
|
||||
content: "\e637";
|
||||
}
|
||||
|
||||
.icon-a-Vector6-copy:before {
|
||||
content: "\e655";
|
||||
}
|
||||
|
||||
.icon-saoyisao:before {
|
||||
content: "\e600";
|
||||
}
|
||||
|
||||
.icon-a-shengchanshijian1:before {
|
||||
content: "\e63b";
|
||||
}
|
||||
|
||||
.icon-weixuanzhong:before {
|
||||
content: "\e635";
|
||||
}
|
||||
|
||||
.icon-paizhao:before {
|
||||
content: "\e633";
|
||||
}
|
||||
|
||||
.icon-qiehuanjingtou:before {
|
||||
content: "\e634";
|
||||
}
|
||||
|
||||
.icon-renlianrenzheng:before {
|
||||
content: "\e632";
|
||||
}
|
||||
|
||||
.icon-xuanzhong:before {
|
||||
content: "\e631";
|
||||
}
|
||||
|
||||
.icon-renzhengshibai:before {
|
||||
content: "\e62f";
|
||||
}
|
||||
|
||||
.icon-renzhengchenggong:before {
|
||||
content: "\e630";
|
||||
}
|
||||
|
||||
.icon-shenpi:before {
|
||||
content: "\e62d";
|
||||
}
|
||||
|
||||
.icon-a-shanchu21:before {
|
||||
content: "\e62e";
|
||||
}
|
||||
|
||||
.icon-weixiubaoyangpinshuai:before {
|
||||
content: "\e62a";
|
||||
}
|
||||
|
||||
.icon-brokenrate:before {
|
||||
content: "\e652";
|
||||
}
|
||||
|
||||
.icon-setting:before {
|
||||
content: "\e651";
|
||||
}
|
||||
|
||||
.icon-broken:before {
|
||||
content: "\e650";
|
||||
}
|
||||
|
||||
.icon-WIFI_off:before {
|
||||
content: "\e654";
|
||||
}
|
||||
|
||||
.icon-WIFI_on:before {
|
||||
content: "\e653";
|
||||
}
|
||||
|
||||
.icon-yasuokongqi:before {
|
||||
content: "\e62b";
|
||||
}
|
||||
|
||||
.icon-dianliang:before {
|
||||
content: "\e62c";
|
||||
}
|
||||
|
||||
.icon-tianjia1:before {
|
||||
content: "\e629";
|
||||
}
|
||||
|
||||
.icon-jinyong2:before {
|
||||
content: "\e627";
|
||||
}
|
||||
|
||||
.icon-qiyong1:before {
|
||||
content: "\e628";
|
||||
}
|
||||
|
||||
.icon-jinyong1:before {
|
||||
content: "\e626";
|
||||
}
|
||||
|
||||
.icon-a-Group10234:before {
|
||||
content: "\e625";
|
||||
}
|
||||
|
||||
.icon-a-sousuo41:before {
|
||||
content: "\e624";
|
||||
}
|
||||
|
||||
.icon-tianjia:before {
|
||||
content: "\e623";
|
||||
}
|
||||
|
||||
.icon-qiyong:before {
|
||||
content: "\e620";
|
||||
}
|
||||
|
||||
.icon-gengduo:before {
|
||||
content: "\e61c";
|
||||
}
|
||||
|
||||
.icon-a-shangchuanzhaopian2:before {
|
||||
content: "\e61d";
|
||||
}
|
||||
|
||||
.icon-bangding:before {
|
||||
content: "\e61e";
|
||||
}
|
||||
|
||||
.icon-jinyong:before {
|
||||
content: "\e61f";
|
||||
}
|
||||
|
||||
.icon-gengduo-1:before {
|
||||
content: "\e621";
|
||||
}
|
||||
|
||||
.icon-bianji:before {
|
||||
content: "\e622";
|
||||
}
|
||||
|
||||
.icon-xiala:before {
|
||||
content: "\e61b";
|
||||
}
|
||||
|
||||
.icon-xitongshezhi-gerenzhongxin:before {
|
||||
content: "\e611";
|
||||
}
|
||||
|
BIN
static/indexA.png
Normal file
After Width: | Height: | Size: 978 B |
BIN
static/indexB.png
Normal file
After Width: | Height: | Size: 940 B |
BIN
static/personA.png
Normal file
After Width: | Height: | Size: 884 B |
BIN
static/personB.png
Normal file
After Width: | Height: | Size: 949 B |
BIN
static/sweep.png
Normal file
After Width: | Height: | Size: 6.8 KiB |
51
uni.scss
@ -1,10 +1,59 @@
|
||||
@import '@/uni_modules/uni-scss/variables.scss';
|
||||
/* 行为基本色 */
|
||||
$uni-color-primary: #009688;
|
||||
$uni-color-success: #67C23A;
|
||||
$uni-color-warning: #F5AC3F;
|
||||
$uni-color-error: #F84545;
|
||||
$uni-color-info: #6576B7;
|
||||
|
||||
/* 文字基本色 */
|
||||
$uni-text-color-primary: #009688;
|
||||
$uni-text-color-success: #67C23A;
|
||||
$uni-text-color-info: #909398;
|
||||
$uni-text-color-warning: #F5AC3F;
|
||||
$uni-text-color-danger: #FA3758;
|
||||
$uni-text-color: #333;
|
||||
$uni-text-color-tip: #6E6E6E;
|
||||
$uni-text-color-inverse: #fff;
|
||||
$uni-text-color-grey: #999999;
|
||||
$uni-text-color-placeholder: rgba(255,255,255,0.7);
|
||||
$uni-text-color-default: #000000;
|
||||
$uni-text-color-loading: #5D71A3;
|
||||
|
||||
|
||||
/* 文字尺寸 */
|
||||
$uni-font-size-sm:24rpx;
|
||||
$uni-font-size-base:28rpx;
|
||||
$uni-font-size-lg:32rpx;
|
||||
|
||||
/* 背景色 */
|
||||
$uni-bg-color-default:#060B26;
|
||||
$uni-bg-color-primary:#1C2755;
|
||||
$uni-bg-color-success:#67C23A;
|
||||
$uni-bg-color-warning:#F5AC3F;
|
||||
$uni-bg-color-error:#F84545;
|
||||
$uni-bg-color-info:#6576B7;
|
||||
$uni-bg-color-grey:#CCCCCC;
|
||||
$uni-bg-color-whith:#FFFFFF;
|
||||
$uni-bg-color-schedule:#45538C;
|
||||
$uni-bg-color-default-dark:rgba(0, 150, 136, 0.5);
|
||||
$uni-bg-color-success-dark:rgba(103, 194, 58, 0.25);
|
||||
$uni-bg-color-warning-dark:rgba(230, 162, 60, 0.25);
|
||||
$uni-bg-color-error-dark:rgba(248, 69, 69, 0.25);
|
||||
$uni-bg-color-placeholder:rgba(255, 255, 255, 0.5);
|
||||
$uni-bg-color-delete:rgba(0, 0, 0, 0.5);
|
||||
|
||||
|
||||
/* 边框的颜色 */
|
||||
$uni-border-color-primary:#2D3A6F;
|
||||
$uni-border-color-default:#131E3B;
|
||||
|
||||
|
||||
/* 边框阴影 */
|
||||
$uni-border-shadow-color-default:#999999;
|
||||
$uni-border-shadow-color-white:#ffffff;
|
||||
$uni-border-shadow-color-black:#000000;
|
||||
|
||||
/* 透明度 */
|
||||
$uni-opacity-disabled: 0.3; // 组件禁用态的透明度
|
||||
|
||||
|
||||
|
156
utils/api.js
Normal file
@ -0,0 +1,156 @@
|
||||
import config from './envConfig.js';
|
||||
import wf from './public.js';
|
||||
|
||||
const request = (url = '', data = {}, header = {
|
||||
'Authorization': 'Bearer '+uni.getStorageSync('mes_token') ? 'Bearer '+uni.getStorageSync('mes_token') : '',
|
||||
}) => {
|
||||
return new Promise((resolve, reject) => {
|
||||
uni.request({
|
||||
url: config.dev.VITE_BASE_API + url,
|
||||
method: "POST",
|
||||
dataType: "json",
|
||||
data: data,
|
||||
header: header,
|
||||
success: (res) => {
|
||||
if (res.data.code == 401){
|
||||
setTimeout( ()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
uni.showModal({
|
||||
showCancel: false,
|
||||
title: '温馨提示',
|
||||
confirmColor:'#009688',
|
||||
content: res.data.message,
|
||||
success: (result)=> {
|
||||
if (result.confirm) {
|
||||
uni.reLaunch({
|
||||
url: '/pages/login/login'
|
||||
});
|
||||
wf.removeLoginData();
|
||||
}
|
||||
}
|
||||
});
|
||||
return
|
||||
}
|
||||
if(res.header.Authorization){
|
||||
uni.removeStorageSync('mes_token');
|
||||
let obj = new Object();
|
||||
let str = String(res.header.Authorization)
|
||||
let newStr = str.slice(0, 0) + str.slice(7)
|
||||
obj.mes_token = newStr;
|
||||
uni.setStorageSync("mes_token",obj.mes_token);
|
||||
}
|
||||
|
||||
// 成功的回调
|
||||
if(res.data.code == 200){
|
||||
resolve(res.data);
|
||||
}else{
|
||||
uni.showToast({
|
||||
icon:'none',
|
||||
title:res.data.message
|
||||
})
|
||||
}
|
||||
},
|
||||
fail: (err) => {
|
||||
uni.showToast({
|
||||
title: "" + err.msg,
|
||||
icon: 'none'
|
||||
});
|
||||
reject(err)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
const postFuncLoading = (url = '', data = {}, header = {
|
||||
'Authorization': 'Bearer '+uni.getStorageSync('mes_token') ? 'Bearer '+uni.getStorageSync('mes_token') : '',
|
||||
}) => {
|
||||
uni.showLoading({
|
||||
title: '加载中',
|
||||
mask: true
|
||||
})
|
||||
return new Promise((resolve, reject) => {
|
||||
uni.request({
|
||||
url: config.dev.VITE_BASE_API + url, //接口地址:前缀+方法中传入的地址
|
||||
method: "POST", //请求方法
|
||||
dataType: "json",
|
||||
data: data, //传递参数
|
||||
header: header, //自定义头部,和后端商同后编写
|
||||
success: (res) => {
|
||||
setTimeout( ()=> {
|
||||
uni.hideLoading();
|
||||
}, 200);
|
||||
if (res.data.code == 401){
|
||||
wf.removeLoginData();
|
||||
uni.showModal({
|
||||
showCancel: false,
|
||||
title: '温馨提示',
|
||||
confirmColor:'#009688',
|
||||
content: res.data.message,
|
||||
success: (result)=> {
|
||||
if (result.confirm) {
|
||||
uni.reLaunch({
|
||||
url: '/pages/login/login'
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
return
|
||||
}
|
||||
if(res.header.Authorization){
|
||||
uni.removeStorageSync('mes_token');
|
||||
let obj = new Object();
|
||||
let str = String(res.header.Authorization)
|
||||
let newStr = str.slice(0, 0) + str.slice(7)
|
||||
obj.mes_token = newStr;
|
||||
uni.setStorageSync("mes_token",obj.mes_token);
|
||||
}
|
||||
// 成功的回调
|
||||
if(res.data.code == 200){
|
||||
resolve(res.data)
|
||||
}else{
|
||||
uni.showToast({
|
||||
icon:'none',
|
||||
title:res.data.message
|
||||
})
|
||||
}
|
||||
},
|
||||
fail: (err) => {
|
||||
uni.showToast({
|
||||
title: "" + err.msg,
|
||||
icon: 'none'
|
||||
});
|
||||
reject(err)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
const getOss = (url = '', data = {}, header = {
|
||||
'content-type':'application/json; charset=UTF-8',
|
||||
'Authorization':''
|
||||
})=>{
|
||||
return new Promise((resolve, reject) => {
|
||||
uni.request({
|
||||
url: config.dev.VITE_OSS_URL + url, //接口地址:前缀+方法中传入的地址
|
||||
method: "POST",
|
||||
dataType: "json",
|
||||
data: data,
|
||||
header: header,
|
||||
success:(res)=>{
|
||||
if(res.data.code == 200){
|
||||
resolve(res.data);
|
||||
}
|
||||
},
|
||||
fail:(err)=>{
|
||||
reject(err);
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
export default {
|
||||
request,
|
||||
postFuncLoading,
|
||||
getOss
|
||||
};
|
||||
|
16
utils/envConfig.js
Normal file
@ -0,0 +1,16 @@
|
||||
//本地环境
|
||||
const dev = {
|
||||
ENV: "dev",
|
||||
VITE_BASE_API: "https://api.dev.dwoodauto.com/mobile/v1",
|
||||
VITE_OSS_URL: "https://cloud-wh-dev.dwood365.com/mobile/v1",
|
||||
};
|
||||
//正式环境
|
||||
const pro = {
|
||||
ENV: "pro",
|
||||
VITE_BASE_API: "https://api.dev.dwoodauto.com",
|
||||
VITE_OSS_URL: "https://wf-api.dwood168.com/wh-mobile/v1",
|
||||
};
|
||||
export default {
|
||||
dev,
|
||||
pro,
|
||||
};
|
421
utils/public.js
Normal file
@ -0,0 +1,421 @@
|
||||
//登录存储信息
|
||||
const setLoginData=function(obj){
|
||||
uni.setStorageSync("demu_mes_user_name",obj.mes_user_name);
|
||||
uni.setStorageSync("mes_token",obj.mes_token);
|
||||
}
|
||||
|
||||
const removeLoginData=function(){
|
||||
uni.removeStorageSync("demu_mes_user_name");
|
||||
uni.removeStorageSync("mes_token");
|
||||
}
|
||||
// 重定义 弹窗
|
||||
const toast = function(params){
|
||||
uni.showToast({
|
||||
title:params.text,
|
||||
icon:params.type,
|
||||
duration:1000
|
||||
})
|
||||
}
|
||||
|
||||
// 0~9 对应小数转换
|
||||
const numberToChineseLower = function(num) {
|
||||
const chineseMonths = {
|
||||
'1': '一',
|
||||
'2': '二',
|
||||
'3': '三',
|
||||
'4': '四',
|
||||
'5': '五',
|
||||
'6': '六',
|
||||
'7': '七',
|
||||
'8': '八',
|
||||
'9': '九',
|
||||
'10': '十',
|
||||
'11': '十一',
|
||||
'12': '十二'
|
||||
};
|
||||
return chineseMonths[num] || '';
|
||||
}
|
||||
|
||||
const getToday = function() {
|
||||
let today = new Date();
|
||||
let year = today.getFullYear();
|
||||
let month = today.getMonth() + 1;
|
||||
let day = today.getDate();
|
||||
|
||||
let formattedMonth = month < 10 ? '0' + month : month;
|
||||
let formattedDay = day < 10 ? '0' + day : day;
|
||||
|
||||
// 返回格式化后的日期字符串,格式为 yyyy-mm-dd
|
||||
return year + '-' + formattedMonth + '-' + formattedDay;
|
||||
}
|
||||
|
||||
const getDatesOfWeek = function() {
|
||||
var now = new Date();
|
||||
// 获取当前日期是周几,0表示周日,1表示周一,以此类推
|
||||
var dayOfWeek = now.getDay();
|
||||
var monday = new Date(now.setDate(now.getDate() - dayOfWeek + (dayOfWeek === 0 ? 0 : 1)));
|
||||
var datesOfWeek = [];
|
||||
for (var i = 0; i < 7; i++) {
|
||||
var currentDate = new Date(monday.getTime() + i * 24 * 60 * 60 * 1000);
|
||||
var weekdays = ['日', '一', '二', '三', '四', '五', '六'];
|
||||
var weekday = weekdays[currentDate.getDay()];
|
||||
|
||||
var dateInfo = {
|
||||
date: currentDate.toISOString().split('T')[0],
|
||||
name: weekday
|
||||
};
|
||||
datesOfWeek.push(dateInfo);
|
||||
}
|
||||
return datesOfWeek;
|
||||
}
|
||||
|
||||
// 往前一周
|
||||
const getPreviousWeekDatesWithDays = function(date=null) {
|
||||
var now = new Date(date);
|
||||
var lastMonday = new Date(now);
|
||||
lastMonday.setDate(lastMonday.getDate() - 7);
|
||||
var datesAndDays = [];
|
||||
|
||||
for (var i = 0; i < 7; i++) {
|
||||
var currentDate = new Date(lastMonday.getTime() + i * 24 * 60 * 60 * 1000);
|
||||
var weekdays = ['日', '一', '二', '三', '四', '五', '六'];
|
||||
datesAndDays.push({
|
||||
date: currentDate.toISOString().split('T')[0],
|
||||
name: weekdays[currentDate.getDay()]
|
||||
});
|
||||
}
|
||||
|
||||
return datesAndDays;
|
||||
}
|
||||
|
||||
// 往后一周
|
||||
const getNextWeekDatesWithDays = function(date = null) {
|
||||
var now = new Date(date);
|
||||
var nextMonday = new Date(now);
|
||||
nextMonday.setDate(nextMonday.getDate() + (8 - now.getDay()) % 7);
|
||||
var datesAndDays = [];
|
||||
|
||||
for (var i = 0; i < 7; i++) {
|
||||
var currentDate = new Date(nextMonday.getTime() + i * 24 * 60 * 60 * 1000);
|
||||
var weekdays = ['日', '一', '二', '三', '四', '五', '六'];
|
||||
datesAndDays.push({
|
||||
date: currentDate.toISOString().split('T')[0],
|
||||
name: weekdays[currentDate.getDay()]
|
||||
});
|
||||
}
|
||||
|
||||
return datesAndDays;
|
||||
}
|
||||
|
||||
// 获取本月日期
|
||||
// year, month
|
||||
const getWeeksOfMonth = function() {
|
||||
var now = new Date();
|
||||
var year = now.getFullYear();
|
||||
var month = now.getMonth() + 1;
|
||||
const startDate = new Date(year, month - 1, 1);
|
||||
const endDate = new Date(year, month, 0);
|
||||
const startDateDayOfWeek = startDate.getDay(); // 获取本月第一天是周几
|
||||
const totalDays = endDate.getDate(); // 获取本月总天数
|
||||
|
||||
let weeks = [];
|
||||
let currentWeek = [];
|
||||
let currentDate = new Date(startDate);
|
||||
|
||||
// 填充到本周开始
|
||||
for (let i = 0; i < startDateDayOfWeek; i++) {
|
||||
currentWeek.push(null);
|
||||
}
|
||||
|
||||
while (currentDate <= endDate) {
|
||||
let textMonth = month<10?'0'+month:month;
|
||||
let textDate = currentDate.getDate()<10?'0'+currentDate.getDate():currentDate.getDate();
|
||||
currentWeek.push({
|
||||
date: year +'-'+ textMonth +'-'+ textDate,
|
||||
name: ['一', '二', '三', '四', '五', '六','日'][currentDate.getDay()]
|
||||
});
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
|
||||
// 当前周已满,开始新周
|
||||
if (currentWeek.length === 7) {
|
||||
weeks.push(currentWeek);
|
||||
currentWeek = [];
|
||||
}
|
||||
}
|
||||
|
||||
// 处理最后不满一周的情况
|
||||
if (currentWeek.length > 0) {
|
||||
while (currentWeek.length < 7) {
|
||||
currentWeek.push(null);
|
||||
}
|
||||
weeks.push(currentWeek);
|
||||
}
|
||||
|
||||
return weeks;
|
||||
}
|
||||
|
||||
// 往前推一个月
|
||||
const getPreviousMonthGroupedByWeek = function(date = null) {
|
||||
let now = new Date(date);
|
||||
var year = now.getFullYear();
|
||||
var month = now.getMonth();
|
||||
// 如果当前月份是1月,则年份减1,月份变成12月
|
||||
if (month === 0) {
|
||||
year--;
|
||||
month = 11;
|
||||
} else {
|
||||
month--;
|
||||
}
|
||||
let prevMonthFirstDay = new Date(year, month, 1); // 获取上一个月的第一天
|
||||
let prevMonthLastDay = new Date(year, month + 1, 0); // 获取上一个月的最后一天
|
||||
let currentDate = new Date(prevMonthFirstDay); // 从上一个月的第一天开始
|
||||
let weeksData = [];
|
||||
let currentWeek = [];
|
||||
|
||||
const weekdays = ['一', '二', '三', '四', '五', '六', '日'];
|
||||
|
||||
while (currentDate <= prevMonthLastDay) {
|
||||
// 获取当前日期和星期几
|
||||
let date = currentDate.getDate();
|
||||
let weekdayIndex = currentDate.getDay();
|
||||
|
||||
let textMonth = month<9?'0'+(month+1):(month+1);
|
||||
let textDate = date<10?'0'+date:date;
|
||||
currentWeek.push({
|
||||
date: year + '-' + textMonth + '-' + textDate,
|
||||
name: weekdays[weekdayIndex]
|
||||
});
|
||||
|
||||
// 如果到达了周日或者已经是最后一日,将当前周添加到weeksData,并重置currentWeek
|
||||
if (weekdayIndex === 6 || currentDate.getTime() === prevMonthLastDay.getTime()) {
|
||||
weeksData.push(currentWeek);
|
||||
currentWeek = [];
|
||||
}
|
||||
|
||||
// 前往下一天
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
}
|
||||
|
||||
return weeksData;
|
||||
}
|
||||
|
||||
const getNextMonthGroupedByWeek = function(date = null) {
|
||||
let now = new Date(date);
|
||||
var year = now.getFullYear();
|
||||
var month = now.getMonth();
|
||||
if (month === 11) {
|
||||
year++;
|
||||
month = 0;
|
||||
} else {
|
||||
month++;
|
||||
}
|
||||
let nextMonthFirstDay = new Date(year, month, 1); // 获取下一个月的第一天
|
||||
let nextMonthLastDay = new Date(year, month + 1, 0); // 获取下一个月的最后一天
|
||||
let currentDate = new Date(nextMonthFirstDay); // 从下一个月的第一天开始
|
||||
let weeksData = [];
|
||||
let currentWeek = [];
|
||||
|
||||
const weekdays = ['一', '二', '三', '四', '五', '六', '日'];
|
||||
|
||||
while (currentDate <= nextMonthLastDay) {
|
||||
let date = currentDate.getDate();
|
||||
let weekdayIndex = currentDate.getDay();
|
||||
|
||||
let textMonth = month<9?'0'+(month+1):(month+1);
|
||||
let textDate = date<10?'0'+date:date;
|
||||
currentWeek.push({
|
||||
date: year + '-' + textMonth + '-' + textDate,
|
||||
name: weekdays[weekdayIndex]
|
||||
});
|
||||
|
||||
if (weekdayIndex === 6 || currentDate.getTime() === nextMonthLastDay.getTime()) {
|
||||
weeksData.push(currentWeek);
|
||||
currentWeek = [];
|
||||
}
|
||||
|
||||
// 前往下一天
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
}
|
||||
|
||||
return weeksData;
|
||||
}
|
||||
|
||||
// 上一个月有几周
|
||||
const getPreviousMonthWeekCount = function(date = null) {
|
||||
let now = new Date(date);
|
||||
var year = now.getFullYear();
|
||||
var month = now.getMonth();
|
||||
if (month === 0) {
|
||||
year--;
|
||||
month = 11;
|
||||
} else {
|
||||
month--;
|
||||
}
|
||||
let prevMonthFirstDay = new Date(year, month, 1); // 获取上一个月的第一天
|
||||
let prevMonthLastDay = new Date(year, month + 1, 0); // 获取上一个月的最后一天
|
||||
let totalWeeks = 0;
|
||||
|
||||
// 计算上一个月有几周
|
||||
let currentDate = new Date(prevMonthFirstDay);
|
||||
while (currentDate <= prevMonthLastDay) {
|
||||
let weekdayIndex = currentDate.getDay();
|
||||
if (weekdayIndex === 6 || currentDate.getTime() === prevMonthLastDay.getTime()) {
|
||||
totalWeeks++;
|
||||
}
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
}
|
||||
|
||||
return totalWeeks;
|
||||
}
|
||||
|
||||
|
||||
// 下个月有几周
|
||||
const getNextMonthWeekCount = function(date = null) {
|
||||
let now = new Date(date);
|
||||
var year = now.getFullYear();
|
||||
var month = now.getMonth();
|
||||
if (month === 11) {
|
||||
year++;
|
||||
month = 0;
|
||||
} else {
|
||||
month++;
|
||||
}
|
||||
let nextMonthFirstDay = new Date(year, month, 1); // 获取下一个月的第一天
|
||||
let nextMonthLastDay = new Date(year, month + 1, 0); // 获取下一个月的最后一天
|
||||
let totalWeeks = 0;
|
||||
|
||||
let currentDate = new Date(nextMonthFirstDay);
|
||||
while (currentDate <= nextMonthLastDay) {
|
||||
let weekdayIndex = currentDate.getDay();
|
||||
if (weekdayIndex === 6 || currentDate.getTime() === nextMonthLastDay.getTime()) {
|
||||
totalWeeks++;
|
||||
}
|
||||
// 前往下一天
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
}
|
||||
|
||||
return totalWeeks;
|
||||
}
|
||||
|
||||
// 获取当前的日期
|
||||
const getCurrentYearData = function() {
|
||||
let today = new Date(); // 获取当前日期
|
||||
let year = today.getFullYear(); // 获取年份
|
||||
let yearData = []; // 存储当前年份的数据
|
||||
|
||||
// 循环遍历每个月份
|
||||
for (let month = 0; month < 12; month++) {
|
||||
let list = getCurrentMonthData(year,month+1);
|
||||
let monthData = {
|
||||
month: month + 1, // 月份从 1 开始
|
||||
weeks: list, // 存储该月份的所有周数据
|
||||
};
|
||||
|
||||
// 将该月份的数据添加到当前年份的数据中
|
||||
yearData.push(monthData);
|
||||
}
|
||||
|
||||
return yearData;
|
||||
}
|
||||
|
||||
// 获取上一年的日期
|
||||
const getPreviousYearData = function(date = null) {
|
||||
let currentDate = new Date(date); // 获取指定日期或者当前日期
|
||||
currentDate.setFullYear(currentDate.getFullYear() - 1); // 获取指定日期的上一年日期
|
||||
let year = currentDate.getFullYear(); // 获取年份
|
||||
let yearData = []; // 存储指定日期的上一年的数据
|
||||
|
||||
for (let month = 0; month < 12; month++) {
|
||||
let list = getCurrentMonthData(year, month + 1);
|
||||
let monthData = {
|
||||
month: month + 1,
|
||||
weeks: list,
|
||||
};
|
||||
|
||||
yearData.push(monthData);
|
||||
}
|
||||
|
||||
return yearData;
|
||||
}
|
||||
|
||||
// 获取下一年的日期
|
||||
const getNextYearData = function(date = null) {
|
||||
let currentDate = new Date(date); // 获取指定日期或者当前日期
|
||||
currentDate.setFullYear(currentDate.getFullYear() + 1); // 获取指定日期的上一年日期
|
||||
let year = currentDate.getFullYear(); // 获取年份
|
||||
let yearData = []; // 存储指定日期的上一年的数据
|
||||
|
||||
for (let month = 0; month < 12; month++) {
|
||||
let list = getCurrentMonthData(year, month + 1);
|
||||
let monthData = {
|
||||
month: month + 1,
|
||||
weeks: list,
|
||||
};
|
||||
|
||||
yearData.push(monthData);
|
||||
}
|
||||
|
||||
return yearData;
|
||||
}
|
||||
|
||||
|
||||
// 获取当前月的所有周
|
||||
const getCurrentMonthData = function(year,month) {
|
||||
const startDate = new Date(year, month - 1, 1);
|
||||
const endDate = new Date(year, month, 0);
|
||||
const startDateDayOfWeek = startDate.getDay(); // 获取本月第一天是周几
|
||||
const totalDays = endDate.getDate(); // 获取本月总天数
|
||||
|
||||
let weeks = [];
|
||||
let currentWeek = [];
|
||||
let currentDate = new Date(startDate);
|
||||
|
||||
// 填充到本周开始
|
||||
for (let i = 0; i < startDateDayOfWeek; i++) {
|
||||
currentWeek.push(null);
|
||||
}
|
||||
while (currentDate <= endDate) {
|
||||
let textMonth = month<10?'0'+month:month;
|
||||
let textDate = currentDate.getDate()<10?'0'+currentDate.getDate():currentDate.getDate();
|
||||
currentWeek.push({
|
||||
date: year +'-'+ textMonth +'-'+ textDate,
|
||||
name: ['一', '二', '三', '四', '五', '六','日'][currentDate.getDay()]
|
||||
});
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
|
||||
// 当前周已满,开始新周
|
||||
if (currentWeek.length === 7) {
|
||||
weeks.push(currentWeek);
|
||||
currentWeek = [];
|
||||
}
|
||||
}
|
||||
|
||||
// 处理最后不满一周的情况
|
||||
if (currentWeek.length > 0) {
|
||||
while (currentWeek.length < 7) {
|
||||
currentWeek.push(null);
|
||||
}
|
||||
weeks.push(currentWeek);
|
||||
}
|
||||
return weeks;
|
||||
}
|
||||
|
||||
|
||||
export default {
|
||||
setLoginData,
|
||||
removeLoginData,
|
||||
toast,
|
||||
numberToChineseLower,
|
||||
getToday,
|
||||
getDatesOfWeek,
|
||||
getPreviousWeekDatesWithDays,
|
||||
getNextWeekDatesWithDays,
|
||||
getWeeksOfMonth,
|
||||
getPreviousMonthGroupedByWeek,
|
||||
getNextMonthGroupedByWeek,
|
||||
getPreviousMonthWeekCount,
|
||||
getNextMonthWeekCount,
|
||||
getCurrentYearData,
|
||||
getPreviousYearData,
|
||||
getNextYearData,
|
||||
};
|
21
vite.config.js
Normal file
@ -0,0 +1,21 @@
|
||||
import { defineConfig } from "vite";
|
||||
import uni from "@dcloudio/vite-plugin-uni";
|
||||
import ENV_CONFIG from "./utils/envConfig.js";
|
||||
import { resolve } from "path"; // 导入 path 模块,帮助我们解析路径
|
||||
export default defineConfig(() => {
|
||||
return {
|
||||
server: {
|
||||
port: "3002",
|
||||
},
|
||||
resolve: {
|
||||
alias: {
|
||||
"@": resolve(__dirname, "/src"),
|
||||
},
|
||||
},
|
||||
plugins: [uni()],
|
||||
define: {
|
||||
"process.env.config": ENV_CONFIG, //配置一
|
||||
'process.env': process.env, //配置二
|
||||
},
|
||||
};
|
||||
});
|