forked from github/plane
dev: show all issues on the gantt chart (#3487)
This commit is contained in:
parent
d53a086206
commit
9debd81a50
4
packages/types/src/view-props.d.ts
vendored
4
packages/types/src/view-props.d.ts
vendored
@ -64,8 +64,7 @@ export type TIssueParams =
|
|||||||
| "order_by"
|
| "order_by"
|
||||||
| "type"
|
| "type"
|
||||||
| "sub_issue"
|
| "sub_issue"
|
||||||
| "show_empty_groups"
|
| "show_empty_groups";
|
||||||
| "start_target_date";
|
|
||||||
|
|
||||||
export type TCalendarLayouts = "month" | "week";
|
export type TCalendarLayouts = "month" | "week";
|
||||||
|
|
||||||
@ -93,7 +92,6 @@ export interface IIssueDisplayFilterOptions {
|
|||||||
layout?: TIssueLayouts;
|
layout?: TIssueLayouts;
|
||||||
order_by?: TIssueOrderByOptions;
|
order_by?: TIssueOrderByOptions;
|
||||||
show_empty_groups?: boolean;
|
show_empty_groups?: boolean;
|
||||||
start_target_date?: boolean;
|
|
||||||
sub_issue?: boolean;
|
sub_issue?: boolean;
|
||||||
type?: TIssueTypeFilters;
|
type?: TIssueTypeFilters;
|
||||||
}
|
}
|
||||||
|
@ -40,9 +40,9 @@ export const IssueLink = ({ activity }: { activity: IIssueActivity }) => {
|
|||||||
}`}`}
|
}`}`}
|
||||||
target={activity.issue === null ? "_self" : "_blank"}
|
target={activity.issue === null ? "_self" : "_blank"}
|
||||||
rel={activity.issue === null ? "" : "noopener noreferrer"}
|
rel={activity.issue === null ? "" : "noopener noreferrer"}
|
||||||
className="inline-flex items-center gap-1 font-medium text-custom-text-100 hover:underline whitespace-nowrap"
|
className="inline-flex items-center gap-1 font-medium text-custom-text-100 hover:underline"
|
||||||
>
|
>
|
||||||
{`${activity.project_detail.identifier}-${activity.issue_detail.sequence_id}`}{" "}
|
<span className="whitespace-nowrap">{`${activity.project_detail.identifier}-${activity.issue_detail.sequence_id}`}</span>{" "}
|
||||||
<span className="font-normal">{activity.issue_detail?.name}</span>
|
<span className="font-normal">{activity.issue_detail?.name}</span>
|
||||||
</a>
|
</a>
|
||||||
) : (
|
) : (
|
||||||
@ -267,7 +267,7 @@ const activityDetails: {
|
|||||||
<span className="flex-shrink truncate font-medium text-custom-text-100">{activity.new_value}</span>
|
<span className="flex-shrink truncate font-medium text-custom-text-100">{activity.new_value}</span>
|
||||||
</span>
|
</span>
|
||||||
{showIssue && (
|
{showIssue && (
|
||||||
<span>
|
<span className="">
|
||||||
{" "}
|
{" "}
|
||||||
to <IssueLink activity={activity} />
|
to <IssueLink activity={activity} />
|
||||||
</span>
|
</span>
|
||||||
|
@ -86,7 +86,7 @@ export const OverviewStatsWidget: React.FC<WidgetProps> = observer((props) => {
|
|||||||
)}
|
)}
|
||||||
>
|
>
|
||||||
<h5 className="font-semibold text-xl">{stat.count}</h5>
|
<h5 className="font-semibold text-xl">{stat.count}</h5>
|
||||||
<p className="text-custom-text-300">{stat.title}</p>
|
<p className="text-custom-text-300 text-sm xl:text-base">{stat.title}</p>
|
||||||
</Link>
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
@ -1,23 +0,0 @@
|
|||||||
import React, { useState, useEffect } from "react";
|
|
||||||
|
|
||||||
// react beautiful dnd
|
|
||||||
import { Droppable, DroppableProps } from "@hello-pangea/dnd";
|
|
||||||
|
|
||||||
const StrictModeDroppable = ({ children, ...props }: DroppableProps) => {
|
|
||||||
const [enabled, setEnabled] = useState(false);
|
|
||||||
|
|
||||||
useEffect(() => {
|
|
||||||
const animation = requestAnimationFrame(() => setEnabled(true));
|
|
||||||
|
|
||||||
return () => {
|
|
||||||
cancelAnimationFrame(animation);
|
|
||||||
setEnabled(false);
|
|
||||||
};
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
if (!enabled) return null;
|
|
||||||
|
|
||||||
return <Droppable {...props}>{children}</Droppable>;
|
|
||||||
};
|
|
||||||
|
|
||||||
export default StrictModeDroppable;
|
|
@ -2,7 +2,7 @@ import { FC } from "react";
|
|||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "../hooks";
|
import { useChart } from "../hooks";
|
||||||
// helpers
|
// helpers
|
||||||
import { ChartDraggable } from "../helpers/draggable";
|
import { ChartAddBlock, ChartDraggable } from "components/gantt-chart";
|
||||||
import { renderFormattedPayloadDate } from "helpers/date-time.helper";
|
import { renderFormattedPayloadDate } from "helpers/date-time.helper";
|
||||||
// types
|
// types
|
||||||
import { IBlockUpdateData, IGanttBlock } from "../types";
|
import { IBlockUpdateData, IGanttBlock } from "../types";
|
||||||
@ -15,6 +15,7 @@ export type GanttChartBlocksProps = {
|
|||||||
enableBlockLeftResize: boolean;
|
enableBlockLeftResize: boolean;
|
||||||
enableBlockRightResize: boolean;
|
enableBlockRightResize: boolean;
|
||||||
enableBlockMove: boolean;
|
enableBlockMove: boolean;
|
||||||
|
showAllBlocks: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const GanttChartBlocks: FC<GanttChartBlocksProps> = (props) => {
|
export const GanttChartBlocks: FC<GanttChartBlocksProps> = (props) => {
|
||||||
@ -26,6 +27,7 @@ export const GanttChartBlocks: FC<GanttChartBlocksProps> = (props) => {
|
|||||||
enableBlockLeftResize,
|
enableBlockLeftResize,
|
||||||
enableBlockRightResize,
|
enableBlockRightResize,
|
||||||
enableBlockMove,
|
enableBlockMove,
|
||||||
|
showAllBlocks,
|
||||||
} = props;
|
} = props;
|
||||||
|
|
||||||
const { activeBlock, dispatch } = useChart();
|
const { activeBlock, dispatch } = useChart();
|
||||||
@ -45,6 +47,8 @@ export const GanttChartBlocks: FC<GanttChartBlocksProps> = (props) => {
|
|||||||
totalBlockShifts: number,
|
totalBlockShifts: number,
|
||||||
dragDirection: "left" | "right" | "move"
|
dragDirection: "left" | "right" | "move"
|
||||||
) => {
|
) => {
|
||||||
|
if (!block.start_date || !block.target_date) return;
|
||||||
|
|
||||||
const originalStartDate = new Date(block.start_date);
|
const originalStartDate = new Date(block.start_date);
|
||||||
const updatedStartDate = new Date(originalStartDate);
|
const updatedStartDate = new Date(originalStartDate);
|
||||||
|
|
||||||
@ -75,27 +79,31 @@ export const GanttChartBlocks: FC<GanttChartBlocksProps> = (props) => {
|
|||||||
>
|
>
|
||||||
{blocks &&
|
{blocks &&
|
||||||
blocks.length > 0 &&
|
blocks.length > 0 &&
|
||||||
blocks.map(
|
blocks.map((block) => {
|
||||||
(block) =>
|
// hide the block if it doesn't have start and target dates and showAllBlocks is false
|
||||||
block.start_date &&
|
if (!showAllBlocks && !(block.start_date && block.target_date)) return;
|
||||||
block.target_date && (
|
|
||||||
<div
|
const isBlockVisibleOnChart = block.start_date && block.target_date;
|
||||||
key={`block-${block.id}`}
|
|
||||||
className={`h-11 ${activeBlock?.id === block.id ? "bg-custom-background-80" : ""}`}
|
return (
|
||||||
onMouseEnter={() => updateActiveBlock(block)}
|
<div
|
||||||
onMouseLeave={() => updateActiveBlock(null)}
|
key={`block-${block.id}`}
|
||||||
>
|
className={`h-11 ${activeBlock?.id === block.id ? "bg-custom-background-80" : ""}`}
|
||||||
<ChartDraggable
|
onMouseEnter={() => updateActiveBlock(block)}
|
||||||
block={block}
|
onMouseLeave={() => updateActiveBlock(null)}
|
||||||
blockToRender={blockToRender}
|
>
|
||||||
handleBlock={(...args) => handleChartBlockPosition(block, ...args)}
|
{!isBlockVisibleOnChart && <ChartAddBlock block={block} blockUpdateHandler={blockUpdateHandler} />}
|
||||||
enableBlockLeftResize={enableBlockLeftResize}
|
<ChartDraggable
|
||||||
enableBlockRightResize={enableBlockRightResize}
|
block={block}
|
||||||
enableBlockMove={enableBlockMove}
|
blockToRender={blockToRender}
|
||||||
/>
|
handleBlock={(...args) => handleChartBlockPosition(block, ...args)}
|
||||||
</div>
|
enableBlockLeftResize={enableBlockLeftResize}
|
||||||
)
|
enableBlockRightResize={enableBlockRightResize}
|
||||||
)}
|
enableBlockMove={enableBlockMove}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
})}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@ -46,22 +46,25 @@ type ChartViewRootProps = {
|
|||||||
enableBlockMove: boolean;
|
enableBlockMove: boolean;
|
||||||
enableReorder: boolean;
|
enableReorder: boolean;
|
||||||
bottomSpacing: boolean;
|
bottomSpacing: boolean;
|
||||||
|
showAllBlocks: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const ChartViewRoot: FC<ChartViewRootProps> = ({
|
export const ChartViewRoot: FC<ChartViewRootProps> = (props) => {
|
||||||
border,
|
const {
|
||||||
title,
|
border,
|
||||||
blocks = null,
|
title,
|
||||||
loaderTitle,
|
blocks = null,
|
||||||
blockUpdateHandler,
|
loaderTitle,
|
||||||
sidebarToRender,
|
blockUpdateHandler,
|
||||||
blockToRender,
|
sidebarToRender,
|
||||||
enableBlockLeftResize,
|
blockToRender,
|
||||||
enableBlockRightResize,
|
enableBlockLeftResize,
|
||||||
enableBlockMove,
|
enableBlockRightResize,
|
||||||
enableReorder,
|
enableBlockMove,
|
||||||
bottomSpacing,
|
enableReorder,
|
||||||
}) => {
|
bottomSpacing,
|
||||||
|
showAllBlocks,
|
||||||
|
} = props;
|
||||||
// states
|
// states
|
||||||
const [itemsContainerWidth, setItemsContainerWidth] = useState<number>(0);
|
const [itemsContainerWidth, setItemsContainerWidth] = useState<number>(0);
|
||||||
const [fullScreenMode, setFullScreenMode] = useState<boolean>(false);
|
const [fullScreenMode, setFullScreenMode] = useState<boolean>(false);
|
||||||
@ -311,6 +314,7 @@ export const ChartViewRoot: FC<ChartViewRootProps> = ({
|
|||||||
enableBlockLeftResize={enableBlockLeftResize}
|
enableBlockLeftResize={enableBlockLeftResize}
|
||||||
enableBlockRightResize={enableBlockRightResize}
|
enableBlockRightResize={enableBlockRightResize}
|
||||||
enableBlockMove={enableBlockMove}
|
enableBlockMove={enableBlockMove}
|
||||||
|
showAllBlocks={showAllBlocks}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
@ -1,5 +1,4 @@
|
|||||||
import { FC } from "react";
|
import { FC } from "react";
|
||||||
|
|
||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "../hooks";
|
import { useChart } from "../hooks";
|
||||||
// types
|
// types
|
||||||
|
91
web/components/gantt-chart/helpers/add-block.tsx
Normal file
91
web/components/gantt-chart/helpers/add-block.tsx
Normal file
@ -0,0 +1,91 @@
|
|||||||
|
import { useEffect, useRef, useState } from "react";
|
||||||
|
import { addDays } from "date-fns";
|
||||||
|
import { Plus } from "lucide-react";
|
||||||
|
// hooks
|
||||||
|
import { useChart } from "../hooks";
|
||||||
|
// ui
|
||||||
|
import { Tooltip } from "@plane/ui";
|
||||||
|
// helpers
|
||||||
|
import { renderFormattedDate, renderFormattedPayloadDate } from "helpers/date-time.helper";
|
||||||
|
// types
|
||||||
|
import { IBlockUpdateData, IGanttBlock } from "../types";
|
||||||
|
|
||||||
|
type Props = {
|
||||||
|
block: IGanttBlock;
|
||||||
|
blockUpdateHandler: (block: any, payload: IBlockUpdateData) => void;
|
||||||
|
};
|
||||||
|
|
||||||
|
export const ChartAddBlock: React.FC<Props> = (props) => {
|
||||||
|
const { block, blockUpdateHandler } = props;
|
||||||
|
// states
|
||||||
|
const [isButtonVisible, setIsButtonVisible] = useState(false);
|
||||||
|
const [buttonXPosition, setButtonXPosition] = useState(0);
|
||||||
|
const [buttonStartDate, setButtonStartDate] = useState<Date | null>(null);
|
||||||
|
// refs
|
||||||
|
const containerRef = useRef<HTMLDivElement>(null);
|
||||||
|
// chart hook
|
||||||
|
const { currentViewData } = useChart();
|
||||||
|
|
||||||
|
const handleButtonClick = () => {
|
||||||
|
if (!currentViewData) return;
|
||||||
|
|
||||||
|
const { startDate: chartStartDate, width } = currentViewData.data;
|
||||||
|
const columnNumber = buttonXPosition / width;
|
||||||
|
|
||||||
|
const startDate = addDays(chartStartDate, columnNumber);
|
||||||
|
const endDate = addDays(startDate, 1);
|
||||||
|
|
||||||
|
blockUpdateHandler(block.data, {
|
||||||
|
start_date: renderFormattedPayloadDate(startDate) ?? undefined,
|
||||||
|
target_date: renderFormattedPayloadDate(endDate) ?? undefined,
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
const container = containerRef.current;
|
||||||
|
|
||||||
|
if (!container) return;
|
||||||
|
|
||||||
|
const handleMouseMove = (e: MouseEvent) => {
|
||||||
|
if (!currentViewData) return;
|
||||||
|
|
||||||
|
setButtonXPosition(e.offsetX);
|
||||||
|
|
||||||
|
const { startDate: chartStartDate, width } = currentViewData.data;
|
||||||
|
const columnNumber = buttonXPosition / width;
|
||||||
|
|
||||||
|
const startDate = addDays(chartStartDate, columnNumber);
|
||||||
|
setButtonStartDate(startDate);
|
||||||
|
};
|
||||||
|
|
||||||
|
container.addEventListener("mousemove", handleMouseMove);
|
||||||
|
|
||||||
|
return () => {
|
||||||
|
container?.removeEventListener("mousemove", handleMouseMove);
|
||||||
|
};
|
||||||
|
}, [buttonXPosition, currentViewData]);
|
||||||
|
|
||||||
|
return (
|
||||||
|
<div
|
||||||
|
className="relative h-full w-full"
|
||||||
|
onMouseEnter={() => setIsButtonVisible(true)}
|
||||||
|
onMouseLeave={() => setIsButtonVisible(false)}
|
||||||
|
>
|
||||||
|
<div ref={containerRef} className="h-full w-full" />
|
||||||
|
{isButtonVisible && (
|
||||||
|
<Tooltip tooltipContent={buttonStartDate && renderFormattedDate(buttonStartDate)}>
|
||||||
|
<button
|
||||||
|
type="button"
|
||||||
|
className="absolute top-1/2 -translate-x-1/2 -translate-y-1/2 h-8 w-8 bg-custom-background-80 p-1.5 rounded border border-custom-border-300 grid place-items-center text-custom-text-200 hover:text-custom-text-100"
|
||||||
|
style={{
|
||||||
|
marginLeft: `${buttonXPosition}px`,
|
||||||
|
}}
|
||||||
|
onClick={handleButtonClick}
|
||||||
|
>
|
||||||
|
<Plus className="h-3.5 w-3.5" />
|
||||||
|
</button>
|
||||||
|
</Tooltip>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
};
|
@ -3,14 +3,11 @@ import { TIssue } from "@plane/types";
|
|||||||
import { IGanttBlock } from "components/gantt-chart";
|
import { IGanttBlock } from "components/gantt-chart";
|
||||||
|
|
||||||
export const renderIssueBlocksStructure = (blocks: TIssue[]): IGanttBlock[] =>
|
export const renderIssueBlocksStructure = (blocks: TIssue[]): IGanttBlock[] =>
|
||||||
blocks && blocks.length > 0
|
blocks &&
|
||||||
? blocks
|
blocks.map((block) => ({
|
||||||
.filter((b) => new Date(b?.start_date ?? "") <= new Date(b?.target_date ?? ""))
|
data: block,
|
||||||
.map((block) => ({
|
id: block.id,
|
||||||
data: block,
|
sort_order: block.sort_order,
|
||||||
id: block.id,
|
start_date: block.start_date ? new Date(block.start_date) : null,
|
||||||
sort_order: block.sort_order,
|
target_date: block.target_date ? new Date(block.target_date) : null,
|
||||||
start_date: new Date(block.start_date ?? ""),
|
}));
|
||||||
target_date: new Date(block.target_date ?? ""),
|
|
||||||
}))
|
|
||||||
: [];
|
|
||||||
|
@ -1,6 +1,4 @@
|
|||||||
import React, { useEffect, useRef, useState } from "react";
|
import React, { useEffect, useRef, useState } from "react";
|
||||||
|
|
||||||
// icons
|
|
||||||
import { ArrowLeft, ArrowRight } from "lucide-react";
|
import { ArrowLeft, ArrowRight } from "lucide-react";
|
||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "../hooks";
|
import { useChart } from "../hooks";
|
||||||
@ -16,23 +14,17 @@ type Props = {
|
|||||||
enableBlockMove: boolean;
|
enableBlockMove: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const ChartDraggable: React.FC<Props> = ({
|
export const ChartDraggable: React.FC<Props> = (props) => {
|
||||||
block,
|
const { block, blockToRender, handleBlock, enableBlockLeftResize, enableBlockRightResize, enableBlockMove } = props;
|
||||||
blockToRender,
|
// states
|
||||||
handleBlock,
|
|
||||||
enableBlockLeftResize,
|
|
||||||
enableBlockRightResize,
|
|
||||||
enableBlockMove,
|
|
||||||
}) => {
|
|
||||||
const [isLeftResizing, setIsLeftResizing] = useState(false);
|
const [isLeftResizing, setIsLeftResizing] = useState(false);
|
||||||
const [isRightResizing, setIsRightResizing] = useState(false);
|
const [isRightResizing, setIsRightResizing] = useState(false);
|
||||||
const [isMoving, setIsMoving] = useState(false);
|
const [isMoving, setIsMoving] = useState(false);
|
||||||
const [posFromLeft, setPosFromLeft] = useState<number | null>(null);
|
const [posFromLeft, setPosFromLeft] = useState<number | null>(null);
|
||||||
|
// refs
|
||||||
const resizableRef = useRef<HTMLDivElement>(null);
|
const resizableRef = useRef<HTMLDivElement>(null);
|
||||||
|
// chart hook
|
||||||
const { currentViewData, scrollLeft } = useChart();
|
const { currentViewData, scrollLeft } = useChart();
|
||||||
|
|
||||||
// check if cursor reaches either end while resizing/dragging
|
// check if cursor reaches either end while resizing/dragging
|
||||||
const checkScrollEnd = (e: MouseEvent): number => {
|
const checkScrollEnd = (e: MouseEvent): number => {
|
||||||
const SCROLL_THRESHOLD = 70;
|
const SCROLL_THRESHOLD = 70;
|
||||||
@ -68,7 +60,6 @@ export const ChartDraggable: React.FC<Props> = ({
|
|||||||
|
|
||||||
return delWidth;
|
return delWidth;
|
||||||
};
|
};
|
||||||
|
|
||||||
// handle block resize from the left end
|
// handle block resize from the left end
|
||||||
const handleBlockLeftResize = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
|
const handleBlockLeftResize = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
|
||||||
if (!currentViewData || !resizableRef.current || !block.position) return;
|
if (!currentViewData || !resizableRef.current || !block.position) return;
|
||||||
@ -120,7 +111,6 @@ export const ChartDraggable: React.FC<Props> = ({
|
|||||||
document.addEventListener("mousemove", handleMouseMove);
|
document.addEventListener("mousemove", handleMouseMove);
|
||||||
document.addEventListener("mouseup", handleMouseUp);
|
document.addEventListener("mouseup", handleMouseUp);
|
||||||
};
|
};
|
||||||
|
|
||||||
// handle block resize from the right end
|
// handle block resize from the right end
|
||||||
const handleBlockRightResize = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
|
const handleBlockRightResize = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
|
||||||
if (!currentViewData || !resizableRef.current || !block.position) return;
|
if (!currentViewData || !resizableRef.current || !block.position) return;
|
||||||
@ -163,7 +153,6 @@ export const ChartDraggable: React.FC<Props> = ({
|
|||||||
document.addEventListener("mousemove", handleMouseMove);
|
document.addEventListener("mousemove", handleMouseMove);
|
||||||
document.addEventListener("mouseup", handleMouseUp);
|
document.addEventListener("mouseup", handleMouseUp);
|
||||||
};
|
};
|
||||||
|
|
||||||
// handle block x-axis move
|
// handle block x-axis move
|
||||||
const handleBlockMove = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
|
const handleBlockMove = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) => {
|
||||||
if (!enableBlockMove || !currentViewData || !resizableRef.current || !block.position) return;
|
if (!enableBlockMove || !currentViewData || !resizableRef.current || !block.position) return;
|
||||||
@ -210,7 +199,6 @@ export const ChartDraggable: React.FC<Props> = ({
|
|||||||
document.addEventListener("mousemove", handleMouseMove);
|
document.addEventListener("mousemove", handleMouseMove);
|
||||||
document.addEventListener("mouseup", handleMouseUp);
|
document.addEventListener("mouseup", handleMouseUp);
|
||||||
};
|
};
|
||||||
|
|
||||||
// scroll to a hidden block
|
// scroll to a hidden block
|
||||||
const handleScrollToBlock = () => {
|
const handleScrollToBlock = () => {
|
||||||
const scrollContainer = document.querySelector("#scroll-container") as HTMLElement;
|
const scrollContainer = document.querySelector("#scroll-container") as HTMLElement;
|
||||||
@ -220,7 +208,6 @@ export const ChartDraggable: React.FC<Props> = ({
|
|||||||
// update container's scroll position to the block's position
|
// update container's scroll position to the block's position
|
||||||
scrollContainer.scrollLeft = block.position.marginLeft - 4;
|
scrollContainer.scrollLeft = block.position.marginLeft - 4;
|
||||||
};
|
};
|
||||||
|
|
||||||
// update block position from viewport's left end on scroll
|
// update block position from viewport's left end on scroll
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const block = resizableRef.current;
|
const block = resizableRef.current;
|
||||||
@ -229,7 +216,6 @@ export const ChartDraggable: React.FC<Props> = ({
|
|||||||
|
|
||||||
setPosFromLeft(block.getBoundingClientRect().left);
|
setPosFromLeft(block.getBoundingClientRect().left);
|
||||||
}, [scrollLeft]);
|
}, [scrollLeft]);
|
||||||
|
|
||||||
// check if block is hidden on either side
|
// check if block is hidden on either side
|
||||||
const isBlockHiddenOnLeft =
|
const isBlockHiddenOnLeft =
|
||||||
block.position?.marginLeft &&
|
block.position?.marginLeft &&
|
||||||
|
@ -1 +1,3 @@
|
|||||||
|
export * from "./add-block";
|
||||||
export * from "./block-structure";
|
export * from "./block-structure";
|
||||||
|
export * from "./draggable";
|
||||||
|
@ -19,36 +19,43 @@ type GanttChartRootProps = {
|
|||||||
enableBlockMove?: boolean;
|
enableBlockMove?: boolean;
|
||||||
enableReorder?: boolean;
|
enableReorder?: boolean;
|
||||||
bottomSpacing?: boolean;
|
bottomSpacing?: boolean;
|
||||||
|
showAllBlocks?: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const GanttChartRoot: FC<GanttChartRootProps> = ({
|
export const GanttChartRoot: FC<GanttChartRootProps> = (props) => {
|
||||||
border = true,
|
const {
|
||||||
title,
|
border = true,
|
||||||
blocks,
|
title,
|
||||||
loaderTitle = "blocks",
|
blocks,
|
||||||
blockUpdateHandler,
|
loaderTitle = "blocks",
|
||||||
sidebarToRender,
|
blockUpdateHandler,
|
||||||
blockToRender,
|
sidebarToRender,
|
||||||
enableBlockLeftResize = true,
|
blockToRender,
|
||||||
enableBlockRightResize = true,
|
enableBlockLeftResize = true,
|
||||||
enableBlockMove = true,
|
enableBlockRightResize = true,
|
||||||
enableReorder = true,
|
enableBlockMove = true,
|
||||||
bottomSpacing = false,
|
enableReorder = true,
|
||||||
}) => (
|
bottomSpacing = false,
|
||||||
<ChartContextProvider>
|
showAllBlocks = false,
|
||||||
<ChartViewRoot
|
} = props;
|
||||||
border={border}
|
|
||||||
title={title}
|
return (
|
||||||
blocks={blocks}
|
<ChartContextProvider>
|
||||||
loaderTitle={loaderTitle}
|
<ChartViewRoot
|
||||||
blockUpdateHandler={blockUpdateHandler}
|
border={border}
|
||||||
sidebarToRender={sidebarToRender}
|
title={title}
|
||||||
blockToRender={blockToRender}
|
blocks={blocks}
|
||||||
enableBlockLeftResize={enableBlockLeftResize}
|
loaderTitle={loaderTitle}
|
||||||
enableBlockRightResize={enableBlockRightResize}
|
blockUpdateHandler={blockUpdateHandler}
|
||||||
enableBlockMove={enableBlockMove}
|
sidebarToRender={sidebarToRender}
|
||||||
enableReorder={enableReorder}
|
blockToRender={blockToRender}
|
||||||
bottomSpacing={bottomSpacing}
|
enableBlockLeftResize={enableBlockLeftResize}
|
||||||
/>
|
enableBlockRightResize={enableBlockRightResize}
|
||||||
</ChartContextProvider>
|
enableBlockMove={enableBlockMove}
|
||||||
);
|
enableReorder={enableReorder}
|
||||||
|
bottomSpacing={bottomSpacing}
|
||||||
|
showAllBlocks={showAllBlocks}
|
||||||
|
/>
|
||||||
|
</ChartContextProvider>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import { DragDropContext, Draggable, DropResult } from "@hello-pangea/dnd";
|
import { DragDropContext, Draggable, DropResult, Droppable } from "@hello-pangea/dnd";
|
||||||
import StrictModeDroppable from "components/dnd/StrictModeDroppable";
|
|
||||||
import { MoreVertical } from "lucide-react";
|
import { MoreVertical } from "lucide-react";
|
||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "components/gantt-chart/hooks";
|
import { useChart } from "components/gantt-chart/hooks";
|
||||||
@ -83,7 +82,7 @@ export const CycleGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<DragDropContext onDragEnd={handleOrderChange}>
|
<DragDropContext onDragEnd={handleOrderChange}>
|
||||||
<StrictModeDroppable droppableId="gantt-sidebar">
|
<Droppable droppableId="gantt-sidebar">
|
||||||
{(droppableProvided) => (
|
{(droppableProvided) => (
|
||||||
<div
|
<div
|
||||||
id={`gantt-sidebar-${cycleId}`}
|
id={`gantt-sidebar-${cycleId}`}
|
||||||
@ -153,7 +152,7 @@ export const CycleGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
</>
|
</>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</StrictModeDroppable>
|
</Droppable>
|
||||||
</DragDropContext>
|
</DragDropContext>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import { DragDropContext, Draggable, DropResult } from "@hello-pangea/dnd";
|
import { DragDropContext, Draggable, Droppable, DropResult } from "@hello-pangea/dnd";
|
||||||
import StrictModeDroppable from "components/dnd/StrictModeDroppable";
|
|
||||||
import { MoreVertical } from "lucide-react";
|
import { MoreVertical } from "lucide-react";
|
||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "components/gantt-chart/hooks";
|
import { useChart } from "components/gantt-chart/hooks";
|
||||||
@ -83,7 +82,7 @@ export const ModuleGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<DragDropContext onDragEnd={handleOrderChange}>
|
<DragDropContext onDragEnd={handleOrderChange}>
|
||||||
<StrictModeDroppable droppableId="gantt-sidebar">
|
<Droppable droppableId="gantt-sidebar">
|
||||||
{(droppableProvided) => (
|
{(droppableProvided) => (
|
||||||
<div
|
<div
|
||||||
id={`gantt-sidebar-${cycleId}`}
|
id={`gantt-sidebar-${cycleId}`}
|
||||||
@ -153,7 +152,7 @@ export const ModuleGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
</>
|
</>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</StrictModeDroppable>
|
</Droppable>
|
||||||
</DragDropContext>
|
</DragDropContext>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import { DragDropContext, Draggable, DropResult } from "@hello-pangea/dnd";
|
import { DragDropContext, Draggable, Droppable, DropResult } from "@hello-pangea/dnd";
|
||||||
import StrictModeDroppable from "components/dnd/StrictModeDroppable";
|
|
||||||
import { MoreVertical } from "lucide-react";
|
import { MoreVertical } from "lucide-react";
|
||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "components/gantt-chart/hooks";
|
import { useChart } from "components/gantt-chart/hooks";
|
||||||
@ -84,7 +83,7 @@ export const ProjectViewGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<DragDropContext onDragEnd={handleOrderChange}>
|
<DragDropContext onDragEnd={handleOrderChange}>
|
||||||
<StrictModeDroppable droppableId="gantt-sidebar">
|
<Droppable droppableId="gantt-sidebar">
|
||||||
{(droppableProvided) => (
|
{(droppableProvided) => (
|
||||||
<div
|
<div
|
||||||
id={`gantt-sidebar-${cycleId}`}
|
id={`gantt-sidebar-${cycleId}`}
|
||||||
@ -154,7 +153,7 @@ export const ProjectViewGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
</>
|
</>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</StrictModeDroppable>
|
</Droppable>
|
||||||
</DragDropContext>
|
</DragDropContext>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@ -1,6 +1,5 @@
|
|||||||
import { useRouter } from "next/router";
|
import { useRouter } from "next/router";
|
||||||
import { DragDropContext, Draggable, DropResult } from "@hello-pangea/dnd";
|
import { DragDropContext, Draggable, Droppable, DropResult } from "@hello-pangea/dnd";
|
||||||
import StrictModeDroppable from "components/dnd/StrictModeDroppable";
|
|
||||||
import { MoreVertical } from "lucide-react";
|
import { MoreVertical } from "lucide-react";
|
||||||
// hooks
|
// hooks
|
||||||
import { useChart } from "components/gantt-chart/hooks";
|
import { useChart } from "components/gantt-chart/hooks";
|
||||||
@ -27,10 +26,10 @@ type Props = {
|
|||||||
) => Promise<TIssue | undefined>;
|
) => Promise<TIssue | undefined>;
|
||||||
viewId?: string;
|
viewId?: string;
|
||||||
disableIssueCreation?: boolean;
|
disableIssueCreation?: boolean;
|
||||||
|
showAllBlocks?: boolean;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
||||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
||||||
const {
|
const {
|
||||||
blockUpdateHandler,
|
blockUpdateHandler,
|
||||||
blocks,
|
blocks,
|
||||||
@ -39,6 +38,7 @@ export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
quickAddCallback,
|
quickAddCallback,
|
||||||
viewId,
|
viewId,
|
||||||
disableIssueCreation,
|
disableIssueCreation,
|
||||||
|
showAllBlocks = false,
|
||||||
} = props;
|
} = props;
|
||||||
|
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
@ -100,7 +100,7 @@ export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<DragDropContext onDragEnd={handleOrderChange}>
|
<DragDropContext onDragEnd={handleOrderChange}>
|
||||||
<StrictModeDroppable droppableId="gantt-sidebar">
|
<Droppable droppableId="gantt-sidebar">
|
||||||
{(droppableProvided) => (
|
{(droppableProvided) => (
|
||||||
<div
|
<div
|
||||||
id={`gantt-sidebar-${cycleId}`}
|
id={`gantt-sidebar-${cycleId}`}
|
||||||
@ -111,7 +111,15 @@ export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
<>
|
<>
|
||||||
{blocks ? (
|
{blocks ? (
|
||||||
blocks.map((block, index) => {
|
blocks.map((block, index) => {
|
||||||
const duration = findTotalDaysInRange(block.start_date ?? "", block.target_date ?? "");
|
const isBlockVisibleOnSidebar = block.start_date && block.target_date;
|
||||||
|
|
||||||
|
// hide the block if it doesn't have start and target dates and showAllBlocks is false
|
||||||
|
if (!showAllBlocks && !isBlockVisibleOnSidebar) return;
|
||||||
|
|
||||||
|
const duration =
|
||||||
|
!block.start_date || !block.target_date
|
||||||
|
? null
|
||||||
|
: findTotalDaysInRange(block.start_date, block.target_date);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Draggable
|
<Draggable
|
||||||
@ -149,7 +157,11 @@ export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
<IssueGanttSidebarBlock data={block.data} />
|
<IssueGanttSidebarBlock data={block.data} />
|
||||||
</div>
|
</div>
|
||||||
<div className="flex-shrink-0 text-sm text-custom-text-200">
|
<div className="flex-shrink-0 text-sm text-custom-text-200">
|
||||||
{duration} day{duration > 1 ? "s" : ""}
|
{duration && (
|
||||||
|
<span>
|
||||||
|
{duration} day{duration > 1 ? "s" : ""}
|
||||||
|
</span>
|
||||||
|
)}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -173,7 +185,7 @@ export const IssueGanttSidebar: React.FC<Props> = (props) => {
|
|||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
</StrictModeDroppable>
|
</Droppable>
|
||||||
</DragDropContext>
|
</DragDropContext>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
@ -13,8 +13,8 @@ export interface IGanttBlock {
|
|||||||
width: number;
|
width: number;
|
||||||
};
|
};
|
||||||
sort_order: number;
|
sort_order: number;
|
||||||
start_date: Date;
|
start_date: Date | null;
|
||||||
target_date: Date;
|
target_date: Date | null;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface IBlockUpdateData {
|
export interface IBlockUpdateData {
|
||||||
|
@ -167,6 +167,8 @@ export const getMonthChartItemPositionWidthInMonth = (chartData: ChartDataType,
|
|||||||
const { startDate } = chartData.data;
|
const { startDate } = chartData.data;
|
||||||
const { start_date: itemStartDate, target_date: itemTargetDate } = itemData;
|
const { start_date: itemStartDate, target_date: itemTargetDate } = itemData;
|
||||||
|
|
||||||
|
if (!itemStartDate || !itemTargetDate) return null;
|
||||||
|
|
||||||
startDate.setHours(0, 0, 0, 0);
|
startDate.setHours(0, 0, 0, 0);
|
||||||
itemStartDate.setHours(0, 0, 0, 0);
|
itemStartDate.setHours(0, 0, 0, 0);
|
||||||
itemTargetDate.setHours(0, 0, 0, 0);
|
itemTargetDate.setHours(0, 0, 0, 0);
|
||||||
|
@ -13,11 +13,12 @@ import {
|
|||||||
} from "components/gantt-chart";
|
} from "components/gantt-chart";
|
||||||
// types
|
// types
|
||||||
import { TIssue, TUnGroupedIssues } from "@plane/types";
|
import { TIssue, TUnGroupedIssues } from "@plane/types";
|
||||||
import { EUserProjectRoles } from "constants/project";
|
|
||||||
import { ICycleIssues, ICycleIssuesFilter } from "store/issue/cycle";
|
import { ICycleIssues, ICycleIssuesFilter } from "store/issue/cycle";
|
||||||
import { IModuleIssues, IModuleIssuesFilter } from "store/issue/module";
|
import { IModuleIssues, IModuleIssuesFilter } from "store/issue/module";
|
||||||
import { IProjectIssues, IProjectIssuesFilter } from "store/issue/project";
|
import { IProjectIssues, IProjectIssuesFilter } from "store/issue/project";
|
||||||
import { IProjectViewIssues, IProjectViewIssuesFilter } from "store/issue/project-views";
|
import { IProjectViewIssues, IProjectViewIssuesFilter } from "store/issue/project-views";
|
||||||
|
// constants
|
||||||
|
import { EUserProjectRoles } from "constants/project";
|
||||||
import { EIssueActions } from "../types";
|
import { EIssueActions } from "../types";
|
||||||
|
|
||||||
interface IBaseGanttRoot {
|
interface IBaseGanttRoot {
|
||||||
@ -76,12 +77,14 @@ export const BaseGanttRoot: React.FC<IBaseGanttRoot> = observer((props: IBaseGan
|
|||||||
viewId={viewId}
|
viewId={viewId}
|
||||||
enableQuickIssueCreate
|
enableQuickIssueCreate
|
||||||
disableIssueCreation={!enableIssueCreation || !isAllowed}
|
disableIssueCreation={!enableIssueCreation || !isAllowed}
|
||||||
|
showAllBlocks
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
enableBlockLeftResize={isAllowed}
|
enableBlockLeftResize={isAllowed}
|
||||||
enableBlockRightResize={isAllowed}
|
enableBlockRightResize={isAllowed}
|
||||||
enableBlockMove={isAllowed}
|
enableBlockMove={isAllowed}
|
||||||
enableReorder={appliedDisplayFilters?.order_by === "sort_order" && isAllowed}
|
enableReorder={appliedDisplayFilters?.order_by === "sort_order" && isAllowed}
|
||||||
|
showAllBlocks
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</>
|
</>
|
||||||
|
@ -13,7 +13,6 @@ const paramsToKey = (params: any) => {
|
|||||||
start_date,
|
start_date,
|
||||||
target_date,
|
target_date,
|
||||||
sub_issue,
|
sub_issue,
|
||||||
start_target_date,
|
|
||||||
project,
|
project,
|
||||||
layout,
|
layout,
|
||||||
subscriber,
|
subscriber,
|
||||||
@ -28,7 +27,6 @@ const paramsToKey = (params: any) => {
|
|||||||
let createdByKey = created_by ? created_by.split(",") : [];
|
let createdByKey = created_by ? created_by.split(",") : [];
|
||||||
let labelsKey = labels ? labels.split(",") : [];
|
let labelsKey = labels ? labels.split(",") : [];
|
||||||
let subscriberKey = subscriber ? subscriber.split(",") : [];
|
let subscriberKey = subscriber ? subscriber.split(",") : [];
|
||||||
const startTargetDate = start_target_date ? `${start_target_date}`.toUpperCase() : "FALSE";
|
|
||||||
const startDateKey = start_date ?? "";
|
const startDateKey = start_date ?? "";
|
||||||
const targetDateKey = target_date ?? "";
|
const targetDateKey = target_date ?? "";
|
||||||
const type = params.type ? params.type.toUpperCase() : "NULL";
|
const type = params.type ? params.type.toUpperCase() : "NULL";
|
||||||
@ -47,7 +45,7 @@ const paramsToKey = (params: any) => {
|
|||||||
labelsKey = labelsKey.sort().join("_");
|
labelsKey = labelsKey.sort().join("_");
|
||||||
subscriberKey = subscriberKey.sort().join("_");
|
subscriberKey = subscriberKey.sort().join("_");
|
||||||
|
|
||||||
return `${layoutKey}_${projectKey}_${stateGroupKey}_${stateKey}_${priorityKey}_${assigneesKey}_${mentionsKey}_${createdByKey}_${type}_${groupBy}_${orderBy}_${labelsKey}_${startDateKey}_${targetDateKey}_${sub_issue}_${startTargetDate}_${subscriberKey}`;
|
return `${layoutKey}_${projectKey}_${stateGroupKey}_${stateKey}_${priorityKey}_${assigneesKey}_${mentionsKey}_${createdByKey}_${type}_${groupBy}_${orderBy}_${labelsKey}_${startDateKey}_${targetDateKey}_${sub_issue}_${subscriberKey}`;
|
||||||
};
|
};
|
||||||
|
|
||||||
const myIssuesParamsToKey = (params: any) => {
|
const myIssuesParamsToKey = (params: any) => {
|
||||||
|
@ -105,9 +105,6 @@ export const handleIssueQueryParamsByLayout = (
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
// add start_target_date query param for the gantt_chart layout
|
|
||||||
if (layout === "gantt_chart") queryParams.push("start_target_date");
|
|
||||||
|
|
||||||
return queryParams;
|
return queryParams;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -89,7 +89,6 @@ export class ArchivedIssuesFilter extends IssueFilterHelperStore implements IArc
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -90,7 +90,6 @@ export class CycleIssuesFilter extends IssueFilterHelperStore implements ICycleI
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -89,7 +89,6 @@ export class DraftIssuesFilter extends IssueFilterHelperStore implements IDraftI
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -81,7 +81,6 @@ export class IssueFilterHelperStore implements IIssueFilterHelperStore {
|
|||||||
// display filters
|
// display filters
|
||||||
type: displayFilters?.type || undefined,
|
type: displayFilters?.type || undefined,
|
||||||
sub_issue: displayFilters?.sub_issue ?? true,
|
sub_issue: displayFilters?.sub_issue ?? true,
|
||||||
start_target_date: displayFilters?.start_target_date ?? true,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
const issueFiltersParams: Partial<Record<TIssueParams, boolean | string>> = {};
|
const issueFiltersParams: Partial<Record<TIssueParams, boolean | string>> = {};
|
||||||
@ -170,7 +169,6 @@ export class IssueFilterHelperStore implements IIssueFilterHelperStore {
|
|||||||
type: filters?.type || null,
|
type: filters?.type || null,
|
||||||
sub_issue: filters?.sub_issue || false,
|
sub_issue: filters?.sub_issue || false,
|
||||||
show_empty_groups: filters?.show_empty_groups || false,
|
show_empty_groups: filters?.show_empty_groups || false,
|
||||||
start_target_date: filters?.start_target_date || false,
|
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -90,7 +90,6 @@ export class ModuleIssuesFilter extends IssueFilterHelperStore implements IModul
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -93,7 +93,6 @@ export class ProfileIssuesFilter extends IssueFilterHelperStore implements IProf
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -90,7 +90,6 @@ export class ProjectViewIssuesFilter extends IssueFilterHelperStore implements I
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -89,7 +89,6 @@ export class ProjectIssuesFilter extends IssueFilterHelperStore implements IProj
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
@ -99,7 +99,6 @@ export class WorkspaceIssuesFilter extends IssueFilterHelperStore implements IWo
|
|||||||
filteredParams
|
filteredParams
|
||||||
);
|
);
|
||||||
|
|
||||||
if (userFilters?.displayFilters?.layout === "gantt_chart") filteredRouteParams.start_target_date = true;
|
|
||||||
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
if (userFilters?.displayFilters?.layout === "spreadsheet") filteredRouteParams.sub_issue = false;
|
||||||
|
|
||||||
return filteredRouteParams;
|
return filteredRouteParams;
|
||||||
|
Loading…
Reference in New Issue
Block a user