fix
Deskripsi: - Upload foto profil ke storage - Upload background profile ke storge ## No Issue
This commit is contained in:
@@ -95,6 +95,8 @@ model Profile {
|
||||
Portofolio Portofolio[]
|
||||
ImagesBackground ImagesBackground? @relation(fields: [imagesBackgroundId], references: [id])
|
||||
imagesBackgroundId String? @unique
|
||||
imageId String?
|
||||
imageBackgroundId String?
|
||||
}
|
||||
|
||||
model Images {
|
||||
@@ -925,7 +927,7 @@ model BusinessMaps {
|
||||
Portofolio Portofolio? @relation(fields: [portofolioId], references: [id])
|
||||
portofolioId String? @unique
|
||||
imageId String?
|
||||
pinId String?
|
||||
pinId String?
|
||||
}
|
||||
|
||||
// Kategori App
|
||||
|
||||
@@ -1,9 +1,35 @@
|
||||
"use client";
|
||||
import { Box, Center, Image, Loader, Text } from "@mantine/core";
|
||||
import {
|
||||
ActionIcon,
|
||||
Avatar,
|
||||
Box,
|
||||
Center,
|
||||
Image,
|
||||
Loader,
|
||||
Text,
|
||||
} from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import { useState } from "react";
|
||||
|
||||
export default function Page() {
|
||||
return (
|
||||
<>
|
||||
<Box p={"lg"} bg={"gray"} h={"100vh"}>
|
||||
<Center h={"100%"}>
|
||||
<ActionIcon bg={"blue"}>
|
||||
<Avatar
|
||||
size={100}
|
||||
radius={"100%"}
|
||||
src={
|
||||
// "https://wibu-storage.wibudev.com/api/files/cm1efheqx005vkp7jo7lqarnf"
|
||||
"/aset/global/avatar.png"
|
||||
}
|
||||
/>
|
||||
</ActionIcon>
|
||||
</Center>
|
||||
</Box>
|
||||
</>
|
||||
);
|
||||
return (
|
||||
<>
|
||||
<LoadImage
|
||||
|
||||
@@ -1,8 +1,18 @@
|
||||
import { CreatePortofolio, CreatePortofolioLayout, PortofolioLayout } from "@/app_modules/katalog/portofolio";
|
||||
import { CreatePortofolioLayout } from "@/app_modules/katalog/portofolio";
|
||||
import React from "react";
|
||||
|
||||
export default async function Layout({children, params}: {children: React.ReactNode, params: {id: string}}) {
|
||||
return<>
|
||||
<CreatePortofolioLayout profileId={params.id}>{children}</CreatePortofolioLayout>
|
||||
export default async function Layout({
|
||||
children,
|
||||
params,
|
||||
}: {
|
||||
children: React.ReactNode;
|
||||
params: { id: string };
|
||||
}) {
|
||||
return (
|
||||
<>
|
||||
<CreatePortofolioLayout profileId={params.id}>
|
||||
{children}
|
||||
</CreatePortofolioLayout>
|
||||
</>
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@@ -2,13 +2,14 @@ import { CreatePortofolio } from "@/app_modules/katalog/portofolio";
|
||||
import { Portofolio_getMasterBidangBisnis } from "@/app_modules/katalog/portofolio/fun/master/get_bidang_bisnis";
|
||||
|
||||
export default async function Page({ params }: { params: { id: string } }) {
|
||||
const profileId = params.id;
|
||||
const bidangBisnis = await Portofolio_getMasterBidangBisnis();
|
||||
|
||||
return (
|
||||
<>
|
||||
<CreatePortofolio
|
||||
bidangBisnis={bidangBisnis as any}
|
||||
profileId={params.id}
|
||||
profileId={profileId}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
|
||||
@@ -2,11 +2,9 @@ import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { CreateProfile } from "@/app_modules/katalog/profile";
|
||||
|
||||
export default async function Page() {
|
||||
const userLoginId = await funGetUserIdByToken();
|
||||
|
||||
return (
|
||||
<>
|
||||
<CreateProfile userLoginId={userLoginId} />
|
||||
<CreateProfile />
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1,7 +1,14 @@
|
||||
const APIs = {
|
||||
GET: "https://wibu-storage.wibudev.com/api/files/",
|
||||
/**
|
||||
*
|
||||
* @param fileId | file id from wibu storage , atau bisa disimpan di DB
|
||||
* @param size | file size 10 - 1000 , tergantung ukuran file dan kebutuhan saar di tampilkan
|
||||
* @type {string}
|
||||
*/
|
||||
GET: ({ fileId, size }: { fileId: string; size?: string }) =>
|
||||
size
|
||||
? `https://wibu-storage.wibudev.com/api/files/${fileId}-size-${size}`
|
||||
: `https://wibu-storage.wibudev.com/api/files/${fileId}`,
|
||||
};
|
||||
|
||||
export default APIs
|
||||
|
||||
|
||||
export default APIs;
|
||||
|
||||
44
src/app_modules/_global/button/comp_button_upload_photo.tsx
Normal file
44
src/app_modules/_global/button/comp_button_upload_photo.tsx
Normal file
@@ -0,0 +1,44 @@
|
||||
"use client";
|
||||
|
||||
import { Button, FileButton } from "@mantine/core";
|
||||
import { IconCamera } from "@tabler/icons-react";
|
||||
import { MainColor } from "../color";
|
||||
|
||||
export function ComponentGlobal_ButtonUploadFileImage({
|
||||
onSetFile,
|
||||
onSetImage,
|
||||
}: {
|
||||
onSetFile: File | any;
|
||||
onSetImage: any | null;
|
||||
}) {
|
||||
return (
|
||||
<FileButton
|
||||
onChange={async (files: any | null) => {
|
||||
try {
|
||||
const buffer = URL.createObjectURL(
|
||||
new Blob([new Uint8Array(await files.arrayBuffer())])
|
||||
);
|
||||
|
||||
onSetFile(files);
|
||||
onSetImage(buffer);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}}
|
||||
accept="image/png,image/jpeg"
|
||||
>
|
||||
{(props) => (
|
||||
<Button
|
||||
{...props}
|
||||
radius={"xl"}
|
||||
leftIcon={<IconCamera />}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
>
|
||||
Upload
|
||||
</Button>
|
||||
)}
|
||||
</FileButton>
|
||||
);
|
||||
}
|
||||
@@ -1,14 +1,28 @@
|
||||
import { ComponentGlobal_CardStyles } from "@/app_modules/_global/component";
|
||||
import { Box } from "@mantine/core";
|
||||
|
||||
/**
|
||||
*
|
||||
* @param children
|
||||
* @tutorial |
|
||||
<AspectRatio ratio={1 / 1} mt={5} maw={300} mx={"auto"} >
|
||||
<Image
|
||||
style={{ maxHeight: 250 }}
|
||||
alt="Avatar"
|
||||
src={image ? image : APIs.GET({ fileId: profile.imageId as any })}/>
|
||||
</AspectRatio>
|
||||
* @returns folllow like this
|
||||
*/
|
||||
export function ComponentGlobal_BoxUploadImage({
|
||||
children,
|
||||
height,
|
||||
}: {
|
||||
children: React.ReactNode;
|
||||
height?: number;
|
||||
}) {
|
||||
return (
|
||||
<>
|
||||
<ComponentGlobal_CardStyles height={300}>
|
||||
<ComponentGlobal_CardStyles height={height ? height : 300}>
|
||||
<Box
|
||||
style={{
|
||||
height: "100%",
|
||||
|
||||
@@ -5,14 +5,17 @@ import { useShallowEffect } from "@mantine/hooks";
|
||||
import { useState } from "react";
|
||||
import ComponentGlobal_Loader from "./loader";
|
||||
|
||||
type IRadius = "xs" | "sm" | "md" | "lg" | "xl";
|
||||
export function ComponentGlobal_LoadImage({
|
||||
url,
|
||||
maw,
|
||||
h,
|
||||
radius,
|
||||
}: {
|
||||
url: string;
|
||||
maw?: number;
|
||||
maw?: number | string;
|
||||
h?: number;
|
||||
radius?: IRadius;
|
||||
}) {
|
||||
const [isImage, setIsImage] = useState<boolean | null>(null);
|
||||
|
||||
@@ -34,7 +37,7 @@ export function ComponentGlobal_LoadImage({
|
||||
|
||||
if (isImage === null)
|
||||
return (
|
||||
<Center h={h ? h : 250}>
|
||||
<Center h={250}>
|
||||
<ComponentGlobal_Loader variant="dots" size={50} />
|
||||
</Center>
|
||||
);
|
||||
@@ -42,7 +45,7 @@ export function ComponentGlobal_LoadImage({
|
||||
if (!isImage)
|
||||
return (
|
||||
<>
|
||||
<Center h={250}>
|
||||
<Center h={250} >
|
||||
<Image
|
||||
alt="No Image"
|
||||
maw={150}
|
||||
@@ -56,24 +59,18 @@ export function ComponentGlobal_LoadImage({
|
||||
|
||||
return (
|
||||
<>
|
||||
{h ? (
|
||||
<Image
|
||||
height={h}
|
||||
alt="Image"
|
||||
maw={maw ? maw : 200}
|
||||
m={"auto"}
|
||||
p={"xs"}
|
||||
src={url}
|
||||
/>
|
||||
) : (
|
||||
<Image
|
||||
alt="Image"
|
||||
maw={maw ? maw : 200}
|
||||
m={"auto"}
|
||||
p={"xs"}
|
||||
src={url}
|
||||
/>
|
||||
)}
|
||||
<Box h={h ? h : 250}>
|
||||
<Center h={"100%"}>
|
||||
<Image
|
||||
radius={radius ? radius : 0}
|
||||
alt="Image"
|
||||
maw={maw ? maw : 200}
|
||||
m={"auto"}
|
||||
p={"xs"}
|
||||
src={url}
|
||||
/>
|
||||
</Center>
|
||||
</Box>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import { ComponentGlobal_ButtonUploadFileImage } from "../button/comp_button_upload_photo";
|
||||
import ComponentGlobal_BoxInformation from "./box_information";
|
||||
import ComponentGlobal_AvatarAndAuthorName from "./comp_author_name_and_avatar";
|
||||
import { ComponentGlobal_BoxUploadImage } from "./comp_box_upload_image";
|
||||
@@ -6,6 +7,7 @@ import { ComponentGlobal_LoadImage } from "./comp_load_image";
|
||||
import ComponentGlobal_CardLoadingOverlay from "./comp_loading_card";
|
||||
import ComponentGlobal_TampilanAngkaRatusan from "./comp_tampilan_angka_ratusan";
|
||||
import ComponentGlobal_TampilanRupiah from "./comp_tampilan_rupiah";
|
||||
import ComponentGlobal_ErrorInput from "./error_input";
|
||||
import ComponentGlobal_InputCountDown from "./input_countdown";
|
||||
|
||||
export { ComponentGlobal_TampilanRupiah };
|
||||
@@ -17,3 +19,5 @@ export { ComponentGlobal_InputCountDown };
|
||||
export { ComponentGlobal_CardStyles };
|
||||
export { ComponentGlobal_BoxUploadImage };
|
||||
export { ComponentGlobal_LoadImage };
|
||||
export { ComponentGlobal_ErrorInput };
|
||||
export { ComponentGlobal_ButtonUploadFileImage };
|
||||
|
||||
@@ -19,7 +19,13 @@ export default function AdminJob_DetailPoster({
|
||||
<Stack>
|
||||
<ComponentAdminGlobal_BackButton />
|
||||
<Center>
|
||||
<Image onLoad={() => setLoading(false)} alt="Foto" src={APIs.GET + imageId} mah={500} maw={300} />
|
||||
<Image
|
||||
onLoad={() => setLoading(false)}
|
||||
alt="Foto"
|
||||
src={APIs.GET({ fileId: imageId })}
|
||||
mah={500}
|
||||
maw={300}
|
||||
/>
|
||||
{isLoading ? (
|
||||
<Center h={"100%"}>
|
||||
<ComponentGlobal_Loader size={30} variant="dots" />
|
||||
|
||||
@@ -49,7 +49,7 @@ export function ComponentAdminMap_DetailDataDrawer({
|
||||
radius={"md"}
|
||||
width={300}
|
||||
alt="Photo"
|
||||
src={APIs.GET + data?.imageId}
|
||||
src={APIs.GET({ fileId: data?.imageId as string })}
|
||||
/>
|
||||
</AspectRatio>
|
||||
|
||||
|
||||
@@ -90,8 +90,8 @@ export function UiAdminMap_MapBoxView({
|
||||
}}
|
||||
src={
|
||||
e.pinId === null
|
||||
? APIs.GET + e.Portofolio.logoId
|
||||
: APIs.GET + e.pinId
|
||||
? APIs.GET({ fileId: e.Portofolio.logoId })
|
||||
: APIs.GET({ fileId: e.pinId })
|
||||
}
|
||||
/>
|
||||
</Stack>
|
||||
|
||||
@@ -2,11 +2,15 @@
|
||||
|
||||
import prisma from "@/app/lib/prisma";
|
||||
|
||||
export async function auth_funDeleteAktivasiKodeOtpById(otpId: string) {
|
||||
export async function auth_funDeleteAktivasiKodeOtpById({
|
||||
nomor,
|
||||
}: {
|
||||
nomor: string;
|
||||
}) {
|
||||
// console.log(otpId);
|
||||
const updt = await prisma.kodeOtp.delete({
|
||||
const updt = await prisma.kodeOtp.deleteMany({
|
||||
where: {
|
||||
id: otpId,
|
||||
nomor: nomor,
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
@@ -13,6 +13,9 @@ export async function Auth_funRegister({
|
||||
data: any;
|
||||
HIPMI_PWD: string;
|
||||
}) {
|
||||
const pswd = process.env.WIBU_PWD as string;
|
||||
|
||||
|
||||
const cekUsername = await prisma.user.findUnique({
|
||||
where: {
|
||||
username: data.username,
|
||||
@@ -39,14 +42,14 @@ export async function Auth_funRegister({
|
||||
username: create.username,
|
||||
}),
|
||||
{
|
||||
password: HIPMI_PWD,
|
||||
password: pswd,
|
||||
}
|
||||
);
|
||||
|
||||
cookies().set({
|
||||
name: "ssn",
|
||||
value: sealToken,
|
||||
// maxAge: 60 * 60 * 24 * 7,
|
||||
maxAge: 60 * 60 * 24 * 7,
|
||||
});
|
||||
|
||||
try {
|
||||
|
||||
@@ -13,6 +13,9 @@ export async function auth_funValidasi({
|
||||
nomor: string;
|
||||
HIPMI_PWD: string;
|
||||
}) {
|
||||
const pswd = process.env.WIBU_PWD as string;
|
||||
|
||||
|
||||
const cekUser = await prisma.user.findUnique({
|
||||
where: {
|
||||
nomor: nomor,
|
||||
@@ -34,7 +37,7 @@ export async function auth_funValidasi({
|
||||
username: cekUser.username,
|
||||
}),
|
||||
{
|
||||
password: HIPMI_PWD,
|
||||
password: pswd,
|
||||
}
|
||||
);
|
||||
|
||||
|
||||
@@ -52,7 +52,7 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
|
||||
HIPMI_PWD: GlobalEnv.value?.WIBU_PWD as string,
|
||||
});
|
||||
if (res.status === 200) {
|
||||
await auth_funDeleteAktivasiKodeOtpById(dataOtp.id).then((val) => {
|
||||
await auth_funDeleteAktivasiKodeOtpById({ nomor: nomor }).then((val) => {
|
||||
if (val.status === 200) {
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
setLoading(true);
|
||||
|
||||
@@ -69,7 +69,9 @@ export default function Validasi({ dataOtp }: { dataOtp: any }) {
|
||||
}
|
||||
|
||||
if (res.status === 401) {
|
||||
const resAktivasi = await auth_funDeleteAktivasiKodeOtpById(dataOtp.id);
|
||||
const resAktivasi = await auth_funDeleteAktivasiKodeOtpById({
|
||||
nomor: nomor,
|
||||
});
|
||||
if (resAktivasi.status === 200) {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
router.push(RouterAuth.login, { scroll: false });
|
||||
@@ -77,6 +79,11 @@ export default function Validasi({ dataOtp }: { dataOtp: any }) {
|
||||
}
|
||||
}
|
||||
|
||||
async function onBack() {
|
||||
await auth_funDeleteAktivasiKodeOtpById({ nomor: nomor });
|
||||
router.back();
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<BackgroundImage
|
||||
@@ -93,7 +100,7 @@ export default function Validasi({ dataOtp }: { dataOtp: any }) {
|
||||
top: 0,
|
||||
}}
|
||||
>
|
||||
<ActionIcon variant="transparent" onClick={() => router.back()}>
|
||||
<ActionIcon variant="transparent" onClick={() => onBack()}>
|
||||
<IconChevronLeft color="white" />
|
||||
</ActionIcon>
|
||||
</Box>
|
||||
|
||||
63
src/app_modules/home/component/comp_avatar_profile.tsx
Normal file
63
src/app_modules/home/component/comp_avatar_profile.tsx
Normal file
@@ -0,0 +1,63 @@
|
||||
"use client";
|
||||
|
||||
import ComponentGlobal_Loader from "@/app_modules/_global/component/loader";
|
||||
import { Avatar, Center } from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import { useState } from "react";
|
||||
|
||||
export function Home_ComponentAvatarProfile({ url }: { url: string }) {
|
||||
const [isImage, setIsImage] = useState<boolean | null>(null);
|
||||
|
||||
useShallowEffect(() => {
|
||||
onLoadImage();
|
||||
}, []);
|
||||
|
||||
async function onLoadImage() {
|
||||
try {
|
||||
const res = await fetch(url);
|
||||
if (res.ok) {
|
||||
return setIsImage(true);
|
||||
}
|
||||
setIsImage(false);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}
|
||||
|
||||
if (isImage === null) {
|
||||
<Center>
|
||||
<ComponentGlobal_Loader />
|
||||
</Center>;
|
||||
}
|
||||
|
||||
if (!isImage) {
|
||||
return (
|
||||
<>
|
||||
<Avatar
|
||||
radius={"xl"}
|
||||
size={25}
|
||||
sx={{
|
||||
borderStyle: "solid",
|
||||
borderWidth: "0.5px",
|
||||
borderColor: "white",
|
||||
}}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<Avatar
|
||||
radius={"xl"}
|
||||
size={25}
|
||||
sx={{
|
||||
borderStyle: "solid",
|
||||
borderWidth: "0.5px",
|
||||
borderColor: "white",
|
||||
}}
|
||||
src={url}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
}
|
||||
3
src/app_modules/home/component/index.ts
Normal file
3
src/app_modules/home/component/index.ts
Normal file
@@ -0,0 +1,3 @@
|
||||
import { Home_ComponentAvatarProfile } from "./comp_avatar_profile";
|
||||
|
||||
export { Home_ComponentAvatarProfile };
|
||||
@@ -43,6 +43,8 @@ import { MODEL_JOB } from "@/app_modules/job/model/interface";
|
||||
import { RouterForum } from "@/app/lib/router_hipmi/router_forum";
|
||||
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { RouterMap } from "@/app/lib/router_hipmi/router_map";
|
||||
import { Home_ComponentAvatarProfile } from "./comp_avatar_profile";
|
||||
import { APIs } from "@/app/lib";
|
||||
|
||||
export function Home_UiView({
|
||||
dataUser,
|
||||
@@ -341,18 +343,11 @@ export function Home_UiFooter({ dataUser }: { dataUser: MODEL_USER }) {
|
||||
) : isLoadingProfil ? (
|
||||
<Loader color={AccentColor.yellow} size={20} />
|
||||
) : (
|
||||
<Avatar
|
||||
radius={"xl"}
|
||||
size={25}
|
||||
sx={{
|
||||
borderStyle: "solid",
|
||||
borderWidth: "0.5px",
|
||||
borderColor: "white",
|
||||
}}
|
||||
src={
|
||||
RouterProfile.api_foto_profile +
|
||||
`${dataUser?.Profile.imagesId}`
|
||||
}
|
||||
<Home_ComponentAvatarProfile
|
||||
url={APIs.GET({
|
||||
fileId: dataUser?.Profile?.imageId as string,
|
||||
size: "50"
|
||||
})}
|
||||
/>
|
||||
)}
|
||||
</ActionIcon>
|
||||
|
||||
@@ -45,7 +45,9 @@ export default function ComponentJob_DetailData({
|
||||
<Card.Section px={"xs"} pb={"lg"}>
|
||||
<Stack spacing={"xl"}>
|
||||
{data.imageId ? (
|
||||
<ComponentGlobal_LoadImage url={APIs.GET + data?.imageId} />
|
||||
<ComponentGlobal_LoadImage
|
||||
url={APIs.GET({ fileId: data?.imageId })}
|
||||
/>
|
||||
) : (
|
||||
// <Stack align="center">
|
||||
// {isLoading ? (
|
||||
|
||||
@@ -8,7 +8,7 @@ import {
|
||||
Image,
|
||||
Stack,
|
||||
Text,
|
||||
TextInput
|
||||
TextInput,
|
||||
} from "@mantine/core";
|
||||
import { IconCamera, IconUpload } from "@tabler/icons-react";
|
||||
import { useState } from "react";
|
||||
@@ -19,11 +19,17 @@ import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
} from "@/app_modules/_global/color/color_pallet";
|
||||
import { ComponentGlobal_BoxUploadImage, ComponentGlobal_CardStyles } from "@/app_modules/_global/component";
|
||||
import {
|
||||
ComponentGlobal_BoxUploadImage,
|
||||
ComponentGlobal_CardStyles,
|
||||
} from "@/app_modules/_global/component";
|
||||
import ComponentGlobal_InputCountDown from "@/app_modules/_global/component/input_countdown";
|
||||
import dynamic from "next/dynamic";
|
||||
import "react-quill/dist/quill.snow.css";
|
||||
import { Job_ComponentBoxUploadImage, Job_ComponentButtonUpdate } from "../component";
|
||||
import {
|
||||
Job_ComponentBoxUploadImage,
|
||||
Job_ComponentButtonUpdate,
|
||||
} from "../component";
|
||||
const ReactQuill = dynamic(
|
||||
() => {
|
||||
return import("react-quill");
|
||||
@@ -52,7 +58,7 @@ export default function Job_Edit({ dataJob }: { dataJob: MODEL_JOB }) {
|
||||
style={{ maxHeight: 250, margin: "auto", padding: "5px" }}
|
||||
alt="Foto"
|
||||
height={250}
|
||||
src={img ? img : APIs.GET + value.imageId}
|
||||
src={img ? img : APIs.GET({ fileId: value.imageId })}
|
||||
/>
|
||||
</AspectRatio>
|
||||
) : (
|
||||
@@ -201,5 +207,3 @@ export default function Job_Edit({ dataJob }: { dataJob: MODEL_JOB }) {
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -40,7 +40,7 @@ export default function Job_NonUserView({ data }: { data: MODEL_JOB }) {
|
||||
<Image
|
||||
radius={"sm"}
|
||||
alt=""
|
||||
src={APIs.GET + data.imageId}
|
||||
src={APIs.GET({ fileId: data.imageId })}
|
||||
maw={200}
|
||||
/>
|
||||
</Stack>
|
||||
|
||||
@@ -1,4 +1,7 @@
|
||||
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
|
||||
import {
|
||||
RouterPortofolio,
|
||||
RouterProfile,
|
||||
} from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { AccentColor } from "@/app_modules/_global/color/color_pallet";
|
||||
import ComponentGlobal_Loader from "@/app_modules/_global/component/loader";
|
||||
import Component_Logout from "@/app_modules/auth/logout/view";
|
||||
@@ -12,9 +15,10 @@ import {
|
||||
} from "@mantine/core";
|
||||
import {
|
||||
IconEdit,
|
||||
IconPencilPlus,
|
||||
IconPhotoEdit,
|
||||
IconPolaroid,
|
||||
IconX
|
||||
IconX,
|
||||
} from "@tabler/icons-react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
@@ -41,16 +45,22 @@ export function ComponentKatalog_DrawerKatalog({
|
||||
},
|
||||
{
|
||||
id: "2",
|
||||
name: "Ubah Foto Profile",
|
||||
name: "Ubah foto profile",
|
||||
icon: <IconPhotoEdit />,
|
||||
path: RouterProfile.update_foto_profile + profileId,
|
||||
},
|
||||
{
|
||||
id: "3",
|
||||
name: "Ubah Latar Belakang",
|
||||
name: "Ubah latar belakang",
|
||||
icon: <IconPolaroid />,
|
||||
path: RouterProfile.update_foto_background + profileId,
|
||||
},
|
||||
{
|
||||
id: "4",
|
||||
name: "Tambah portofolio",
|
||||
icon: <IconPencilPlus />,
|
||||
path: RouterPortofolio.create + profileId,
|
||||
},
|
||||
];
|
||||
|
||||
return (
|
||||
@@ -95,12 +105,16 @@ export function ComponentKatalog_DrawerKatalog({
|
||||
variant="transparent"
|
||||
c="white"
|
||||
onClick={() => {
|
||||
router.push(e.path);
|
||||
router.push(e.path, { scroll: false });
|
||||
setPageId(e?.id);
|
||||
setIsLoading(true)
|
||||
setIsLoading(true);
|
||||
}}
|
||||
>
|
||||
{isLoading && e.id === pageId ? <ComponentGlobal_Loader /> : e.icon}
|
||||
{isLoading && e.id === pageId ? (
|
||||
<ComponentGlobal_Loader />
|
||||
) : (
|
||||
e.icon
|
||||
)}
|
||||
</ActionIcon>
|
||||
<Text align="center" color="white">
|
||||
{e.name}
|
||||
|
||||
@@ -1,9 +1,8 @@
|
||||
"use client";
|
||||
|
||||
import { Header, Group, ActionIcon, Text, Title } from "@mantine/core";
|
||||
import { IconArrowLeft, IconChevronLeft } from "@tabler/icons-react";
|
||||
import { ActionIcon, Group, Header, Title } from "@mantine/core";
|
||||
import { IconChevronLeft } from "@tabler/icons-react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
|
||||
export default function ComponentKatalog_HeaderTamplate({
|
||||
hideBack,
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
import { validRegex } from "./regular_expressions";
|
||||
|
||||
export { validRegex };
|
||||
|
||||
@@ -61,7 +61,10 @@ export function ComponentPortofolio_DetailDataMap({ mapId }: { mapId: any }) {
|
||||
{ maxWidth: 600, cols: 1, spacing: "sm" },
|
||||
]}
|
||||
>
|
||||
<ComponentGlobal_LoadImage maw={200} url={APIs.GET + data.imageId} />
|
||||
<ComponentGlobal_LoadImage
|
||||
maw={200}
|
||||
url={APIs.GET({ fileId: data?.imageId })}
|
||||
/>
|
||||
{/* <Image
|
||||
radius={"sm"}
|
||||
mah={300}
|
||||
|
||||
@@ -37,7 +37,9 @@ export default function Portofolio_EditLogoBisnis({
|
||||
{img ? (
|
||||
<Image maw={250} alt="Image" src={img} />
|
||||
) : (
|
||||
<ComponentGlobal_LoadImage url={APIs.GET + dataPorto.logoId} />
|
||||
<ComponentGlobal_LoadImage
|
||||
url={APIs.GET({ fileId: dataPorto.logoId })}
|
||||
/>
|
||||
)}
|
||||
|
||||
<Center>
|
||||
|
||||
@@ -3,13 +3,12 @@ import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
} from "@/app_modules/_global/color/color_pallet";
|
||||
import { ComponentGlobal_LoadImage } from "@/app_modules/_global/component";
|
||||
import {
|
||||
AspectRatio,
|
||||
Box,
|
||||
Divider,
|
||||
Grid,
|
||||
Group,
|
||||
Image,
|
||||
Paper,
|
||||
SimpleGrid,
|
||||
Stack,
|
||||
@@ -24,7 +23,6 @@ import {
|
||||
IconPinned,
|
||||
} from "@tabler/icons-react";
|
||||
import { MODEL_PORTOFOLIO } from "../model/interface";
|
||||
import { ComponentGlobal_LoadImage } from "@/app_modules/_global/component";
|
||||
|
||||
export function Portofolio_UiDetailData({
|
||||
dataPorto,
|
||||
@@ -65,7 +63,9 @@ export function Portofolio_UiDetailData({
|
||||
>
|
||||
<Box>
|
||||
<Paper>
|
||||
<ComponentGlobal_LoadImage url={APIs.GET + dataPorto.logoId}/>
|
||||
<ComponentGlobal_LoadImage
|
||||
url={APIs.GET({ fileId: dataPorto.logoId })}
|
||||
/>
|
||||
{/* <AspectRatio ratio={1 / 1} mah={250} mx={"auto"}>
|
||||
<Image
|
||||
// style={{ maxHeight: 200, margin: "auto", padding: "5px" }}
|
||||
|
||||
@@ -99,7 +99,9 @@ function MapView({
|
||||
<Stack spacing={0} align="center">
|
||||
<Avatar
|
||||
src={
|
||||
data.pinId === null ? APIs.GET + logoId : APIs.GET + data.pinId
|
||||
data.pinId === null
|
||||
? APIs.GET({ fileId: logoId })
|
||||
: APIs.GET({ fileId: data.pinId })
|
||||
}
|
||||
alt="Logo"
|
||||
style={{
|
||||
|
||||
@@ -0,0 +1,73 @@
|
||||
import { MainColor } from "@/app_modules/_global/color";
|
||||
import {
|
||||
ComponentGlobal_NotifikasiBerhasil,
|
||||
ComponentGlobal_NotifikasiGagal,
|
||||
ComponentGlobal_NotifikasiPeringatan,
|
||||
} from "@/app_modules/_global/notif_global";
|
||||
import { Box, Button } from "@mantine/core";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { profile_funUpdateBackground } from "../../fun/update/fun_update_background";
|
||||
import { DIRECTORY_ID } from "@/app/lib";
|
||||
import { funGlobal_UploadToStorage } from "@/app_modules/_global/fun";
|
||||
|
||||
export function Profile_ComponentButtonUpdateBackgroundProfile({
|
||||
profileId,
|
||||
file,
|
||||
}: {
|
||||
profileId: string;
|
||||
file: File;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [loading, setLoading] = useState(false);
|
||||
async function onUpdate() {
|
||||
const uploadFile = await funGlobal_UploadToStorage({
|
||||
file: file,
|
||||
dirId: DIRECTORY_ID.profile_background,
|
||||
});
|
||||
if (!uploadFile.success)
|
||||
return ComponentGlobal_NotifikasiPeringatan("Gagal upload foto profile");
|
||||
|
||||
const res = await profile_funUpdateBackground({
|
||||
profileId: profileId,
|
||||
fileId: uploadFile.data.id,
|
||||
});
|
||||
if (res.status === 200) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
router.back();
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(res.message);
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<Box
|
||||
style={{
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
}}
|
||||
>
|
||||
<Button
|
||||
style={{
|
||||
transition: "all 0.3s ease",
|
||||
position: "absolute",
|
||||
bottom: 20,
|
||||
width: 300,
|
||||
}}
|
||||
disabled={file ? false : true}
|
||||
loading={loading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"xl"}
|
||||
onClick={() => onUpdate()}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
>
|
||||
Update
|
||||
</Button>
|
||||
</Box>
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -0,0 +1,76 @@
|
||||
"use client";
|
||||
|
||||
import { MainColor } from "@/app_modules/_global/color";
|
||||
import {
|
||||
ComponentGlobal_NotifikasiBerhasil,
|
||||
ComponentGlobal_NotifikasiGagal,
|
||||
ComponentGlobal_NotifikasiPeringatan,
|
||||
} from "@/app_modules/_global/notif_global";
|
||||
import { Box, Button, Center } from "@mantine/core";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { profile_funUpdatePhoto } from "../../fun";
|
||||
import { funGlobal_UploadToStorage } from "@/app_modules/_global/fun";
|
||||
import { DIRECTORY_ID } from "@/app/lib";
|
||||
|
||||
export function Profile_ComponentButtonUpdatePhotoProfile({
|
||||
file,
|
||||
profileId,
|
||||
}: {
|
||||
file: File;
|
||||
profileId: string;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [isLoading, setLoading] = useState(false);
|
||||
async function onUpdate() {
|
||||
const uploadPhoto = await funGlobal_UploadToStorage({
|
||||
file: file,
|
||||
dirId: DIRECTORY_ID.profile_foto,
|
||||
});
|
||||
if (!uploadPhoto.success)
|
||||
return ComponentGlobal_NotifikasiPeringatan("Gagal upload foto profile");
|
||||
|
||||
const res = await profile_funUpdatePhoto({
|
||||
fileId: uploadPhoto.data.id,
|
||||
profileId: profileId,
|
||||
});
|
||||
if (res.status === 200) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
router.back();
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(res.message);
|
||||
}
|
||||
}
|
||||
return (
|
||||
<>
|
||||
<Box
|
||||
style={{
|
||||
display: "flex",
|
||||
justifyContent: "center",
|
||||
}}
|
||||
>
|
||||
<Button
|
||||
style={{
|
||||
transition: "all 0.3s ease",
|
||||
position: "absolute",
|
||||
bottom: 20,
|
||||
width: 300,
|
||||
}}
|
||||
disabled={file ? false : true}
|
||||
loading={isLoading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"xl"}
|
||||
onClick={() => {
|
||||
onUpdate();
|
||||
}}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
>
|
||||
Update
|
||||
</Button>
|
||||
</Box>
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -1,69 +1,81 @@
|
||||
"use client";
|
||||
|
||||
import { DIRECTORY_ID } from "@/app/lib";
|
||||
import { RouterHome } from "@/app/lib/router_hipmi/router_home";
|
||||
import { MainColor, AccentColor } from "@/app_modules/_global/color";
|
||||
import { AccentColor, MainColor } from "@/app_modules/_global/color";
|
||||
import { funGlobal_UploadToStorage } from "@/app_modules/_global/fun";
|
||||
import {
|
||||
ComponentGlobal_NotifikasiPeringatan,
|
||||
ComponentGlobal_NotifikasiBerhasil,
|
||||
ComponentGlobal_NotifikasiGagal,
|
||||
ComponentGlobal_NotifikasiPeringatan,
|
||||
} from "@/app_modules/_global/notif_global";
|
||||
import { validRegex } from "@/app_modules/katalog/component/regular_expressions";
|
||||
import { Button } from "@mantine/core";
|
||||
import _ from "lodash";
|
||||
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import funCreateNewProfile from "../../fun/fun_create_profile";
|
||||
import { MODEL_PROFILE } from "../../model/interface";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { validRegex } from "@/app_modules/katalog/component";
|
||||
|
||||
export function Profile_ComponentCreateNewProfile({
|
||||
value,
|
||||
userLoginId,
|
||||
filePP,
|
||||
fileBg,
|
||||
fileBG,
|
||||
}: {
|
||||
value: MODEL_PROFILE;
|
||||
userLoginId: string;
|
||||
filePP: FormData;
|
||||
fileBg: FormData;
|
||||
filePP: File;
|
||||
fileBG: File;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
async function onSubmit() {
|
||||
const body = {
|
||||
userId: userLoginId,
|
||||
const newData = {
|
||||
name: value.name,
|
||||
email: value.email,
|
||||
alamat: value.alamat,
|
||||
jenisKelamin: value.jenisKelamin,
|
||||
};
|
||||
if (_.values(body).includes(""))
|
||||
if (_.values(newData).includes(""))
|
||||
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Data");
|
||||
if (!body.email.match(validRegex)) return null;
|
||||
if (!newData.email.match(validRegex)) return null;
|
||||
|
||||
const gambarPP = new FormData();
|
||||
gambarPP.append("filePP", filePP as any);
|
||||
|
||||
const gambarBG = new FormData();
|
||||
gambarBG.append("fileBG", fileBg as any);
|
||||
|
||||
if (!gambarPP)
|
||||
if (filePP == null)
|
||||
return ComponentGlobal_NotifikasiPeringatan("Lengkapi foto profile");
|
||||
if (!gambarBG)
|
||||
if (fileBG == null)
|
||||
return ComponentGlobal_NotifikasiPeringatan(
|
||||
"Lengkapi background profile"
|
||||
);
|
||||
|
||||
await funCreateNewProfile(body as any, gambarPP, gambarBG).then((res) => {
|
||||
if (res.status === 201) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil("Berhasil Membuat Profile", 3000);
|
||||
router.push(RouterHome.main_home, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(res.message);
|
||||
}
|
||||
const uploadPhoto = await funGlobal_UploadToStorage({
|
||||
file: filePP,
|
||||
dirId: DIRECTORY_ID.profile_foto,
|
||||
});
|
||||
if (!uploadPhoto.success)
|
||||
return ComponentGlobal_NotifikasiPeringatan("Gagal upload foto profile");
|
||||
|
||||
const uploadBackground = await funGlobal_UploadToStorage({
|
||||
file: fileBG,
|
||||
dirId: DIRECTORY_ID.profile_background,
|
||||
});
|
||||
if (!uploadBackground.success)
|
||||
return ComponentGlobal_NotifikasiPeringatan(
|
||||
"Gagal upload background profile"
|
||||
);
|
||||
|
||||
const create = await funCreateNewProfile({
|
||||
data: newData as any,
|
||||
imageId: uploadPhoto.data.id,
|
||||
imageBackgroundId: uploadBackground.data.id,
|
||||
});
|
||||
|
||||
if (create.status === 201) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil("Berhasil membuat profile", 3000);
|
||||
router.push(RouterHome.main_home, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(create.message);
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
"use client";
|
||||
|
||||
import { AccentColor } from "@/app_modules/_global/color";
|
||||
import ComponentGlobal_Loader from "@/app_modules/_global/component/loader";
|
||||
import { Avatar, Box, Center, Image, Paper, Skeleton } from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import { CSSProperties, useState } from "react";
|
||||
|
||||
export function Profile_ComponentAvatarProfile({
|
||||
url,
|
||||
style,
|
||||
}: {
|
||||
url: string;
|
||||
style?: CSSProperties;
|
||||
}) {
|
||||
const [isImage, setIsImage] = useState<boolean | null>(null);
|
||||
|
||||
useShallowEffect(() => {
|
||||
onLoadImage();
|
||||
}, []);
|
||||
|
||||
async function onLoadImage() {
|
||||
try {
|
||||
const res = await fetch(url);
|
||||
if (res.ok) {
|
||||
return setIsImage(true);
|
||||
}
|
||||
setIsImage(false);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}
|
||||
|
||||
if (isImage === null) {
|
||||
return (
|
||||
<Skeleton
|
||||
style={{ borderStyle: "solid", borderColor: AccentColor.darkblue }}
|
||||
radius={"50%"}
|
||||
h={100}
|
||||
w={100}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
if (!isImage) {
|
||||
return (
|
||||
<>
|
||||
<Avatar
|
||||
variant="outline"
|
||||
size={100}
|
||||
bg={"gray"}
|
||||
radius={"50%"}
|
||||
style={style}
|
||||
>
|
||||
<Image
|
||||
alt="Avatar"
|
||||
height={100}
|
||||
width={100}
|
||||
src={"/aset/global/avatar.png"}
|
||||
/>
|
||||
</Avatar>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<Avatar
|
||||
bg={"white"}
|
||||
style={style}
|
||||
radius={"50%"}
|
||||
size={100}
|
||||
sx={{
|
||||
borderStyle: "solid",
|
||||
borderWidth: "0.5px",
|
||||
borderColor: "white",
|
||||
}}
|
||||
src={url}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
"use client";
|
||||
|
||||
import { AspectRatio, Box, Center, Image, Skeleton } from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import { useState } from "react";
|
||||
|
||||
type IRadius = "xs" | "sm" | "md" | "lg" | "xl";
|
||||
export function Profile_ComponentLoadBackgroundImage({
|
||||
url,
|
||||
radius,
|
||||
}: {
|
||||
url: string;
|
||||
radius?: IRadius;
|
||||
}) {
|
||||
const [isImage, setIsImage] = useState<boolean | null>(null);
|
||||
|
||||
useShallowEffect(() => {
|
||||
onLoadImage();
|
||||
}, []);
|
||||
|
||||
async function onLoadImage() {
|
||||
try {
|
||||
const res = await fetch(url);
|
||||
if (res.ok) {
|
||||
return setIsImage(true);
|
||||
}
|
||||
setIsImage(false);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}
|
||||
|
||||
if (isImage === null) return <Skeleton h={200} w={"100%"} />;
|
||||
|
||||
if (!isImage)
|
||||
return (
|
||||
<>
|
||||
<Center h={200} bg={"white"} style={{borderRadius: "10px"}} >
|
||||
<Image
|
||||
alt="No Image"
|
||||
maw={150}
|
||||
m={"auto"}
|
||||
p={"xs"}
|
||||
src={"/aset/global/no-image.svg"}
|
||||
/>
|
||||
</Center>
|
||||
</>
|
||||
);
|
||||
|
||||
return (
|
||||
<>
|
||||
<Image height={200} radius={radius ? radius : 0} alt="Image" src={url} />
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -1,3 +1,11 @@
|
||||
import { Profile_ComponentButtonUpdateBackgroundProfile } from "./button/comp_button_update_background_profile";
|
||||
import { Profile_ComponentButtonUpdatePhotoProfile } from "./button/comp_button_update_photo_profile";
|
||||
import { Profile_ComponentCreateNewProfile } from "./button/comp_create_new_profile";
|
||||
import { Profile_ComponentAvatarProfile } from "./comp_load_avatar";
|
||||
import { Profile_ComponentLoadBackgroundImage } from "./comp_load_background";
|
||||
|
||||
export {Profile_ComponentCreateNewProfile}
|
||||
export { Profile_ComponentCreateNewProfile };
|
||||
export { Profile_ComponentAvatarProfile };
|
||||
export { Profile_ComponentLoadBackgroundImage };
|
||||
export { Profile_ComponentButtonUpdateBackgroundProfile };
|
||||
export { Profile_ComponentButtonUpdatePhotoProfile };
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
"use client";
|
||||
|
||||
import { MainColor } from "@/app_modules/_global/color/color_pallet";
|
||||
import { ComponentGlobal_BoxUploadImage } from "@/app_modules/_global/component";
|
||||
import ComponentGlobal_BoxInformation from "@/app_modules/_global/component/box_information";
|
||||
import ComponentGlobal_ErrorInput from "@/app_modules/_global/component/error_input";
|
||||
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/_global/notif_global/notifikasi_peringatan";
|
||||
import {
|
||||
ComponentGlobal_BoxInformation,
|
||||
ComponentGlobal_BoxUploadImage,
|
||||
ComponentGlobal_ErrorInput,
|
||||
} from "@/app_modules/_global/component";
|
||||
import {
|
||||
AspectRatio,
|
||||
Avatar,
|
||||
@@ -21,14 +21,12 @@ import {
|
||||
} from "@mantine/core";
|
||||
import { IconAt, IconCamera, IconUpload } from "@tabler/icons-react";
|
||||
import { useState } from "react";
|
||||
import { validRegex } from "../../component/regular_expressions";
|
||||
import { Profile_ComponentCreateNewProfile } from "../_component";
|
||||
import { validRegex } from "../../component";
|
||||
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/_global/notif_global";
|
||||
import { MainColor } from "@/app_modules/_global/color";
|
||||
|
||||
export default function CreateProfile({
|
||||
userLoginId,
|
||||
}: {
|
||||
userLoginId: string;
|
||||
}) {
|
||||
export default function CreateProfile() {
|
||||
const [filePP, setFilePP] = useState<File | null>(null);
|
||||
const [imgPP, setImgPP] = useState<any | null>();
|
||||
const [fileBG, setFileBG] = useState<File | null>(null);
|
||||
@@ -45,7 +43,7 @@ export default function CreateProfile({
|
||||
<>
|
||||
<Stack px={"sm"} spacing={40}>
|
||||
<Box>
|
||||
<Stack spacing={"xs"}>
|
||||
<Stack spacing={"lg"}>
|
||||
<ComponentGlobal_BoxInformation informasi="Upload foto profile anda." />
|
||||
<Center>
|
||||
{imgPP ? (
|
||||
@@ -78,6 +76,7 @@ export default function CreateProfile({
|
||||
</Paper>
|
||||
)}
|
||||
</Center>
|
||||
|
||||
<Center>
|
||||
<FileButton
|
||||
onChange={async (files: any | null) => {
|
||||
@@ -118,7 +117,7 @@ export default function CreateProfile({
|
||||
</Box>
|
||||
|
||||
<Box>
|
||||
<Stack spacing={"xs"}>
|
||||
<Stack spacing={"lg"}>
|
||||
<ComponentGlobal_BoxInformation informasi="Upload foto latar belakang profile anda." />
|
||||
<ComponentGlobal_BoxUploadImage>
|
||||
{imgBG ? (
|
||||
@@ -257,9 +256,8 @@ export default function CreateProfile({
|
||||
|
||||
<Profile_ComponentCreateNewProfile
|
||||
value={value as any}
|
||||
userLoginId={userLoginId}
|
||||
filePP={filePP as any}
|
||||
fileBg={fileBG as any}
|
||||
fileBG={fileBG as any}
|
||||
/>
|
||||
</Stack>
|
||||
</Stack>
|
||||
|
||||
@@ -7,82 +7,37 @@ import { v4 } from "uuid";
|
||||
import fs from "fs";
|
||||
import { revalidatePath } from "next/cache";
|
||||
import { RouterHome } from "@/app/lib/router_hipmi/router_home";
|
||||
import { Prisma } from "@prisma/client";
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
|
||||
export default async function funCreateNewProfile(
|
||||
req: MODEL_PROFILE,
|
||||
gambarPP: FormData,
|
||||
gambarBG: FormData
|
||||
) {
|
||||
const body = req;
|
||||
export default async function funCreateNewProfile({
|
||||
data,
|
||||
imageId,
|
||||
imageBackgroundId,
|
||||
}: {
|
||||
data: Prisma.ProfileCreateInput;
|
||||
imageId: string;
|
||||
imageBackgroundId: string;
|
||||
}) {
|
||||
const userLoginId = await funGetUserIdByToken();
|
||||
|
||||
const findEmail = await prisma.profile.findUnique({
|
||||
where: {
|
||||
email: body.email,
|
||||
email: data.email,
|
||||
},
|
||||
});
|
||||
|
||||
if (findEmail) return { status: 400, message: "Email telah digunakan" };
|
||||
|
||||
const gambarProfile: any = gambarPP.get("filePP");
|
||||
|
||||
if (gambarProfile === "null")
|
||||
return { status: 400, message: "Lengkapi Foto Profile" };
|
||||
|
||||
const fileName = gambarProfile.name;
|
||||
const fileExtension = _.lowerCase(gambarProfile.name.split(".").pop());
|
||||
const fRandomName = v4(fileName) + "." + fileExtension;
|
||||
|
||||
const uploadPP = await prisma.images.create({
|
||||
data: {
|
||||
url: fRandomName,
|
||||
label: "PROFILE_FOTO",
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
url: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (!uploadPP) return { status: 400, message: "Gagal upload foto profile" };
|
||||
const uploadPP_Folder = Buffer.from(await gambarProfile.arrayBuffer());
|
||||
fs.writeFileSync(`./public/profile/foto/${uploadPP.url}`, uploadPP_Folder);
|
||||
|
||||
const gambarBackground: any = gambarBG.get("fileBG");
|
||||
if (gambarBackground === "null")
|
||||
return { status: 400, message: "Lengkapi Foto Background" };
|
||||
|
||||
const fileNameBG = gambarBackground.name;
|
||||
const fileExtensionBG = _.lowerCase(gambarBackground.name.split(".").pop());
|
||||
const fRandomNameBG = v4(fileNameBG) + "." + fileExtensionBG;
|
||||
|
||||
const uploadBG = await prisma.imagesBackground.create({
|
||||
data: {
|
||||
url: fRandomNameBG,
|
||||
label: "PROFILE_BACKGROUND",
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
url: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (!uploadBG)
|
||||
return { status: 400, message: "Gagal upload background profile" };
|
||||
const uploadBG_Folder = Buffer.from(await gambarBackground.arrayBuffer());
|
||||
fs.writeFileSync(
|
||||
`./public/profile/background/${uploadBG.url}`,
|
||||
uploadBG_Folder
|
||||
);
|
||||
|
||||
const createProfile = await prisma.profile.create({
|
||||
data: {
|
||||
userId: body.userId,
|
||||
name: body.name,
|
||||
email: body.email,
|
||||
alamat: body.alamat,
|
||||
jenisKelamin: body.jenisKelamin,
|
||||
imagesId: uploadPP.id,
|
||||
imagesBackgroundId: uploadBG.id,
|
||||
userId: userLoginId,
|
||||
name: data.name,
|
||||
email: data.email,
|
||||
alamat: data.alamat,
|
||||
jenisKelamin: data.jenisKelamin,
|
||||
imageId: imageId,
|
||||
imageBackgroundId: imageBackgroundId,
|
||||
},
|
||||
});
|
||||
|
||||
|
||||
@@ -7,18 +7,8 @@ export async function Profile_getOneProfileAndUserById(profileId: string) {
|
||||
where: {
|
||||
id: profileId,
|
||||
},
|
||||
select: {
|
||||
userId: true,
|
||||
include: {
|
||||
User: true,
|
||||
id: true,
|
||||
name: true,
|
||||
email: true,
|
||||
alamat: true,
|
||||
jenisKelamin: true,
|
||||
imagesId: true,
|
||||
imagesBackgroundId: true,
|
||||
ImageProfile: true,
|
||||
ImagesBackground: true,
|
||||
},
|
||||
});
|
||||
// console.log(data)
|
||||
|
||||
3
src/app_modules/katalog/profile/fun/index.ts
Normal file
3
src/app_modules/katalog/profile/fun/index.ts
Normal file
@@ -0,0 +1,3 @@
|
||||
import { profile_funUpdatePhoto } from "./update/fun_update_foto_profile";
|
||||
|
||||
export { profile_funUpdatePhoto };
|
||||
@@ -1,47 +1,21 @@
|
||||
"use server";
|
||||
|
||||
import fs from "fs";
|
||||
import prisma from "@/app/lib/prisma";
|
||||
import _ from "lodash";
|
||||
import { v4 } from "uuid";
|
||||
import { revalidatePath } from "next/cache";
|
||||
|
||||
export async function Profile_funUpdateBackground(
|
||||
profileId: string,
|
||||
file: FormData
|
||||
) {
|
||||
const gambarBackground: any = file.get("file");
|
||||
const fileName = gambarBackground.name;
|
||||
const fileExtension = _.lowerCase(gambarBackground.name.split(".").pop());
|
||||
const fRandomName = v4(fileName) + "." + fileExtension;
|
||||
|
||||
const uploadBG = await prisma.imagesBackground.create({
|
||||
data: {
|
||||
url: fRandomName,
|
||||
label: "PROFILE_BACKGROUND",
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
url: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (!uploadBG)
|
||||
return { status: 400, message: "Gagal upload gambar background" };
|
||||
const uploadBG_Folder = Buffer.from(await gambarBackground.arrayBuffer());
|
||||
fs.writeFileSync(
|
||||
`./public/profile/background/${uploadBG.url}`,
|
||||
uploadBG_Folder
|
||||
);
|
||||
|
||||
revalidatePath("/dev/katalog");
|
||||
|
||||
export async function profile_funUpdateBackground({
|
||||
profileId,
|
||||
fileId,
|
||||
}: {
|
||||
profileId: string;
|
||||
fileId: string;
|
||||
}) {
|
||||
const updateBackground = await prisma.profile.update({
|
||||
where: {
|
||||
id: profileId,
|
||||
},
|
||||
data: {
|
||||
imagesBackgroundId: uploadBG.id,
|
||||
imageBackgroundId: fileId,
|
||||
},
|
||||
});
|
||||
|
||||
@@ -53,50 +27,4 @@ export async function Profile_funUpdateBackground(
|
||||
status: 200,
|
||||
message: "Update berhasil",
|
||||
};
|
||||
|
||||
// const findProfile = await prisma.profile.findFirst({
|
||||
// where: {
|
||||
// id: profileId,
|
||||
// },
|
||||
// });
|
||||
|
||||
// const findBackground = await prisma.imagesBackground.findFirst({
|
||||
// where: {
|
||||
// id: findProfile?.imagesBackgroundId as string,
|
||||
// },
|
||||
// select: {
|
||||
// url: true,
|
||||
// },
|
||||
// });
|
||||
// if (!findBackground) return { status: 400, message: "Foto tidak ditemukan" };
|
||||
// if (findBackground) fs.unlinkSync(`./public/profile/background/${findBackground.url}`);
|
||||
|
||||
// const gambarBackground: any = file.get("file");
|
||||
// const fileName = gambarBackground.name;
|
||||
// const fileExtension = _.lowerCase(gambarBackground.name.split(".").pop());
|
||||
// const randomName = v4(fileName) + "." + fileExtension;
|
||||
|
||||
// const uploadBG = await prisma.imagesBackground.update({
|
||||
// where: {
|
||||
// id: findProfile?.imagesBackgroundId as string,
|
||||
// },
|
||||
// data: {
|
||||
// url: randomName,
|
||||
// label: "PROFILE_BACKGROUND",
|
||||
// },
|
||||
// select: {
|
||||
// id: true,
|
||||
// url: true,
|
||||
// },
|
||||
// });
|
||||
|
||||
// if (!uploadBG) return { status: 400, message: "Gagal upload foto background" };
|
||||
// const uploadBG_Folder = Buffer.from(await gambarBackground.arrayBuffer());
|
||||
// fs.writeFileSync(`./public/profile/background/${uploadBG.url}`, uploadBG_Folder);
|
||||
// revalidatePath("/dev/katalog");
|
||||
|
||||
// return {
|
||||
// status: 200,
|
||||
// message: "Update berhasil",
|
||||
// };
|
||||
}
|
||||
|
||||
@@ -1,38 +1,21 @@
|
||||
"use server";
|
||||
|
||||
import fs from "fs";
|
||||
import prisma from "@/app/lib/prisma";
|
||||
import _ from "lodash";
|
||||
import { v4 } from "uuid";
|
||||
import { revalidatePath } from "next/cache";
|
||||
|
||||
export async function Profile_funUpdateFoto(profileId: string, file: FormData) {
|
||||
const gambarProfile: any = file.get("file");
|
||||
const fileName = gambarProfile.name;
|
||||
const fileExtension = _.lowerCase(gambarProfile.name.split(".").pop());
|
||||
const fRandomName = v4(fileName) + "." + fileExtension;
|
||||
|
||||
const uploadPP = await prisma.images.create({
|
||||
data: {
|
||||
url: fRandomName,
|
||||
label: "PROFILE_FOTO",
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
url: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (!uploadPP) return { status: 400, message: "Gagal upload foto profile" };
|
||||
const uploadPP_Folder = Buffer.from(await gambarProfile.arrayBuffer());
|
||||
fs.writeFileSync(`./public/profile/foto/${uploadPP.url}`, uploadPP_Folder);
|
||||
|
||||
export async function profile_funUpdatePhoto({
|
||||
profileId,
|
||||
fileId,
|
||||
}: {
|
||||
profileId: string;
|
||||
fileId: string;
|
||||
}) {
|
||||
const updateProfile = await prisma.profile.update({
|
||||
where: {
|
||||
id: profileId,
|
||||
},
|
||||
data: {
|
||||
imagesId: uploadPP.id,
|
||||
imageId: fileId,
|
||||
},
|
||||
});
|
||||
|
||||
@@ -43,52 +26,4 @@ export async function Profile_funUpdateFoto(profileId: string, file: FormData) {
|
||||
status: 200,
|
||||
message: "Update berhasil",
|
||||
};
|
||||
|
||||
|
||||
|
||||
// const findProfile = await prisma.profile.findFirst({
|
||||
// where: {
|
||||
// id: profileId,
|
||||
// },
|
||||
// });
|
||||
|
||||
// const findFoto = await prisma.images.findFirst({
|
||||
// where: {
|
||||
// id: findProfile?.imagesId as string,
|
||||
// },
|
||||
// select: {
|
||||
// url: true,
|
||||
// },
|
||||
// });
|
||||
// if (!findFoto) return { status: 400, message: "Foto tidak ditemukan" };
|
||||
// if (findFoto) fs.unlinkSync(`./public/profile/foto/${findFoto.url}`);
|
||||
|
||||
// const gambarProfile: any = file.get("file");
|
||||
// const fileName = gambarProfile.name;
|
||||
// const fileExtension = _.lowerCase(gambarProfile.name.split(".").pop());
|
||||
// const randomName = v4(fileName) + "." + fileExtension;
|
||||
|
||||
// const uploadPP = await prisma.images.update({
|
||||
// where: {
|
||||
// id: findProfile?.imagesId as string,
|
||||
// },
|
||||
// data: {
|
||||
// url: randomName,
|
||||
// label: "PROFILE_FOTO",
|
||||
// },
|
||||
// select: {
|
||||
// id: true,
|
||||
// url: true,
|
||||
// },
|
||||
// });
|
||||
|
||||
// if (!uploadPP) return { status: 400, message: "Gagal upload foto profile" };
|
||||
// const uploadPP_Folder = Buffer.from(await gambarProfile.arrayBuffer());
|
||||
// fs.writeFileSync(`./public/profile/foto/${uploadPP.url}`, uploadPP_Folder);
|
||||
// revalidatePath("/dev/katalog");
|
||||
|
||||
// return {
|
||||
// status: 200,
|
||||
// message: "Update berhasil",
|
||||
// };
|
||||
}
|
||||
|
||||
@@ -2,12 +2,14 @@ import ProfileLayout from "./create/layout";
|
||||
import CreateProfile from "./create/view";
|
||||
import EditProfileLayout from "./edit/layout";
|
||||
import EditProfileView from "./edit/view";
|
||||
import ProfileView from "./main/view_profile";
|
||||
import UploadFotoProfile from "./upload/foto_profile";
|
||||
import UploadFotoProfileLayout from "./upload/foto_profile/layout";
|
||||
|
||||
export {
|
||||
CreateProfile, EditProfileLayout, EditProfileView, ProfileLayout, ProfileView, UploadFotoProfile,
|
||||
UploadFotoProfileLayout
|
||||
CreateProfile,
|
||||
EditProfileLayout,
|
||||
EditProfileView,
|
||||
ProfileLayout,
|
||||
UploadFotoProfile,
|
||||
UploadFotoProfileLayout,
|
||||
};
|
||||
|
||||
|
||||
@@ -1,276 +0,0 @@
|
||||
"use client";
|
||||
|
||||
import { Warna } from "@/app/lib/warna";
|
||||
import {
|
||||
ActionIcon,
|
||||
AspectRatio,
|
||||
Avatar,
|
||||
BackgroundImage,
|
||||
Box,
|
||||
Center,
|
||||
Flex,
|
||||
Grid,
|
||||
Group,
|
||||
Image,
|
||||
Paper,
|
||||
Stack,
|
||||
Text,
|
||||
} from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import {
|
||||
IconAddressBook,
|
||||
IconCamera,
|
||||
IconEditCircle,
|
||||
IconGenderFemale,
|
||||
IconGenderMale,
|
||||
IconHome,
|
||||
IconMail,
|
||||
} from "@tabler/icons-react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { MODEL_PROFILE_OLD } from "@/app_modules/home/model/user_profile";
|
||||
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { MODEL_PROFILE } from "../model/interface";
|
||||
import { AccentColor, MainColor } from "@/app_modules/_global/color/color_pallet";
|
||||
|
||||
export default function ProfileView({
|
||||
profile,
|
||||
userLoginId,
|
||||
}: {
|
||||
profile: MODEL_PROFILE;
|
||||
userLoginId: string;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [loadingPP, setLoadingPP] = useState(false);
|
||||
const [loadingBG, setLoadingBG] = useState(false);
|
||||
const [loadingEdit, setLoadingEdit] = useState(false);
|
||||
|
||||
|
||||
return (
|
||||
<>
|
||||
{/* <pre>{JSON.stringify(profile, null,2)}</pre> */}
|
||||
<Paper px={"md"} py={"sm"} shadow="lg" style={{
|
||||
backgroundColor: MainColor.darkblue,
|
||||
border: `2px solid ${AccentColor.blue}`,
|
||||
}}>
|
||||
{/* Background dan foto */}
|
||||
|
||||
{/* Upload Background Profile */}
|
||||
<Box>
|
||||
<AspectRatio ratio={16 / 9}>
|
||||
<Paper radius={"sm"} shadow="md">
|
||||
<Image
|
||||
mah={"100%"}
|
||||
maw={"100%"}
|
||||
alt="Background"
|
||||
src={
|
||||
profile?.ImagesBackground.url
|
||||
? RouterProfile.api_url_background +
|
||||
`${profile?.ImagesBackground.url}`
|
||||
: "/aset/no-image.png"
|
||||
}
|
||||
/>
|
||||
</Paper>
|
||||
</AspectRatio>
|
||||
|
||||
{/* Upload Background Profile */}
|
||||
{profile?.User.id === userLoginId ? (
|
||||
<Center>
|
||||
<ActionIcon
|
||||
loading={loadingBG ? true : false}
|
||||
ml={{ base: 300, sm: 500, md: 900, lg: 1000 }}
|
||||
mt={-10}
|
||||
bg={"gray.5"}
|
||||
variant="transparent"
|
||||
radius={50}
|
||||
onClick={() => {
|
||||
setLoadingBG(true);
|
||||
router.push(
|
||||
RouterProfile.update_foto_background + `${profile.id}`
|
||||
);
|
||||
}}
|
||||
sx={{
|
||||
position: "relative",
|
||||
color: "gray",
|
||||
border: "1px",
|
||||
borderStyle: "solid",
|
||||
}}
|
||||
>
|
||||
<IconCamera color="black" size={20} />
|
||||
</ActionIcon>
|
||||
</Center>
|
||||
) : (
|
||||
""
|
||||
)}
|
||||
|
||||
{/* Foto Profile */}
|
||||
<Center>
|
||||
<Box
|
||||
sx={{
|
||||
marginBottom: 10,
|
||||
paddingBottom: 10,
|
||||
position: "absolute",
|
||||
zIndex: 0,
|
||||
}}
|
||||
>
|
||||
<Avatar
|
||||
bg={"gray.2"}
|
||||
sx={{
|
||||
borderStyle: "solid",
|
||||
borderColor: "gray",
|
||||
borderWidth: "0.5px",
|
||||
}}
|
||||
src={
|
||||
profile?.ImageProfile?.url
|
||||
? RouterProfile.api_url_foto +
|
||||
`${profile?.ImageProfile.url}`
|
||||
: "/aset/global/avatar.png"
|
||||
}
|
||||
size={100}
|
||||
radius={"100%"}
|
||||
/>
|
||||
</Box>
|
||||
</Center>
|
||||
|
||||
{/* Upload Foto Profile */}
|
||||
{profile?.User.id === userLoginId ? (
|
||||
<Center>
|
||||
<ActionIcon
|
||||
loading={loadingPP ? true : false}
|
||||
mr={-70}
|
||||
mt={15}
|
||||
variant="transparent"
|
||||
bg={"gray.5"}
|
||||
radius={50}
|
||||
onClick={() => {
|
||||
setLoadingPP(true);
|
||||
router.push(
|
||||
RouterProfile.update_foto_profile + `${profile.id}`
|
||||
);
|
||||
}}
|
||||
sx={{
|
||||
position: "relative",
|
||||
border: "1px",
|
||||
borderStyle: "solid",
|
||||
}}
|
||||
>
|
||||
<IconCamera color="black" size={20} />
|
||||
</ActionIcon>
|
||||
</Center>
|
||||
) : (
|
||||
""
|
||||
)}
|
||||
</Box>
|
||||
|
||||
{/* Username dan Nama */}
|
||||
|
||||
<Grid>
|
||||
<Grid.Col
|
||||
span={"auto"}
|
||||
pt={profile?.User.id === userLoginId ? 10 : 50}
|
||||
>
|
||||
<Stack spacing={0}>
|
||||
<Text fz={"lg"} fw={"bold"} lineClamp={1}>
|
||||
{profile?.name}
|
||||
</Text>
|
||||
<Text fz={"xs"} c={"dark.3"}>
|
||||
@{profile?.User?.username}
|
||||
</Text>
|
||||
</Stack>
|
||||
</Grid.Col>
|
||||
<Grid.Col span={"content"}>
|
||||
{profile?.User.id === userLoginId ? (
|
||||
<ActionIcon
|
||||
loading={loadingEdit ? true : false}
|
||||
variant="transparent"
|
||||
onClick={() => {
|
||||
setLoadingEdit(true);
|
||||
router.push(RouterProfile.edit + `${profile.id}`);
|
||||
}}
|
||||
>
|
||||
<IconEditCircle color={Warna.hijau_muda} />
|
||||
</ActionIcon>
|
||||
) : (
|
||||
""
|
||||
)}
|
||||
</Grid.Col>
|
||||
</Grid>
|
||||
|
||||
{/* <Group
|
||||
position="apart"
|
||||
pt={profile?.User.id === userLoginId ? 0 : "xl"}
|
||||
>
|
||||
<Flex direction={"column"} mt={"lg"}></Flex>
|
||||
</Group> */}
|
||||
|
||||
{/* Info user: nomor, email dll */}
|
||||
<Stack spacing={"xs"} pt={"lg"}>
|
||||
<Grid>
|
||||
<Grid.Col span={"content"}>
|
||||
<IconAddressBook />
|
||||
</Grid.Col>
|
||||
<Grid.Col span={"auto"}>
|
||||
<Text>
|
||||
{" "}
|
||||
<Text>+{profile?.User.nomor}</Text>
|
||||
</Text>
|
||||
</Grid.Col>
|
||||
</Grid>
|
||||
|
||||
<Grid>
|
||||
<Grid.Col span={"content"}>
|
||||
<IconMail />
|
||||
</Grid.Col>
|
||||
<Grid.Col span={"auto"}>
|
||||
<Text>
|
||||
{" "}
|
||||
<Text> {profile?.email}</Text>
|
||||
</Text>
|
||||
</Grid.Col>
|
||||
</Grid>
|
||||
|
||||
<Grid>
|
||||
<Grid.Col span={"content"}>
|
||||
<IconHome />
|
||||
</Grid.Col>
|
||||
<Grid.Col span={"auto"}>
|
||||
<Text> {profile?.alamat}</Text>
|
||||
</Grid.Col>
|
||||
</Grid>
|
||||
|
||||
{(() => {
|
||||
if (profile?.jenisKelamin === "Laki - laki") {
|
||||
return (
|
||||
<>
|
||||
<Grid>
|
||||
<Grid.Col span={"content"}>
|
||||
<IconGenderMale />
|
||||
</Grid.Col>
|
||||
<Grid.Col span={"auto"}>
|
||||
<Text> {profile?.jenisKelamin}</Text>
|
||||
</Grid.Col>
|
||||
</Grid>
|
||||
</>
|
||||
);
|
||||
} else {
|
||||
return (
|
||||
<>
|
||||
<Grid>
|
||||
<Grid.Col span={"content"}>
|
||||
<IconGenderFemale />
|
||||
</Grid.Col>
|
||||
<Grid.Col span={"auto"}>
|
||||
<Text> {profile?.jenisKelamin}</Text>
|
||||
</Grid.Col>
|
||||
</Grid>
|
||||
</>
|
||||
);
|
||||
}
|
||||
})()}
|
||||
</Stack>
|
||||
</Paper>
|
||||
|
||||
{/* <pre>{JSON.stringify(profile, null, 2)}</pre> */}
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -16,4 +16,6 @@ export interface MODEL_PROFILE {
|
||||
imagesId: string;
|
||||
ImagesBackground: MODEL_IMAGES;
|
||||
imagesBackgroundId: string;
|
||||
imageId?: string;
|
||||
imageBackgroundId?: string;
|
||||
}
|
||||
|
||||
@@ -1,138 +1,52 @@
|
||||
"use client";
|
||||
|
||||
import { APIs } from "@/app/lib";
|
||||
import {
|
||||
AspectRatio,
|
||||
Button,
|
||||
Center,
|
||||
FileButton,
|
||||
Image,
|
||||
Paper,
|
||||
Stack,
|
||||
} from "@mantine/core";
|
||||
|
||||
ComponentGlobal_BoxUploadImage,
|
||||
ComponentGlobal_ButtonUploadFileImage,
|
||||
} from "@/app_modules/_global/component";
|
||||
import { AspectRatio, Center, Image, Stack } from "@mantine/core";
|
||||
import { useState } from "react";
|
||||
|
||||
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/_global/notif_global/notifikasi_berhasil";
|
||||
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/_global/notif_global/notifikasi_gagal";
|
||||
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/_global/notif_global/notifikasi_peringatan";
|
||||
import { IconCamera } from "@tabler/icons-react";
|
||||
import { AppRouterInstance } from "next/dist/shared/lib/app-router-context.shared-runtime";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { Profile_funUpdateBackground } from "../../fun/update/fun_update_background";
|
||||
import { Profile_ComponentButtonUpdateBackgroundProfile } from "../../_component";
|
||||
import { MODEL_PROFILE } from "../../model/interface";
|
||||
import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
} from "@/app_modules/_global/color/color_pallet";
|
||||
|
||||
export default function Profile_UpdateFotoBackground({
|
||||
dataProfile,
|
||||
}: {
|
||||
dataProfile: MODEL_PROFILE;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [profile, setProfile] = useState(dataProfile);
|
||||
const [file, setFile] = useState<File | null>(null);
|
||||
const [image, setImage] = useState<any | null>(null);
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
return (
|
||||
<>
|
||||
<Stack spacing={"xl"}>
|
||||
<Paper
|
||||
p={"sm"}
|
||||
radius={"sm"}
|
||||
style={{
|
||||
backgroundColor: AccentColor.darkblue,
|
||||
border: `2px solid ${AccentColor.blue}`,
|
||||
}}
|
||||
>
|
||||
<Stack>
|
||||
<AspectRatio ratio={16 / 9}>
|
||||
<Image
|
||||
alt="Foto"
|
||||
src={
|
||||
image
|
||||
? image
|
||||
: RouterProfile.api_background_profile +
|
||||
profile.imagesBackgroundId
|
||||
}
|
||||
/>
|
||||
</AspectRatio>
|
||||
<Center>
|
||||
<FileButton
|
||||
onChange={async (files: any | null) => {
|
||||
try {
|
||||
const buffer = URL.createObjectURL(
|
||||
new Blob([new Uint8Array(await files.arrayBuffer())])
|
||||
);
|
||||
if (files.size > 2000000) {
|
||||
ComponentGlobal_NotifikasiPeringatan(
|
||||
"Maaf, Ukuran file terlalu besar, maximum 2mb",
|
||||
3000
|
||||
);
|
||||
} else {
|
||||
setImage(buffer);
|
||||
setFile(files);
|
||||
}
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}}
|
||||
accept="image/png,image/jpeg"
|
||||
>
|
||||
{(props) => (
|
||||
<Button
|
||||
{...props}
|
||||
radius={"xl"}
|
||||
leftIcon={<IconCamera />}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
>
|
||||
Upload
|
||||
</Button>
|
||||
)}
|
||||
</FileButton>
|
||||
</Center>
|
||||
</Stack>
|
||||
</Paper>
|
||||
<Stack px={"xs"}>
|
||||
<ComponentGlobal_BoxUploadImage>
|
||||
<AspectRatio ratio={1 / 1} mt={5} maw={300} mx={"auto"}>
|
||||
<Image
|
||||
style={{ maxHeight: 250 }}
|
||||
alt="Background"
|
||||
src={
|
||||
image
|
||||
? image
|
||||
: APIs.GET({ fileId: profile.imageBackgroundId as any })
|
||||
}
|
||||
/>
|
||||
</AspectRatio>
|
||||
</ComponentGlobal_BoxUploadImage>
|
||||
<Center>
|
||||
<ComponentGlobal_ButtonUploadFileImage
|
||||
onSetFile={setFile}
|
||||
onSetImage={setImage}
|
||||
/>
|
||||
</Center>
|
||||
|
||||
<Button
|
||||
disabled={file ? false : true}
|
||||
loading={loading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"xl"}
|
||||
onClick={() => onUpdate(router, profile.id, file as any, setLoading)}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
|
||||
>
|
||||
Update
|
||||
</Button>
|
||||
<Profile_ComponentButtonUpdateBackgroundProfile
|
||||
file={file as any}
|
||||
profileId={profile.id}
|
||||
/>
|
||||
</Stack>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
async function onUpdate(
|
||||
router: AppRouterInstance,
|
||||
profileId: string,
|
||||
file: FormData,
|
||||
setLoading: any
|
||||
) {
|
||||
const gambar = new FormData();
|
||||
gambar.append("file", file as any);
|
||||
|
||||
await Profile_funUpdateBackground(profileId, gambar).then((res) => {
|
||||
if (res.status === 200) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
router.back();
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(res.message);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@@ -1,137 +1,47 @@
|
||||
"use client";
|
||||
|
||||
import { APIs } from "@/app/lib";
|
||||
import {
|
||||
AspectRatio,
|
||||
Button,
|
||||
Center,
|
||||
FileButton,
|
||||
Image,
|
||||
Paper,
|
||||
Stack,
|
||||
Title,
|
||||
} from "@mantine/core";
|
||||
ComponentGlobal_BoxUploadImage,
|
||||
ComponentGlobal_ButtonUploadFileImage,
|
||||
} from "@/app_modules/_global/component";
|
||||
import { AspectRatio, Center, Image, Stack } from "@mantine/core";
|
||||
import { useState } from "react";
|
||||
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { Profile_ComponentButtonUpdatePhotoProfile } from "../../_component";
|
||||
import { MODEL_PROFILE } from "../../model/interface";
|
||||
import { IconCamera } from "@tabler/icons-react";
|
||||
import { AppRouterInstance } from "next/dist/shared/lib/app-router-context.shared-runtime";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { Profile_funUpdateFoto } from "../../fun/update/fun_update_foto_profile";
|
||||
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/_global/notif_global/notifikasi_berhasil";
|
||||
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/_global/notif_global/notifikasi_gagal";
|
||||
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/_global/notif_global/notifikasi_peringatan";
|
||||
import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
} from "@/app_modules/_global/color/color_pallet";
|
||||
|
||||
export default function UploadFotoProfile({
|
||||
dataProfile,
|
||||
}: {
|
||||
dataProfile: MODEL_PROFILE;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [profile, setProfile] = useState(dataProfile);
|
||||
const [file, setFile] = useState<File | null>(null);
|
||||
const [image, setImage] = useState<any | null>(null);
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
return (
|
||||
<>
|
||||
<Stack spacing={"xl"}>
|
||||
<Paper
|
||||
p={"sm"}
|
||||
radius={"sm"}
|
||||
style={{
|
||||
backgroundColor: AccentColor.darkblue,
|
||||
border: `2px solid ${AccentColor.blue}`,
|
||||
}}
|
||||
>
|
||||
<Stack>
|
||||
<AspectRatio ratio={1 / 1}>
|
||||
<Image
|
||||
alt="Foto"
|
||||
src={
|
||||
image
|
||||
? image
|
||||
: RouterProfile.api_foto_profile + profile.imagesId
|
||||
}
|
||||
/>
|
||||
</AspectRatio>
|
||||
<Center>
|
||||
<FileButton
|
||||
onChange={async (files: any | null) => {
|
||||
try {
|
||||
const buffer = URL.createObjectURL(
|
||||
new Blob([new Uint8Array(await files.arrayBuffer())])
|
||||
);
|
||||
if (files.size > 2000000) {
|
||||
ComponentGlobal_NotifikasiPeringatan(
|
||||
"Maaf, Ukuran file terlalu besar, maximum 2mb",
|
||||
3000
|
||||
);
|
||||
} else {
|
||||
setImage(buffer);
|
||||
setFile(files);
|
||||
}
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}}
|
||||
accept="image/png,image/jpeg"
|
||||
>
|
||||
{(props) => (
|
||||
<Button
|
||||
{...props}
|
||||
radius={"xl"}
|
||||
leftIcon={<IconCamera />}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
>
|
||||
Upload
|
||||
</Button>
|
||||
)}
|
||||
</FileButton>
|
||||
</Center>
|
||||
</Stack>
|
||||
</Paper>
|
||||
|
||||
<Button
|
||||
disabled={file ? false : true}
|
||||
loading={loading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"xl"}
|
||||
onClick={() => {
|
||||
onUpdate(router, profile.id, file as any, setLoading);
|
||||
}}
|
||||
bg={MainColor.yellow}
|
||||
color="yellow"
|
||||
c={"black"}
|
||||
>
|
||||
Update
|
||||
</Button>
|
||||
<Stack px={"xs"}>
|
||||
<ComponentGlobal_BoxUploadImage>
|
||||
<AspectRatio ratio={1 / 1} mt={5} maw={300} mx={"auto"}>
|
||||
<Image
|
||||
style={{ maxHeight: 250 }}
|
||||
alt="Avatar"
|
||||
src={image ? image : APIs.GET({ fileId: profile.imageId as any })}
|
||||
/>
|
||||
</AspectRatio>
|
||||
</ComponentGlobal_BoxUploadImage>
|
||||
<Center>
|
||||
<ComponentGlobal_ButtonUploadFileImage
|
||||
onSetFile={setFile}
|
||||
onSetImage={setImage}
|
||||
/>
|
||||
</Center>
|
||||
<Profile_ComponentButtonUpdatePhotoProfile
|
||||
file={file as any}
|
||||
profileId={profile.id}
|
||||
/>
|
||||
</Stack>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
async function onUpdate(
|
||||
router: AppRouterInstance,
|
||||
profileId: string,
|
||||
file: FormData,
|
||||
setLoading: any
|
||||
) {
|
||||
const gambar = new FormData();
|
||||
gambar.append("file", file as any);
|
||||
|
||||
await Profile_funUpdateFoto(profileId, gambar).then((res) => {
|
||||
if (res.status === 200) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
router.back();
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(res.message);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@@ -48,10 +48,10 @@ export function Portofolio_UiListView({
|
||||
}}
|
||||
>
|
||||
<Stack spacing={"sm"}>
|
||||
<Group position="apart">
|
||||
<ActionIcon variant="transparent" disabled></ActionIcon>
|
||||
<Group position="center">
|
||||
|
||||
<Title order={4}>Portofolio</Title>
|
||||
{profile?.User.id === userLoginId ? (
|
||||
{/* {profile?.User.id === userLoginId ? (
|
||||
<ActionIcon
|
||||
variant="transparent"
|
||||
onClick={() => {
|
||||
@@ -69,7 +69,7 @@ export function Portofolio_UiListView({
|
||||
</ActionIcon>
|
||||
) : (
|
||||
<ActionIcon variant="transparent" disabled></ActionIcon>
|
||||
)}
|
||||
)} */}
|
||||
</Group>
|
||||
|
||||
<Stack
|
||||
|
||||
@@ -1,24 +1,8 @@
|
||||
"use client";
|
||||
|
||||
import {
|
||||
MainColor,
|
||||
AccentColor,
|
||||
} from "@/app_modules/_global/color/color_pallet";
|
||||
import {
|
||||
Avatar,
|
||||
Box,
|
||||
Center,
|
||||
Group,
|
||||
Image,
|
||||
Paper,
|
||||
Stack,
|
||||
Text,
|
||||
ThemeIcon,
|
||||
} from "@mantine/core";
|
||||
import { MODEL_PROFILE } from "../profile/model/interface";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { APIs } from "@/app/lib";
|
||||
import { AccentColor } from "@/app_modules/_global/color/color_pallet";
|
||||
import { Box, Center, Group, Stack, Text, ThemeIcon } from "@mantine/core";
|
||||
import {
|
||||
IconBrandGmail,
|
||||
IconGenderFemale,
|
||||
@@ -26,6 +10,13 @@ import {
|
||||
IconHome,
|
||||
IconPhone,
|
||||
} from "@tabler/icons-react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import {
|
||||
Profile_ComponentAvatarProfile,
|
||||
Profile_ComponentLoadBackgroundImage,
|
||||
} from "../profile/_component";
|
||||
import { MODEL_PROFILE } from "../profile/model/interface";
|
||||
|
||||
export function Profile_UiView({
|
||||
profile,
|
||||
@@ -76,17 +67,19 @@ export function Profile_UiView({
|
||||
}}
|
||||
>
|
||||
<Box>
|
||||
<Image
|
||||
<Profile_ComponentLoadBackgroundImage
|
||||
url={APIs.GET({
|
||||
fileId: profile.imageBackgroundId as string,
|
||||
})}
|
||||
radius="sm"
|
||||
/>
|
||||
{/* <Image
|
||||
radius={"sm"}
|
||||
height={200}
|
||||
alt="Background"
|
||||
src={
|
||||
profile?.ImagesBackground.url
|
||||
? RouterProfile.api_url_background +
|
||||
`${profile?.ImagesBackground.url}`
|
||||
: "/aset/no-image.png"
|
||||
}
|
||||
/>
|
||||
src={APIs.GET({ fileId: profile.imageBackgroundId as string })}
|
||||
/> */}
|
||||
|
||||
<Box
|
||||
sx={{
|
||||
position: "relative",
|
||||
@@ -97,22 +90,27 @@ export function Profile_UiView({
|
||||
}}
|
||||
>
|
||||
<Center>
|
||||
<Avatar
|
||||
<Profile_ComponentAvatarProfile
|
||||
url={APIs.GET({ fileId: profile.imageId as any, size: "200" })}
|
||||
style={{
|
||||
borderStyle: "solid",
|
||||
borderColor: AccentColor.darkblue,
|
||||
borderWidth: "2px",
|
||||
}}
|
||||
/>
|
||||
{/* <Avatar
|
||||
bg={"gray.2"}
|
||||
sx={{
|
||||
borderStyle: "solid",
|
||||
borderColor: "gray",
|
||||
borderWidth: "0.5px",
|
||||
borderColor: AccentColor.darkblue,
|
||||
borderWidth: "2px",
|
||||
}}
|
||||
src={
|
||||
profile?.ImageProfile?.url
|
||||
? RouterProfile.api_url_foto +
|
||||
`${profile?.ImageProfile.url}`
|
||||
: "/aset/global/avatar.png"
|
||||
APIs.GET({fileId: profile.imageId as any})
|
||||
}
|
||||
size={100}
|
||||
radius={"100%"}
|
||||
/>
|
||||
/> */}
|
||||
</Center>
|
||||
<Stack align="center" c={"white"} mt={"xs"} spacing={0}>
|
||||
<Text fw={"bold"} lineClamp={1}>
|
||||
@@ -128,7 +126,7 @@ export function Profile_UiView({
|
||||
<Box>
|
||||
<Stack spacing={"xs"}>
|
||||
{listInformation.map((e, i) => (
|
||||
<Group key={i} align="flex-start">
|
||||
<Group key={i} align="flex-start">
|
||||
<ThemeIcon
|
||||
style={{
|
||||
backgroundColor: "transparent",
|
||||
@@ -136,20 +134,13 @@ export function Profile_UiView({
|
||||
>
|
||||
{e.icon}
|
||||
</ThemeIcon>
|
||||
<Box w={"85%"} >
|
||||
<Box w={"85%"}>
|
||||
<Text fw={"bold"}>{e?.value}</Text>
|
||||
</Box>
|
||||
</Group>
|
||||
))}
|
||||
</Stack>
|
||||
</Box>
|
||||
{/* <pre
|
||||
style={{
|
||||
color: "white",
|
||||
}}
|
||||
>
|
||||
{JSON.stringify(profile, null, 2)}
|
||||
</pre> */}
|
||||
</Stack>
|
||||
</>
|
||||
);
|
||||
|
||||
@@ -61,7 +61,9 @@ export function ComponentMap_DetailData({ mapId }: { mapId: any }) {
|
||||
{ maxWidth: 600, cols: 1, spacing: "sm" },
|
||||
]}
|
||||
>
|
||||
<ComponentGlobal_LoadImage url={APIs.GET + data?.imageId} />
|
||||
<ComponentGlobal_LoadImage
|
||||
url={APIs.GET({ fileId: data?.imageId })}
|
||||
/>
|
||||
{/* <Image radius={"sm"} mah={300} maw={200} alt="Photo" src={} /> */}
|
||||
<Box>
|
||||
<Grid>
|
||||
|
||||
@@ -72,8 +72,8 @@ export function UiMap_CustomPin({
|
||||
radius={"100%"}
|
||||
src={
|
||||
data.pinId === null
|
||||
? APIs.GET + data.Portofolio.logoId
|
||||
: APIs.GET + data.pinId
|
||||
? APIs.GET({ fileId: data.Portofolio.logoId })
|
||||
: APIs.GET({ fileId: data.pinId })
|
||||
}
|
||||
style={{
|
||||
border: `2px solid ${AccentColor.skyblue}`,
|
||||
@@ -155,8 +155,8 @@ export function UiMap_CustomPin({
|
||||
imgPin
|
||||
? imgPin
|
||||
: data.pinId === null
|
||||
? APIs.GET + data.Portofolio.logoId
|
||||
: APIs.GET + data.pinId
|
||||
? APIs.GET({ fileId: data.Portofolio.logoId })
|
||||
: APIs.GET({ fileId: data.pinId })
|
||||
}
|
||||
style={{
|
||||
border: `2px solid ${AccentColor.softblue}`,
|
||||
|
||||
@@ -36,7 +36,10 @@ import { map_funEditMap } from "../fun/edit/fun_edit_map";
|
||||
import { defaultMapZoom } from "../lib/default_lat_long";
|
||||
import { MODEL_MAP } from "../lib/interface";
|
||||
import { APIs } from "@/app/lib";
|
||||
import { ComponentGlobal_BoxUploadImage, ComponentGlobal_LoadImage } from "@/app_modules/_global/component";
|
||||
import {
|
||||
ComponentGlobal_BoxUploadImage,
|
||||
ComponentGlobal_LoadImage,
|
||||
} from "@/app_modules/_global/component";
|
||||
import { ComponentMap_ButtonUpdateDataMap } from "../_component";
|
||||
|
||||
export function UiMap_EditMap({
|
||||
@@ -90,8 +93,8 @@ export function UiMap_EditMap({
|
||||
<Avatar
|
||||
src={
|
||||
data.pinId === null
|
||||
? APIs.GET + dataMap.Portofolio.logoId
|
||||
: APIs.GET + data.pinId
|
||||
? APIs.GET({ fileId: dataMap.Portofolio.logoId })
|
||||
: APIs.GET({ fileId: data.pinId })
|
||||
}
|
||||
alt="Logo"
|
||||
style={{
|
||||
@@ -148,8 +151,7 @@ export function UiMap_EditMap({
|
||||
</AspectRatio>
|
||||
) : (
|
||||
<ComponentGlobal_LoadImage
|
||||
|
||||
url={APIs.GET + data.imageId}
|
||||
url={APIs.GET({ fileId: data.imageId })}
|
||||
/>
|
||||
)}
|
||||
</ComponentGlobal_BoxUploadImage>
|
||||
@@ -235,5 +237,3 @@ export function UiMap_EditMap({
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -91,8 +91,8 @@ export function UiMap_MapBoxView({
|
||||
}}
|
||||
src={
|
||||
e.pinId === null
|
||||
? APIs.GET + e.Portofolio.logoId
|
||||
: APIs.GET + e.pinId
|
||||
? APIs.GET({ fileId: e.Portofolio.logoId })
|
||||
: APIs.GET({ fileId: e.pinId })
|
||||
}
|
||||
/>
|
||||
</Stack>
|
||||
|
||||
Reference in New Issue
Block a user