parkingSiteDes.vue 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395
  1. <template>
  2. <view class="container">
  3. <u-navbar title="停车场主页" :background="{backgroundColor: '#ffffff'}" class="top-navbar" title-size="30">
  4. </u-navbar>
  5. <view class="parking-panel">
  6. <view class="panel-left">
  7. <view>
  8. <text class="left-title">{{parkingSite.parking_name}}</text>
  9. <u-icon name="edit-pen" size="32" color="#4a4a4a" style="margin-left:100rpx;padding:10rpx;" @tap="editParking"></u-icon>
  10. </view>
  11. <view class="left-txt">
  12. <text>总车位数 </text><text class="num-txt">{{parkingSite.total_parking_number}}</text>
  13. </view>
  14. <view class="left-txt">剩余车位数<text class="num-txt">{{parkingSite.surplus_parking_number}}</text></view>
  15. </view>
  16. <image :src="parkingSite.pic_url" style="width:200rpx;height:160rpx;border-radius: 10rpx;"></image>
  17. </view>
  18. <view class="parking-adr">
  19. <view style="padding-left:30rpx;line-height:60rpx;height: 60rpx;position: absolute;z-index: 2;width:100%;background-color: rgba(255,255,255,0.9);">{{parkingSite.address_}}</view>
  20. <image src="../../static/img/addrbg.png" style="height: 60rpx;width:100%;position: relative;z-index: 1;"></image>
  21. </view>
  22. <view class="li-title">收费规则</view>
  23. <view class="li-con">
  24. <text space="emsp"> {{chargeRule.rule_txt}}</text>
  25. <!-- <view style="margin-top:15rpx;"><text space="emsp"> {{chargeRule.oth_rule_txt}}</text></view> -->
  26. </view>
  27. <view class="li-title" style="display: flex;justify-content: space-between;">
  28. <text>设备列表</text>
  29. <u-icon name="reload" size="32" color="#55aaff" @click="loadPageData(crtparkId)"></u-icon>
  30. </view>
  31. <view class="li-con" v-for="(item,index) in devs">
  32. <view class="dev-tit">
  33. <text>{{item.gateName}}</text>
  34. <u-button type="primary" :custom-style="{height:'60rpx',margin:'0rpx 30rpx'}" :plain="true" @tap="manualPass(item.onlineDevId,item.gateName)">手动放行</u-button>
  35. <!-- <view class="dev-view"><text>查看</text><u-icon name="arrow-right"></u-icon></view> -->
  36. </view>
  37. <view class="dev-stat">
  38. <view><text style="margin-right:10rpx;">闸口状态:{{item.gateStatus?'在线':'离线'}} </text>
  39. <u-icon :name="item.channel_status=='1'?'checkmark-circle-fill':'error-circle-fill'" size="30" :color="item.gateStatus?'#15b53a':'#888888'"></u-icon>
  40. <!-- <text style="margin:0rpx 10rpx 0rpx 40rpx;">摄像头状态:正常 </text><u-icon name="checkmark-circle-fill" size="30" color="#15b53a"></u-icon> -->
  41. </view>
  42. </view>
  43. </view>
  44. <!-- <u-button type="primary" style="margin:50rpx 50rpx;" @tap="manualPass">出口抬杆放行</u-button> -->
  45. <u-modal v-model="showModal" :title="modalTitle" :show-cancel-button="true" @confirm="exePass">
  46. <view class="slot-content">
  47. <u-field v-model="passNote" label="" placeholder="请填写放行说明" type="textarea" label-width="0" :auto-height="false" :field-style="{height:'140rpx'}"/>
  48. </view>
  49. </u-modal>
  50. <u-modal v-model="showEditModal" ref="editModal" title="车位数编辑" :show-cancel-button="true" :async-close="true" @confirm="submitSeat">
  51. <view class="slot-content">
  52. <u-field type="number" v-model="seatModel.total" label="总车位数" :label-width="150" :field-style="{'border-bottom':'1px solid #55aaff'}"/>
  53. <u-field type="number" v-model="seatModel.idle" label="剩余车位数" :label-width="150" :field-style="{'border-bottom':'1px solid #55aaff'}"/>
  54. </view>
  55. </u-modal>
  56. </view>
  57. </template>
  58. <script>
  59. import * as api from '@/apis/myparkings.js'
  60. export default {
  61. data() {
  62. return {
  63. crtparkId:null,
  64. showModal:false,
  65. modalTitle:'放行说明',
  66. passNote:'',
  67. opening:false,
  68. openingChannel:'',
  69. parkingSite:{},
  70. chargeRule:{},
  71. othChargeRule:[],
  72. devs:[],
  73. showEditModal:false,
  74. seatModel:{
  75. total:null,
  76. idle:null
  77. }
  78. }
  79. },
  80. onLoad(opt){
  81. this.loadPageData(opt.park_id);
  82. this.crtparkId=opt.park_id
  83. },
  84. methods: {
  85. editParking(){
  86. this.showEditModal=true;
  87. this.seatModel.total=this.parkingSite.total_parking_number;
  88. this.seatModel.idle=this.parkingSite.surplus_parking_number;
  89. },
  90. closeEditModal(isClose){
  91. if(isClose){
  92. this.showEditModal=false;
  93. }
  94. else{
  95. this.$refs.editModal.clearLoading();
  96. }
  97. },
  98. submitSeat(){
  99. api.updateParkingSeat(this.parkingSite.id,this.seatModel.total,this.seatModel.idle).then(resp=>{
  100. if(!resp.success){
  101. uni.showToast({
  102. title:resp.msg||'保存数据失败',
  103. icon:'none'
  104. })
  105. this.closeEditModal()
  106. return;
  107. }
  108. uni.showToast({
  109. title:'操作成功',
  110. icon:'success'
  111. })
  112. this.closeEditModal(true)
  113. //编辑后的值设置到显示对象中,不用请求后台
  114. this.parkingSite.total_parking_number=this.seatModel.total;
  115. this.parkingSite.surplus_parking_number=this.seatModel.idle;
  116. }).catch(err=>{
  117. uni.showToast({
  118. title:'保存数据出错',
  119. icon:'none'
  120. })
  121. this.closeEditModal()
  122. })
  123. },
  124. manualPass(channelId,gateName){
  125. if(this.opening){
  126. uni.showToast({
  127. title:'开门中,勿重复操作',
  128. icon:'none'
  129. })
  130. return;
  131. }
  132. this.modalTitle=gateName+"放行";
  133. this.showModal=true;
  134. this.openingChannel=channelId;
  135. },
  136. exePass(){
  137. if(!this.openingChannel){
  138. uni.showToast({
  139. title:'未选择要开启设备',
  140. icon:'none'
  141. })
  142. return;
  143. }
  144. uni.showLoading({
  145. title:'开门中...'
  146. });
  147. api.manualPass(this.openingChannel,this.passNote).then(resp => {
  148. this.opening=false;
  149. uni.hideLoading();
  150. if(!resp.success){
  151. uni.showToast({
  152. title:resp.msg||'开门失败',
  153. icon:'none'
  154. })
  155. }
  156. else{
  157. uni.showToast({
  158. title:'手动开门已执行',
  159. icon:'none'
  160. })
  161. }
  162. }).catch(error => {
  163. this.opening=false;
  164. uni.hideLoading();
  165. });
  166. this.opening=true;
  167. },
  168. loadPageData(id){
  169. uni.showLoading({
  170. title:'加载中...'
  171. });
  172. api.loadParkingCompose(id).then(resp => {
  173. //console.log(resp);
  174. uni.hideLoading();
  175. if(!resp.success){
  176. uni.showToast({
  177. title:resp.msg||'加载数据失败',
  178. icon:'none'
  179. })
  180. return;
  181. }
  182. this.parkingSite=resp.data.parkInfo;
  183. if(!this.parkingSite.pic_url){
  184. this.parkingSite.pic_url="../../static/img/header_bg.png";
  185. }
  186. this.chargeRule=resp.data.chargeRule;
  187. let othchargeRule=resp.data.othchargeRule||[];
  188. let othRuleTxt={ryc:[],xny:[]};
  189. othchargeRule.forEach((item) => {
  190. if(item.car_type=='1'){ //燃油车
  191. othRuleTxt.ryc.push(`${item.min_section}-${item.max_section}分钟:${item.parking_cost}元`);
  192. }
  193. else if(item.car_type=='2'){ //新能源车
  194. othRuleTxt.xny.push(`${item.min_section}-${item.max_section}分钟:${item.parking_cost}元`);
  195. }
  196. });
  197. this.chargeRule['rule_txt']=`燃油车\n 免费时长:${this.chargeRule.free_duration}分钟,每小时费用:${this.chargeRule.hour_cost}元,${othRuleTxt.ryc.join(',')} \n新能源车\n 免费时长:${this.chargeRule.new_energy_free_duration}分钟,每小时费用:${this.chargeRule.new_energy_hour_cost}元,${othRuleTxt.xny.join(',')} \n每日封顶费用:${this.chargeRule.day_capping_cost}元`;
  198. //this.chargeRule['oth_rule_txt']=othRuleTxt.join(' ');
  199. console.log(resp.data.devs)
  200. this.devs=this.processDevDatas(resp.data.devs,id); //resp.data.devs
  201. console.log(this.devs)
  202. }).catch(error => {
  203. uni.hideLoading();
  204. });
  205. },
  206. //设备(通道设备-摄像头),分级显示(停车场-区域-出口、入口),根据所属道闸合并显示
  207. /*
  208. {
  209. area:{
  210. 'areaName':xxx,
  211. 'gate':{
  212. channelFlag:{
  213. 'gateName':xxx,
  214. 'gateStatus':xxx , //[true:online ,false:offline]
  215. 'onlineDevId':'',
  216. 'channels':[]
  217. }
  218. }
  219. }
  220. }*/
  221. processDevDatas(devs,parkId){
  222. if(!devs){
  223. return []
  224. }
  225. if(parkId!='1'){ //非荆鹏停车场
  226. devs.forEach(dev=>{
  227. dev['gateName']=dev['channel_name']
  228. dev['gateStatus']=dev['channel_status']=='1'
  229. dev['onlineDevId']=dev['id']
  230. })
  231. return devs
  232. }
  233. //荆鹏停车场(按道闸合并处理)
  234. let glbDev={},areaKey=null,gateNameStr=null
  235. devs.forEach(dev=>{ //dev.area=['0','1','2',null] 大楼院内(0)、公寓(1)、大楼前门(2)、全部区域(null)
  236. if(!dev.channel_flag){
  237. dev.channel_flag='1'
  238. }
  239. areaKey=dev.area || 'all'
  240. if(!glbDev[areaKey]){ //按区域分组
  241. glbDev[areaKey]={'areaName':api.getAreaName(areaKey),'gate':{}} //gate 道闸下的通道设备
  242. }
  243. if(!glbDev[areaKey]['gate'][dev.channel_flag]){ //按所属道闸合并显示,道闸名=区域名+道闸序号+'入口/出口'
  244. gateNameStr=`${glbDev[areaKey]['areaName']}道闸${dev.channel_flag||'1'}`
  245. gateNameStr=gateNameStr.replace('全部区域','')
  246. glbDev[areaKey]['gate'][dev.channel_flag]={'gateName':gateNameStr,'gateStatus':false,'onlineDevId':null, 'channels':[]}
  247. }
  248. glbDev[areaKey]['gate'][dev.channel_flag]['channels'].push(dev)
  249. if(dev.channel_status=="1"){
  250. glbDev[areaKey]['gate'][dev.channel_flag]['gateStatus']=true
  251. glbDev[areaKey]['gate'][dev.channel_flag]['onlineDevId']=dev.id
  252. }
  253. })
  254. //console.log(glbDev)
  255. let gateAry=[]
  256. for(let are in glbDev){
  257. for(let gateIdx in glbDev[are]['gate']){
  258. gateAry.push(glbDev[are]['gate'][gateIdx])
  259. }
  260. }
  261. return gateAry
  262. }
  263. }
  264. }
  265. </script>
  266. <style>
  267. page{
  268. background-color: #f4f4f4;
  269. font-family: '华文行楷';
  270. }
  271. .parking-panel{
  272. background-color: #ffffff;
  273. border-radius: 10rpx;
  274. padding:20rpx;
  275. display: flex;
  276. flex-flow: row nowrap;
  277. justify-content: space-between;
  278. align-items: center;
  279. }
  280. .parking-panel .panel-left{
  281. display: flex;
  282. flex-flow: column nowrap;
  283. justify-content: space-between;
  284. align-items: flex-start;
  285. font-family: '华文行楷';
  286. }
  287. .parking-panel .panel-left .left-txt{
  288. font-size:24rpx;
  289. color:#695f5f;
  290. margin-top:15rpx;
  291. }
  292. .parking-panel .panel-left .left-title{
  293. font-weight: bold;
  294. font-size:32rpx;
  295. color:#000000;
  296. }
  297. .left-txt .num-txt{
  298. font-size: 28rpx;
  299. font-weight: bold;
  300. margin:0rpx 10rpx;
  301. }
  302. .newpower-txt{
  303. color:#27bf3e;
  304. margin:0rpx 10rpx;
  305. }
  306. .parking-adr{
  307. background-color: #ffffff;
  308. /* padding:15rpx 20rpx; */
  309. font-size: 28rpx;
  310. height: 60rpx;
  311. }
  312. .li-title{
  313. margin:30rpx 20rpx 15rpx;
  314. border-left:6rpx solid #1b68e3;
  315. padding:0rpx 20rpx;
  316. }
  317. .li-con{
  318. background-color: #ffffff;
  319. padding:15rpx;
  320. font-size: 26rpx;
  321. color:#4a4a4a;
  322. margin-bottom: 5rpx;
  323. }
  324. .dev-tit{
  325. display: flex;
  326. flex-flow: row nowrap;
  327. justify-content: space-between;
  328. align-items: center;
  329. }
  330. .dev-tit>text{
  331. font-size:32rpx;
  332. font-weight: bold;
  333. }
  334. .dev-tit .dev-view>text{
  335. font-size: 24rpx;
  336. color:#1B68E3;
  337. margin-right:10rpx;
  338. }
  339. .dev-stat{
  340. font-size:24rpx;
  341. color:#646464;
  342. margin:20rpx 0rpx 0rpx;
  343. }
  344. /deep/.u-textarea-inner{
  345. background-color: #ececec;
  346. }
  347. </style>