feat: ability to change logo in frontend
This commit is contained in:
Binary file not shown.
|
Before Width: | Height: | Size: 4.3 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 12 KiB |
@@ -0,0 +1,39 @@
|
||||
import { Box, FileInput, Group, Stack, Text, Title } from "@mantine/core";
|
||||
import { useMediaQuery } from "@mantine/hooks";
|
||||
import { Dispatch, SetStateAction } from "react";
|
||||
import { TbUpload } from "react-icons/tb";
|
||||
|
||||
const LogoConfigInput = ({
|
||||
logo,
|
||||
setLogo,
|
||||
}: {
|
||||
logo: File | null;
|
||||
setLogo: Dispatch<SetStateAction<File | null>>;
|
||||
}) => {
|
||||
const isMobile = useMediaQuery("(max-width: 560px)");
|
||||
|
||||
return (
|
||||
<Group position="apart">
|
||||
<Stack style={{ maxWidth: isMobile ? "100%" : "40%" }} spacing={0}>
|
||||
<Title order={6}>Logo</Title>
|
||||
<Text color="dimmed" size="sm" mb="xs">
|
||||
Change your logo by uploading a new image. The image must be a PNG and
|
||||
should have the format 1:1.
|
||||
</Text>
|
||||
</Stack>
|
||||
<Stack></Stack>
|
||||
<Box style={{ width: isMobile ? "100%" : "50%" }}>
|
||||
<FileInput
|
||||
clearable
|
||||
icon={<TbUpload size={14} />}
|
||||
value={logo}
|
||||
onChange={(v) => setLogo(v)}
|
||||
accept=".png"
|
||||
placeholder="Pick image"
|
||||
/>
|
||||
</Box>
|
||||
</Group>
|
||||
);
|
||||
};
|
||||
|
||||
export default LogoConfigInput;
|
||||
@@ -12,14 +12,8 @@ export default class _Document extends Document {
|
||||
<Head>
|
||||
<link rel="manifest" href="/manifest.json" />
|
||||
<link rel="icon" type="image/x-icon" href="/img/favicon.ico" />
|
||||
<link
|
||||
rel="apple-touch-icon"
|
||||
href="/img/icons/icon-white-128x128.png"
|
||||
/>
|
||||
<link rel="apple-touch-icon" href="/img/icons/icon-128x128.png" />
|
||||
|
||||
<meta property="og:image" content="/img/opengraph.png" />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<meta name="twitter:image" content="/img/opengraph.png" />
|
||||
<meta name="robots" content="noindex" />
|
||||
<meta name="theme-color" content="#46509e" />
|
||||
</Head>
|
||||
|
||||
@@ -16,6 +16,7 @@ import { useEffect, useState } from "react";
|
||||
import AdminConfigInput from "../../../components/admin/configuration/AdminConfigInput";
|
||||
import ConfigurationHeader from "../../../components/admin/configuration/ConfigurationHeader";
|
||||
import ConfigurationNavBar from "../../../components/admin/configuration/ConfigurationNavBar";
|
||||
import LogoConfigInput from "../../../components/admin/configuration/LogoConfigInput";
|
||||
import TestEmailButton from "../../../components/admin/configuration/TestEmailButton";
|
||||
import CenterLoader from "../../../components/core/CenterLoader";
|
||||
import Meta from "../../../components/Meta";
|
||||
@@ -36,22 +37,38 @@ export default function AppShellDemo() {
|
||||
const isMobile = useMediaQuery("(max-width: 560px)");
|
||||
const config = useConfig();
|
||||
|
||||
const categoryId = router.query.category as string;
|
||||
const categoryId = (router.query.category as string | undefined) ?? "general";
|
||||
|
||||
const [configVariables, setConfigVariables] = useState<AdminConfig[]>();
|
||||
const [updatedConfigVariables, setUpdatedConfigVariables] = useState<
|
||||
UpdateConfig[]
|
||||
>([]);
|
||||
|
||||
const [logo, setLogo] = useState<File | null>(null);
|
||||
|
||||
const saveConfigVariables = async () => {
|
||||
await configService
|
||||
.updateMany(updatedConfigVariables)
|
||||
.then(() => {
|
||||
setUpdatedConfigVariables([]);
|
||||
toast.success("Configurations updated successfully");
|
||||
})
|
||||
.catch(toast.axiosError);
|
||||
config.refresh();
|
||||
if (logo) {
|
||||
configService
|
||||
.changeLogo(logo)
|
||||
.then(() => {
|
||||
setLogo(null);
|
||||
toast.success(
|
||||
"Logo updated successfully. It may take a few minutes to update on the website."
|
||||
);
|
||||
})
|
||||
.catch(toast.axiosError);
|
||||
}
|
||||
|
||||
if (updatedConfigVariables.length > 0) {
|
||||
await configService
|
||||
.updateMany(updatedConfigVariables)
|
||||
.then(() => {
|
||||
setUpdatedConfigVariables([]);
|
||||
toast.success("Configurations updated successfully");
|
||||
})
|
||||
.catch(toast.axiosError);
|
||||
config.refresh();
|
||||
}
|
||||
};
|
||||
|
||||
const updateConfigVariable = (configVariable: UpdateConfig) => {
|
||||
@@ -129,6 +146,9 @@ export default function AppShellDemo() {
|
||||
</Box>
|
||||
</Group>
|
||||
))}
|
||||
{categoryId == "general" && (
|
||||
<LogoConfigInput logo={logo} setLogo={setLogo} />
|
||||
)}
|
||||
</Stack>
|
||||
<Group mt="lg" position="right">
|
||||
{categoryId == "smtp" && (
|
||||
|
||||
@@ -1,15 +0,0 @@
|
||||
export function getServerSideProps() {
|
||||
return {
|
||||
redirect: {
|
||||
permanent: false,
|
||||
destination: "/admin/config/general",
|
||||
},
|
||||
props: {},
|
||||
};
|
||||
}
|
||||
|
||||
const Config = () => {
|
||||
return null;
|
||||
};
|
||||
|
||||
export default Config;
|
||||
@@ -46,6 +46,12 @@ const isNewReleaseAvailable = async () => {
|
||||
return response.tag_name.replace("v", "") != process.env.VERSION;
|
||||
};
|
||||
|
||||
const changeLogo = async (file: File) => {
|
||||
const form = new FormData();
|
||||
form.append("file", file);
|
||||
|
||||
await api.post("/configs/admin/logo", form);
|
||||
};
|
||||
export default {
|
||||
list,
|
||||
getByCategory,
|
||||
@@ -54,4 +60,5 @@ export default {
|
||||
finishSetup,
|
||||
sendTestEmail,
|
||||
isNewReleaseAvailable,
|
||||
changeLogo,
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user