diff --git a/index.html b/index.html index f2770de..b2fc2fd 100644 --- a/index.html +++ b/index.html @@ -9,7 +9,7 @@ -
+
diff --git a/src/components/accordion-item.tsx b/src/components/accordion-item.tsx new file mode 100644 index 0000000..91512f8 --- /dev/null +++ b/src/components/accordion-item.tsx @@ -0,0 +1,15 @@ +import { } from 'react' + +export function AccordionItem({ title, children, isOpen, onClick }: { title: string; children: JSX.Element; isOpen: boolean, onClick: () => void; }) { + return ( + <> + + {isOpen &&
{children}
} + + ); +} diff --git a/src/components/consts.ts b/src/components/consts.ts new file mode 100644 index 0000000..621d23b --- /dev/null +++ b/src/components/consts.ts @@ -0,0 +1,11 @@ +export const taskTypes = { + task: 'Užduotis', + bug: "Bug'as", +}; + +export const taskStatuses = { + paused: 'Laukia', + 'in progress': 'Daroma', + testing: 'Testuojama', + released: 'Padaryta', +}; \ No newline at end of file diff --git a/src/components/enum-select.tsx b/src/components/enum-select.tsx new file mode 100644 index 0000000..0820ec8 --- /dev/null +++ b/src/components/enum-select.tsx @@ -0,0 +1,10 @@ +import { } from 'react' + +export function EnumSelect({ name, entries }: { name: string; entries: Record }): JSX.Element { + return ( + + ); +} + diff --git a/src/components/task-form.tsx b/src/components/task-form.tsx new file mode 100644 index 0000000..9c33b68 --- /dev/null +++ b/src/components/task-form.tsx @@ -0,0 +1,63 @@ +import { } from 'react' +import { taskTypes, taskStatuses } from './consts'; +import { EnumSelect } from './enum-select'; + +export function TaskForm({ tasks, setTasks, setExpanded }: { tasks: TodoTasks, setTasks: (t: TodoTasks) => void, setExpanded: (p: number) => void }): JSX.Element { + return ( +
{ + event.preventDefault(); + + const data = Object.fromEntries(new FormData(event.currentTarget)); + const newTask = { + id: tasks.reduce((max, row) => row.id > max ? row.id : max, 1) + 1, + type: data.type as TaskType, + title: data.title as string, + status: data.status as TaskStatus, + }; + + + if (data.insert) { + setTasks([newTask, ...tasks]); + } else { + setTasks([...tasks, newTask]); + } + + setExpanded(0); + }}> +
+ +
+ +
+
+
+ +
+ +
+
+
+ +
+ +
+
+
+ + +
+
+ + +
+
+ ); +} + diff --git a/src/components/task-list.tsx b/src/components/task-list.tsx new file mode 100644 index 0000000..4300f8f --- /dev/null +++ b/src/components/task-list.tsx @@ -0,0 +1,24 @@ +import { } from 'react' +import { taskTypes, taskStatuses } from './consts'; + +export function TaskList({ tasks }: { tasks: TodoTasks }): JSX.Element { + return ( + + + + + + + + + + {tasks.map(task => + + + + )} + +
TipasPavadinimasStatusas
{taskTypes[task.type]}{task.title}{taskStatuses[task.status]}
+ ); +} + diff --git a/src/index.css b/src/index.css index 7be8d7f..0435fc5 100644 --- a/src/index.css +++ b/src/index.css @@ -2,18 +2,42 @@ @tailwind components; @tailwind utilities; -@layer base { - h1 { - @apply text-2xl my-5; - } - +@layer utilities { p, li { @apply my-4; } a.nav-button { - @apply bg-neutral-100 dark:bg-neutral-900 cursor-pointer px-5 py-2 rounded-lg border border-transparent hover:border-indigo-500 transition-colors duration-1000; + @apply bg-neutral-100 dark:bg-neutral-900 cursor-pointer px-5 py-2 rounded-lg border border-gray-300 hover:border-indigo-500 transition-colors duration-700; + } + + th { + @apply border-b dark:border-slate-600 pl-8 pt-0 pb-3 text-slate-400 dark:text-slate-200 text-left; + } + + td { + @apply border-b border-slate-100 dark:border-slate-700 p-4 pl-8 text-slate-500 dark:text-slate-400; + } + + select, input { + @apply w-full rounded-lg border-0 px-3 py-2 ring-1 ring-inset ring-gray-300 focus:ring-2 focus:ring-indigo-500 focus:outline-none hover:ring-indigo-500 transition-shadow duration-700; + } + + .accordion-title { + @apply text-2xl flex items-center justify-between w-full p-5 font-medium border border-b-0 border-slate-200 dark:focus:ring-slate-800 dark:border-slate-700 hover:bg-slate-100 dark:hover:bg-slate-800 gap-3; + } + + .accordion-title:first-child { + @apply rounded-t-xl; + } + + .accordion-title:last-child, .accordion-body:last-child { + @apply border-b rounded-b-xl; + } + + .accordion-body { + @apply p-5 border border-b-0 border-slate-200 dark:border-slate-700; } } diff --git a/src/routes/list.tsx b/src/routes/list.tsx index 839bcbb..e535b95 100644 --- a/src/routes/list.tsx +++ b/src/routes/list.tsx @@ -1,16 +1,42 @@ import { useState } from 'react' +import { AccordionItem } from '../components/accordion-item'; +import { TaskList } from '../components/task-list'; +import { TaskForm } from '../components/task-form'; function App() { - const [count, setCount] = useState(0) + const [tasks, setTasks] = useState([ + { + id: 1, + type: 'task', + title: 'Lipk iš lovos', + status: 'in progress', + }, + { + id: 2, + type: 'task', + title: 'Susirask kavos', + status: 'paused', + }, + { + id: 3, + type: 'bug', + title: 'Sudaryk TODO sąrašą', + status: 'testing', + }, + ]); + + const [expanded, setExpanded] = useState(0); + + const handleAccordion = (panel: number) => setExpanded(expanded == panel ? -1 : panel); return ( <> -

Vite + React

-
- -
+ handleAccordion(0)}> + + + handleAccordion(1)}> + + ) } diff --git a/src/routes/root.tsx b/src/routes/root.tsx index ccee0e6..b62a255 100644 --- a/src/routes/root.tsx +++ b/src/routes/root.tsx @@ -7,10 +7,8 @@ export default function Root() { Sąrašas Duomenys -
-
+
-
); diff --git a/src/vite-env.d.ts b/src/vite-env.d.ts index 11f02fe..6723c91 100644 --- a/src/vite-env.d.ts +++ b/src/vite-env.d.ts @@ -1 +1,13 @@ /// + +type TaskType = 'task' | 'bug'; +type TaskStatus = 'paused' | 'in progress' | 'testing' | 'released'; +class TodoTask { + id: number; + type: TaskType; + title: string; + status: TaskStatus; +} + +type TodoTasks = TodoTask[]; +