From c1147646b9ef1d713a202d7ab8cf3ea8d677f142 Mon Sep 17 00:00:00 2001 From: wlzboy <66905212@qq.com> Date: 星期六, 27 九月 2025 21:56:54 +0800 Subject: [PATCH] fix:优化评价 --- ruoyi-admin/src/main/java/com/ruoyi/web/controller/evaluation/VehicleEvaluationQrcodeController.java | 21 ++ ruoyi-system/src/main/java/com/ruoyi/system/service/impl/VehicleEvaluationQrcodeServiceImpl.java | 97 ++++++++++- ruoyi-system/src/main/java/com/ruoyi/system/service/IVehicleEvaluationQrcodeService.java | 9 + ruoyi-ui/src/views/evaluation/qrcode/index.vue | 98 ++++++++++- ruoyi-system/src/main/java/com/ruoyi/system/config/QRCodeConfig.java | 39 ++++ ruoyi-admin/src/main/resources/application.yml | 6 ruoyi-common/src/main/java/com/ruoyi/common/utils/QRCodeUtils.java | 52 ++++++ ruoyi-ui/src/views/evaluation/index.vue | 150 +++++++++++++++++- ruoyi-ui/src/api/evaluation.js | 5 9 files changed, 430 insertions(+), 47 deletions(-) diff --git a/ruoyi-admin/src/main/java/com/ruoyi/web/controller/evaluation/VehicleEvaluationQrcodeController.java b/ruoyi-admin/src/main/java/com/ruoyi/web/controller/evaluation/VehicleEvaluationQrcodeController.java index 3aa5fa2..f36e2ca 100644 --- a/ruoyi-admin/src/main/java/com/ruoyi/web/controller/evaluation/VehicleEvaluationQrcodeController.java +++ b/ruoyi-admin/src/main/java/com/ruoyi/web/controller/evaluation/VehicleEvaluationQrcodeController.java @@ -111,11 +111,16 @@ if (StringUtils.isEmpty(vehicleNo)) { return error("杞︾墝鍙蜂笉鑳戒负绌�"); } + + VehicleEvaluationQrcode qrcode; if (StringUtils.isEmpty(qrcodeUrl)) { - return error("浜岀淮鐮乁RL涓嶈兘涓虹┖"); + // 濡傛灉URL涓虹┖锛屼娇鐢ㄩ粯璁RL + qrcode = vehicleEvaluationQrcodeService.generateVehicleEvaluationQrcode(vehicleNo); + } else { + // 濡傛灉URL涓嶄负绌猴紝浣跨敤鎸囧畾鐨刄RL + qrcode = vehicleEvaluationQrcodeService.generateVehicleEvaluationQrcode(vehicleNo, qrcodeUrl); } - VehicleEvaluationQrcode qrcode = vehicleEvaluationQrcodeService.generateVehicleEvaluationQrcode(vehicleNo, qrcodeUrl); if (qrcode != null) { return success(qrcode); } else { @@ -133,9 +138,17 @@ @PreAuthorize("@ss.hasPermi('evaluation:qrcode:batch')") @Log(title = "杞﹁締璇勪环浜岀淮鐮�", businessType = BusinessType.INSERT) @PostMapping("/batch") - public AjaxResult batchGenerateQrcode() { + public AjaxResult batchGenerateQrcode(@RequestBody JSONObject params) { try { - int count = vehicleEvaluationQrcodeService.batchGenerateVehicleEvaluationQrcode(); + String qrcodeUrl = params.getString("qrcodeUrl"); + @SuppressWarnings("unchecked") + List<String> vehicleNos = (List<String>) params.get("vehicleNos"); + + if (vehicleNos == null || vehicleNos.isEmpty()) { + return error("杞︾墝鍙峰垪琛ㄤ笉鑳戒负绌�"); + } + + int count = vehicleEvaluationQrcodeService.batchGenerateVehicleEvaluationQrcode(vehicleNos, qrcodeUrl); return success("鎴愬姛鐢熸垚 " + count + " 涓簩缁寸爜"); } catch (Exception e) { logger.error("鎵归噺鐢熸垚浜岀淮鐮佸け璐�", e); diff --git a/ruoyi-admin/src/main/resources/application.yml b/ruoyi-admin/src/main/resources/application.yml index 626c3a6..8fae9c6 100644 --- a/ruoyi-admin/src/main/resources/application.yml +++ b/ruoyi-admin/src/main/resources/application.yml @@ -154,4 +154,8 @@ dev: enabled: true # 鏄惁鍚敤寮�鍙戞ā寮� mockUserInfo: true # 鏄惁妯℃嫙鐢ㄦ埛淇℃伅 - ngrokUrl: http://your-ngrok-url.ngrok.io # 鍐呯綉绌块�忓湴鍧� \ No newline at end of file + ngrokUrl: http://your-ngrok-url.ngrok.io # 鍐呯綉绌块�忓湴鍧� + +# 浜岀淮鐮侀厤缃� +qrcode: + defaultUrl: http://localhost:81/evaluation?vehicle={vehicleNo} # 榛樿浜岀淮鐮乁RL妯℃澘锛寋vehicleNo}浼氳鏇挎崲涓哄疄闄呰溅鐗屽彿 \ No newline at end of file diff --git a/ruoyi-common/src/main/java/com/ruoyi/common/utils/QRCodeUtils.java b/ruoyi-common/src/main/java/com/ruoyi/common/utils/QRCodeUtils.java index 5a28d53..cb983db 100644 --- a/ruoyi-common/src/main/java/com/ruoyi/common/utils/QRCodeUtils.java +++ b/ruoyi-common/src/main/java/com/ruoyi/common/utils/QRCodeUtils.java @@ -9,6 +9,7 @@ import org.slf4j.LoggerFactory; import javax.imageio.ImageIO; +import java.awt.*; import java.awt.image.BufferedImage; import java.io.ByteArrayOutputStream; import java.io.File; @@ -95,4 +96,55 @@ } return null; } + + /** + * 鐢熸垚甯﹁溅鐗屽彿鐨凚ase64缂栫爜浜岀淮鐮� + * + * @param content 浜岀淮鐮佸唴瀹� + * @param vehicleNo 杞︾墝鍙� + * @return Base64缂栫爜鐨勪簩缁寸爜 + */ + public static String generateQRCodeWithVehicleNoToBase64(String content, String vehicleNo) { + try { + Map<EncodeHintType, Object> hints = new HashMap<>(); + hints.put(EncodeHintType.CHARACTER_SET, "UTF-8"); + hints.put(EncodeHintType.MARGIN, 1); + + BitMatrix bitMatrix = new MultiFormatWriter().encode(content, BarcodeFormat.QR_CODE, WIDTH, HEIGHT, hints); + BufferedImage qrImage = MatrixToImageWriter.toBufferedImage(bitMatrix); + + // 鍒涘缓甯︽枃瀛楃殑鍥剧墖 + int textHeight = 40; // 鏂囧瓧鍖哄煙楂樺害 + int totalHeight = HEIGHT + textHeight; + BufferedImage finalImage = new BufferedImage(WIDTH, totalHeight, BufferedImage.TYPE_INT_RGB); + Graphics2D g2d = finalImage.createGraphics(); + + // 璁剧疆鑳屾櫙涓虹櫧鑹� + g2d.setColor(Color.WHITE); + g2d.fillRect(0, 0, WIDTH, totalHeight); + + // 缁樺埗浜岀淮鐮� + g2d.drawImage(qrImage, 0, 0, null); + + // 缁樺埗杞︾墝鍙锋枃瀛� + g2d.setColor(Color.BLACK); + g2d.setFont(new Font("寰蒋闆呴粦", Font.BOLD, 16)); + FontMetrics fm = g2d.getFontMetrics(); + int textWidth = fm.stringWidth(vehicleNo); + int x = (WIDTH - textWidth) / 2; + int y = HEIGHT + (textHeight + fm.getAscent()) / 2; + g2d.drawString(vehicleNo, x, y); + + g2d.dispose(); + + // 杞崲涓築ase64 + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + ImageIO.write(finalImage, FORMAT, baos); + return "data:image/png;base64," + java.util.Base64.getEncoder().encodeToString(baos.toByteArray()); + + } catch (Exception e) { + log.error("鐢熸垚甯﹁溅鐗屽彿鐨勪簩缁寸爜澶辫触: {}", e.getMessage()); + return null; + } + } } diff --git a/ruoyi-system/src/main/java/com/ruoyi/system/config/QRCodeConfig.java b/ruoyi-system/src/main/java/com/ruoyi/system/config/QRCodeConfig.java new file mode 100644 index 0000000..d88fee4 --- /dev/null +++ b/ruoyi-system/src/main/java/com/ruoyi/system/config/QRCodeConfig.java @@ -0,0 +1,39 @@ +package com.ruoyi.system.config; + +import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.stereotype.Component; + +/** + * 浜岀淮鐮侀厤缃� + * + * @author ruoyi + */ +@Component +@ConfigurationProperties(prefix = "qrcode") +public class QRCodeConfig { + /** + * 榛樿浜岀淮鐮乁RL妯℃澘 + */ + private String defaultUrl = "http://localhost:8080/evaluation?vehicle={vehicleNo}"; + + public String getDefaultUrl() { + return defaultUrl; + } + + public void setDefaultUrl(String defaultUrl) { + this.defaultUrl = defaultUrl; + } + + /** + * 鏍规嵁杞︾墝鍙风敓鎴愪簩缁寸爜URL + * + * @param vehicleNo 杞︾墝鍙� + * @return 浜岀淮鐮乁RL + */ + public String generateUrl(String vehicleNo) { + if (defaultUrl != null && defaultUrl.contains("{vehicleNo}")) { + return defaultUrl.replace("{vehicleNo}", vehicleNo); + } + return defaultUrl + "?vehicle=" + vehicleNo; + } +} diff --git a/ruoyi-system/src/main/java/com/ruoyi/system/service/IVehicleEvaluationQrcodeService.java b/ruoyi-system/src/main/java/com/ruoyi/system/service/IVehicleEvaluationQrcodeService.java index ddaac80..f789d08 100644 --- a/ruoyi-system/src/main/java/com/ruoyi/system/service/IVehicleEvaluationQrcodeService.java +++ b/ruoyi-system/src/main/java/com/ruoyi/system/service/IVehicleEvaluationQrcodeService.java @@ -89,4 +89,13 @@ * @return 缁撴灉 */ public int batchGenerateVehicleEvaluationQrcode(); + + /** + * 鎵归噺鐢熸垚杞﹁締璇勪环浜岀淮鐮侊紙鎸囧畾杞︾墝鍙峰垪琛級 + * + * @param vehicleNos 杞︾墝鍙峰垪琛� + * @param qrcodeUrl 浜岀淮鐮乁RL锛堝彲閫夛級 + * @return 缁撴灉 + */ + public int batchGenerateVehicleEvaluationQrcode(List<String> vehicleNos, String qrcodeUrl); } diff --git a/ruoyi-system/src/main/java/com/ruoyi/system/service/impl/VehicleEvaluationQrcodeServiceImpl.java b/ruoyi-system/src/main/java/com/ruoyi/system/service/impl/VehicleEvaluationQrcodeServiceImpl.java index a36f68f..5de0d50 100644 --- a/ruoyi-system/src/main/java/com/ruoyi/system/service/impl/VehicleEvaluationQrcodeServiceImpl.java +++ b/ruoyi-system/src/main/java/com/ruoyi/system/service/impl/VehicleEvaluationQrcodeServiceImpl.java @@ -5,6 +5,7 @@ import com.ruoyi.common.utils.DateUtils; import com.ruoyi.common.utils.QRCodeUtils; import com.ruoyi.common.utils.StringUtils; +import com.ruoyi.system.config.QRCodeConfig; import com.ruoyi.system.mapper.VehicleInfoMapper; import com.ruoyi.system.domain.VehicleInfo; import com.ruoyi.system.mapper.VehicleEvaluationQrcodeMapper; @@ -27,6 +28,9 @@ @Autowired private VehicleInfoMapper vehicleInfoMapper; + + @Autowired + private QRCodeConfig qrCodeConfig; @Value("${ruoyi.profile}") private String uploadPath; @@ -125,9 +129,48 @@ return null; } - // 妫�鏌ヨ溅杈嗘槸鍚﹀瓨鍦� - VehicleInfo vehicleInfo = vehicleInfoMapper.selectVehicleInfoByVehicleNo(vehicleNo); - if (vehicleInfo == null) { + // 娉ㄦ剰锛氳繖閲屼笉妫�鏌ヨ溅杈嗕俊鎭〃锛屽厑璁镐负浠绘剰杞︾墝鍙风敓鎴愪簩缁寸爜 + + // 妫�鏌ユ槸鍚﹀凡瀛樺湪浜岀淮鐮� + VehicleEvaluationQrcode existingQrcode = vehicleEvaluationQrcodeMapper.selectVehicleEvaluationQrcodeByVehicleNo(vehicleNo); + if (existingQrcode != null) { + return existingQrcode; + } + + // 鐢熸垚浜岀淮鐮佸唴瀹� + String qrcodeContent = "EVAL:" + vehicleNo; + String qrcodeUrl = qrCodeConfig.generateUrl(vehicleNo); + + // 鐢熸垚甯﹁溅鐗屽彿鐨勪簩缁寸爜鍥剧墖涓篵ase64鏍煎紡 + String qrcodeImageBase64 = QRCodeUtils.generateQRCodeWithVehicleNoToBase64(qrcodeUrl, vehicleNo); + + if (qrcodeImageBase64 != null) { + VehicleEvaluationQrcode qrcode = new VehicleEvaluationQrcode(); + qrcode.setVehicleNo(vehicleNo); + qrcode.setQrcodeUrl(qrcodeUrl); + qrcode.setQrcodeContent(qrcodeContent); + qrcode.setQrcodeImage(qrcodeImageBase64); + qrcode.setStatus("0"); + qrcode.setCreateBy("system"); + qrcode.setCreateTime(DateUtils.getNowDate()); + + int result = vehicleEvaluationQrcodeMapper.insertVehicleEvaluationQrcode(qrcode); + if (result > 0) { + return qrcode; + } + } + + return null; + } + + /** + * 鐢熸垚杞﹁締璇勪环浜岀淮鐮侊紙涓嶆鏌ヨ溅杈嗕俊鎭〃锛� + * + * @param vehicleNo 杞︾墝鍙� + * @return 浜岀淮鐮佷俊鎭� + */ + private VehicleEvaluationQrcode generateVehicleEvaluationQrcodeWithoutVehicleCheck(String vehicleNo) { + if (StringUtils.isEmpty(vehicleNo)) { return null; } @@ -139,10 +182,10 @@ // 鐢熸垚浜岀淮鐮佸唴瀹� String qrcodeContent = "EVAL:" + vehicleNo; - String qrcodeUrl = "http://localhost:" + serverPort + "/evaluation?vehicle=" + vehicleNo; + String qrcodeUrl = qrCodeConfig.generateUrl(vehicleNo); - // 鐢熸垚浜岀淮鐮佸浘鐗囦负base64鏍煎紡 - String qrcodeImageBase64 = QRCodeUtils.generateQRCodeToBase64(qrcodeUrl); + // 鐢熸垚甯﹁溅鐗屽彿鐨勪簩缁寸爜鍥剧墖涓篵ase64鏍煎紡 + String qrcodeImageBase64 = QRCodeUtils.generateQRCodeWithVehicleNoToBase64(qrcodeUrl, vehicleNo); if (qrcodeImageBase64 != null) { VehicleEvaluationQrcode qrcode = new VehicleEvaluationQrcode(); @@ -176,11 +219,7 @@ return null; } - // 妫�鏌ヨ溅杈嗘槸鍚﹀瓨鍦� - VehicleInfo vehicleInfo = vehicleInfoMapper.selectVehicleInfoByVehicleNo(vehicleNo); - if (vehicleInfo == null) { - return null; - } + // 娉ㄦ剰锛氳繖閲屼笉妫�鏌ヨ溅杈嗕俊鎭〃锛屽厑璁镐负浠绘剰杞︾墝鍙风敓鎴愪簩缁寸爜 // 妫�鏌ユ槸鍚﹀凡瀛樺湪浜岀淮鐮� VehicleEvaluationQrcode existingQrcode = vehicleEvaluationQrcodeMapper.selectVehicleEvaluationQrcodeByVehicleNo(vehicleNo); @@ -191,8 +230,8 @@ existingQrcode.setUpdateBy("system"); existingQrcode.setUpdateTime(DateUtils.getNowDate()); - // 閲嶆柊鐢熸垚浜岀淮鐮佸浘鐗囦负base64鏍煎紡 - String qrcodeImageBase64 = QRCodeUtils.generateQRCodeToBase64(qrcodeUrl); + // 閲嶆柊鐢熸垚甯﹁溅鐗屽彿鐨勪簩缁寸爜鍥剧墖涓篵ase64鏍煎紡 + String qrcodeImageBase64 = QRCodeUtils.generateQRCodeWithVehicleNoToBase64(qrcodeUrl, vehicleNo); if (qrcodeImageBase64 != null) { existingQrcode.setQrcodeImage(qrcodeImageBase64); @@ -205,8 +244,8 @@ // 鐢熸垚浜岀淮鐮佸唴瀹� String qrcodeContent = "EVAL:" + vehicleNo; - // 鐢熸垚浜岀淮鐮佸浘鐗囦负base64鏍煎紡 - String qrcodeImageBase64 = QRCodeUtils.generateQRCodeToBase64(qrcodeUrl); + // 鐢熸垚甯﹁溅鐗屽彿鐨勪簩缁寸爜鍥剧墖涓篵ase64鏍煎紡 + String qrcodeImageBase64 = QRCodeUtils.generateQRCodeWithVehicleNoToBase64(qrcodeUrl, vehicleNo); if (qrcodeImageBase64 != null) { VehicleEvaluationQrcode qrcode = new VehicleEvaluationQrcode(); @@ -249,4 +288,32 @@ return successCount; } + + /** + * 鎵归噺鐢熸垚杞﹁締璇勪环浜岀淮鐮侊紙鎸囧畾杞︾墝鍙峰垪琛級 + * + * @param vehicleNos 杞︾墝鍙峰垪琛� + * @param qrcodeUrl 浜岀淮鐮乁RL锛堝彲閫夛級 + * @return 缁撴灉 + */ + @Override + public int batchGenerateVehicleEvaluationQrcode(List<String> vehicleNos, String qrcodeUrl) { + int successCount = 0; + for (String vehicleNo : vehicleNos) { + if (StringUtils.isEmpty(vehicleNo)) { + continue; // 璺宠繃绌虹殑杞︾墝鍙� + } + + VehicleEvaluationQrcode qrcode; + if (StringUtils.isEmpty(qrcodeUrl)) { + qrcode = generateVehicleEvaluationQrcodeWithoutVehicleCheck(vehicleNo); + } else { + qrcode = generateVehicleEvaluationQrcode(vehicleNo, qrcodeUrl); + } + if (qrcode != null) { + successCount++; + } + } + return successCount; + } } diff --git a/ruoyi-ui/src/api/evaluation.js b/ruoyi-ui/src/api/evaluation.js index 41651b8..83a8e1f 100644 --- a/ruoyi-ui/src/api/evaluation.js +++ b/ruoyi-ui/src/api/evaluation.js @@ -88,10 +88,11 @@ } // 鎵归噺鐢熸垚杞﹁締璇勪环浜岀淮鐮� -export function batchGenerateQrcode() { +export function batchGenerateQrcode(data) { return request({ url: '/evaluation/qrcode/batch', - method: 'post' + method: 'post', + data: data }) } diff --git a/ruoyi-ui/src/views/evaluation/index.vue b/ruoyi-ui/src/views/evaluation/index.vue index d4db6f1..e0fae2a 100644 --- a/ruoyi-ui/src/views/evaluation/index.vue +++ b/ruoyi-ui/src/views/evaluation/index.vue @@ -3,7 +3,7 @@ <!-- 椤甸潰澶撮儴 --> <div class="evaluation-header"> <h1>鏈嶅姟璇勪环</h1> - <p>鎰熻阿鎮ㄤ娇鐢ㄦ垜浠殑鏈嶅姟锛岃瀵规湰娆℃湇鍔¤繘琛岃瘎浠�</p> + <p>鎰熻阿鎮ㄤ娇鐢ㄦ垜浠殑闈�120鎬ユ晳鍖荤枟杞繍鏈嶅姟锛岃瀵规湰娆℃湇鍔¤繘琛岃瘎浠凤紒</p> </div> <!-- 杞﹁締淇℃伅 --> @@ -19,7 +19,7 @@ <el-form ref="evaluationForm" :model="evaluationForm" :rules="rules" label-width="80px" size="small"> <!-- 瀹㈡埛淇℃伅 --> <div class="form-section"> - <h3>瀹㈡埛淇℃伅</h3> + <h3>瀹㈡埛淇℃伅:</h3> <!-- 寰俊鎺堟潈淇℃伅鏄剧ず --> <div v-if="evaluationForm.wechatOpenid" class="wechat-info"> @@ -46,14 +46,13 @@ <div class="wechat-tip">鐐瑰嚮鍙嚜鍔ㄨ幏鍙栨偍鐨勫井淇′俊鎭�</div> </div> - <el-form-item label="濮撳悕" prop="customerName"> + <el-form-item label="绉板懠" prop="customerName"> <el-input v-model="evaluationForm.customerName" placeholder="璇疯緭鍏ユ偍鐨勫鍚�" /> </el-form-item> <el-form-item label="鎵嬫満鍙�" prop="customerPhone"> <el-input v-model="evaluationForm.customerPhone" placeholder="璇疯緭鍏ユ偍鐨勬墜鏈哄彿" /> <div v-if="evaluationForm.wechatOpenid" class="phone-tip"> - <i class="el-icon-info"></i> - 寰俊鎺堟潈鏃犳硶鐩存帴鑾峰彇鎵嬫満鍙凤紝璇锋墜鍔ㄨ緭鍏� + </div> </el-form-item> </div> @@ -65,17 +64,16 @@ <!-- 鏄熺骇璇勪环 - 鏍囬鍜岃瘎鍒嗗湪鍚屼竴琛� --> <div v-if="dimension.dimensionType === 'star'" class="star-rating-inline"> <div class="dimension-title-inline"> - <span>{{ dimension.dimensionName }}</span> + <span class="dimension-name-fixed">{{ dimension.dimensionName }}</span> <span v-if="dimension.isRequired === '1'" class="required">*</span> </div> <div class="star-rating-content"> <el-rate :value="getDimensionScore(dimension.dimensionId)" :max="5" - show-text - :texts="['寰堝樊', '杈冨樊', '涓�鑸�', '婊℃剰', '闈炲父婊℃剰']" @change="updateDimensionScore(dimension.dimensionId, $event)" size="small" + :aria-label="`璇勪环${dimension.dimensionName}`" /> </div> </div> @@ -90,8 +88,16 @@ {{ dimension.dimensionDesc }} </div> <div class="select-rating"> - <el-radio-group :value="getDimensionOption(dimension.dimensionId)" @change="updateDimensionOption(dimension.dimensionId, $event)" size="small"> - <el-radio v-for="option in getDimensionOptions(dimension)" :key="option.value" :label="option.value"> + <el-radio-group + v-model="selectedOptions[dimension.dimensionId]" + @change="(value) => handleOptionChange(dimension.dimensionId, value)" + size="small" + :aria-label="`閫夋嫨${dimension.dimensionName}`"> + <el-radio + v-for="option in getDimensionOptions(dimension)" + :key="option.value" + :label="option.value" + :aria-label="option.label"> {{ option.label }} </el-radio> </el-radio-group> @@ -115,6 +121,7 @@ placeholder="璇疯緭鍏ユ偍鐨勬剰瑙佹垨寤鸿" @input="updateDimensionText(dimension.dimensionId, $event)" size="small" + :aria-label="`${dimension.dimensionName}璇勪环鎰忚`" /> </div> </div> @@ -166,6 +173,8 @@ wechatPhone: '', evaluationDetails: [] }, + // 鐢ㄤ簬瀛樺偍閫夋嫨绫诲瀷鐨勮瘎浠烽�夐」 + selectedOptions: {}, rules: { customerName: [ { required: true, message: '璇疯緭鍏ユ偍鐨勫鍚�', trigger: 'blur' } @@ -303,13 +312,37 @@ detail = { dimensionId, score: 0 }; this.evaluationForm.evaluationDetails.push(detail); } - detail.score = score; + // 浣跨敤Vue.set纭繚鍝嶅簲寮忔洿鏂� + this.$set(detail, 'score', score); }, // 鑾峰彇缁村害閫夐」 getDimensionOption(dimensionId) { const detail = this.evaluationForm.evaluationDetails.find(d => d.dimensionId === dimensionId); return detail ? detail.optionValue : ''; + }, + + // 鑾峰彇缁村害閫夐」鍊硷紙鐢ㄤ簬v-model锛� + getDimensionOptionValue(dimensionId) { + const detail = this.evaluationForm.evaluationDetails.find(d => d.dimensionId === dimensionId); + if (!detail) { + // 濡傛灉涓嶅瓨鍦紝鍒涘缓涓�涓柊鐨刣etail瀵硅薄 + const newDetail = { dimensionId, optionValue: '' }; + this.evaluationForm.evaluationDetails.push(newDetail); + return newDetail; + } + return detail; + }, + + // 鑾峰彇缁村害閫夐」鐨剉-model瀵硅薄 + getDimensionOptionModel(dimensionId) { + const detail = this.evaluationForm.evaluationDetails.find(d => d.dimensionId === dimensionId); + if (!detail) { + const newDetail = { dimensionId, optionValue: '' }; + this.evaluationForm.evaluationDetails.push(newDetail); + return newDetail; + } + return detail; }, // 鏇存柊缁村害閫夐」 @@ -319,7 +352,16 @@ detail = { dimensionId, optionValue: '' }; this.evaluationForm.evaluationDetails.push(detail); } - detail.optionValue = optionValue; + // 浣跨敤Vue.set纭繚鍝嶅簲寮忔洿鏂� + this.$set(detail, 'optionValue', optionValue); + }, + + // 澶勭悊閫夐」鍙樺寲 + handleOptionChange(dimensionId, value) { + // 鏇存柊selectedOptions + this.$set(this.selectedOptions, dimensionId, value); + // 鍚屾椂鏇存柊evaluationDetails + this.updateDimensionOption(dimensionId, value); }, // 鑾峰彇缁村害鏂囨湰 @@ -335,7 +377,8 @@ detail = { dimensionId, textContent: '' }; this.evaluationForm.evaluationDetails.push(detail); } - detail.textContent = textContent; + // 浣跨敤Vue.set纭繚鍝嶅簲寮忔洿鏂� + this.$set(detail, 'textContent', textContent); }, // 鑾峰彇缁村害閫夐」閰嶇疆 @@ -344,6 +387,7 @@ try { return JSON.parse(dimension.options); } catch (error) { + console.error('Error parsing options for', dimension.dimensionName, ':', error); return []; } }, @@ -372,7 +416,7 @@ // 鎻愪氦璇勪环 const response = await submitEvaluation(this.evaluationForm); if (response.code === 200) { - this.resultMessage = response.msg; + this.resultMessage = "鎰熻阿鎮ㄧ殑鍙嶉锛屾偍鐨勫弽棣堝皢淇冧娇鎴戜滑涓嶆柇杩涙锛屾垜浠皢缁х画鎻愪緵鏇村ソ鐨勬湇鍔�"; this.showResult = true; } else { this.$message.error(response.msg || '鎻愪氦澶辫触锛岃閲嶈瘯'); @@ -391,6 +435,7 @@ this.evaluationForm.customerName = ''; this.evaluationForm.customerPhone = ''; this.evaluationForm.evaluationDetails = []; + this.selectedOptions = {}; this.$refs.evaluationForm.resetFields(); } } @@ -513,6 +558,15 @@ flex-shrink: 0; } +.dimension-name-fixed { + display: inline-block; + width: 100px; + text-align: left; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; +} + .star-rating-content { flex: 1; min-width: 200px; @@ -540,6 +594,69 @@ .select-rating .el-radio__label { font-size: 13px; +} + +/* 鏀瑰杽鏃犻殰纰嶈闂� */ +.select-rating .el-radio__original { + position: absolute !important; + opacity: 0 !important; + width: 0 !important; + height: 0 !important; + margin: 0 !important; + padding: 0 !important; + border: none !important; + outline: none !important; + clip: rect(0, 0, 0, 0) !important; + -webkit-appearance: none !important; + -moz-appearance: none !important; + appearance: none !important; +} + +.select-rating .el-radio__input { + position: relative; + white-space: nowrap; + vertical-align: middle; + outline: none; + line-height: 1; +} + +.select-rating .el-radio__inner { + border: 1px solid #dcdfe6; + border-radius: 100%; + width: 14px; + height: 14px; + background-color: #fff; + position: relative; + cursor: pointer; + display: inline-block; + box-sizing: border-box; + transition: border-color 0.25s cubic-bezier(0.71, -0.46, 0.29, 1.46), background-color 0.25s cubic-bezier(0.71, -0.46, 0.29, 1.46); +} + +.select-rating .el-radio__inner:hover { + border-color: #409eff; +} + +.select-rating .el-radio.is-checked .el-radio__inner { + border-color: #409eff; + background: #409eff; +} + +.select-rating .el-radio.is-checked .el-radio__inner::after { + transform: translate(-50%, -50%) scale(1); +} + +.select-rating .el-radio__inner::after { + width: 4px; + height: 4px; + border-radius: 100%; + background-color: #fff; + content: ""; + position: absolute; + left: 50%; + top: 50%; + transform: translate(-50%, -50%) scale(0); + transition: transform 0.15s ease-in; } /* 浼樺寲鏂囨湰璇勪环鏄剧ず */ @@ -736,6 +853,11 @@ font-size: 13px; } + .dimension-name-fixed { + width: 120px; + font-size: 13px; + } + .star-rating-content { min-width: auto; width: 100%; diff --git a/ruoyi-ui/src/views/evaluation/qrcode/index.vue b/ruoyi-ui/src/views/evaluation/qrcode/index.vue index be23c18..e29cf62 100644 --- a/ruoyi-ui/src/views/evaluation/qrcode/index.vue +++ b/ruoyi-ui/src/views/evaluation/qrcode/index.vue @@ -58,7 +58,7 @@ <el-table v-loading="loading" :data="qrcodeList" @selection-change="handleSelectionChange"> <el-table-column type="selection" width="55" align="center" /> - <el-table-column label="浜岀淮鐮両D" align="center" prop="qrcodeId" /> + <el-table-column label="杞︾墝鍙�" align="center" prop="vehicleNo" /> <el-table-column label="浜岀淮鐮乁RL" align="center" prop="qrcodeUrl" width="200"> <template slot-scope="scope"> @@ -128,7 +128,7 @@ <el-input v-model="form.vehicleNo" placeholder="璇疯緭鍏ヨ溅鐗屽彿" /> </el-form-item> <el-form-item label="浜岀淮鐮乁RL" prop="qrcodeUrl"> - <el-input v-model="form.qrcodeUrl" placeholder="璇疯緭鍏ヤ簩缁寸爜URL" /> + <el-input v-model="form.qrcodeUrl" placeholder="鍙�夛紝鐣欑┖鍒欎娇鐢ㄩ粯璁RL" /> </el-form-item> </el-form> <div slot="footer" class="dialog-footer"> @@ -137,10 +137,30 @@ </div> </el-dialog> + <!-- 鎵归噺鐢熸垚浜岀淮鐮佸璇濇 --> + <el-dialog title="鎵归噺鐢熸垚浜岀淮鐮�" :visible.sync="batchOpen" width="600px" append-to-body> + <el-form ref="batchForm" :model="batchForm" :rules="batchRules" label-width="100px"> + <el-form-item label="杞︾墝鍙�" prop="vehicleNos"> + <el-input + v-model="batchForm.vehicleNos" + type="textarea" + :rows="6" + placeholder="璇疯緭鍏ヨ溅鐗屽彿锛屽涓溅鐗屽彿鐢ㄩ�楀彿鍒嗛殧锛屼緥濡傦細绮12345,绮67890,绮11111" /> + </el-form-item> + <el-form-item label="浜岀淮鐮乁RL" prop="qrcodeUrl"> + <el-input v-model="batchForm.qrcodeUrl" placeholder="鍙�夛紝鐣欑┖鍒欎娇鐢ㄩ粯璁RL" /> + </el-form-item> + </el-form> + <div slot="footer" class="dialog-footer"> + <el-button type="primary" @click="submitBatchForm">纭� 瀹�</el-button> + <el-button @click="cancelBatch">鍙� 娑�</el-button> + </div> + </el-dialog> + <!-- 浜岀淮鐮佽鎯呭璇濇 --> <el-dialog title="浜岀淮鐮佽鎯�" :visible.sync="viewOpen" width="600px" append-to-body> <el-descriptions :column="2" border> - <el-descriptions-item label="浜岀淮鐮両D">{{ viewForm.qrcodeId }}</el-descriptions-item> + <el-descriptions-item label="杞︾墝鍙�">{{ viewForm.vehicleNo }}</el-descriptions-item> <el-descriptions-item label="浜岀淮鐮乁RL" :span="2"> <el-link :href="viewForm.qrcodeUrl" target="_blank" type="primary">{{ viewForm.qrcodeUrl }}</el-link> @@ -194,6 +214,8 @@ title: "", // 鏄惁鏄剧ず寮瑰嚭灞� open: false, + // 鏄惁鏄剧ず鎵归噺鐢熸垚寮瑰嚭灞� + batchOpen: false, // 鏄惁鏄剧ず鏌ョ湅寮瑰嚭灞� viewOpen: false, // 鏌ヨ鍙傛暟 @@ -205,6 +227,8 @@ }, // 琛ㄥ崟鍙傛暟 form: {}, + // 鎵归噺鐢熸垚琛ㄥ崟鍙傛暟 + batchForm: {}, // 鏌ョ湅琛ㄥ崟鍙傛暟 viewForm: {}, // 琛ㄥ崟鏍¢獙 @@ -213,7 +237,15 @@ { required: true, message: "杞︾墝鍙蜂笉鑳戒负绌�", trigger: "blur" } ], qrcodeUrl: [ - { required: true, message: "浜岀淮鐮乁RL涓嶈兘涓虹┖", trigger: "blur" }, + { type: 'url', message: '璇疯緭鍏ユ纭殑URL鏍煎紡', trigger: 'blur' } + ] + }, + // 鎵归噺鐢熸垚琛ㄥ崟鏍¢獙 + batchRules: { + vehicleNos: [ + { required: true, message: "杞︾墝鍙蜂笉鑳戒负绌�", trigger: "blur" } + ], + qrcodeUrl: [ { type: 'url', message: '璇疯緭鍏ユ纭殑URL鏍煎紡', trigger: 'blur' } ] } @@ -249,6 +281,14 @@ }; this.resetForm("form"); }, + // 鎵归噺琛ㄥ崟閲嶇疆 + resetBatch() { + this.batchForm = { + vehicleNos: null, + qrcodeUrl: null + }; + this.resetForm("batchForm"); + }, /** 鎼滅储鎸夐挳鎿嶄綔 */ handleQuery() { this.queryParams.pageNum = 1; @@ -277,7 +317,7 @@ if (valid) { const params = { vehicleNo: this.form.vehicleNo, - qrcodeUrl: this.form.qrcodeUrl + qrcodeUrl: this.form.qrcodeUrl || null }; generateQrcode(params).then(response => { this.$modal.msgSuccess("鐢熸垚鎴愬姛"); @@ -289,12 +329,48 @@ }, /** 鎵归噺鐢熸垚鎸夐挳鎿嶄綔 */ handleBatchGenerate() { - this.$modal.confirm('鏄惁纭鎵归噺鐢熸垚鎵�鏈夎溅杈嗙殑浜岀淮鐮侊紵').then(function() { - return batchGenerateQrcode(); - }).then(() => { - this.getList(); - this.$modal.msgSuccess("鎵归噺鐢熸垚鎴愬姛"); - }).catch(() => {}); + this.resetBatch(); + this.batchOpen = true; + }, + // 鍙栨秷鎵归噺鐢熸垚 + cancelBatch() { + this.batchOpen = false; + this.resetBatch(); + }, + /** 鎵归噺鎻愪氦鎸夐挳 */ + submitBatchForm() { + this.$refs["batchForm"].validate(valid => { + if (valid) { + const vehicleNos = this.batchForm.vehicleNos.split(',').map(no => no.trim()).filter(no => no); + if (vehicleNos.length === 0) { + this.$modal.msgError("璇疯緭鍏ユ湁鏁堢殑杞︾墝鍙�"); + return; + } + + console.log('鎵归噺鐢熸垚杞︾墝鍙峰垪琛�:', vehicleNos); + + const params = { + vehicleNos: vehicleNos, + qrcodeUrl: this.batchForm.qrcodeUrl || null + }; + + console.log('鎵归噺鐢熸垚鍙傛暟:', params); + + batchGenerateQrcode(params).then(response => { + console.log('鎵归噺鐢熸垚鍝嶅簲:', response); + if (response.code === 200) { + this.$modal.msgSuccess(response.msg || "鎵归噺鐢熸垚鎴愬姛"); + } else { + this.$modal.msgError(response.msg || "鎵归噺鐢熸垚澶辫触"); + } + this.batchOpen = false; + this.getList(); + }).catch(error => { + console.error('鎵归噺鐢熸垚澶辫触:', error); + this.$modal.msgError("鎵归噺鐢熸垚澶辫触锛岃閲嶈瘯"); + }); + } + }); }, /** 鏌ョ湅鎸夐挳鎿嶄綔 */ handleView(row) { -- Gitblit v1.9.1