| <template> | |
|   <div class="progress"> | |
|     <div class="progress-item flex" v-for="(item, index) in arr" :key="`${code}-${index}`" | |
|       :style="getStyle(item.index)" | |
|     > | |
|       {{ item.text }} | |
|     </div> | |
|     <div class="progress-text" :style="textStyle"> | |
|       <div class="flex" v-for="(item, index) in arr" :key="`${code}-text-${index}`" > | |
|         {{ item.text }} | |
|       </div> | |
|     </div> | |
|   </div> | |
| </template> | |
| 
 | |
| <script> | |
|   const WIDTH = 40; | |
| 
 | |
|   export default { | |
|     props: { | |
|       value: { | |
|         default: 0 | |
|       } | |
|     }, | |
|     data() { | |
|       return { | |
|         code: Math.floor(Math.random() * 100).toString() | |
|       } | |
|     }, | |
|     computed: { | |
|       current() { | |
|         return Math.floor(this.value / 20) | |
|       }, | |
|       arr() { | |
|         let arr = new Array(this.current).fill(1).map((item, index) => { | |
|           return { | |
|             text: `${(index + 1) * 20}%`, | |
|             index, | |
|           } | |
|         }) | |
| 
 | |
|         return arr.reverse() | |
|       }, | |
|       textStyle() { | |
|         const n = this.arr.length | |
|         const width = WIDTH * n | |
| 
 | |
|         return `width: ${width}rpx; grid-template-columns: repeat(${n}, 1fr);` | |
|       }, | |
|     }, | |
|     methods: { | |
|       getStyle(index) { | |
|         const width = WIDTH * (index + 1) | |
| 
 | |
|         return `width: ${width}rpx;` | |
|       }, | |
|     }, | |
|   } | |
| </script> | |
| 
 | |
| <style lang="scss" scoped> | |
|   .progress { | |
|     position: relative; | |
|     font-size: 0; | |
|     width: 100%; | |
|     box-sizing: border-box; | |
| 
 | |
|     &-item { | |
|       position: absolute; | |
|       top: 0; | |
|       left: 0; | |
|       padding: 2rpx 0; | |
|       font-size: 6rpx; | |
|       color: transparent; | |
|       background: #ee751c; | |
|       border: 2rpx solid #FFFFFF; | |
|       border-radius: 20rpx; | |
| 
 | |
|       &:first-child { | |
|       } | |
|     } | |
| 
 | |
|     &-text { | |
|       position: absolute; | |
|       display: grid; | |
|       padding: 2rpx 0; | |
|       font-size: 6rpx; | |
|       color: #FFFFFF; | |
|       background: transparent; | |
|       border: 2rpx solid transparent; | |
|     } | |
|   } | |
| </style> |