setup: route group

This commit is contained in:
Mahyar Khanbolooki
2025-07-31 19:13:24 +03:30
parent 118daf7cc0
commit 52b5b880d0
25 changed files with 169 additions and 111 deletions
@@ -22,24 +22,24 @@ const CartIndex = ({ }: Props) => {
return (
<div className='absolute top-0 left-0 bg-container bottom-0 flex flex-col px-4 pt-10 right-0 z-[100] h-full'>
<h1 className='text-lg flex justify-between items-center pb-10'>
<div className='bg-inherit flex flex-col h-full'>
<div className='grid grid-cols-3 items-center py-4 '>
<Trash
className='cursor-pointer'
className='cursor-pointer place-self-start'
size='24'
color='currentColor'
onClick={() => { router.back() }}
/>
{t('Heading')}
<h1 className='text-sm2 place-self-center font-medium'>{t("Heading")}</h1>
<ArrowLeft
className='cursor-pointer'
className='cursor-pointer place-self-end'
size='24'
color='currentColor'
onClick={() => { router.back() }}
/>
</h1>
</div>
<div className='flex overflow-y-auto noscrollbar flex-col h-full py-4 ' dir='rtl'>
<div className='flex overflow-y-auto noscrollbar flex-col h-full pt-4' dir='rtl'>
<ul className="pb-10 flex-1">
<li className=''>
+13
View File
@@ -0,0 +1,13 @@
'use client';
import React from 'react'
function DialogsLayout({ children }: { children: React.ReactNode }) {
return (
<main className='h-full w-full bg-container lg:bg-background pt-4 pb-6 px-6'>
{children}
</main>
)
}
export default DialogsLayout
@@ -1,7 +1,8 @@
'use client';
import { ef } from '@/lib/helpers/utfNumbers';
import { Trash } from 'iconsax-react';
import { ArrowLeft, Trash } from 'iconsax-react';
import { useRouter } from 'next/navigation';
import React from 'react'
import { useTranslation } from 'react-i18next';
@@ -9,10 +10,20 @@ type Props = object
export default function NotificationsIndex({ }: Props) {
const { t } = useTranslation('notifications')
const router = useRouter();
return (
<div className='flex flex-col h-full'>
<h1 className='text-lg py-4'>{t('Heading')}</h1>
<div className='h-full bg-inherit relative flex flex-col lg:gap-4'>
<div className='grid grid-cols-3 items-center py-4 '>
<span></span>
<h1 className='text-sm2 place-self-center font-medium'>{t("Heading")}</h1>
<ArrowLeft
className='cursor-pointer place-self-end'
size='24'
color='currentColor'
onClick={() => { router.back() }}
/>
</div>
<ul className='flex flex-col gap-4 pb-20'>
<li className='bg-container py-5 px-4 rounded-container shadow-lg'>
+90
View File
@@ -0,0 +1,90 @@
'use client';
import Button from '@/components/button/PrimaryButton';
import InputField from '@/components/input/InputField';
import { ArrowLeft } from 'iconsax-react';
import Image from 'next/image'
import { useRouter } from 'next/navigation';
import React from 'react'
import { useTranslation } from 'react-i18next'
type Props = object;
function ReportIndex({ }: Props) {
const router = useRouter();
const { t } = useTranslation('parallels', {
keyPrefix: 'Report'
})
return (
<div className='h-full bg-inherit relative flex flex-col lg:gap-4'>
<div className='grid grid-cols-3 items-center'>
<span></span>
<h1 className='text-sm2 place-self-center font-medium'>{t("Heading")}</h1>
<ArrowLeft
className='cursor-pointer place-self-end'
size='24'
color='currentColor'
onClick={() => { router.back() }}
/>
</div>
<div className="flex lg:justify-center lg:items-center flex-1 bg-inherit">
<div className="w-full lg:w-fit lg:h-fit lg:min-w-3/4 lg:min-h-3/4 flex flex-col-reverse lg:grid lg:gap-8 lg:bg-container lg:grid-cols-2 lg:p-8 lg:rounded-container lg:justify-around lg:items-center bg-inherit">
<form className='flex-1 bg-inherit flex flex-col justify-between items-end'>
<div className='bg-inherit lg:max-w-4/5 w-full flex flex-col justify-between flex-1'>
<div className="bg-inherit flex flex-col h-full">
<div className='w-full px-4 mt-10'>
<h2 className='text-sm2 font-medium'>{t('FormHeading')}</h2>
<p className='text-sm2 text-disabled-text mt-2'>{t('Description')}</p>
</div>
<InputField
className='w-full mt-6 px-4 bg-inherit'
type='text'
placeholder={t('InputTitle.Placeholder')}
labelText={t('InputTitle.Label')}
htmlFor='report-title'
onChange={() => { }}
/>
<div className='relative bg-inherit mt-6 flex-1'>
<textarea
className='w-full px-4 py-2.5 text-sm2 leading-6 outline-0 border border-border rounded-normal h-full max-h-[200px] min-h-[50px] resize-none focus:ring-0'
placeholder={t('InputDescription.Placeholder')}
id='report-description'
name='report-description'
></textarea>
<span className='absolute -top-2 right-2 px-2 bg-inherit text-foreground text-xs'>
{t('InputDescription.Label')}
</span>
</div>
</div>
<Button
className='w-full px-4 mt-6'
type='submit'
onClick={() => { }}
>
{t('ButtonSubmit')}
</Button>
</div>
</form>
<div className='relative'>
<Image
className='place-self-center w-full px-4 mt-8 md:max-w-4/5'
src={'/assets/images/report-hero.svg'}
height={200}
width={312}
unoptimized
alt='report hero image'
/>
<hr className='absolute bottom-0 left-9 right-4 border-border' />
</div>
</div>
</div>
</div>
)
}
export default ReportIndex
+13
View File
@@ -0,0 +1,13 @@
'use client';
import React from 'react'
function DialogsLayout({ children }: { children: React.ReactNode }) {
return (
<main className='h-full w-full bg-background pt-4 pb-6 px-6'>
{children}
</main>
)
}
export default DialogsLayout
@@ -0,0 +1,173 @@
"use client";
import Button from '@/components/button/PrimaryButton';
import { Button as ShadButton } from '@/components/ui/button';
import ComboBox from '@/components/combobox/Combobox';
import InputField from '@/components/input/InputField';
import { PORFILE_EDIT_PAGE_ELEMENT } from '@/enums';
import { Popover, PopoverTrigger, PopoverContent } from '@radix-ui/react-popover';
// import { useProfile } from '@/hooks/auth/useProfile';
// import { useAuthStore } from '@/zustand/authStore';
import { Calendar2, Camera } from 'iconsax-react';
import Image from 'next/image';
import React, { ChangeEvent, useState } from 'react'
import Calendar from '@/components/ui/calendar';
import { getDateLib } from "react-day-picker/persian";
import { useRouter } from 'next/navigation';
type Props = object
function ProfileIndex({ }: Props) {
const [fullname, setFullName] = useState("");
const [email, setEmail] = useState("");
const [phoneNumber, setPhoneNumber] = useState("");
const [dateOfBirth, setDateOfBirth] = React.useState<Date | undefined>(new Date());
const [selectedGender, setSelectedGender] = useState("");
const [showCalendar, setShowCalendar] = useState(false);
const dateLib = getDateLib()
const router = useRouter();
const changeGender = (e: React.MouseEvent<HTMLDivElement, MouseEvent>, index: number) => {
setSelectedGender(() => String(index));
}
// const isAuthenticated = useAuthStore((state) => state.isAuthenticated);
// const { mutate, data, isPending } = useProfile();
// useEffect(() => {
// if (isAuthenticated) {
// mutate();
// }
// // eslint-disable-next-line react-hooks/exhaustive-deps
// }, [isAuthenticated])
const onChange = (e: ChangeEvent<HTMLInputElement>) => {
if (e.target.name == PORFILE_EDIT_PAGE_ELEMENT.INPUT_FULLNAME) {
setFullName(() => e.target.value)
}
else if (e.target.name == PORFILE_EDIT_PAGE_ELEMENT.INPUT_EMAIL) {
setEmail(() => e.target.value)
}
else if (e.target.name == PORFILE_EDIT_PAGE_ELEMENT.INPUT_PHONE) {
setPhoneNumber(() => e.target.value)
}
// else if (e.target.name == PORFILE_EDIT_PAGE_ELEMENT.INPUT_DOB) {
// setDateOfBirth(() => e.target.value)
// }
}
return (
<div className='h-full noscrollbar overflow-y-auto flex flex-col'>
<div className='grid grid-cols-3 items-center'>
<span></span>
<h1 className='text-sm2 place-self-center font-medium'>ویرایش اطلاعات</h1>
</div>
<div className="mt-8 flex-1 bg-container rounded-container w-full box-shadow-normal py-6 px-4 flex flex-col justify-between">
<div className="bg-inherit">
<div className="justify-self-center w-fit relative text-center pb-10"
>
<button>
<Image
src={'/assets/images/user-avatar.png'}
className='rounded-full'
alt='user avatar'
width={96}
height={96}
/>
<div
className='w-24 h-24 absolute top-0 left-0 rounded-full'
style={{
background: 'linear-gradient(180deg, rgba(0, 0, 0, 0) 51.56%, rgba(0, 0, 0, 0.5) 100%)'
}}>
<Camera size={20} className='stroke-white absolute bottom-3 left-1/2 -translate-x-1/2' />
</div>
</button>
</div>
<div className="grid gap-6 mt-6 bg-inherit">
<InputField
onChange={onChange}
className='bg-inherit'
labelText='نام و نام خانوادگی'
htmlFor={PORFILE_EDIT_PAGE_ELEMENT.INPUT_FULLNAME}
value={fullname}
/>
<InputField
onChange={onChange}
dir='ltr'
type='email'
className='bg-inherit'
labelText='ایمیل'
htmlFor={PORFILE_EDIT_PAGE_ELEMENT.INPUT_EMAIL}
value={email}
/>
<InputField
onChange={onChange}
dir='ltr'
type='number'
className='bg-inherit'
labelText='شماره همراه'
htmlFor={PORFILE_EDIT_PAGE_ELEMENT.INPUT_PHONE}
value={phoneNumber}
/>
<Popover open={showCalendar} onOpenChange={setShowCalendar}>
<PopoverTrigger asChild>
<ShadButton
variant="outline"
id="date"
className="w-full bg-white justify-between font-normal relative h-11 rounded-normal hover:bg-white"
>
{dateOfBirth ? dateLib.format(dateOfBirth, "yyyy/MM/dd") : "انتخاب کنید"}
<Calendar2 className='stroke-disabled2' size={24} />
<span className='absolute text-xs top-0 -translate-y-2 right-2 bg-white px-2'>تاریخ تولد</span>
</ShadButton>
</PopoverTrigger>
<PopoverContent className="w-auto overflow-hidden p-0 z-20 box-shadow-normal rounded-lg" align="center">
<Calendar
className='bg-white z-20 min-w-64 rounded-lg'
mode="single"
defaultMonth={dateOfBirth}
selected={dateOfBirth}
captionLayout="dropdown"
onSelect={(date) => {
setDateOfBirth(date)
setShowCalendar(false)
}}
/>
</PopoverContent>
</Popover>
<div className='relative'>
<ComboBox
searchable={false}
title=""
options={[{ id: '0', title: 'آقا', label: 'آقا' }, { id: '1', title: 'خانوم', label: 'خانوم' }]}
id={PORFILE_EDIT_PAGE_ELEMENT.INPUT_GENDER}
selectedId={selectedGender}
onSelectionChange={changeGender} />
<span className='absolute text-xs top-0 -translate-y-2 right-2 bg-white px-2'>جنسیت</span>
</div>
</div>
</div>
<div className='w-full text-center mt-16 grid grid-cols-2 gap-4'>
<Button>ذخیره</Button>
<Button
className='bg-neutral-200! text-disabled-text!'
onClick={() => router.back()}
>
انصراف
</Button>
</div>
</div>
</div>
)
}
export default ProfileIndex
+98
View File
@@ -0,0 +1,98 @@
"use client";
import Button from '@/components/button/PrimaryButton';
// import { useProfile } from '@/hooks/auth/useProfile';
// import { useAuthStore } from '@/zustand/authStore';
import { ArrowLeft, Calendar2, CallCalling, Profile, Sms, Verify } from 'iconsax-react';
import Image from 'next/image';
import Link from 'next/link';
import { useRouter } from 'next/navigation';
import React from 'react'
type Props = object
function ProfileIndex({ }: Props) {
const router = useRouter();
// const isAuthenticated = useAuthStore((state) => state.isAuthenticated);
// const { mutate, data, isPending } = useProfile();
// useEffect(() => {
// if (isAuthenticated) {
// mutate();
// }
// // eslint-disable-next-line react-hooks/exhaustive-deps
// }, [isAuthenticated])
return (
<div className='overflow-y-auto h-full noscrollbar flex flex-col'>
<div className='grid grid-cols-3 items-center'>
<span></span>
<h1 className='text-sm2 place-self-center font-medium'>پروفایل کاربری</h1>
<ArrowLeft
className='cursor-pointer place-self-end'
size='24'
color='currentColor'
onClick={() => { router.back() }}
/>
</div>
<div className="mt-8 flex-1 h-full bg-container rounded-container w-full box-shadow-normal py-6 px-4 flex flex-col justify-between">
<div className="">
<div className="flex items-center justify-start gap-4 pb-6 border-b-[1.5px] border-border">
<Image
src={'/assets/images/user-avatar.png'}
className='rounded-full'
alt='user avatar'
width={80}
height={80}
/>
<div className='block'>
<div className='font-medium text-base '>علیرضا عابدزاده</div>
<div className='text-xs text-primary mt-3 inline-flex items-center gap-2'>
<Verify size={16} className='stroke-primary mb-0.5' />
<span>
شناسه کاربری:
</span>
<span>2162165</span>
</div>
</div>
</div>
<div className="grid gap-6 mt-6">
<div className='inline-flex items-center gap-2.5'>
<CallCalling size={16} className='stroke-disabled2 mb-0.5' />
<span className='text-sm2 text-disabled2'>شماره همراه:</span>
<span className='text-sm2'>09010901738</span>
</div>
<div className='inline-flex items-center gap-2.5'>
<Sms size={16} className='stroke-disabled2 mb-0.5' />
<span className='text-sm2 text-disabled2'>ایمیل:</span>
<span className='text-sm2'>alirezaabed@gmail.com</span>
</div>
<div className='inline-flex items-center gap-2.5'>
<Calendar2 size={16} className='stroke-disabled2 mb-0.5' />
<span className='text-sm2 text-disabled2'>تاریخ تولد:</span>
<span className='text-sm2'>1375/5/14</span>
</div>
<div className='inline-flex items-center gap-2.5'>
<Profile size={16} className='stroke-disabled2 mb-0.5' />
<span className='text-sm2 text-disabled2'>جنسیت:</span>
<span className='text-sm2'>آقا</span>
</div>
</div>
</div>
<div className='w-full text-center mt-6'>
<Link href={'profile/edit'}>
<Button>ویرایش اطلاعات</Button>
</Link>
</div>
</div>
</div>
)
}
export default ProfileIndex
-75
View File
@@ -1,75 +0,0 @@
'use client';
import Button from '@/components/button/PrimaryButton';
import InputField from '@/components/input/InputField';
import { ArrowLeft } from 'iconsax-react';
import Image from 'next/image'
import { useRouter } from 'next/navigation';
import React from 'react'
import { useTranslation } from 'react-i18next'
type Props = object;
function ReportIndex({ }: Props) {
const router = useRouter();
const { t } = useTranslation('parallels', {
keyPrefix: 'Report'
})
return (
<div className='w-full z-[100] px-6 py-6 absolute top-0 left-0 right-0 bottom-0 bg-background'>
<ArrowLeft
className='absolute top-6 left-6 cursor-pointer'
size='24'
color='currentColor'
onClick={() => { router.back() }}
/>
<Image
className='place-self-center w-full px-4'
src={'/assets/images/report-hero.svg'}
height={200}
width={312}
unoptimized
alt='report hero image'
/>
<div className='w-full px-4 mt-6'>
<h2 className='text-sm2 font-bold'>{t('Heading')}</h2>
<p className='text-sm2 text-disabled-text mt-2'>{t('Description')}</p>
</div>
<form>
<InputField
className='w-full mt-6 px-4 bg-background'
type='text'
placeholder={t('InputTitle.Placeholder')}
labelText={t('InputTitle.Label')}
htmlFor='report-title'
onChange={() => { }}
/>
<div className='relative'>
<textarea
className='w-full px-4 py-2.5 mt-6 text-sm2 leading-6 outline-0 border border-border rounded-normal resize-none h-[200px] focus:ring-0'
placeholder={t('InputDescription.Placeholder')}
id='report-description'
name='report-description'
></textarea>
<span className='absolute top-4 right-2 px-2 bg-background text-foreground text-xs'>
{t('InputDescription.Label')}
</span>
</div>
<Button
className='w-full px-4 mt-6'
type='submit'
onClick={() => { }}
>
{t('ButtonSubmit')}
</Button>
</form>
</div>
)
}
export default ReportIndex