88 lines
2.5 KiB
TypeScript
Raw Normal View History

2021-03-25 23:06:20 +02:00
import React, { useRef, useEffect, SyntheticEvent, useState } from "react";
import { GridProps, Grid } from "../grid/grid";
import { CalendarProps, Calendar } from "../calendar/calendar";
import { TaskGanttContentProps, TaskGanttContent } from "./task-gantt-content";
import styles from "./gantt.module.css";
export type TaskGanttProps = {
gridProps: GridProps;
calendarProps: CalendarProps;
barProps: TaskGanttContentProps;
ganttHeight: number;
scrollY: number;
2020-08-25 20:58:36 +03:00
scrollX: number;
onScroll: (event: SyntheticEvent<HTMLDivElement>) => void;
};
export const TaskGantt: React.FC<TaskGanttProps> = ({
gridProps,
calendarProps,
barProps,
ganttHeight,
scrollY,
2020-08-25 20:58:36 +03:00
scrollX,
onScroll,
}) => {
const ganttSVGRef = useRef<SVGSVGElement>(null);
const horizontalContainerRef = useRef<HTMLDivElement>(null);
2020-08-25 20:58:36 +03:00
const verticalContainerRef = useRef<HTMLDivElement>(null);
2021-03-28 16:12:28 +03:00
const [displayXStartEndpoint, setDisplayXStartEndpoint] = useState({
start: 0,
end: 0,
});
const newBarProps = { ...barProps, svg: ganttSVGRef, displayXStartEndpoint };
useEffect(() => {
if (horizontalContainerRef.current) {
horizontalContainerRef.current.scrollTop = scrollY;
}
}, [scrollY]);
2020-08-25 20:58:36 +03:00
useEffect(() => {
if (verticalContainerRef.current) {
verticalContainerRef.current.scrollLeft = scrollX;
2021-03-28 16:12:28 +03:00
setDisplayXStartEndpoint({
start: scrollX,
end: verticalContainerRef.current.clientWidth + scrollX,
});
2020-08-25 20:58:36 +03:00
}
2021-03-25 23:06:20 +02:00
// verticalContainerRef.current?.clientWidth need for resize window tracking
}, [scrollX, verticalContainerRef.current?.clientWidth]);
2020-08-25 20:58:36 +03:00
return (
2020-08-25 20:58:36 +03:00
<div
className={styles.ganttVerticalContainer}
ref={verticalContainerRef}
onScroll={onScroll}
>
<svg
xmlns="http://www.w3.org/2000/svg"
2021-03-25 23:06:20 +02:00
width={gridProps.svgWidth}
height={calendarProps.headerHeight}
fontFamily={barProps.fontFamily}
>
<Calendar {...calendarProps} />
</svg>
<div
ref={horizontalContainerRef}
className={styles.horizontalContainer}
style={
ganttHeight
2021-03-25 23:06:20 +02:00
? { height: ganttHeight, width: gridProps.svgWidth }
: { width: gridProps.svgWidth }
}
>
<svg
xmlns="http://www.w3.org/2000/svg"
2021-03-25 23:06:20 +02:00
width={gridProps.svgWidth}
height={barProps.rowHeight * barProps.tasks.length}
fontFamily={barProps.fontFamily}
ref={ganttSVGRef}
>
<Grid {...gridProps} />
<TaskGanttContent {...newBarProps} />
</svg>
</div>
</div>
);
};