Code review fixes
continuous-integration/drone/push Build is passing
Details
continuous-integration/drone/push Build is passing
Details
This commit is contained in:
parent
3de0f67ccb
commit
4f6f3265fd
|
@ -1,15 +1,17 @@
|
|||
.wrapper {
|
||||
position: relative;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.line {
|
||||
position: absolute;
|
||||
width: calc(5rem / 16);
|
||||
height: 100%;
|
||||
border-radius: calc(10rem / 16);
|
||||
background-color: var(--secondary-accent);
|
||||
z-index: -1;
|
||||
}
|
||||
|
||||
.timelineSections {
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
|
@ -20,7 +22,7 @@
|
|||
|
||||
.timelineSection {
|
||||
width: 100%;
|
||||
height: inherit;
|
||||
height: 100%;
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
justify-content: center;
|
||||
|
@ -35,15 +37,7 @@
|
|||
word-wrap: break-word;
|
||||
}
|
||||
|
||||
.timeHover {
|
||||
color: var(--secondary-accent-light);
|
||||
}
|
||||
|
||||
.circle {
|
||||
margin-left: calc(2rem / 16);
|
||||
width: calc(30rem / 16);
|
||||
height: calc(30rem / 16);
|
||||
border-radius: calc(30rem / 16);
|
||||
background-color: var(--secondary-accent);
|
||||
box-shadow: calc(0rem / 16) calc(0rem / 16) calc(30rem / 16) var(--secondary-accent);
|
||||
display: flex;
|
||||
|
@ -52,10 +46,8 @@
|
|||
}
|
||||
|
||||
.innerCircle {
|
||||
width: calc(15rem / 16);
|
||||
height: calc(15rem / 16);
|
||||
border-radius: calc(15rem / 16);
|
||||
background-color: var(--label);
|
||||
display: none;
|
||||
}
|
||||
|
||||
.text {
|
||||
|
@ -66,12 +58,21 @@
|
|||
font-size: calc(20rem / 16);
|
||||
font-weight: 700;
|
||||
color: var(--label);
|
||||
border: calc(2rem / 16) solid var(--card-background);
|
||||
background-color: var(--card-background);
|
||||
word-wrap: break-word;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
.textHover {
|
||||
.timelineSection:hover .time {
|
||||
color: var(--secondary-accent-light);
|
||||
}
|
||||
|
||||
.timelineSection:hover .innerCircle {
|
||||
display: inline;
|
||||
}
|
||||
|
||||
.timelineSection:hover .text {
|
||||
border: calc(2rem / 16) solid var(--secondary-accent-light);
|
||||
box-shadow: calc(0rem / 16) calc(0rem / 16) calc(20rem / 16) var(--secondary-accent);
|
||||
}
|
|
@ -11,50 +11,78 @@ interface TimelineProps {
|
|||
data: TimelineData[];
|
||||
/** Width of the entire timeline, in pixels. */
|
||||
width: number;
|
||||
/** Height of the entire timeline, in pixels. */
|
||||
height: number;
|
||||
/** Whether the time is transformed to uppercase */
|
||||
/** Whether the time is transformed to uppercase. */
|
||||
isTimeUppercase?: boolean;
|
||||
/** Width of the middle timeline line, in pixels */
|
||||
lineWidth?: number;
|
||||
/** Width of the outer circles on the timeline, in pixels. */
|
||||
outerCircleWidth?: number;
|
||||
/** Width of the inner circles on the timeline, in pixels. */
|
||||
innerCircleWidth?: number;
|
||||
/** Width of time label, in pixels. */
|
||||
timeWidth?: number;
|
||||
/** Width of text label, in pixels. */
|
||||
textWidth?: number;
|
||||
/** Distance between labels to middle line, in pixels. */
|
||||
labelsOffset?: number;
|
||||
/** Distance between the time label AND the text label to middle line, in pixels. */
|
||||
gap?: number;
|
||||
className?: string;
|
||||
}
|
||||
|
||||
export default function Timeline({
|
||||
data,
|
||||
width,
|
||||
height,
|
||||
isTimeUppercase = true,
|
||||
lineWidth = 5,
|
||||
outerCircleWidth = 30,
|
||||
innerCircleWidth = 15,
|
||||
timeWidth = 200,
|
||||
textWidth = 300,
|
||||
labelsOffset = 50,
|
||||
gap = 50,
|
||||
className,
|
||||
}: TimelineProps) {
|
||||
const largerMiddleElemeent =
|
||||
outerCircleWidth > lineWidth ? outerCircleWidth : lineWidth;
|
||||
const requestedWidth =
|
||||
timeWidth + gap + largerMiddleElemeent + gap + textWidth;
|
||||
if (requestedWidth > width) {
|
||||
throw new Error(
|
||||
`<Timeline /> - timeWidth + gap + ${
|
||||
outerCircleWidth > lineWidth ? "outerCircleWidth" : "lineWidth"
|
||||
} + gap + textWidth (${timeWidth} + ${gap} + ${largerMiddleElemeent} + ${gap} + ${textWidth} = ${requestedWidth}) is larger than width (${width})`
|
||||
);
|
||||
}
|
||||
if (innerCircleWidth > outerCircleWidth) {
|
||||
throw new Error(
|
||||
`<Timeline /> - innerCircleWidth (${innerCircleWidth}) is larger than outerCircleWidth (${outerCircleWidth})`
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div
|
||||
className={
|
||||
className ? `${className} ${styles.wrapper}` : `${styles.wrapper}`
|
||||
}
|
||||
style={{ width: width, height: height }}
|
||||
style={{ width: width }}
|
||||
>
|
||||
<div
|
||||
className={styles.line}
|
||||
style={{ height: height, left: width / 2 }}
|
||||
></div>
|
||||
<div className={styles.timelineSections} style={{ width: width }}>
|
||||
style={{
|
||||
width: lineWidth,
|
||||
left: width / 2 - lineWidth / 2,
|
||||
}}
|
||||
/>
|
||||
<div className={styles.timelineSections}>
|
||||
{data.map((datum) => (
|
||||
<TimelineSection
|
||||
key={datum.time}
|
||||
datum={datum}
|
||||
width={width}
|
||||
isTimeUppercase={isTimeUppercase}
|
||||
outerCircleWidth={outerCircleWidth}
|
||||
innerCircleWidth={innerCircleWidth}
|
||||
timeWidth={timeWidth}
|
||||
textWidth={textWidth}
|
||||
labelsOffset={labelsOffset}
|
||||
gap={gap}
|
||||
/>
|
||||
))}
|
||||
</div>
|
||||
|
@ -66,74 +94,73 @@ interface TimelineSectionProps {
|
|||
datum: TimelineData;
|
||||
width: number;
|
||||
isTimeUppercase: boolean;
|
||||
outerCircleWidth: number;
|
||||
innerCircleWidth: number;
|
||||
timeWidth: number;
|
||||
textWidth: number;
|
||||
labelsOffset: number;
|
||||
gap: number;
|
||||
}
|
||||
|
||||
function TimelineSection({
|
||||
datum,
|
||||
width,
|
||||
isTimeUppercase,
|
||||
outerCircleWidth,
|
||||
innerCircleWidth,
|
||||
timeWidth,
|
||||
|
||||
textWidth,
|
||||
labelsOffset,
|
||||
gap,
|
||||
}: TimelineSectionProps) {
|
||||
const [onHover, setHover] = useState(false);
|
||||
|
||||
const handleMouseEnter = () => {
|
||||
setHover(true);
|
||||
console.log(onHover);
|
||||
};
|
||||
const handleMouseLeave = () => setHover(false);
|
||||
|
||||
// divs for customizable margins are necessary, absolute positioning loses vertical flex-box functionality
|
||||
return (
|
||||
<div className={styles.timelineSection}>
|
||||
<div
|
||||
style={{
|
||||
width: (width - labelsOffset - labelsOffset - 30) / 2 - timeWidth,
|
||||
}}
|
||||
></div>
|
||||
<div className={styles.timelineSection} style={{ gap: gap }}>
|
||||
<div
|
||||
className={onHover ? `${styles.time} ${styles.timeHover}` : styles.time}
|
||||
style={{
|
||||
width: timeWidth,
|
||||
marginLeft: (width - 2 * gap - outerCircleWidth) / 2 - timeWidth,
|
||||
}}
|
||||
onMouseEnter={handleMouseEnter}
|
||||
onMouseLeave={handleMouseLeave}
|
||||
>
|
||||
{isTimeUppercase ? datum.time.toUpperCase() : datum.time}
|
||||
</div>
|
||||
<div style={{ width: labelsOffset }}></div>
|
||||
<div
|
||||
className={styles.circle}
|
||||
style={{ width: 30 }}
|
||||
onMouseEnter={handleMouseEnter}
|
||||
onMouseLeave={handleMouseLeave}
|
||||
style={{
|
||||
width: outerCircleWidth,
|
||||
height: outerCircleWidth,
|
||||
borderRadius: outerCircleWidth,
|
||||
}}
|
||||
>
|
||||
<div
|
||||
className={styles.innerCircle}
|
||||
style={{ display: onHover ? "inline" : "none" }}
|
||||
></div>
|
||||
style={{
|
||||
width: innerCircleWidth,
|
||||
height: innerCircleWidth,
|
||||
borderRadius: innerCircleWidth,
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
<div style={{ width: labelsOffset }}></div>
|
||||
<div
|
||||
className={onHover ? `${styles.text} ${styles.textHover}` : styles.text}
|
||||
style={{
|
||||
width: textWidth,
|
||||
marginRight: (width - 2 * gap - outerCircleWidth) / 2 - textWidth,
|
||||
}}
|
||||
onMouseEnter={handleMouseEnter}
|
||||
onMouseLeave={handleMouseLeave}
|
||||
>
|
||||
{datum.text}
|
||||
</div>
|
||||
<div
|
||||
style={{
|
||||
width: (width - labelsOffset - labelsOffset - 30) / 2 - textWidth,
|
||||
}}
|
||||
></div>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -68,7 +68,7 @@ export default function Home() {
|
|||
<h2>
|
||||
<code>{"<Timeline />"}</code>
|
||||
</h2>
|
||||
<Timeline data={mockTimelineData} width={800} height={1500} />
|
||||
<Timeline data={mockTimelineData} width={800} />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue