Merge branch 'develop' into DimentorinAuth
This commit is contained in:
Binary file not shown.
|
After Width: | Height: | Size: 13 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 17 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 3.9 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 1.8 MiB |
Binary file not shown.
|
After Width: | Height: | Size: 63 KiB |
@@ -7,7 +7,7 @@ export const AppLayout: FC = (): ReactElement => {
|
||||
<div className="bg-primary-50 min-h-screen flex justify-center">
|
||||
<div className="bg-primary-50 min-h-screen w-full flex">
|
||||
<BackofficeSidebar />
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] mx-auto">
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] 2xl:max-w-[1280px] mx-auto">
|
||||
<Outlet />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
import * as React from 'react';
|
||||
|
||||
import { FC, ReactElement } from 'react';
|
||||
import { FC, ReactElement, useState } from 'react';
|
||||
import {
|
||||
FilterOutlined,
|
||||
SearchOutlined,
|
||||
EditOutlined,
|
||||
} from '@ant-design/icons';
|
||||
import { Button, Input } from '@imphnen-frontend-service/ui/atoms';
|
||||
import { DataTable } from '@imphnen-frontend-service/ui/organisms';
|
||||
import { DataTable, Filter } from '@imphnen-frontend-service/ui/organisms';
|
||||
|
||||
import {
|
||||
ColumnDef,
|
||||
@@ -32,7 +32,7 @@ const mockData: Account[] = Array.from({ length: 90 }, (_, i) => ({
|
||||
name: i === 0 ? 'Ahmad Wijuana' : 'Nama Lengkap',
|
||||
email: 'fullname23@gmail.com',
|
||||
phone: '081904423804',
|
||||
address: 'Jl. Pantai Cibaduyut Indonesia',
|
||||
address: 'Jl. Pantai Cibaduyut Indah',
|
||||
}));
|
||||
|
||||
const columns: ColumnDef<Account>[] = [
|
||||
@@ -100,6 +100,7 @@ export const Components: FC = (): ReactElement => {
|
||||
});
|
||||
|
||||
const [rowSelection, setRowSelection] = React.useState<RowSelectionState>({});
|
||||
const [showFilter, setShowFilter] = useState(false);
|
||||
|
||||
const table = useReactTable({
|
||||
data: mockData,
|
||||
@@ -120,7 +121,7 @@ export const Components: FC = (): ReactElement => {
|
||||
return (
|
||||
<main className="w-full px-[48px] py-[40px] flex flex-col gap-8">
|
||||
{/* Header */}
|
||||
<header className="bg-white py-4 px-8 rounded-md shadow p-4">
|
||||
<header className="bg-white py-4 px-8 rounded-lg shadow p-4">
|
||||
<h1 className="text-p2 font-semibold">Data Akun</h1>
|
||||
</header>
|
||||
|
||||
@@ -138,15 +139,23 @@ export const Components: FC = (): ReactElement => {
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Button
|
||||
variant="primary"
|
||||
disabled
|
||||
size="md"
|
||||
className="flex items-center gap-3"
|
||||
>
|
||||
<FilterOutlined />
|
||||
Filters
|
||||
</Button>
|
||||
<div className="relative">
|
||||
<Button
|
||||
variant="primary"
|
||||
size="md"
|
||||
className="flex items-center gap-3"
|
||||
disabled
|
||||
onClick={() => setShowFilter(!showFilter)}
|
||||
>
|
||||
<FilterOutlined />
|
||||
Filters
|
||||
</Button>
|
||||
{showFilter && (
|
||||
<div className="absolute right-0 top-[calc(100%+12px)] z-10 shadow-lg">
|
||||
<Filter onClose={() => setShowFilter(false)} />
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Table */}
|
||||
|
||||
@@ -7,7 +7,7 @@ export const AppLayout: FC = (): ReactElement => {
|
||||
<div className="bg-primary-50 min-h-screen flex justify-center">
|
||||
<div className="bg-primary-50 min-h-screen w-full flex">
|
||||
<BackofficeSidebar />
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] mx-auto">
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] 2xl:max-w-[1280px] mx-auto">
|
||||
<Outlet />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1,4 +1,10 @@
|
||||
import { ArrowDownOutlined, PlusOutlined } from '@ant-design/icons';
|
||||
import {
|
||||
PlusOutlined,
|
||||
ReloadOutlined,
|
||||
UsergroupAddOutlined,
|
||||
UsergroupDeleteOutlined,
|
||||
UserSwitchOutlined,
|
||||
} from '@ant-design/icons';
|
||||
import { Button } from '@imphnen-frontend-service/ui/atoms';
|
||||
import { FC, ReactElement } from 'react';
|
||||
|
||||
@@ -6,7 +12,7 @@ export const Components: FC = (): ReactElement => {
|
||||
return (
|
||||
<main className="w-full px-[48px] py-[40px] flex flex-col gap-8">
|
||||
{/* Dashboard Header */}
|
||||
<header className="bg-white py-4 px-8 rounded-md shadow p-4">
|
||||
<header className="bg-white py-4 px-8 rounded-lg shadow p-4">
|
||||
<h1 className="text-p2 font-semibold">Dashboard</h1>
|
||||
</header>
|
||||
|
||||
@@ -18,23 +24,51 @@ export const Components: FC = (): ReactElement => {
|
||||
Summary
|
||||
</h2>
|
||||
<div className="grid grid-cols-2 gap-4">
|
||||
{/* Summary Cards */}
|
||||
{[1, 2, 3, 4].map((item) => (
|
||||
<div
|
||||
key={item}
|
||||
className="bg-white rounded-lg shadow-sm py-4 px-6 flex items-center border border-neutral-100"
|
||||
>
|
||||
<div className="mr-4 text-primary-500 bg-primary-100 p-[8px] rounded-md">
|
||||
<ArrowDownOutlined className="text-[20px]" />
|
||||
</div>
|
||||
<div className="flex flex-col gap-1">
|
||||
<h3 className="text-p1 font-semibold">1000</h3>
|
||||
<p className="text-label1 text-neutral-500">
|
||||
Total Participants
|
||||
</p>
|
||||
</div>
|
||||
{/* Participants */}
|
||||
<div className="bg-white rounded-lg shadow-sm py-4 px-6 flex items-center border border-neutral-100">
|
||||
<div className="mr-4 text-primary-500 bg-primary-100 p-[8px] rounded-md">
|
||||
<UsergroupAddOutlined className="text-[20px]" />
|
||||
</div>
|
||||
))}
|
||||
<div className="flex flex-col gap-1">
|
||||
<h3 className="text-p1 font-semibold">1000</h3>
|
||||
<p className="text-label1 text-neutral-500">Participants</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Roll and Reroll */}
|
||||
<div className="bg-white rounded-lg shadow-sm py-4 px-6 flex items-center border border-neutral-100">
|
||||
<div className="mr-4 text-primary-500 bg-primary-100 p-[8px] rounded-md">
|
||||
<ReloadOutlined className="text-[20px]" />
|
||||
</div>
|
||||
<div className="flex flex-col gap-1">
|
||||
<h3 className="text-p1 font-semibold">1000</h3>
|
||||
<p className="text-label1 text-neutral-500">
|
||||
Roll and Reroll
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Redeem */}
|
||||
<div className="bg-white rounded-lg shadow-sm py-4 px-6 flex items-center border border-neutral-100">
|
||||
<div className="mr-4 text-primary-500 bg-primary-100 p-[8px] rounded-md">
|
||||
<UserSwitchOutlined className="text-[20px]" />
|
||||
</div>
|
||||
<div className="flex flex-col gap-1">
|
||||
<h3 className="text-p1 font-semibold">1000</h3>
|
||||
<p className="text-label1 text-neutral-500">Redeem</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Inactive Users */}
|
||||
<div className="bg-white rounded-lg shadow-sm py-4 px-6 flex items-center border border-neutral-100">
|
||||
<div className="mr-4 text-primary-500 bg-primary-100 p-[8px] rounded-md">
|
||||
<UsergroupDeleteOutlined className="text-[20px]" />
|
||||
</div>
|
||||
<div className="flex flex-col gap-1">
|
||||
<h3 className="text-p1 font-semibold">1000</h3>
|
||||
<p className="text-label1 text-neutral-500">Inactive Users</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
@@ -78,7 +112,7 @@ export const Components: FC = (): ReactElement => {
|
||||
<Button
|
||||
variant="text"
|
||||
size="sm"
|
||||
className="text-[10px] text-neutral-500 p-0 font-normal hover:bg-transparent hover:text-red-500"
|
||||
className="text-[10px] text-red-500 p-0 font-normal hover:bg-transparent hover:text-red-700"
|
||||
>
|
||||
Delete
|
||||
</Button>
|
||||
@@ -87,7 +121,7 @@ export const Components: FC = (): ReactElement => {
|
||||
|
||||
{/* Lebih baik gunakan gambar yang sudah di-clip dengan size height: 78px daripada hard-code object-position dan margin */}
|
||||
<img
|
||||
src="gacha-clip.png"
|
||||
src="gacha-clip.webp"
|
||||
alt="Lanyard IMPHNEN"
|
||||
className="h-full"
|
||||
/>
|
||||
@@ -99,7 +133,7 @@ export const Components: FC = (): ReactElement => {
|
||||
|
||||
{/* Right-side illustration */}
|
||||
<img
|
||||
src="gacha.png"
|
||||
src="gacha.webp"
|
||||
alt=""
|
||||
className="rounded-lg hidden xl:block xl:min-w-[436px] h-auto object-cover"
|
||||
/>
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
import { FC, ReactElement } from 'react';
|
||||
import { Outlet } from 'react-router-dom';
|
||||
import { BackofficeSidebar } from '@imphnen-frontend-service/ui/organisms';
|
||||
|
||||
export const AppLayout: FC = (): ReactElement => {
|
||||
return (
|
||||
<div className="bg-primary-50 min-h-screen flex justify-center">
|
||||
<div className="bg-primary-50 min-h-screen w-full flex">
|
||||
<BackofficeSidebar />
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] 2xl:max-w-[1280px] mx-auto">
|
||||
<Outlet />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default AppLayout;
|
||||
@@ -0,0 +1,232 @@
|
||||
import * as React from 'react';
|
||||
|
||||
import { FC, ReactElement, useState } from 'react';
|
||||
import {
|
||||
FilterOutlined,
|
||||
SearchOutlined,
|
||||
AuditOutlined,
|
||||
} from '@ant-design/icons';
|
||||
import { Button, Input } from '@imphnen-frontend-service/ui/atoms';
|
||||
import { DataTable, Filter } from '@imphnen-frontend-service/ui/organisms';
|
||||
|
||||
import {
|
||||
ColumnDef,
|
||||
getCoreRowModel,
|
||||
getPaginationRowModel,
|
||||
PaginationState,
|
||||
useReactTable,
|
||||
RowSelectionState,
|
||||
} from '@tanstack/react-table';
|
||||
|
||||
type Status = 'valid' | 'invalid' | 'unchecked';
|
||||
|
||||
interface Prize {
|
||||
id: number;
|
||||
name: string;
|
||||
orderValid: Status;
|
||||
items: string;
|
||||
address: string;
|
||||
status: Status;
|
||||
}
|
||||
|
||||
const items = [
|
||||
'Sertifikat + Laminating',
|
||||
'Lanyard + ID Card',
|
||||
'Pin',
|
||||
'Sticker Isi 3',
|
||||
'Sticker Isi 5',
|
||||
'Gelang Karet',
|
||||
];
|
||||
|
||||
// Mock data for transactions
|
||||
const mockData: Prize[] = Array.from({ length: 90 }, (_, i) => ({
|
||||
id: i + 1,
|
||||
name: 'Nama Lengkap',
|
||||
orderValid: (i % 3 === 0
|
||||
? 'invalid'
|
||||
: i % 5 === 0
|
||||
? 'unchecked'
|
||||
: 'valid') as Status,
|
||||
items: items[i % items.length],
|
||||
address: 'Jl. Pantai Cibaduyut Indah',
|
||||
status: (i % 3 === 0
|
||||
? 'unchecked'
|
||||
: i % 5 === 0
|
||||
? 'invalid'
|
||||
: 'valid') as Status,
|
||||
}));
|
||||
|
||||
const columns: ColumnDef<Prize>[] = [
|
||||
{
|
||||
id: 'select',
|
||||
header: ({ table }) => (
|
||||
<input
|
||||
type="checkbox"
|
||||
className="rounded"
|
||||
checked={table.getIsAllRowsSelected()}
|
||||
onChange={table.getToggleAllRowsSelectedHandler()}
|
||||
/>
|
||||
),
|
||||
cell: ({ row }) => (
|
||||
<input
|
||||
type="checkbox"
|
||||
className="rounded"
|
||||
checked={row.getIsSelected()}
|
||||
onChange={row.getToggleSelectedHandler()}
|
||||
/>
|
||||
),
|
||||
},
|
||||
{
|
||||
header: 'No',
|
||||
accessorKey: 'id',
|
||||
},
|
||||
{
|
||||
header: 'Nama Lengkap',
|
||||
accessorKey: 'name',
|
||||
},
|
||||
{
|
||||
header: 'Order Valid?',
|
||||
accessorKey: 'orderValid',
|
||||
cell: ({ row }) => {
|
||||
const status = row.original.orderValid;
|
||||
const statusColors: Record<Status, string> = {
|
||||
valid: 'bg-success-200 text-success-500',
|
||||
invalid: 'bg-danger-200 text-danger-500',
|
||||
unchecked: 'bg-warning-200 text-warning-900',
|
||||
};
|
||||
const statusText: Record<Status, string> = {
|
||||
valid: 'Valid',
|
||||
invalid: 'Invalid',
|
||||
unchecked: 'Unchecked',
|
||||
};
|
||||
return (
|
||||
<div
|
||||
className={`py-2 px-4 rounded-md text-center ${statusColors[status]}`}
|
||||
>
|
||||
{statusText[status]}
|
||||
</div>
|
||||
);
|
||||
},
|
||||
},
|
||||
{
|
||||
header: 'Items',
|
||||
accessorKey: 'items',
|
||||
},
|
||||
{
|
||||
header: 'Alamat Pengiriman',
|
||||
accessorKey: 'address',
|
||||
},
|
||||
{
|
||||
header: 'Status',
|
||||
accessorKey: 'status',
|
||||
cell: ({ row }) => {
|
||||
const status = row.original.status;
|
||||
const statusColors: Record<Status, string> = {
|
||||
valid: 'bg-success-200 text-success-500',
|
||||
invalid: 'bg-danger-200 text-danger-500',
|
||||
unchecked: 'bg-warning-200 text-warning-900',
|
||||
};
|
||||
const statusText: Record<Status, string> = {
|
||||
valid: 'Valid',
|
||||
invalid: 'Invalid',
|
||||
unchecked: 'Unchecked',
|
||||
};
|
||||
return (
|
||||
<div
|
||||
className={`py-2 px-4 rounded-md text-center ${statusColors[status]}`}
|
||||
>
|
||||
{statusText[status]}
|
||||
</div>
|
||||
);
|
||||
},
|
||||
},
|
||||
{
|
||||
header: 'Action',
|
||||
cell: ({ row }) => (
|
||||
<Button
|
||||
variant="primary"
|
||||
size="sm"
|
||||
onClick={(e) => {
|
||||
e.stopPropagation();
|
||||
// handleUpdate(row.id);
|
||||
}}
|
||||
className="flex items-center gap-2 w-full"
|
||||
>
|
||||
<AuditOutlined className="text-[16px]" /> Process
|
||||
</Button>
|
||||
),
|
||||
},
|
||||
];
|
||||
|
||||
export const Components: FC = (): ReactElement => {
|
||||
const [pagination, setPagination] = React.useState<PaginationState>({
|
||||
pageIndex: 0,
|
||||
pageSize: 9,
|
||||
});
|
||||
|
||||
const [rowSelection, setRowSelection] = React.useState<RowSelectionState>({});
|
||||
const [showFilter, setShowFilter] = useState(false);
|
||||
|
||||
const table = useReactTable({
|
||||
data: mockData,
|
||||
columns,
|
||||
state: {
|
||||
pagination,
|
||||
rowSelection,
|
||||
},
|
||||
enableRowSelection: true,
|
||||
onRowSelectionChange: setRowSelection,
|
||||
getCoreRowModel: getCoreRowModel(),
|
||||
getPaginationRowModel: getPaginationRowModel(),
|
||||
onPaginationChange: setPagination,
|
||||
pageCount: Math.ceil(mockData.length / pagination.pageSize),
|
||||
manualPagination: false,
|
||||
});
|
||||
|
||||
return (
|
||||
<main className="w-full px-[48px] py-[40px] flex flex-col gap-8">
|
||||
{/* Header */}
|
||||
<header className="bg-white py-4 px-8 rounded-lg shadow p-4">
|
||||
<h1 className="text-p2 font-semibold">Data Pengiriman Hadiah</h1>
|
||||
</header>
|
||||
|
||||
{/* Account Table Section */}
|
||||
<section className="flex flex-col gap-6 p-8 bg-white rounded-md">
|
||||
{/* Search and Filter */}
|
||||
<div className="flex justify-between items-center gap-8 mb-2">
|
||||
<div className="relative w-full">
|
||||
<Input
|
||||
placeholder="Cari berdasarkan nama lengkap, nomor order Shopee"
|
||||
className="pl-12 w-full max-h-full"
|
||||
/>
|
||||
<div className="absolute left-3 top-1/2 transform -translate-y-1/2 text-[16px]">
|
||||
<SearchOutlined />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="relative">
|
||||
<Button
|
||||
variant="primary"
|
||||
size="md"
|
||||
className="flex items-center gap-3"
|
||||
onClick={() => setShowFilter(!showFilter)}
|
||||
>
|
||||
<FilterOutlined />
|
||||
Filters
|
||||
</Button>
|
||||
{showFilter && (
|
||||
<div className="absolute right-0 top-[calc(100%+12px)] z-10 shadow-lg">
|
||||
<Filter onClose={() => setShowFilter(false)} />
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Table */}
|
||||
<DataTable data={mockData} columns={columns} table={table} />
|
||||
</section>
|
||||
</main>
|
||||
);
|
||||
};
|
||||
|
||||
export default Components;
|
||||
@@ -7,7 +7,7 @@ export const AppLayout: FC = (): ReactElement => {
|
||||
<div className="bg-primary-50 min-h-screen flex justify-center">
|
||||
<div className="bg-primary-50 min-h-screen w-full flex">
|
||||
<BackofficeSidebar />
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] mx-auto">
|
||||
<div className="flex-1 overflow-auto lg:max-w-[1000px] 2xl:max-w-[1280px] mx-auto">
|
||||
<Outlet />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -1,13 +1,12 @@
|
||||
import * as React from 'react';
|
||||
|
||||
import { FC, ReactElement } from 'react';
|
||||
import { FC, ReactElement, useState } from 'react';
|
||||
import {
|
||||
FilterOutlined,
|
||||
SearchOutlined,
|
||||
AuditOutlined,
|
||||
} from '@ant-design/icons';
|
||||
import { Button, Input } from '@imphnen-frontend-service/ui/atoms';
|
||||
import { DataTable } from '@imphnen-frontend-service/ui/organisms';
|
||||
import { DataTable, Filter } from '@imphnen-frontend-service/ui/organisms';
|
||||
|
||||
import {
|
||||
ColumnDef,
|
||||
@@ -39,7 +38,7 @@ const mockTransactions: Transaction[] = Array.from({ length: 20 }, (_, i) => ({
|
||||
: 'valid') as TransactionStatus,
|
||||
}));
|
||||
|
||||
const columns: ColumnDef<Account>[] = [
|
||||
const columns: ColumnDef<Transaction>[] = [
|
||||
{
|
||||
id: 'select',
|
||||
header: ({ table }) => (
|
||||
@@ -77,9 +76,9 @@ const columns: ColumnDef<Account>[] = [
|
||||
cell: ({ row }) => {
|
||||
const status = row.original.status;
|
||||
const statusColors: Record<TransactionStatus, string> = {
|
||||
valid: 'bg-success-500 text-white',
|
||||
invalid: 'bg-danger-500 text-white',
|
||||
unchecked: 'bg-yellow-400 text-black',
|
||||
valid: 'bg-success-200 text-success-500',
|
||||
invalid: 'bg-danger-200 text-danger-500',
|
||||
unchecked: 'bg-warning-200 text-warning-900',
|
||||
};
|
||||
const statusText: Record<TransactionStatus, string> = {
|
||||
valid: 'Valid',
|
||||
@@ -88,7 +87,7 @@ const columns: ColumnDef<Account>[] = [
|
||||
};
|
||||
return (
|
||||
<div
|
||||
className={`py-1 px-3 rounded-md text-center ${statusColors[status]}`}
|
||||
className={`py-2 px-4 rounded-md text-center ${statusColors[status]}`}
|
||||
>
|
||||
{statusText[status]}
|
||||
</div>
|
||||
@@ -120,6 +119,7 @@ export const Components: FC = (): ReactElement => {
|
||||
});
|
||||
|
||||
const [rowSelection, setRowSelection] = React.useState<RowSelectionState>({});
|
||||
const [showFilter, setShowFilter] = useState(false);
|
||||
|
||||
const table = useReactTable({
|
||||
data: mockTransactions,
|
||||
@@ -140,7 +140,7 @@ export const Components: FC = (): ReactElement => {
|
||||
return (
|
||||
<main className="w-full px-[48px] py-[40px] flex flex-col gap-8">
|
||||
{/* Header */}
|
||||
<header className="bg-white py-4 px-8 rounded-md shadow p-4">
|
||||
<header className="bg-white py-4 px-8 rounded-lg shadow p-4">
|
||||
<h1 className="text-p2 font-semibold">Validasi Transaksi</h1>
|
||||
</header>
|
||||
|
||||
@@ -158,14 +158,22 @@ export const Components: FC = (): ReactElement => {
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Button
|
||||
variant="primary"
|
||||
size="md"
|
||||
className="flex items-center gap-3"
|
||||
>
|
||||
<FilterOutlined />
|
||||
Filters
|
||||
</Button>
|
||||
<div className="relative">
|
||||
<Button
|
||||
variant="primary"
|
||||
size="md"
|
||||
className="flex items-center gap-3"
|
||||
onClick={() => setShowFilter(!showFilter)}
|
||||
>
|
||||
<FilterOutlined />
|
||||
Filters
|
||||
</Button>
|
||||
{showFilter && (
|
||||
<div className="absolute right-0 top-[calc(100%+12px)] z-10 shadow-lg">
|
||||
<Filter onClose={() => setShowFilter(false)} />
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Table */}
|
||||
|
||||
@@ -17,14 +17,14 @@
|
||||
|
||||
--color-neutral-50: #f6f6f6;
|
||||
--color-neutral-100: #e7e7e7;
|
||||
--color-neutral-200: #d0d0d0;
|
||||
--color-neutral-300: #b7b7b7;
|
||||
--color-neutral-400: #9f9f9f;
|
||||
--color-neutral-500: #7e7e7e;
|
||||
--color-neutral-200: #d1d1d1;
|
||||
--color-neutral-300: #b0b0b0;
|
||||
--color-neutral-400: #888888;
|
||||
--color-neutral-500: #6d6d6d;
|
||||
--color-neutral-600: #5d5d5d;
|
||||
--color-neutral-700: #4a4a4a;
|
||||
--color-neutral-800: #3a3a3a;
|
||||
--color-neutral-900: #2f2f2f;
|
||||
--color-neutral-700: #4f4f4f;
|
||||
--color-neutral-800: #454545;
|
||||
--color-neutral-900: #3d3d3d;
|
||||
--color-neutral-950: #2b2b2b;
|
||||
|
||||
--color-success-100: #e0fbd8;
|
||||
|
||||
+54
-13
@@ -1,9 +1,9 @@
|
||||
import { ArrowDownOutlined } from '@ant-design/icons';
|
||||
import { Button } from '@imphnen-frontend-service/ui/atoms';
|
||||
import { ModalsGacha } from '@imphnen-frontend-service/ui/organisms';
|
||||
import { InputForm, Modal } from '@imphnen-frontend-service/ui/molecules';
|
||||
import { cn } from '@imphnen-frontend-service/utils';
|
||||
import { FC, Fragment, ReactElement, useEffect, useState } from 'react';
|
||||
import { createPortal } from 'react-dom';
|
||||
import { Link } from 'react-router';
|
||||
|
||||
interface GachaItemProps {
|
||||
src: string;
|
||||
@@ -14,7 +14,6 @@ interface GachaItemProps {
|
||||
export const Components: FC = (): ReactElement => {
|
||||
// Pinjem
|
||||
const [showModal, setShowModal] = useState(false);
|
||||
//
|
||||
|
||||
const scrollToRoulette = () => {
|
||||
const rouletteSection = document.getElementById('roulette');
|
||||
@@ -222,16 +221,58 @@ export const Components: FC = (): ReactElement => {
|
||||
<div className="sticky bottom-0 h-[86px] md:h-[200px] bg-gradient-to-b from-primary-500/0 to-primary-500/50 to-80%"></div>
|
||||
|
||||
{/**Izin pake untuk debug modals gacha */}
|
||||
<div>
|
||||
<p>Debug : Test Modals Gacha</p>
|
||||
<Button onClick={
|
||||
() => setShowModal(true)
|
||||
}>Tekan</Button>
|
||||
</div>
|
||||
{showModal && createPortal(
|
||||
<ModalsGacha></ModalsGacha>,
|
||||
document.body
|
||||
)}
|
||||
<button onClick={() => setShowModal(true)}>Open Modal</button>
|
||||
<Modal
|
||||
className="py-[45px] min-w-[400px] lg:min-w-[455px] px-7"
|
||||
isOpen={showModal}
|
||||
onClose={() => setShowModal(false)}
|
||||
>
|
||||
<Modal.Header className="space-y-4">
|
||||
<img src="/logos/logo.svg" alt="" className="h-[70px] w-auto" />
|
||||
<h1 className="text-primary-500 text-p1 text-center font-semibold">
|
||||
Login
|
||||
</h1>
|
||||
</Modal.Header>
|
||||
<Modal.Content className="space-y-4">
|
||||
<InputForm
|
||||
label="Email"
|
||||
placeholder="Masukkan Email"
|
||||
type="email"
|
||||
size="lg"
|
||||
className="w-full"
|
||||
/>
|
||||
<InputForm
|
||||
label="Password"
|
||||
placeholder="Masukkan password"
|
||||
type="password"
|
||||
size="lg"
|
||||
className="w-full"
|
||||
/>
|
||||
<Link to="/forgot-password">
|
||||
<h1 className="text-end text-primary-500 text-xl font-medium">
|
||||
Lupa Password?
|
||||
</h1>
|
||||
</Link>
|
||||
</Modal.Content>
|
||||
<Modal.Footer className="flex flex-col md:flex-col pt-4">
|
||||
<Button
|
||||
size="md"
|
||||
className="w-full"
|
||||
onClick={() => console.log('Login')}
|
||||
>
|
||||
Login
|
||||
</Button>
|
||||
<div className="flex justify-center gap-2 pt-2.5 font-medium">
|
||||
<p className="text-neutral-500">Belum punya akun?</p>
|
||||
<Link
|
||||
className="text-primary-500 hover:text-primary-600"
|
||||
to="/register"
|
||||
>
|
||||
Daftar disini
|
||||
</Link>
|
||||
</div>
|
||||
</Modal.Footer>
|
||||
</Modal>
|
||||
{/**Izin pake untuk debug modals gacha */}
|
||||
</Fragment>
|
||||
);
|
||||
|
||||
@@ -17,14 +17,14 @@
|
||||
|
||||
--color-neutral-50: #f6f6f6;
|
||||
--color-neutral-100: #e7e7e7;
|
||||
--color-neutral-200: #d0d0d0;
|
||||
--color-neutral-300: #b7b7b7;
|
||||
--color-neutral-400: #9f9f9f;
|
||||
--color-neutral-500: #7e7e7e;
|
||||
--color-neutral-200: #d1d1d1;
|
||||
--color-neutral-300: #b0b0b0;
|
||||
--color-neutral-400: #888888;
|
||||
--color-neutral-500: #6d6d6d;
|
||||
--color-neutral-600: #5d5d5d;
|
||||
--color-neutral-700: #4a4a4a;
|
||||
--color-neutral-800: #3a3a3a;
|
||||
--color-neutral-900: #2f2f2f;
|
||||
--color-neutral-700: #4f4f4f;
|
||||
--color-neutral-800: #454545;
|
||||
--color-neutral-900: #3d3d3d;
|
||||
--color-neutral-950: #2b2b2b;
|
||||
|
||||
--color-success-100: #e0fbd8;
|
||||
|
||||
Reference in New Issue
Block a user