展品维保小程序前端代码接口
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

381 lines
9.3 KiB

1 week ago
1 week ago
5 days ago
5 days ago
  1. <template>
  2. <view class="maintain-container">
  3. <!-- 顶部选择器区域 -->
  4. <view class="selector-section">
  5. <!-- 紧急程度选择器 -->
  6. <view class="selector-item" @click="openUrgencyPicker">
  7. <text class="selector-label" :class="{ active: urgency }">{{ urgency.label || '紧急状态' }}</text>
  8. <uv-icon name="arrow-down-fill" size="14" :color="urgency ? '#C70019' : '#000'"></uv-icon>
  9. </view>
  10. <!-- 维修状态选择器 -->
  11. <view class="selector-item" @click="openStatusPicker">
  12. <text class="selector-label" :class="{ active: status }">{{ status.label || '维修状态' }}</text>
  13. <uv-icon name="arrow-down-fill" size="14" :color="status ? '#C70019' : '#000'"></uv-icon>
  14. </view>
  15. </view>
  16. <!-- 产品列表 -->
  17. <view class="product-list">
  18. <view class="product-item" v-for="(item, index) in list" :key="index" @click="navigateToDetail(item)">
  19. <!-- 产品ID和状态标签 -->
  20. <view class="item-header">
  21. <view @click.stop="copyID(item.id)">
  22. <text class="item-id">{{ item.id }}</text>
  23. <img src="@/static/copy.png" alt="复制图标" class="item-icon">
  24. </view>
  25. <view class="status-tag" :class="[getStatusClass(item.status)]">
  26. <text class="status-text">{{ item.status_dictText }}</text>
  27. </view>
  28. </view>
  29. <!-- 中间那条下划线 -->
  30. <view class="item-border" />
  31. <!-- 产品标题 -->
  32. <view class="item-title">
  33. <text class="title-text">{{ item.showpieceId_dictText }}</text>
  34. </view>
  35. <!-- 产品详情 -->
  36. <view class="item-details">
  37. <view class="detail-row">
  38. <view class="detail-item">
  39. <text class="detail-label">展品编号</text>
  40. <text class="detail-value">{{ item.showpieceId }}</text>
  41. </view>
  42. <view class="detail-item">
  43. <text class="detail-label">紧急程度</text>
  44. <text class="detail-value">{{ item.urgency_dictText }}</text>
  45. </view>
  46. </view>
  47. <view class="detail-row">
  48. <view class="detail-item">
  49. <text class="detail-label">展品位置</text>
  50. <text class="detail-value">{{ item.showpiece.position }}</text>
  51. </view>
  52. </view>
  53. <view class="detail-row">
  54. <view class="detail-item">
  55. <text class="detail-label">报修人</text>
  56. <text class="detail-value">{{ item.malfunctionName_dictText }}</text>
  57. </view>
  58. <view class="detail-item">
  59. <text class="detail-label">报修日期</text>
  60. <text class="detail-value">{{ item.malfunctionDate }}</text>
  61. </view>
  62. </view>
  63. <view class="detail-row">
  64. <view class="detail-item full-width">
  65. <text class="detail-label">故障描述</text>
  66. <text class="detail-value">{{ item.malfunctionDesc }}</text>
  67. </view>
  68. </view>
  69. </view>
  70. <!-- 操作按钮 -->
  71. <view class="item-actions">
  72. <button class="item-actions-button">立即维修</button>
  73. </view>
  74. </view>
  75. <!-- 空状态 -->
  76. </view>
  77. <uv-empty v-if="!list.length" icon="/static/暂无搜索结果.png" />
  78. <!-- 紧急程度选择器 -->
  79. <uv-picker
  80. ref="urgencyPicker"
  81. v-model="urgencyShow"
  82. :columns="urgencyColumns"
  83. keyName="label"
  84. mode="selector"
  85. @confirm="onUrgencyConfirm"
  86. confirmColor="#C70019"
  87. ></uv-picker>
  88. <!-- 维修状态选择器 -->
  89. <uv-picker
  90. ref="statusPicker"
  91. v-model="statusShow"
  92. :columns="statusColumns"
  93. keyName="label"
  94. mode="selector"
  95. @confirm="onStatusConfirm"
  96. confirmColor="#C70019"
  97. ></uv-picker>
  98. </view>
  99. </template>
  100. <script>
  101. import ListMixin from '@/mixins/list'
  102. export default {
  103. mixins: [ListMixin],
  104. data() {
  105. return {
  106. urgency: null,
  107. status: null,
  108. urgencyShow: false,
  109. statusShow: false,
  110. mixinListApi: 'exhibit.queryMalfunctionList',
  111. urgencyColumns: [
  112. [
  113. {
  114. label: '全部',
  115. value: ''
  116. },
  117. {
  118. label: '一般',
  119. value: '0'
  120. },
  121. {
  122. label: '紧急',
  123. value: '1'
  124. },
  125. ]
  126. ],
  127. statusColumns: [
  128. [
  129. {
  130. label: '全部',
  131. value: ''
  132. },
  133. {
  134. label: '故障中',
  135. value: '0'
  136. },
  137. {
  138. label: '维修中',
  139. value: '1'
  140. },
  141. {
  142. label: '已解决',
  143. value: '2'
  144. }
  145. ]
  146. ],
  147. }
  148. },
  149. methods: {
  150. copyID(id) {
  151. uni.setClipboardData({
  152. data: id,
  153. success: () => {
  154. uni.showToast({
  155. title: '复制成功',
  156. icon: 'success'
  157. })
  158. }
  159. })
  160. },
  161. mixinSetParams(){
  162. return {
  163. urgency: this.urgency?.value || '',
  164. status: this.status?.value || ''
  165. }
  166. },
  167. navigateToDetail(item) {
  168. uni.navigateTo({
  169. url: '/subPages/repair/maintainSubmit?id=' + item.id + '&showpieceId=' + item.showpieceId
  170. })
  171. },
  172. openUrgencyPicker() {
  173. this.$refs.urgencyPicker.open()
  174. },
  175. openStatusPicker() {
  176. this.$refs.statusPicker.open()
  177. },
  178. onUrgencyConfirm(e) {
  179. this.urgency = e.value[0]
  180. console.log('选择紧急程度:', e)
  181. this.initPage()
  182. this.getList(true)
  183. // TODO: 根据紧急程度筛选
  184. },
  185. onStatusConfirm(e) {
  186. this.status = e.value[0]
  187. console.log('选择维修状态:', e)
  188. this.initPage()
  189. this.getList(true)
  190. // TODO: 根据状态筛选
  191. },
  192. getStatusClass(status) {
  193. switch(status) {
  194. case '维修中':
  195. return 'status-repairing'
  196. case '故障中':
  197. return 'status-fault'
  198. case '已解决':
  199. return 'status-resolved'
  200. default:
  201. return ''
  202. }
  203. },
  204. handleRepair(item) {
  205. console.log('立即维修:', item)
  206. // TODO: 处理维修逻辑
  207. }
  208. }
  209. }
  210. </script>
  211. <style lang="scss" scoped>
  212. .maintain-container {
  213. background-color: #fff;
  214. min-height: 100vh;
  215. }
  216. .selector-section {
  217. display: flex;
  218. padding: 34rpx 41rpx;
  219. // background-color: #fff;
  220. gap: 58rpx;
  221. .selector-item {
  222. display: flex;
  223. align-items: center;
  224. gap: 9rpx;
  225. cursor: pointer;
  226. .selector-label {
  227. font-size: 28rpx;
  228. color: #000;
  229. &.active {
  230. color: $primary-color;
  231. }
  232. }
  233. }
  234. }
  235. .product-list {
  236. padding: 20rpx 32rpx;
  237. .product-item {
  238. background-color: #fff;
  239. border-radius: 15rpx;
  240. padding: 30rpx 30rpx 20rpx;
  241. margin-bottom: 24rpx;
  242. box-shadow: 0rpx 3rpx 6rpx 0rpx rgba(0,0,0,0.16);
  243. .item-header {
  244. display: flex;
  245. align-items: center;
  246. justify-content: space-between;
  247. margin-bottom: 13.5rpx;
  248. .item-icon {
  249. width: 25.5rpx;
  250. height: 25.5rpx;
  251. }
  252. .item-id {
  253. font-size: 28rpx;
  254. margin-right: 20rpx;
  255. color: $secondary-text-color;
  256. }
  257. .status-tag {
  258. border-radius: 15rpx;
  259. width: 135rpx;
  260. height: 57rpx;
  261. display: flex;
  262. align-items: center;
  263. justify-content: center;
  264. .status-text {
  265. font-size: 28rpx;
  266. }
  267. &.status-repairing {
  268. background-color: #ffffca;
  269. color: #CE7C62;
  270. }
  271. &.status-fault {
  272. background-color: #fccec7;
  273. color: #b82222;
  274. }
  275. &.status-resolved {
  276. background-color: #cfffca;
  277. color: #528828;
  278. }
  279. }
  280. }
  281. .item-border {
  282. border-bottom: 1rpx solid $secondary-text-color;
  283. // background-color: #E5E5E5;
  284. margin-bottom: 26.5rpx;
  285. opacity: 0.22;
  286. }
  287. .item-title {
  288. margin-bottom: 37rpx;
  289. .title-text {
  290. font-size: 30rpx;
  291. color: $primary-text-color;
  292. font-weight: bold;
  293. }
  294. }
  295. .item-details {
  296. margin-bottom: 52rpx;
  297. .detail-row {
  298. display: flex;
  299. margin-bottom: 25rpx;
  300. &:last-child {
  301. margin-bottom: 0;
  302. }
  303. .detail-item {
  304. flex: 1;
  305. display: flex;
  306. align-items: flex-start;
  307. margin-right: 35rpx;
  308. &.full-width {
  309. flex: 1 1 100%;
  310. margin-right: 0;
  311. }
  312. &:last-child {
  313. margin-right: 0;
  314. margin-bottom: 0;
  315. }
  316. .detail-label {
  317. font-size: 22rpx;
  318. color: $secondary-text-color;
  319. margin-right: 19rpx;
  320. flex-shrink: 0;
  321. min-width: 95rpx;
  322. }
  323. .detail-value {
  324. font-size: 22rpx;
  325. color: $primary-text-color;
  326. flex: 1;
  327. }
  328. }
  329. }
  330. }
  331. .item-actions {
  332. display: flex;
  333. justify-content: center;
  334. .item-actions-button {
  335. width: 378rpx;
  336. height: 78rpx;
  337. background-color: $primary-color;
  338. color: #fff;
  339. font-size: 28rpx;
  340. border-radius: 39rpx;
  341. }
  342. }
  343. }
  344. }
  345. </style>