Box.vue 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. <template>
  2. <svg class="box-display" width="150" height="80" viewBox="0 0 300 160">
  3. <g>
  4. <rect x="0" y="80" width="300" height="80" />
  5. <text x="10" y="135" font-family="Verdana" font-weight="bold" font-size="40" fill="green">
  6. {{ box.name }}
  7. </text>
  8. </g>
  9. <polygon class="line" points="0,80 50,0 250,0 300,80" />
  10. <g v-if="box.category === 1">
  11. <polygon class="single" points="0,80 50,1 250,1 300,80" />
  12. </g>
  13. <g v-if="box.category === 2">
  14. <polygon class="line" points="0,80 50,1 150,1 150,80" />
  15. <polygon class="line" points="150,0 150,80 300,80 250,0" />
  16. </g>
  17. <g v-if="box.category === 3">
  18. <polygon class="line" points="0,80 50,1 120,1 100,80" />
  19. <polygon class="line" points="100,80 120,1 180,1 200,80" />
  20. <polygon class="line" points="200,80 180,1 250,1 300,80" />
  21. </g>
  22. <g v-if="box.category === 4">
  23. <polygon class="line" points="29.17,33.33 50,0 150,0 150,33.33" />
  24. <polygon class="line" points="150,33.33 150,0 250,0 270.83,33.33" />
  25. <polygon class="line" points="0,80 29.17,33.33 150,33.33 150,80" />
  26. <polygon class="line" points="150,33.33 150,80 300,80 270.83,33.33" />
  27. </g>
  28. <g v-if="box.category === 6">
  29. <polygon class="line" points="29.17,33.33 50,0 117,0 110.39,33.33" />
  30. <polygon class="line" points="117,0 110.39,33.33 191.61,33.33 185.5,0" />
  31. <polygon class="line" points="191.61,33.33 185.5,0 250,0 270.83,33.33" />
  32. <polygon class="line" points="200,80 191.61,33.33 270.83,33.33 300,80" />
  33. <polygon class="line" points="110.39,33.33 100,80 200,80 191.61,33.33" />
  34. <polygon class="line" points="0,80 29.17,33.33 110.39,33.33 100,80" />
  35. </g>
  36. <g v-if="box.category === 8">
  37. <polygon class="line" points="29.17,33.33 50,0 100,0 93.39,33.33" />
  38. <polygon class="line" points="100,0 93.39,33.33 150.61,33.33 152.5,0" />
  39. <polygon class="line" points="150.61,33.33 152.5,0 205,0 210.83,33.33" />
  40. <polygon class="line" points="205,33.33 200.83,0 250,0 270.83,33.33" />
  41. <polygon class="line" points="210.83,80 205,33.33 270.83,33.33 300,80" />
  42. <polygon class="line" points="148.5,80 150.61,33.33 205,33.33 210.83,80" />
  43. <polygon class="line" points="93.39,33.33 85,80 148.5,80 150.61,33.33" />
  44. <polygon class="line" points="0,80 29.17,33.33 93.39,33.33 85,80" />
  45. </g>
  46. </svg>
  47. </template>
  48. <script setup>
  49. import { ref, watch } from 'vue';
  50. // 接收父组件传递的数据
  51. const props = defineProps({
  52. box: Object,
  53. });
  54. // 定义响应式变量
  55. const box = ref(props.box);
  56. // 监听 box.category 属性变化,更新 category
  57. watch(() => box.value.category, (newCategory) => {
  58. resetCategory(newCategory);
  59. }, { immediate: true });
  60. // 设置分类并更新
  61. function resetCategory (category){
  62. if (!category) {
  63. category = 1;
  64. } else {
  65. category = Number(category);
  66. if (category >= 0 && category <= 1) {
  67. category = 1;
  68. }
  69. if (category === 5) {
  70. category = 6;
  71. }
  72. if (category > 6) {
  73. category = 8;
  74. }
  75. }
  76. box.value.category = category;
  77. }
  78. // 高亮处理
  79. const clearHigh=()=> {
  80. const elements = document.querySelectorAll('.successHigh, .exceptionHigh, .exception-text');
  81. elements.forEach((element) => {
  82. let className = element.getAttribute('class');
  83. className = className.replace('successHigh', '').replace('exceptionHigh', '').trim();
  84. element.setAttribute('class', className);
  85. if (className.includes('exception-text')) {
  86. element.remove();
  87. }
  88. });
  89. }
  90. const high=(index, isException)=> {
  91. setTimeout(function () {
  92. const element = document.getElementsByTagName('polygon')[index];
  93. if (!element) return;
  94. if (isException) {
  95. element.setAttribute('class', element.getAttribute('class').replace('successHigh', '') + ' exceptionHigh');
  96. const bbox = element.getBBox();
  97. const textX = bbox.x + bbox.width / 2;
  98. const textY = bbox.y + bbox.height / 2;
  99. const textElement = document.createElementNS('http://www.w3.org/2000/svg', 'text');
  100. textElement.setAttribute('class', 'exception-text');
  101. textElement.setAttribute('x', textX);
  102. textElement.setAttribute('y', textY);
  103. textElement.setAttribute('data-index', index);
  104. textElement.setAttribute('font-family', 'Verdana');
  105. textElement.setAttribute('font-weight', 'bold');
  106. textElement.setAttribute('font-size', '15');
  107. textElement.setAttribute('text-anchor', 'middle');
  108. textElement.setAttribute('dominant-baseline', 'central');
  109. textElement.setAttribute('fill', 'red');
  110. textElement.textContent = '异常';
  111. element.parentNode.insertBefore(textElement, element.nextSibling);
  112. } else {
  113. if (element.getAttribute('class').includes('exceptionHigh')) {
  114. element.setAttribute('class', element.getAttribute('class').replace('exceptionHigh', ''));
  115. const textElements = element.parentNode.querySelectorAll(`.exception-text[data-index="${index}"]`);
  116. textElements.forEach((textElement) => {
  117. element.parentNode.removeChild(textElement);
  118. });
  119. }
  120. element.setAttribute('class', element.getAttribute('class') + ' successHigh');
  121. }
  122. }, 50);
  123. }
  124. defineExpose({high,clearHigh})
  125. </script>
  126. <style scoped>
  127. g rect {
  128. fill: #ffffff;
  129. stroke-width: 3;
  130. stroke: rgb(11, 51, 71);
  131. }
  132. .face {
  133. fill: #ffffff;
  134. stroke: rgb(11, 51, 71);
  135. stroke-width: 3;
  136. }
  137. .line {
  138. stroke: rgb(11, 51, 71);
  139. stroke-width: 3;
  140. }
  141. .single {
  142. fill: #ffffff;
  143. }
  144. .successHigh {
  145. fill: RGB(103, 194, 58) !important;
  146. }
  147. .exceptionHigh {
  148. fill: orange !important;
  149. }
  150. .exception-text {
  151. pointer-events: none;
  152. }
  153. </style>