@@ -2,6 +2,8 @@
|
|||||||
|
|
||||||
All notable changes to this project will be documented in this file. See [commit-and-tag-version](https://github.com/absolute-version/commit-and-tag-version) for commit guidelines.
|
All notable changes to this project will be documented in this file. See [commit-and-tag-version](https://github.com/absolute-version/commit-and-tag-version) for commit guidelines.
|
||||||
|
|
||||||
|
## [1.2.74](https://github.com/bipproduction/hipmi/compare/v1.2.73...v1.2.74) (2025-03-07)
|
||||||
|
|
||||||
## [1.2.73](https://github.com/bipproduction/hipmi/compare/v1.2.72...v1.2.73) (2025-03-06)
|
## [1.2.73](https://github.com/bipproduction/hipmi/compare/v1.2.72...v1.2.73) (2025-03-06)
|
||||||
|
|
||||||
## [1.2.72](https://github.com/bipproduction/hipmi/compare/v1.2.71...v1.2.72) (2025-03-05)
|
## [1.2.72](https://github.com/bipproduction/hipmi/compare/v1.2.71...v1.2.72) (2025-03-05)
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "hipmi",
|
"name": "hipmi",
|
||||||
"version": "1.2.73",
|
"version": "1.2.74",
|
||||||
"private": true,
|
"private": true,
|
||||||
"prisma": {
|
"prisma": {
|
||||||
"seed": "bun prisma/seed.ts"
|
"seed": "bun prisma/seed.ts"
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
import { LayoutJob_Main } from "@/app_modules/job";
|
import { LayoutJob_Main } from "@/app_modules/job";
|
||||||
|
import NewLayoutJob_Main from "@/app_modules/job/main/new_layout";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
|
||||||
export default async function Layout({
|
export default async function Layout({
|
||||||
@@ -8,7 +9,8 @@ export default async function Layout({
|
|||||||
}) {
|
}) {
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<LayoutJob_Main>{children}</LayoutJob_Main>
|
{/* <LayoutJob_Main>{children}</LayoutJob_Main> */}
|
||||||
|
<NewLayoutJob_Main>{children}</NewLayoutJob_Main>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { Box } from "@mantine/core";
|
import { Box, rem } from "@mantine/core";
|
||||||
import { AccentColor } from "../color";
|
import { AccentColor } from "../color";
|
||||||
|
|
||||||
export function NewUI_Footer({ children }: { children: React.ReactNode }) {
|
export function NewUI_Footer({ children }: { children: React.ReactNode }) {
|
||||||
@@ -19,6 +19,8 @@ export function NewUI_Footer({ children }: { children: React.ReactNode }) {
|
|||||||
justifyContent: "center",
|
justifyContent: "center",
|
||||||
maxWidth: "500px", // Batasi lebar maksimum untuk tampilan mobile
|
maxWidth: "500px", // Batasi lebar maksimum untuk tampilan mobile
|
||||||
margin: "0 auto", // Pusatkan di tengah layar desktop
|
margin: "0 auto", // Pusatkan di tengah layar desktop
|
||||||
|
borderRadius: "20px 20px 0px 0px",
|
||||||
|
width: "100%",
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
{children}
|
{children}
|
||||||
|
|||||||
@@ -10,22 +10,23 @@ export function NewUI_Tamplate({ children }: { children: React.ReactNode }) {
|
|||||||
width: "100%",
|
width: "100%",
|
||||||
height: "100vh",
|
height: "100vh",
|
||||||
overflow: "hidden",
|
overflow: "hidden",
|
||||||
backgroundColor: MainColor.black,
|
backgroundColor: MainColor.darkblue,
|
||||||
position: "relative",
|
position: "relative",
|
||||||
maxWidth: "500px", // Batasi lebar maksimum untuk tampilan mobile
|
maxWidth: "500px", // Batasi lebar maksimum untuk tampilan mobile
|
||||||
margin: "0 auto", // Pusatkan di tengah layar desktop
|
margin: "0 auto", // Pusatkan di tengah layar desktop
|
||||||
border: "1px solid #ccc", // Garis tepi untuk visualisasi
|
border: "1px solid #ccc", // Garis tepi untuk visualisasi
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<Box
|
<BackgroundImage
|
||||||
|
src="/aset/global/main_background.png"
|
||||||
style={{
|
style={{
|
||||||
|
// backgroundImage: "url(/aset/global/main_background.png)",
|
||||||
position: "fixed",
|
position: "fixed",
|
||||||
top: 0,
|
top: 0,
|
||||||
left: 0,
|
left: 0,
|
||||||
right: 0,
|
right: 0,
|
||||||
bottom: 0,
|
bottom: 0,
|
||||||
zIndex: 1, // Pastikan background di belakang konten
|
zIndex: 1, // Pastikan background di belakang konten
|
||||||
backgroundImage: "url(/aset/global/main_background.png)",
|
|
||||||
backgroundSize: "cover",
|
backgroundSize: "cover",
|
||||||
backgroundPosition: "center",
|
backgroundPosition: "center",
|
||||||
maxWidth: "500px", // Batasi lebar maksimum untuk tampilan mobile
|
maxWidth: "500px", // Batasi lebar maksimum untuk tampilan mobile
|
||||||
@@ -33,7 +34,7 @@ export function NewUI_Tamplate({ children }: { children: React.ReactNode }) {
|
|||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
{children}
|
{children}
|
||||||
</Box>
|
</BackgroundImage>
|
||||||
</Box>
|
</Box>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|||||||
157
src/app_modules/job/main/beranda/view.back.txt
Normal file
157
src/app_modules/job/main/beranda/view.back.txt
Normal file
@@ -0,0 +1,157 @@
|
|||||||
|
"use client";
|
||||||
|
|
||||||
|
import { gs_jobTiggerBeranda } from "@/lib/global_state";
|
||||||
|
import { RouterJob } from "@/lib/router_hipmi/router_job";
|
||||||
|
import ComponentGlobal_CreateButton from "@/app_modules/_global/component/button_create";
|
||||||
|
import ComponentGlobal_IsEmptyData from "@/app_modules/_global/component/is_empty_data";
|
||||||
|
import { Center, Loader, Stack, TextInput } from "@mantine/core";
|
||||||
|
import { useShallowEffect } from "@mantine/hooks";
|
||||||
|
import { IconSearch } from "@tabler/icons-react";
|
||||||
|
import { useAtom } from "jotai";
|
||||||
|
import _ from "lodash";
|
||||||
|
import { ScrollOnly } from "next-scroll-loader";
|
||||||
|
import { useState } from "react";
|
||||||
|
import {
|
||||||
|
Job_ComponentButtonUpdateBeranda,
|
||||||
|
Job_ComponentSkeletonBeranda,
|
||||||
|
} from "../../component";
|
||||||
|
import ComponentJob_BerandaCardView from "../../component/beranda/card_view";
|
||||||
|
import { MODEL_JOB } from "../../model/interface";
|
||||||
|
import { apiGetJob } from "../../component/api_fetch_job";
|
||||||
|
import { clientLogger } from "@/util/clientLogger";
|
||||||
|
|
||||||
|
export default function Job_ViewBeranda() {
|
||||||
|
const [data, setData] = useState<MODEL_JOB[]>([]);
|
||||||
|
const [activePage, setActivePage] = useState(1);
|
||||||
|
const [isSearch, setIsSearch] = useState("");
|
||||||
|
const [hasMore, setHasMore] = useState(true);
|
||||||
|
const [isLoading, setIsLoading] = useState(false);
|
||||||
|
|
||||||
|
// Notifikasi
|
||||||
|
const [isShowUpdate, setIsShowUpdate] = useState(false);
|
||||||
|
const [isTriggerJob, setIsTriggerJob] = useAtom(gs_jobTiggerBeranda);
|
||||||
|
|
||||||
|
useShallowEffect(() => {
|
||||||
|
if (isTriggerJob == true) {
|
||||||
|
setIsShowUpdate(true);
|
||||||
|
}
|
||||||
|
}, [isTriggerJob]);
|
||||||
|
|
||||||
|
useShallowEffect(() => {
|
||||||
|
setIsTriggerJob(false);
|
||||||
|
setIsShowUpdate(false);
|
||||||
|
onLoadNewData();
|
||||||
|
}, [isSearch]);
|
||||||
|
|
||||||
|
async function onSearch(text: string) {
|
||||||
|
setIsSearch(text);
|
||||||
|
setActivePage(1);
|
||||||
|
setHasMore(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
async function onLoadNewData() {
|
||||||
|
try {
|
||||||
|
setIsLoading(true);
|
||||||
|
const response = await apiGetJob({
|
||||||
|
page: `${activePage}`,
|
||||||
|
search: isSearch,
|
||||||
|
});
|
||||||
|
|
||||||
|
if (response.success) {
|
||||||
|
setData(response.data);
|
||||||
|
setActivePage(1);
|
||||||
|
setHasMore(response.data.length > 0);
|
||||||
|
} else {
|
||||||
|
setData([]);
|
||||||
|
setHasMore(false);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
clientLogger.error("Error get job", error);
|
||||||
|
setData([]);
|
||||||
|
setHasMore(false);
|
||||||
|
} finally {
|
||||||
|
setIsLoading(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleMoreData = async () => {
|
||||||
|
if (!hasMore || isLoading) return null;
|
||||||
|
|
||||||
|
try {
|
||||||
|
const nextPage = activePage + 1;
|
||||||
|
|
||||||
|
const response = await apiGetJob({
|
||||||
|
page: `${nextPage}`,
|
||||||
|
search: isSearch,
|
||||||
|
});
|
||||||
|
|
||||||
|
if (response?.data && response.data.length > 0) {
|
||||||
|
setActivePage(nextPage);
|
||||||
|
setHasMore(response.data.length > 0);
|
||||||
|
return response.data;
|
||||||
|
} else {
|
||||||
|
setHasMore(false);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
clientLogger.error("Error get job", error);
|
||||||
|
setHasMore(false);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Stack spacing={30}>
|
||||||
|
{isShowUpdate && (
|
||||||
|
<Job_ComponentButtonUpdateBeranda
|
||||||
|
onSetIsNewPost={(val) => {
|
||||||
|
setIsShowUpdate(val);
|
||||||
|
setIsTriggerJob(val);
|
||||||
|
}}
|
||||||
|
onSetData={(val: any[]) => {
|
||||||
|
setData(val);
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
)}
|
||||||
|
|
||||||
|
<ComponentGlobal_CreateButton path={RouterJob.create} />
|
||||||
|
|
||||||
|
<TextInput
|
||||||
|
style={{
|
||||||
|
position: "sticky",
|
||||||
|
top: 0,
|
||||||
|
zIndex: 99,
|
||||||
|
}}
|
||||||
|
radius={"xl"}
|
||||||
|
icon={<IconSearch />}
|
||||||
|
placeholder="Pekerjaan apa yang anda cari ?"
|
||||||
|
onChange={(val) => {
|
||||||
|
onSearch(val.currentTarget.value);
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
|
||||||
|
{!data?.length && isLoading ? (
|
||||||
|
<Job_ComponentSkeletonBeranda />
|
||||||
|
) : _.isEmpty(data) ? (
|
||||||
|
<ComponentGlobal_IsEmptyData />
|
||||||
|
) : (
|
||||||
|
// --- Main component --- //
|
||||||
|
<ScrollOnly
|
||||||
|
height="75vh"
|
||||||
|
renderLoading={() => (
|
||||||
|
<Center mt={"lg"}>
|
||||||
|
<Loader color={"yellow"} />
|
||||||
|
</Center>
|
||||||
|
)}
|
||||||
|
data={data}
|
||||||
|
setData={setData as any}
|
||||||
|
moreData={handleMoreData}
|
||||||
|
>
|
||||||
|
{(item) => <ComponentJob_BerandaCardView data={item} />}
|
||||||
|
</ScrollOnly>
|
||||||
|
)}
|
||||||
|
</Stack>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
@@ -102,7 +102,7 @@ export default function Job_ViewBeranda() {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Stack my={1} spacing={30}>
|
<Stack spacing={30}>
|
||||||
{isShowUpdate && (
|
{isShowUpdate && (
|
||||||
<Job_ComponentButtonUpdateBeranda
|
<Job_ComponentButtonUpdateBeranda
|
||||||
onSetIsNewPost={(val) => {
|
onSetIsNewPost={(val) => {
|
||||||
|
|||||||
98
src/app_modules/job/main/new_layout.tsx
Normal file
98
src/app_modules/job/main/new_layout.tsx
Normal file
@@ -0,0 +1,98 @@
|
|||||||
|
"use client";
|
||||||
|
|
||||||
|
import { MainColor } from "@/app_modules/_global/color/color_pallet";
|
||||||
|
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/_global/notif_global/notifikasi_peringatan";
|
||||||
|
import { NewUI_Content } from "@/app_modules/_global/ui/new_ui_content";
|
||||||
|
import { NewUI_Footer } from "@/app_modules/_global/ui/new_ui_footer";
|
||||||
|
import { NewUI_Header } from "@/app_modules/_global/ui/new_ui_header";
|
||||||
|
import { NewUI_Tamplate } from "@/app_modules/_global/ui/new_ui_tamplate";
|
||||||
|
import { RouterHome } from "@/lib/router_hipmi/router_home";
|
||||||
|
import { RouterJob } from "@/lib/router_hipmi/router_job";
|
||||||
|
import { ActionIcon, SimpleGrid, Stack, Text } from "@mantine/core";
|
||||||
|
import { IconHistory, IconHome, IconReservedLine } from "@tabler/icons-react";
|
||||||
|
import { useAtom } from "jotai";
|
||||||
|
import { useRouter } from "next/navigation";
|
||||||
|
import React, { useState } from "react";
|
||||||
|
import { gs_job_hot_menu } from "../global_state";
|
||||||
|
|
||||||
|
export default function NewLayoutJob_Main({
|
||||||
|
children,
|
||||||
|
}: {
|
||||||
|
children: React.ReactNode;
|
||||||
|
}) {
|
||||||
|
const router = useRouter();
|
||||||
|
const [hotMenuId, setHotMenuId] = useAtom(gs_job_hot_menu);
|
||||||
|
const [isLoading, setLoading] = useState(false);
|
||||||
|
|
||||||
|
const listFooter = [
|
||||||
|
{
|
||||||
|
id: 1,
|
||||||
|
name: "Beranda",
|
||||||
|
path: RouterJob.beranda,
|
||||||
|
icon: <IconHome />,
|
||||||
|
},
|
||||||
|
|
||||||
|
{
|
||||||
|
id: 2,
|
||||||
|
name: "Status",
|
||||||
|
path: RouterJob.status({ id: "1" }),
|
||||||
|
icon: <IconReservedLine />,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 3,
|
||||||
|
name: "Arsip",
|
||||||
|
path: RouterJob.arsip,
|
||||||
|
icon: <IconHistory />,
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<NewUI_Tamplate>
|
||||||
|
<NewUI_Header title="Job" routerLeft={RouterHome.main_home} />
|
||||||
|
|
||||||
|
<NewUI_Content>{children}</NewUI_Content>
|
||||||
|
|
||||||
|
<NewUI_Footer>
|
||||||
|
<SimpleGrid cols={3} h={"9vh"} mx={"xs"} w={"100%"}>
|
||||||
|
{listFooter.map((e, i) => (
|
||||||
|
<Stack key={i} align="center" justify="center" spacing={0}>
|
||||||
|
<ActionIcon
|
||||||
|
// disabled={e.path === "" ? true : false}
|
||||||
|
variant="transparent"
|
||||||
|
c={hotMenuId === e.id ? MainColor.yellow : "white"}
|
||||||
|
onClick={() =>
|
||||||
|
e.path === ""
|
||||||
|
? ComponentGlobal_NotifikasiPeringatan("Cooming Soon")
|
||||||
|
: (router.replace(e.path), setHotMenuId(e.id))
|
||||||
|
}
|
||||||
|
>
|
||||||
|
{e.icon}
|
||||||
|
</ActionIcon>
|
||||||
|
<Text
|
||||||
|
c={hotMenuId === e.id ? MainColor.yellow : "white"}
|
||||||
|
fz={"xs"}
|
||||||
|
lineClamp={1}
|
||||||
|
>
|
||||||
|
{e.name}
|
||||||
|
</Text>
|
||||||
|
</Stack>
|
||||||
|
))}
|
||||||
|
</SimpleGrid>
|
||||||
|
</NewUI_Footer>
|
||||||
|
</NewUI_Tamplate>
|
||||||
|
|
||||||
|
{/* <UIGlobal_LayoutTamplate
|
||||||
|
header={
|
||||||
|
<UIGlobal_LayoutHeaderTamplate
|
||||||
|
title="Job"
|
||||||
|
routerLeft={RouterHome.main_home}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
footer={}
|
||||||
|
>
|
||||||
|
{children}
|
||||||
|
</UIGlobal_LayoutTamplate> */}
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user