From 788996578c21237b64485b2ea6e98e25a840a9b3 Mon Sep 17 00:00:00 2001 From: qkdflrgs Date: Fri, 11 Aug 2023 12:05:16 +0900 Subject: [PATCH] =?UTF-8?q?refactor/#158:=20=EB=93=9C=EB=A1=AD=EB=8B=A4?= =?UTF-8?q?=EC=9A=B4=20=ED=8C=A8=EB=84=90=20=EC=BB=B4=ED=8F=AC=EB=84=8C?= =?UTF-8?q?=ED=8A=B8=20=EB=A6=AC=ED=8C=A9=ED=86=A0=EB=A7=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../DropdownPanel/DropdownPanel.tsx | 199 ++++++++++++++++-- 1 file changed, 184 insertions(+), 15 deletions(-) diff --git a/FE/src/components/DropdownPanel/DropdownPanel.tsx b/FE/src/components/DropdownPanel/DropdownPanel.tsx index 8ab323740..ca3a4c22b 100644 --- a/FE/src/components/DropdownPanel/DropdownPanel.tsx +++ b/FE/src/components/DropdownPanel/DropdownPanel.tsx @@ -1,43 +1,212 @@ import { styled } from "styled-components"; -import { AssigneesProps } from "../../type"; +import { useEffect, useRef, useState } from "react"; import DropdownItem from "./DropdownItem"; +import { AssigneesList, DropdownMilestone, Label } from "../../type"; +import { useNavigate } from "react-router-dom"; type Props = { - title: string; - assigneesList: AssigneesProps; + type?: "filter" | "assignees" | "labels" | "milestones" | "authors"; + top: string; + left: string; closeDropdown(): void; }; +type AssigneesData = { + assignees: AssigneesList[] | null; +}; + +type LabelsData = { + labels: Label[] | null; +}; + +type MilestonesData = { + milestones: DropdownMilestone[] | null; +}; + +type AuthorsData = { + authors: AssigneesList[] | null; +}; + export default function DropdownPanel({ - title, - assigneesList, + type = "filter", + top, + left, closeDropdown, }: Props) { + const navigate = useNavigate(); + const dropdownRef = useRef(null); + const [assigneesData, setAssigneesData] = useState( + null, + ); + const [labelsData, setLabelsData] = useState(null); + const [milestonesData, setMilestonesData] = useState( + null, + ); + const [authorsData, setAuthorsData] = useState(null); + + const showOpenIssue = () => { + closeDropdown(); + navigate("/issues/isOpen=true"); + }; + + const showCloseIssue = () => { + closeDropdown(); + navigate("/issues/isOpen=false"); + }; + + const showAuthoredByMe = () => { + closeDropdown(); + navigate("/issues/authorId=1"); + }; + + const showAssignedIssue = () => { + closeDropdown(); + navigate("/issues/assigneeId=1"); + }; + + const showCommentedIssue = () => { + closeDropdown(); + navigate("/issues/isCommentedByMe=true"); + }; + + useEffect(() => { + if (type === "filter") { + return; + } + const URL = `http://3.34.141.196/api/issues/${type}`; + const fetchData = async () => { + try { + const response = await fetch(URL); + if (!response.ok) { + throw new Error("데이터를 가져오는 데 실패했습니다."); + } + const jsonData = await response.json(); + type === "assignees" + ? setAssigneesData(jsonData) + : type === "labels" + ? setLabelsData(jsonData) + : type === "milestones" + ? setMilestonesData(jsonData) + : setAuthorsData(jsonData); + } catch (error) { + console.log("error"); + } + }; + + fetchData(); + }, []); + + useEffect(() => { + const handleOutsideClick = (e: MouseEvent) => { + if ( + dropdownRef.current && + !dropdownRef.current.contains(e.target as Node) + ) { + closeDropdown(); + } + }; + + document.addEventListener("mousedown", handleOutsideClick); + + return () => { + document.removeEventListener("mousedown", handleOutsideClick); + }; + }, [closeDropdown]); + return ( - +
- {title} + + {type === "filter" + ? "이슈 필터" + : type === "assignees" + ? "담당자 필터" + : type === "labels" + ? "레이블 필터" + : type === "milestones" + ? "마일스톤 필터" + : "작성자 필터"} +
- {assigneesList && - assigneesList.assignees.map((assignee) => ( + {type === "filter" && ( +
+ + + + + +
+ )} + {type === "assignees" && + assigneesData && + assigneesData.assignees!.map((assignee) => ( { + closeDropdown(); + navigate(`/issues/assigneeId=${assignee.id}`); + }} + /> + ))} + {type === "labels" && + labelsData && + labelsData.labels!.map((label) => ( + { + closeDropdown(); + navigate(`/issues/labelIds=${label.id}`); + }} + /> + ))} + {type === "milestones" && + milestonesData && + milestonesData.milestones!.map((milestone) => ( + { + closeDropdown(); + navigate(`/issues/milestoneId=${milestone.id}`); + }} + /> + ))} + {type === "authors" && + authorsData && + authorsData.authors!.map((author) => ( + { + closeDropdown(); + navigate(`/issues/authorId=${author.id}`); + }} /> ))}
); } -const Container = styled.div` +const Container = styled.div<{ $top: string; $left: string }>` position: absolute; - z-index: 100; - top: 40px; - right: 0px; + z-index: 1000; + top: ${({ $top }) => $top}; + left: ${({ $left }) => $left}; width: 240px; + background-color: ${({ theme }) => theme.colorSystem.neutral.surface.strong}; border: ${({ theme }) => `${theme.border.default} ${theme.colorSystem.neutral.border.default}`}; border-radius: ${({ theme }) => theme.radius.large};