Skip to content

Commit

Permalink
feat: Select how many items you would like to loan, fix skeletons
Browse files Browse the repository at this point in the history
  • Loading branch information
ZeroWave022 committed Sep 25, 2024
1 parent 28bf06e commit 234eadf
Show file tree
Hide file tree
Showing 6 changed files with 56 additions and 21 deletions.
3 changes: 2 additions & 1 deletion messages/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,8 @@
"tableDescription": "A list of your shopping cart items.",
"backToStorage": "Back to storage",
"cartEmpty": "Your shopping cart is empty.",
"clearCart": "Empty shopping cart"
"clearCart": "Empty shopping cart",
"amountOfItemARIA": "Select number of this item"
},
"loanForm": {
"borrowNow": "Borrow now",
Expand Down
3 changes: 2 additions & 1 deletion messages/no.json
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,8 @@
"tableDescription": "En liste over handlekurven din.",
"backToStorage": "Tilbake til lageret",
"cartEmpty": "Handlekurven din er tom.",
"clearCart": "Tøm handlekurven"
"clearCart": "Tøm handlekurven",
"amountOfItemARIA": "Velg antallet av denne gjenstanden"
},
"loanForm": {
"borrowNow": "Lån nå",
Expand Down
10 changes: 3 additions & 7 deletions src/app/[locale]/(default)/storage/(main)/loading.tsx
Original file line number Diff line number Diff line change
@@ -1,15 +1,10 @@
import { PaginationCarouselSkeleton } from '@/components/composites/PaginationCarouselSkeleton';
import { SkeletonCard } from '@/components/storage/SkeletonCard';
import { Skeleton } from '@/components/ui/Skeleton';

export default function StorageSkeleton() {
return (
<>
<div className='my-4 flex flex-col justify-center gap-2 lg:flex-row'>
<Skeleton className='h-10 w-full' />
<Skeleton className='h-10 w-full lg:w-[250px]' />
<Skeleton className='h-10 w-full lg:w-[250px]' />
</div>
<div className='grid grid-cols-1 gap-3 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-4'>
<div className='mt-8 grid grid-cols-1 gap-3 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-4'>
<SkeletonCard />
<SkeletonCard />
<SkeletonCard />
Expand All @@ -19,6 +14,7 @@ export default function StorageSkeleton() {
<SkeletonCard />
<SkeletonCard />
</div>
<PaginationCarouselSkeleton className='mb-4' />
</>
);
}
3 changes: 2 additions & 1 deletion src/app/[locale]/(default)/storage/shopping-cart/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ export default function StorageShoppingCartPage({
location: t('location'),
unitsAvailable: t('unitsAvailable'),
cartEmpty: t('cartEmpty'),
amountOfItemARIA: t('amountOfItemARIA'),
};

const loanFormMessages = {
Expand All @@ -41,7 +42,7 @@ export default function StorageShoppingCartPage({
return (
<>
<h1 className='my-4 md:text-center'>{t('title')}</h1>
<ShoppingCartTable messages={tableMessages} />
<ShoppingCartTable t={tableMessages} />
<div className='my-4 flex justify-center gap-2'>
<Link href='/storage'>
<Button className='flex gap-2'>
Expand Down
6 changes: 6 additions & 0 deletions src/components/storage/LoanForm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import {
import { Input } from '@/components/ui/Input';
import { zodResolver } from '@hookform/resolvers/zod';
import { useForm } from 'react-hook-form';
import { useReadLocalStorage } from 'usehooks-ts';
import { z } from 'zod';

const formSchema = z.object({
Expand All @@ -39,6 +40,9 @@ type LoanFormProps = {
};

function LoanForm({ t }: LoanFormProps) {
const cart = useReadLocalStorage<number[]>('shopping-cart', {
initializeWithValue: false,
});
const form = useForm<z.infer<typeof formSchema>>({
resolver: zodResolver(formSchema),
defaultValues: {
Expand All @@ -54,6 +58,8 @@ function LoanForm({ t }: LoanFormProps) {
console.log(values);
}

if (!cart || cart.length <= 0) return;

return (
<>
<h2 className='text-center'>{t.borrowNow}</h2>
Expand Down
52 changes: 41 additions & 11 deletions src/components/storage/ShoppingCartTable.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
'use client';

import { Button } from '@/components/ui/Button';
import { Input } from '@/components/ui/Input';
import {
Table,
TableBody,
Expand All @@ -17,49 +18,78 @@ import { useLocalStorage } from 'usehooks-ts';
import { items } from '@/mock-data/items';

type ShoppingCartTableProps = {
messages: {
t: {
tableDescription: string;
productId: string;
productName: string;
location: string;
unitsAvailable: string;
cartEmpty: string;
amountOfItemARIA: string;
};
};

function ShoppingCartTable({ messages }: ShoppingCartTableProps) {
function ShoppingCartTable({ t }: ShoppingCartTableProps) {
const [cart, setCart] = useLocalStorage<number[]>('shopping-cart', [], {
initializeWithValue: false,
});

if (cart.length <= 0) {
return <p className='text-center'>{messages.cartEmpty}</p>;
return <p className='text-center'>{t.cartEmpty}</p>;
}

const itemsInCart = items.filter((item) => cart.includes(item.id));

function updateAmountInCart(id: number, newValue: number) {
const amountInCart = cart.filter((i) => i === id).length;
const diff = newValue - amountInCart;

let newCart = cart;
// If we're adding elements, add x new elements
// Else, remove all occurences of the item, and re-add the correct amount
if (diff > 0) {
newCart = newCart.concat(Array(diff).fill(id));
} else {
newCart = newCart.filter((i) => i !== id);
newCart = newCart.concat(Array(newValue).fill(id));
}
setCart(newCart);
}

function removeItem(id: number) {
if (!cart) return;
setCart(cart.filter((itemId) => itemId !== id));
}

return (
<Table className='my-4'>
<TableCaption>{messages.tableDescription}</TableCaption>
<TableCaption>{t.tableDescription}</TableCaption>
<TableHeader>
<TableRow>
<TableHead className='w-[150px]'>{messages.productId}</TableHead>
<TableHead>{messages.productName}</TableHead>
<TableHead>{messages.location}</TableHead>
<TableHead className='text-right'>
{messages.unitsAvailable}
</TableHead>
<TableHead className='w-[100px]' />
<TableHead className='w-[80px]' />
<TableHead className='w-[150px]'>{t.productId}</TableHead>
<TableHead>{t.productName}</TableHead>
<TableHead>{t.location}</TableHead>
<TableHead className='text-right'>{t.unitsAvailable}</TableHead>
<TableHead className='w-[80px]' />
</TableRow>
</TableHeader>
<TableBody>
{itemsInCart.map((item) => (
<TableRow key={item.name}>
<TableCell>
<Input
type='number'
min={1}
max={100}
defaultValue={cart.filter((i) => i === item.id).length}
onChange={(e) =>
updateAmountInCart(item.id, Number(e.currentTarget.value))
}
className='w-[80px]'
aria-label={t.amountOfItemARIA}
/>
</TableCell>
<TableCell className='font-medium'>{item.id}</TableCell>
<TableCell>{item.name}</TableCell>
<TableCell>{item.location}</TableCell>
Expand Down

0 comments on commit 234eadf

Please sign in to comment.