diff --git a/components/Projects/Form/Select.tsx b/components/Projects/Form/Select.tsx index cf9e9d56..efb55aeb 100644 --- a/components/Projects/Form/Select.tsx +++ b/components/Projects/Form/Select.tsx @@ -1,5 +1,6 @@ import { useState } from 'react'; import { cn } from '@/utils/cn'; +import KeyboardArrowDownIcon from '@mui/icons-material/KeyboardArrowDown'; /** * @typedef {Object} Option @@ -20,73 +21,79 @@ interface SelectProps { } const Select = ({ options, className, isDisabled = false }: SelectProps) => { + const [isOpen, setIsOpen] = useState(false); + const [selectedLabel, setSelectedLabel] = useState("全部計畫"); + const handleSelect = (label: string) => { + setSelectedLabel(label); + setIsOpen(false); + }; + if (!options.length) { console.error('no option'); return false; } - const [isOpen, setIsOpen] = useState(false); - const [selectedValue, setSelectedValue] = useState("全部計畫"); - const handleSelect = (value: string, label: string) => { - setSelectedValue(label); - setIsOpen(false); - console.log("Selected:", value); - }; return ( -
+
- diff --git a/components/Projects/GoBackButton.tsx b/components/Projects/GoBackButton.tsx index b9e0ee25..2e2101ad 100644 --- a/components/Projects/GoBackButton.tsx +++ b/components/Projects/GoBackButton.tsx @@ -1,5 +1,5 @@ -import KeyboardArrowLeftIcon from '@mui/icons-material/KeyboardArrowLeft'; import { cn } from '@/utils/cn'; +import React from 'react'; /** * Button component for rendering customizable buttons. @@ -15,6 +15,8 @@ import { cn } from '@/utils/cn'; * - The text displayed on the button. * @param {string} [className] * - Optional custom classes to apply to the button (uses Tailwind CSS). + * @param {React.ReactNode} [icon] + * - Optional custom icon to apply on the button. Typically, a MUI Icon component. * @param {() => void} onClick * - Function to call when the button is clicked. * @returns {JSX.Element} The button element. @@ -22,6 +24,7 @@ import { cn } from '@/utils/cn'; interface ButtonProps { id: string, + icon?: React.ReactNode, buttonText: string; className?: string; onClick: () => void; @@ -32,6 +35,7 @@ const GoBackButton = ({ className = "", id = "", onClick = () => { }, + icon = null, }: ButtonProps ) => { return ( @@ -40,12 +44,12 @@ const GoBackButton = ({ name={id} type="button" onClick={onClick} - className={cn(`flex flex-row items-center group`, className)} + className={cn( + "flex flex-row items-center group", + className + )} > - + {icon && icon} { - if (id) { - setProjectId(projectId); - } else { - setProjectId(null); - } - }, [id]); + const projectId = searchParams.get('id'); return (
diff --git a/pages/manage/projects/index.jsx b/pages/manage/projects/index.jsx index 6b49b93e..276c1b59 100644 --- a/pages/manage/projects/index.jsx +++ b/pages/manage/projects/index.jsx @@ -1,27 +1,28 @@ -import { useState, useEffect } from 'react'; import { useRouter } from 'next/router'; import { useSelector } from 'react-redux'; +import KeyboardArrowLeftIcon from '@mui/icons-material/KeyboardArrowLeft'; import Select from '@/components/Projects/Form/Select'; -import AccessDenied from '@/components/Projects/AccessDenied'; +import AccessDenied from '@/shared/components/AccessDenied'; import GoBackButton from '@/components/Projects/GoBackButton'; import { ProtectedComponent } from '@/contexts/Auth'; import emptyCoverImg from '@/public/assets/empty-cover.png'; import CircleIcon from '@mui/icons-material/Circle'; -import MoreVertIcon from '@mui/icons-material/MoreVert'; import More from '@/components/Projects/More'; +import Button from '@/shared/components/Button'; +import { cn } from '@/utils/cn'; const Projects = () => { const maxProjects = 3; const router = useRouter(); - const [isEditPermitted, setIsEditPermitted] = useState(false); - const [isAddedPermitted, setIsAddedPermitted] = useState(true); const userState = useSelector((state) => state.user); + const projects = Array.isArray(userState.marathons) ? userState.marathons : []; + const isEditPermitted = Boolean(projects.length); + const isAddedDenied = projects.length >= maxProjects; const options = [ { value: "all", label: "全部計畫" }, { value: "learning-marathon", label: "學習馬拉松" }, ]; - const [projects, setProjects] = useState([]); const getProjectType = (eventId) => { switch (eventId) { case "2025S1": @@ -31,21 +32,6 @@ const Projects = () => { } }; - useEffect(() => { - if (userState._id) { - if (userState.marathons.length) { - setProjects(userState.marathons); - setIsEditPermitted(true); - } - } - }, [userState]); - - useEffect(() => { - if (projects.length > (maxProjects - 1)) { - setIsAddedPermitted(false); - } - }, [projects]); - return (
@@ -59,11 +45,22 @@ const Projects = () => { id: 'island' } })} + icon={ + ( + + )} buttonText="返回 我的小島" />

學習計畫

{ options={options} className="max-w-[200px]" /> - +
{ - !isAddedPermitted && ( + isAddedDenied && (

島上空間有限,計畫滿三個就不能再增加了{`><`}

@@ -135,12 +132,7 @@ const Projects = () => { {project.isPublic ? '公開' : '不公開'}

- {/*
*/} - - {/*
*/} +
diff --git a/components/Projects/AccessDenied.tsx b/shared/components/AccessDenied.tsx similarity index 70% rename from components/Projects/AccessDenied.tsx rename to shared/components/AccessDenied.tsx index f7a3d9f8..302b4687 100644 --- a/components/Projects/AccessDenied.tsx +++ b/shared/components/AccessDenied.tsx @@ -1,6 +1,6 @@ import { useRouter } from 'next/router'; import AccessDeniedImg from '@/public/assets/projects/access-denied.png'; -import Button from "./Form/Button"; +import Button from "@/shared/components/Button"; const AccessDenied = () => { const router = useRouter(); @@ -12,11 +12,11 @@ const AccessDenied = () => { rounded-2xl" >

這裡目前只開放給 @@ -33,19 +33,19 @@ const AccessDenied = () => {

); diff --git a/shared/components/Button.tsx b/shared/components/Button.tsx index 2022c9da..592a0479 100644 --- a/shared/components/Button.tsx +++ b/shared/components/Button.tsx @@ -54,7 +54,7 @@ function Button({ variant === ButtonVariantEnum.Outline && [ 'rounded-full border border-solid transition-colors', color === ButtonColorEnum.Primary && - 'border-primary-base text-basic-400 hover:bg-primary hover:text-basic-white', + 'border-primary-base text-primary-base hover:bg-primary-base hover:text-basic-white', color === ButtonColorEnum.White && 'border-basic-white text-basic-white hover:bg-basic-white hover:text-primary-base', ],