cmd-progress.vue 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568
  1. <template>
  2. <view class="cmd-progress cmd-progress-default" :class="setStatusClass">
  3. <block v-if="type == 'circle' || type == 'dashboard'">
  4. <view class="cmd-progress cmd-progress-default" :class="setStatusClass">
  5. <view class="cmd-progress-inner" :style="setCircleStyle">
  6. <!-- 绘制圈 start -->
  7. <!-- #ifdef H5 -->
  8. <svg viewBox="0 0 100 100" class="cmd-progress-circle">
  9. <path
  10. :d="setCirclePath" stroke="#f3f3f3" :stroke-linecap="strokeShape" :stroke-width="strokeWidth"
  11. fill-opacity="0" class="cmd-progress-circle-trail" :style="setCircleTrailStyle" />
  12. <path
  13. :d="setCirclePath" :stroke-linecap="strokeShape" :stroke-width="strokeWidth" fill-opacity="0" class="cmd-progress-circle-path"
  14. :style="setCirclePathStyle" />
  15. </svg>
  16. <!-- #endif -->
  17. <!-- #ifndef H5 -->
  18. <text :style="setCircle" />
  19. <!-- #endif -->
  20. <!-- 绘制圈 end -->
  21. <!-- 状态文本 start -->
  22. <block v-if="showInfo">
  23. <text class="cmd-progress-text" :title="setFormat">
  24. <block v-if="status != 'success' && status != 'exception' && setProgress < 100">
  25. {{ setFormat }}
  26. </block>
  27. <!-- #ifdef H5 -->
  28. <svg
  29. v-if="status == 'exception'" viewBox="64 64 896 896" data-icon="close" width="1em" height="1em" fill="currentColor"
  30. aria-hidden="true">
  31. <path d="M563.8 512l262.5-312.9c4.4-5.2.7-13.1-6.1-13.1h-79.8c-4.7 0-9.2 2.1-12.3 5.7L511.6 449.8 295.1 191.7c-3-3.6-7.5-5.7-12.3-5.7H203c-6.8 0-10.5 7.9-6.1 13.1L459.4 512 196.9 824.9A7.95 7.95 0 0 0 203 838h79.8c4.7 0 9.2-2.1 12.3-5.7l216.5-258.1 216.5 258.1c3 3.6 7.5 5.7 12.3 5.7h79.8c6.8 0 10.5-7.9 6.1-13.1L563.8 512z" />
  32. </svg>
  33. <svg
  34. v-if="status == 'success' || setProgress == 100" viewBox="64 64 896 896" data-icon="check" width="1em"
  35. height="1em" fill="currentColor" aria-hidden="true" :style="{'color': strokeColor ? strokeColor : ''}">
  36. <path d="M912 190h-69.9c-9.8 0-19.1 4.5-25.1 12.2L404.7 724.5 207 474a32 32 0 0 0-25.1-12.2H112c-6.7 0-10.4 7.7-6.3 12.9l273.9 347c12.8 16.2 37.4 16.2 50.3 0l488.4-618.9c4.1-5.1.4-12.8-6.3-12.8z" />
  37. </svg>
  38. <!-- #endif -->
  39. <!-- #ifndef H5 -->
  40. <text v-if="status == 'exception' || status == 'success' || setProgress == 100" :style="setCircleIcon" />
  41. <!-- #endif -->
  42. </text>
  43. </block>
  44. <!-- 状态文本 end -->
  45. </view>
  46. </view>
  47. </block>
  48. <block v-if="type == 'line'">
  49. <!-- 进度条 start -->
  50. <view class="cmd-progress-outer">
  51. <view class="cmd-progress-inner" :style="{'border-radius': strokeShape == 'square' ? 0 : '100px'}">
  52. <view class="cmd-progress-bg" :style="setLineStyle" />
  53. <view v-if="successPercent" class="cmd-progress-success-bg" :style="setLineSuccessStyle" />
  54. </view>
  55. </view>
  56. <!-- 进度条 end -->
  57. <!-- 进度条是否显示信息 start -->
  58. <block v-if="showInfo">
  59. <text class="cmd-progress-text" :title="setFormat">
  60. <block v-if="status != 'success' && status != 'exception' && setProgress < 100">
  61. {{ setFormat }}
  62. </block>
  63. <!-- #ifdef H5 -->
  64. <svg
  65. v-if="status == 'exception'" viewBox="64 64 896 896" data-icon="close-circle" width="1em" height="1em"
  66. fill="currentColor" aria-hidden="true">
  67. <path d="M512 64C264.6 64 64 264.6 64 512s200.6 448 448 448 448-200.6 448-448S759.4 64 512 64zm165.4 618.2l-66-.3L512 563.4l-99.3 118.4-66.1.3c-4.4 0-8-3.5-8-8 0-1.9.7-3.7 1.9-5.2l130.1-155L340.5 359a8.32 8.32 0 0 1-1.9-5.2c0-4.4 3.6-8 8-8l66.1.3L512 464.6l99.3-118.4 66-.3c4.4 0 8 3.5 8 8 0 1.9-.7 3.7-1.9 5.2L553.5 514l130 155c1.2 1.5 1.9 3.3 1.9 5.2 0 4.4-3.6 8-8 8z" />
  68. </svg>
  69. <svg
  70. v-if="status == 'success' || setProgress == 100" viewBox="64 64 896 896" data-icon="check-circle" width="1em"
  71. height="1em" fill="currentColor" aria-hidden="true" :style="{'color': strokeColor ? strokeColor : ''}">
  72. <path d="M512 64C264.6 64 64 264.6 64 512s200.6 448 448 448 448-200.6 448-448S759.4 64 512 64zm193.5 301.7l-210.6 292a31.8 31.8 0 0 1-51.7 0L318.5 484.9c-3.8-5.3 0-12.7 6.5-12.7h46.9c10.2 0 19.9 4.9 25.9 13.3l71.2 98.8 157.2-218c6-8.3 15.6-13.3 25.9-13.3H699c6.5 0 10.3 7.4 6.5 12.7z" />
  73. </svg>
  74. <!-- #endif -->
  75. <!-- #ifndef H5 -->
  76. <text v-if="status == 'exception' || status == 'success' || setProgress == 100" :style="setLineStatusIcon" />
  77. <!-- #endif -->
  78. </text>
  79. </block>
  80. <!-- 进度条是否显示信息 end -->
  81. </block>
  82. </view>
  83. </template>
  84. <script>
  85. /**
  86. * 进度条组件
  87. * @description 显示一个操作完成的百分比时,为用户显示该操作的当前进度和状态。
  88. * @tutorial https://ext.dcloud.net.cn/plugin?id=259
  89. * @property {String} type 进度类型 - 线型:line、圆圈形:circle、仪表盘:dashboard,默认线型:line
  90. * @property {Number} percent 进度百分比值 - 显示范围0-100 ,可能数比较大就需要自己转成百分比的值
  91. * @property {Number} success-percent 进度已完成的百分几 - 仅支持进度线型:line
  92. * @property {String} status 进度状态 - 涌动:active(仅支持线型:line)、正常:normal、完成:success、失败:exception,默认正常:normal
  93. * @property {Boolean} show-info 进度状态信息 - 是否显示进度数值或状态图标,默认true
  94. * @property {Number} stroke-width 进度线条的宽度 - 建议在条线的宽度范围:1-50,与进度条显示宽度有关,默认8
  95. * @property {String} stroke-color 进度线条的颜色 - 渐变色仅支持线型:line
  96. * @property {String} stroke-shape 进度线条两端的形状 - 圆:round、方块直角:square,默认圆:round
  97. * @property {Number} width 进度画布宽度 - 仅支持圆圈形:circle、仪表盘:dashboard,默认80
  98. * @property {String} gap-degree 进度圆形缺口角度 - 可取值 0 ~ 360,仅支持圆圈形:circle、仪表盘:dashboard
  99. * @property {String} gap-position 进度圆形缺口位置 - 可取值'top', 'bottom', 'left', 'right',仅支持圆圈形:circle、仪表盘:dashboard
  100. * @example <cmd-progress :percent="30"></cmd-progress>
  101. */
  102. export default {
  103. name: 'CmdProgress',
  104. props: {
  105. /**
  106. * 类型默认:line,可选 line circle dashboard
  107. */
  108. type: {
  109. validator: val => {
  110. return ['line', 'circle', 'dashboard'].includes(val);
  111. },
  112. default: 'line'
  113. },
  114. /**
  115. * 百分比
  116. */
  117. percent: {
  118. type: Number,
  119. default: 0
  120. },
  121. /**
  122. * 已完成的分段百分,仅支持类型line
  123. */
  124. successPercent: {
  125. type: Number,
  126. default: 0
  127. },
  128. /**
  129. * 是否显示进度数值或状态图标
  130. */
  131. showInfo: {
  132. type: Boolean,
  133. default: true
  134. },
  135. /**
  136. * 进度状态,可选:normal success exception (active仅支持类型line
  137. */
  138. status: {
  139. validator: val => {
  140. return ['normal', 'success', 'exception', 'active'].includes(val);
  141. },
  142. default: 'normal'
  143. },
  144. /**
  145. * 条线的宽度1-50,与width有关
  146. */
  147. strokeWidth: {
  148. type: Number,
  149. default: 6
  150. },
  151. /**
  152. * 条线的颜色,渐变色仅支持类型line
  153. */
  154. strokeColor: {
  155. type: String,
  156. default: ''
  157. },
  158. /**
  159. * 条线两端的形状 可选:'round', 'square'
  160. */
  161. strokeShape: {
  162. validator: val => {
  163. return ['round', 'square'].includes(val);
  164. },
  165. default: 'round'
  166. },
  167. /**
  168. * 圆形进度条画布宽度,支持类型circle dashboard
  169. */
  170. width: {
  171. type: Number,
  172. default: 80
  173. },
  174. /**
  175. * 圆形进度条缺口角度,可取值 0 ~ 360,支持类型circle dashboard
  176. */
  177. gapDegree: {
  178. type: Number,
  179. default: 0
  180. },
  181. /**
  182. * 圆形进度条缺口位置,可取值'top', 'bottom', 'left', 'right' ,支持类型circle dashboard
  183. */
  184. gapPosition: {
  185. validator: val => {
  186. return ['top', 'bottom', 'left', 'right'].includes(val);
  187. },
  188. default: 'top'
  189. }
  190. },
  191. computed: {
  192. /**
  193. * 如果需要自定义格式就在这改
  194. */
  195. setFormat() {
  196. return `${this.setProgress}%`;
  197. },
  198. /**
  199. * 设置显示进度值,禁止小于0和超过100
  200. */
  201. setProgress() {
  202. let percent = this.percent;
  203. if (!this.percent || this.percent < 0) {
  204. percent = 0;
  205. } else if (this.percent >= 100) {
  206. percent = 100;
  207. }
  208. return percent;
  209. },
  210. /**
  211. * 进度圈svg大小
  212. */
  213. setCircleStyle() {
  214. return `width: ${this.width}px;
  215. height: ${this.width}px;
  216. fontSize: ${this.width * 0.15 + 6}px;`
  217. },
  218. /**
  219. * 圈底色
  220. */
  221. setCircleTrailStyle() {
  222. const radius = 50 - this.strokeWidth / 2;
  223. const len = Math.PI * 2 * radius;
  224. const gapDeg = this.gapDegree || (this.type === 'dashboard' && 75);
  225. return `stroke-dasharray: ${len - (gapDeg || 0)}px, ${len}px;
  226. stroke-dashoffset: -${(gapDeg || 0) / 2}px;
  227. transition: stroke-dashoffset 0.3s ease 0s, stroke-dasharray 0.3s ease 0s, stroke 0.3s;`
  228. },
  229. /**
  230. * 圈进度
  231. */
  232. setCirclePathStyle() {
  233. const radius = 50 - this.strokeWidth / 2;
  234. const len = Math.PI * 2 * radius;
  235. const gapDeg = this.gapDegree || (this.type === 'dashboard' && 75);
  236. return `stroke: ${this.strokeColor};
  237. stroke-dasharray: ${(this.setProgress / 100) * (len - (gapDeg || 0))}px, ${len}px;
  238. stroke-dashoffset: -${(gapDeg || 0) / 2}px;
  239. transition: stroke-dashoffset 0.3s ease 0s, stroke-dasharray 0.3s ease 0s, stroke 0.3s, stroke-width 0.06s ease 0.3s;`
  240. },
  241. /**
  242. * 绘制圈
  243. */
  244. setCirclePath() {
  245. const radius = 50 - this.strokeWidth / 2;
  246. let beginPositionX = 0;
  247. let beginPositionY = -radius;
  248. let endPositionX = 0;
  249. let endPositionY = -2 * radius;
  250. const gapPos = (this.type === 'dashboard' && 'bottom') || this.gapPosition || 'top';
  251. switch (gapPos) {
  252. case 'left':
  253. beginPositionX = -radius;
  254. beginPositionY = 0;
  255. endPositionX = 2 * radius;
  256. endPositionY = 0;
  257. break;
  258. case 'right':
  259. beginPositionX = radius;
  260. beginPositionY = 0;
  261. endPositionX = -2 * radius;
  262. endPositionY = 0;
  263. break;
  264. case 'bottom':
  265. beginPositionY = radius;
  266. endPositionY = 2 * radius;
  267. break;
  268. default:
  269. break;
  270. }
  271. return `M 50,50 m ${beginPositionX},${beginPositionY} a ${radius},${radius} 0 1 1 ${endPositionX},${-endPositionY} a ${radius},${radius} 0 1 1 ${-endPositionX},${endPositionY}`;
  272. },
  273. // #ifndef H5
  274. /**
  275. * 非H5端,绘制进度圈svg转base URL
  276. */
  277. setCircle() {
  278. const radius = 50 - this.strokeWidth / 2;
  279. const len = Math.PI * 2 * radius;
  280. const gapDeg = this.gapDegree || (this.type === 'dashboard' && 75);
  281. let currentColor = '#108ee9'
  282. // 异常进度
  283. if (this.status == 'exception') {
  284. currentColor = '#f5222d'
  285. }
  286. // 完成进度
  287. if (this.status == 'success' || this.setProgress >= 100 || this.strokeColor) {
  288. currentColor = this.strokeColor || '#52c41a'
  289. }
  290. let svgToBase =
  291. `data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 100 100' class='cmd-progress-circle'%3E%3Cpath d='${this.setCirclePath}' stroke='%23f3f3f3' stroke-linecap='${this.strokeShape}' stroke-width='${this.strokeWidth}' fill-opacity='0' class='cmd-progress-circle-trail' style='stroke-dasharray: ${len - (gapDeg || 0)}px, ${len}px;stroke-dashoffset: -${(gapDeg || 0) / 2}px;transition: stroke-dashoffset 0.3s ease 0s, stroke-dasharray 0.3s ease 0s, stroke 0.3s;'%3E%3C/path%3E%3Cpath d='${this.setCirclePath}' stroke-linecap='${this.strokeShape}' stroke-width='${this.strokeWidth}' fill-opacity='0' class='cmd-progress-circle-path' style='stroke: ${escape(currentColor)};stroke-dasharray: ${(this.setProgress / 100) * (len - (gapDeg || 0))}px, ${len}px;stroke-dashoffset: -${(gapDeg || 0) / 2}px;transition: stroke-dashoffset 0.3s ease 0s, stroke-dasharray 0.3s ease 0s, stroke 0.3s, stroke-width 0.06s ease 0.3s;'%3E%3C/path%3E%3C/svg%3E`
  292. return `background-image: url("${svgToBase}");
  293. background-size: cover;
  294. display: inline-block;
  295. ${this.setCircleStyle}`;
  296. },
  297. /**
  298. * 设置进度圈状态图标
  299. */
  300. setCircleIcon() {
  301. let currentColor = '#108ee9'
  302. let svgToBase = ''
  303. // 异常进度
  304. if (this.status == 'exception') {
  305. currentColor = '#f5222d'
  306. svgToBase =
  307. `data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='64 64 896 896' data-icon='close' width='1em' height='1em' fill='${escape(currentColor)}' aria-hidden='true'%3E %3Cpath d='M563.8 512l262.5-312.9c4.4-5.2.7-13.1-6.1-13.1h-79.8c-4.7 0-9.2 2.1-12.3 5.7L511.6 449.8 295.1 191.7c-3-3.6-7.5-5.7-12.3-5.7H203c-6.8 0-10.5 7.9-6.1 13.1L459.4 512 196.9 824.9A7.95 7.95 0 0 0 203 838h79.8c4.7 0 9.2-2.1 12.3-5.7l216.5-258.1 216.5 258.1c3 3.6 7.5 5.7 12.3 5.7h79.8c6.8 0 10.5-7.9 6.1-13.1L563.8 512z'%3E%3C/path%3E %3C/svg%3E`;
  308. }
  309. // 完成进度
  310. if (this.status == 'success' || this.setProgress >= 100) {
  311. currentColor = this.strokeColor || '#52c41a'
  312. svgToBase =
  313. `data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='64 64 896 896' data-icon='check' width='1em' height='1em' fill='${escape(currentColor)}' aria-hidden='true'%3E %3Cpath d='M912 190h-69.9c-9.8 0-19.1 4.5-25.1 12.2L404.7 724.5 207 474a32 32 0 0 0-25.1-12.2H112c-6.7 0-10.4 7.7-6.3 12.9l273.9 347c12.8 16.2 37.4 16.2 50.3 0l488.4-618.9c4.1-5.1.4-12.8-6.3-12.8z'%3E%3C/path%3E %3C/svg%3E`;
  314. }
  315. return `background-image: url("${svgToBase}");
  316. background-size: cover;
  317. display: inline-block;
  318. width: 1em;
  319. height: 1em;`;
  320. },
  321. // #endif
  322. /**
  323. * 设置进度条样式
  324. */
  325. setLineStyle() {
  326. return `width: ${this.setProgress}%;
  327. height: ${this.strokeWidth}px;
  328. background: ${this.strokeColor};
  329. border-radius: ${this.strokeShape === 'square' ? 0 : '100px'};`;
  330. },
  331. /**
  332. * 设置已完成分段进度
  333. */
  334. setLineSuccessStyle() {
  335. let successPercent = this.successPercent;
  336. if (!this.successPercent || this.successPercent < 0 || this.setProgress < this.successPercent) {
  337. successPercent = 0;
  338. } else if (this.successPercent >= 100) {
  339. successPercent = 100;
  340. }
  341. return `width: ${successPercent}%;
  342. height: ${this.strokeWidth}px;
  343. border-radius: ${this.strokeShape === 'square' ? 0 : '100px'};`;
  344. },
  345. // #ifndef H5
  346. /**
  347. * 设置进度条状态图标
  348. */
  349. setLineStatusIcon() {
  350. let currentColor = '#108ee9'
  351. let svgToBase = ''
  352. // 异常进度
  353. if (this.status == 'exception') {
  354. currentColor = '#f5222d'
  355. svgToBase =
  356. `data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='64 64 896 896' data-icon='close-circle' width='1em' height='1em' fill='${escape(currentColor)}' aria-hidden='true'%3E %3Cpath d='M512 64C264.6 64 64 264.6 64 512s200.6 448 448 448 448-200.6 448-448S759.4 64 512 64zm165.4 618.2l-66-.3L512 563.4l-99.3 118.4-66.1.3c-4.4 0-8-3.5-8-8 0-1.9.7-3.7 1.9-5.2l130.1-155L340.5 359a8.32 8.32 0 0 1-1.9-5.2c0-4.4 3.6-8 8-8l66.1.3L512 464.6l99.3-118.4 66-.3c4.4 0 8 3.5 8 8 0 1.9-.7 3.7-1.9 5.2L553.5 514l130 155c1.2 1.5 1.9 3.3 1.9 5.2 0 4.4-3.6 8-8 8z'%3E%3C/path%3E %3C/svg%3E`;
  357. }
  358. // 完成进度
  359. if (this.status == 'success' || this.setProgress >= 100) {
  360. currentColor = this.strokeColor || '#52c41a'
  361. svgToBase =
  362. `data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='64 64 896 896' data-icon='check-circle' width='1em' height='1em' fill='${escape(currentColor)}' aria-hidden='true'%3E %3Cpath d='M512 64C264.6 64 64 264.6 64 512s200.6 448 448 448 448-200.6 448-448S759.4 64 512 64zm193.5 301.7l-210.6 292a31.8 31.8 0 0 1-51.7 0L318.5 484.9c-3.8-5.3 0-12.7 6.5-12.7h46.9c10.2 0 19.9 4.9 25.9 13.3l71.2 98.8 157.2-218c6-8.3 15.6-13.3 25.9-13.3H699c6.5 0 10.3 7.4 6.5 12.7z'%3E%3C/path%3E %3C/svg%3E`;
  363. }
  364. return `background-image: url("${svgToBase}");
  365. background-size: cover;
  366. display: inline-block;
  367. width: 1em;
  368. height: 1em;`;
  369. },
  370. // #endif
  371. /**
  372. * 状态样式
  373. */
  374. setStatusClass() {
  375. let statusClass = [];
  376. // 异常进度
  377. if (this.status == 'exception') {
  378. statusClass.push('cmd-progress-status-exception')
  379. }
  380. // 完成进度
  381. if (this.status == 'success' || this.setProgress >= 100) {
  382. statusClass.push('cmd-progress-status-success')
  383. }
  384. // 活动进度条
  385. if (this.status == 'active') {
  386. statusClass.push('cmd-progress-status-active')
  387. }
  388. // 是否显示信息
  389. if (this.showInfo) {
  390. statusClass.push('cmd-progress-show-info')
  391. }
  392. // 进度条类型
  393. if (this.type === 'line') {
  394. statusClass.push('cmd-progress-line')
  395. }
  396. // 进度圈、仪表盘类型
  397. if (this.type === 'circle' || this.type === 'dashboard') {
  398. statusClass.push('cmd-progress-circle')
  399. }
  400. statusClass.push('cmd-progress-status-normal')
  401. return statusClass;
  402. }
  403. }
  404. }
  405. </script>
  406. <style>
  407. .cmd-progress {
  408. box-sizing: border-box;
  409. margin: 0;
  410. padding: 0;
  411. list-style: none;
  412. display: inline-block;
  413. }
  414. .cmd-progress-line {
  415. width: 100%;
  416. font-size: 28upx;
  417. position: relative;
  418. display: flex;
  419. flex-direction: row;
  420. justify-content: center;
  421. align-items: center;
  422. }
  423. .cmd-progress-outer {
  424. display: inline-block;
  425. width: 100%;
  426. margin-right: 0;
  427. padding-right: 0;
  428. }
  429. .cmd-progress-show-info .cmd-progress-outer {
  430. flex: 1;
  431. }
  432. .cmd-progress-inner {
  433. display: inline-block;
  434. width: 100%;
  435. background-color: #f5f5f5;
  436. border-radius: 200upx;
  437. vertical-align: middle;
  438. position: relative;
  439. }
  440. .cmd-progress-circle-trail {
  441. stroke: #f5f5f5;
  442. }
  443. .cmd-progress-circle-path {
  444. stroke: #1890ff;
  445. animation: appear 0.3s;
  446. }
  447. .cmd-progress-success-bg,
  448. .cmd-progress-bg {
  449. background-color: #1890ff;
  450. transition: all 0.4s cubic-bezier(0.08, 0.82, 0.17, 1) 0s;
  451. position: relative;
  452. }
  453. .cmd-progress-success-bg {
  454. background-color: #52c41a;
  455. position: absolute;
  456. top: 0;
  457. left: 0;
  458. }
  459. .cmd-progress-text {
  460. word-break: normal;
  461. width: 60upx;
  462. text-align: left;
  463. margin-left: 16upx;
  464. vertical-align: middle;
  465. display: inline-block;
  466. white-space: nowrap;
  467. color: rgba(0, 0, 0, 0.45);
  468. line-height: 1;
  469. }
  470. .cmd-progress-status-active .cmd-progress-bg:before {
  471. content: "";
  472. opacity: 0;
  473. position: absolute;
  474. top: 0;
  475. left: 0;
  476. right: 0;
  477. bottom: 0;
  478. background: #fff;
  479. border-radius: 20upx;
  480. -webkit-animation: cmd-progress-active 2.4s cubic-bezier(0.23, 1, 0.32, 1) infinite;
  481. animation: cmd-progress-active 2.4s cubic-bezier(0.23, 1, 0.32, 1) infinite;
  482. }
  483. .cmd-progress-status-exception .cmd-progress-bg {
  484. background-color: #f5222d;
  485. }
  486. .cmd-progress-status-exception .cmd-progress-text {
  487. color: #f5222d;
  488. }
  489. .cmd-progress-status-exception .cmd-progress-circle-path {
  490. stroke: #f5222d;
  491. }
  492. .cmd-progress-status-success .cmd-progress-bg {
  493. background-color: #52c41a;
  494. }
  495. .cmd-progress-status-success .cmd-progress-text {
  496. color: #52c41a;
  497. }
  498. .cmd-progress-status-success .cmd-progress-circle-path {
  499. stroke: #52c41a;
  500. }
  501. .cmd-progress-circle .cmd-progress-inner {
  502. position: relative;
  503. line-height: 1;
  504. background-color: transparent;
  505. }
  506. .cmd-progress-circle .cmd-progress-text {
  507. display: block;
  508. position: absolute;
  509. width: 100%;
  510. text-align: center;
  511. line-height: 1;
  512. top: 50%;
  513. -webkit-transform: translateY(-50%);
  514. transform: translateY(-50%);
  515. left: 0;
  516. margin: 0;
  517. color: rgba(0, 0, 0, 0.65);
  518. white-space: normal;
  519. }
  520. .cmd-progress-circle .cmd-progress-status-exception .cmd-progress-text {
  521. color: #f5222d;
  522. }
  523. .cmd-progress-circle .cmd-progress-status-success .cmd-progress-text {
  524. color: #52c41a;
  525. }
  526. @keyframes cmd-progress-active {
  527. 0% {
  528. opacity: 0.1;
  529. width: 0;
  530. }
  531. 20% {
  532. opacity: 0.5;
  533. width: 0;
  534. }
  535. 100% {
  536. opacity: 0;
  537. width: 100%;
  538. }
  539. }
  540. </style>