-
-
Notifications
You must be signed in to change notification settings - Fork 161
/
Copy pathLine.tsx
100 lines (93 loc) · 2.98 KB
/
Line.tsx
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
import * as React from 'react';
import classNames from 'classnames';
import { useTransitionDuration, defaultProps } from './common';
import type { ProgressProps } from './interface';
const Line: React.FC<ProgressProps> = ({
className,
percent,
prefixCls,
strokeColor,
strokeLinecap,
strokeWidth,
style,
trailColor,
trailWidth,
transition,
...restProps
}) => {
// eslint-disable-next-line no-param-reassign
delete restProps.gapPosition;
const percentList = Array.isArray(percent) ? percent : [percent];
const strokeColorList = Array.isArray(strokeColor) ? strokeColor : [strokeColor];
const paths = useTransitionDuration();
const center = strokeWidth / 2;
const right = 100 - strokeWidth / 2;
const pathString = `M ${strokeLinecap === 'round' ? center : 0},${center}
L ${strokeLinecap === 'round' ? right : 100},${center}`;
const viewBoxString = `0 0 100 ${strokeWidth}`;
let stackPtg = 0;
return (
<svg
className={classNames(`${prefixCls}-line`, className)}
viewBox={viewBoxString}
preserveAspectRatio="none"
style={style}
{...restProps}
>
<path
className={`${prefixCls}-line-trail`}
d={pathString}
strokeLinecap={strokeLinecap}
stroke={trailColor}
strokeWidth={trailWidth || strokeWidth}
fillOpacity="0"
/>
{percentList.map((ptg, index) => {
let dashPercent = 1;
switch (strokeLinecap) {
case 'round':
dashPercent = 1 - strokeWidth / 100;
break;
case 'square':
dashPercent = 1 - strokeWidth / 2 / 100;
break;
default:
dashPercent = 1;
break;
}
const pathStyle = {
strokeDasharray: `${ptg * dashPercent}px, 100px`,
strokeDashoffset: `-${stackPtg}px`,
transition:
transition ||
'stroke-dashoffset 0.3s ease 0s, stroke-dasharray .3s ease 0s, stroke 0.3s linear',
};
const color = strokeColorList[index] || strokeColorList[strokeColorList.length - 1];
stackPtg += ptg;
return (
<path
key={index}
className={`${prefixCls}-line-path`}
d={pathString}
strokeLinecap={strokeLinecap}
stroke={color as string}
strokeWidth={strokeWidth}
fillOpacity="0"
opacity={ptg === 0 ? 0 : 1}
ref={(elem) => {
// https://reactjs.org/docs/refs-and-the-dom.html#callback-refs
// React will call the ref callback with the DOM element when the component mounts,
// and call it with `null` when it unmounts.
// Refs are guaranteed to be up-to-date before componentDidMount or componentDidUpdate fires.
paths[index] = elem;
}}
style={pathStyle}
/>
);
})}
</svg>
);
};
Line.defaultProps = defaultProps;
Line.displayName = 'Line';
export default Line;