diff --git a/package-lock.json b/package-lock.json
index 2fe6cced28334ffb5e7bdc7c7210b16cc41b11a7..e3d112a1fb9d00bd734d8c6899d50217003d6f13 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -6278,6 +6278,19 @@
"tslib": "^2.4.0"
}
},
+ "node_modules/@theme-toggles/react": {
+ "version": "4.1.0",
+ "resolved": "https://registry.npmjs.org/@theme-toggles/react/-/react-4.1.0.tgz",
+ "integrity": "sha512-h3SuJMsej8DfelHt5fjNIlaMfJOK52Vku4pPDVoHaTwjAcoTr4fn8hzeur2oiqWBYFYfKugvv1RdQaBFXaiPKg==",
+ "funding": {
+ "type": "github",
+ "url": "https://github.com/sponsors/alfiejones"
+ },
+ "peerDependencies": {
+ "react": "^16 || ^17 || ^18",
+ "react-dom": "^16 || ^17 || ^18"
+ }
+ },
"node_modules/@tsconfig/node10": {
"version": "1.0.9",
"resolved": "https://registry.npmjs.org/@tsconfig/node10/-/node10-1.0.9.tgz",
@@ -16261,10 +16274,12 @@
"@icons-pack/react-simple-icons": "^9.6.0",
"@nextui-org/react": "^2.2.9",
"@sc07-canvas/lib": "^1.0.0",
+ "@theme-toggles/react": "^4.1.0",
"@typescript-eslint/parser": "^7.1.0",
"eventemitter3": "^5.0.1",
"framer-motion": "^11.3.2",
"lodash.throttle": "^4.1.1",
+ "next-themes": "^0.3.0",
"prop-types": "^15.8.1",
"react": "^18.2.0",
"react-dom": "^18.2.0",
@@ -16472,6 +16487,15 @@
"resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz",
"integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w=="
},
+ "packages/client/node_modules/next-themes": {
+ "version": "0.3.0",
+ "resolved": "https://registry.npmjs.org/next-themes/-/next-themes-0.3.0.tgz",
+ "integrity": "sha512-/QHIrsYpd6Kfk7xakK4svpDI5mmXP0gfvCoJdGpZQ2TOrQZmsW0QxjaiLn8wbIKjtm4BTSqLoix4lxYYOnLJ/w==",
+ "peerDependencies": {
+ "react": "^16.8 || ^17 || ^18",
+ "react-dom": "^16.8 || ^17 || ^18"
+ }
+ },
"packages/lib": {
"name": "@sc07-canvas/lib",
"version": "1.0.0",
diff --git a/packages/admin/src/components/ToastWrapper.tsx b/packages/admin/src/components/ToastWrapper.tsx
new file mode 100644
index 0000000000000000000000000000000000000000..a1f159c81dd50d876ee9eb537a61cac6920af338
--- /dev/null
+++ b/packages/admin/src/components/ToastWrapper.tsx
@@ -0,0 +1,13 @@
+import { useTheme } from "next-themes";
+import { ToastContainer } from "react-toastify";
+
+export const ToastWrapper = () => {
+ const { theme } = useTheme()
+
+ return (
+
+ );
+};
\ No newline at end of file
diff --git a/packages/admin/src/main.tsx b/packages/admin/src/main.tsx
index b1a8e3bc7834e16ff00d4040598678c08c0c916d..f5784c08b54f5b851f89051defb4e32f1b0c9c0f 100644
--- a/packages/admin/src/main.tsx
+++ b/packages/admin/src/main.tsx
@@ -10,6 +10,7 @@ import { AccountsPage } from "./pages/Accounts/Accounts/page.tsx";
import { ServiceSettingsPage } from "./pages/Service/settings.tsx";
import { ToastContainer } from "react-toastify";
import { AuditLog } from "./pages/AuditLog/auditlog.tsx";
+import { ToastWrapper } from "./components/ToastWrapper.tsx";
const router = createBrowserRouter(
[
@@ -47,7 +48,7 @@ ReactDOM.createRoot(document.getElementById("root")!).render(
-
+
diff --git a/packages/client/package.json b/packages/client/package.json
index e838032f1e94d0095d35ce24ea4490024468a45a..82d621eb071ee11ee6ff7e2049fa157391792914 100644
--- a/packages/client/package.json
+++ b/packages/client/package.json
@@ -27,10 +27,12 @@
"@icons-pack/react-simple-icons": "^9.6.0",
"@nextui-org/react": "^2.2.9",
"@sc07-canvas/lib": "^1.0.0",
+ "@theme-toggles/react": "^4.1.0",
"@typescript-eslint/parser": "^7.1.0",
"eventemitter3": "^5.0.1",
"framer-motion": "^11.3.2",
"lodash.throttle": "^4.1.1",
+ "next-themes": "^0.3.0",
"prop-types": "^15.8.1",
"react": "^18.2.0",
"react-dom": "^18.2.0",
diff --git a/packages/client/src/components/App.tsx b/packages/client/src/components/App.tsx
index fcba09002e13f6927dc8b613737678183ee96707..1ed97991183057711be6e4d9702139ec1c66d0f3 100644
--- a/packages/client/src/components/App.tsx
+++ b/packages/client/src/components/App.tsx
@@ -19,6 +19,7 @@ import { WelcomeModal } from "./Welcome/WelcomeModal";
import { InfoSidebar } from "./Info/InfoSidebar";
import { ModModal } from "./Moderation/ModModal";
import { DynamicModals } from "./DynamicModals";
+import { ToastWrapper } from "./ToastWrapper";
const Chat = lazy(() => import("./Chat/Chat"));
@@ -152,7 +153,7 @@ const AppInner = () => {
-
+
>
);
diff --git a/packages/client/src/components/Chat/OpenChatButton.tsx b/packages/client/src/components/Chat/OpenChatButton.tsx
index 33dd34853049ac06931445b22ba0687cd44fcdb9..1f1622110e8b27a6020210514833a910bc0e3e24 100644
--- a/packages/client/src/components/Chat/OpenChatButton.tsx
+++ b/packages/client/src/components/Chat/OpenChatButton.tsx
@@ -1,6 +1,8 @@
import { Badge, Button, Link } from "@nextui-org/react";
import { useChatContext } from "../../contexts/ChatContext";
import { useAppContext } from "../../contexts/AppContext";
+import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
+import { faComments } from "@fortawesome/free-solid-svg-icons";
const OpenChatButton = () => {
const { config } = useAppContext();
@@ -13,7 +15,15 @@ const OpenChatButton = () => {
color="danger"
size="sm"
>
- {config?.chat?.element_host && }
+ {
+ config?.chat?.element_host &&
+ }
);
};
diff --git a/packages/client/src/components/Header/Header.tsx b/packages/client/src/components/Header/Header.tsx
index f9a2b912315d915a0bf59644aedb508d42e7efcd..bb3c74ada690d7a42eaa62bce887201acc8b9c61 100644
--- a/packages/client/src/components/Header/Header.tsx
+++ b/packages/client/src/components/Header/Header.tsx
@@ -1,18 +1,8 @@
-import { Button, Card, CardBody, Link } from "@nextui-org/react";
+import { Card, CardBody } from "@nextui-org/react";
import { useAppContext } from "../../contexts/AppContext";
-import { User } from "./User";
-import { Debug } from "@sc07-canvas/lib/src/debug";
-import React, { lazy } from "react";
-import { AccountStanding } from "./AccountStanding";
import { EventInfoOverlay } from "../EventInfoOverlay";
-
-const OpenChatButton = lazy(() => import("../Chat/OpenChatButton"));
-
-const DynamicChat = () => {
- const { loadChat } = useAppContext();
-
- return {loadChat && };
-};
+import { HeaderLeft } from "./HeaderLeft";
+import { HeaderRight } from "./HeaderRight";
export const Header = () => {
const { connected } = useAppContext();
@@ -20,48 +10,19 @@ export const Header = () => {
return (
{import.meta.env.VITE_INCLUDE_EVENT_INFO && }
-
-
- {!connected && (
-
-
- Disconnected
-
-
- )}
-
-
+
+
+ {!connected && (
+
+
+ Disconnected
+
+
+ )}
+
+
);
};
-const HeaderLeft = () => {
- const { setInfoSidebar } = useAppContext();
-
- return (
-
-
-
- {import.meta.env.DEV && (
-
- )}
-
- );
-};
-
-const HeaderRight = () => {
- const { setSettingsSidebar, hasAdmin } = useAppContext();
- return (
-
-
-
- {hasAdmin && (
-
- )}
-
-
- );
-};
diff --git a/packages/client/src/components/Header/HeaderLeft.tsx b/packages/client/src/components/Header/HeaderLeft.tsx
new file mode 100644
index 0000000000000000000000000000000000000000..231e3f5c2fb92bdb5e4082d02c6c7aa7aae5c49e
--- /dev/null
+++ b/packages/client/src/components/Header/HeaderLeft.tsx
@@ -0,0 +1,32 @@
+import { Button } from "@nextui-org/react";
+import { useAppContext } from "../../contexts/AppContext";
+import { AccountStanding } from "./AccountStanding";
+import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
+import { Debug } from "@sc07-canvas/lib/src/debug";
+import { faInfoCircle, faTools } from "@fortawesome/free-solid-svg-icons";
+
+export const HeaderLeft = () => {
+ const { setInfoSidebar } = useAppContext();
+
+ return (
+
+
+
+ {import.meta.env.DEV && (
+
+ )}
+
+ );
+};
\ No newline at end of file
diff --git a/packages/client/src/components/Header/HeaderRight.tsx b/packages/client/src/components/Header/HeaderRight.tsx
new file mode 100644
index 0000000000000000000000000000000000000000..020d6765fd2500726727636cf0a9c435050b123a
--- /dev/null
+++ b/packages/client/src/components/Header/HeaderRight.tsx
@@ -0,0 +1,42 @@
+import { Button, Link } from "@nextui-org/react";
+import { useAppContext } from "../../contexts/AppContext";
+import { User } from "./User";
+import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
+import { ThemeSwitcher } from "./ThemeSwitcher";
+import { faGear, faHammer } from "@fortawesome/free-solid-svg-icons";
+import React, { lazy } from "react";
+
+const OpenChatButton = lazy(() => import("../Chat/OpenChatButton"));
+
+const DynamicChat = () => {
+ const { loadChat } = useAppContext();
+
+ return {loadChat && };
+};
+
+export const HeaderRight = () => {
+ const { setSettingsSidebar, hasAdmin } = useAppContext();
+
+ return (
+
+
+
+
+
+ {hasAdmin && (
+
+ )}
+
+
+
+ );
+};
\ No newline at end of file
diff --git a/packages/client/src/components/Header/ThemeSwitcher.tsx b/packages/client/src/components/Header/ThemeSwitcher.tsx
new file mode 100644
index 0000000000000000000000000000000000000000..eb3dc2b65ab7e9475e6e555fc82bedca103ca6ad
--- /dev/null
+++ b/packages/client/src/components/Header/ThemeSwitcher.tsx
@@ -0,0 +1,34 @@
+import "@theme-toggles/react/css/Classic.css"
+import { Classic } from "@theme-toggles/react"
+
+import {useTheme} from "next-themes";
+import { useEffect, useState } from "react";
+import { Button } from "@nextui-org/react";
+
+export function ThemeSwitcher() {
+ const [mounted, setMounted] = useState(false)
+ const { theme, setTheme } = useTheme()
+ const [isToggled, setToggle] = useState(false)
+
+ useEffect(() => {
+ setMounted(true)
+ setToggle(theme === 'dark')
+ }, [])
+
+ useEffect(() => {
+ if (isToggled) {
+ setTheme('dark')
+ } else {
+ setTheme('light')
+ }
+ }, [isToggled])
+
+ if(!mounted) return null
+
+ return (
+
+ )
+};
\ No newline at end of file
diff --git a/packages/client/src/components/Info/InfoSidebar.tsx b/packages/client/src/components/Info/InfoSidebar.tsx
index 2ee4de0261c715ab44f708a1e1b10d985efa9703..24a18c2210f638e1045a6121da865bdc6a0a88cb 100644
--- a/packages/client/src/components/Info/InfoSidebar.tsx
+++ b/packages/client/src/components/Info/InfoSidebar.tsx
@@ -24,13 +24,13 @@ export const InfoSidebar = () => {
transition={{ type: 'spring', stiffness: 50 }}
/>
{
return (
{loading && (
@@ -95,7 +95,7 @@ export const PixelWhoisSidebar = () => {
-
+
{
return (
diff --git a/packages/client/src/components/ToastWrapper.tsx b/packages/client/src/components/ToastWrapper.tsx
new file mode 100644
index 0000000000000000000000000000000000000000..2f3ac862a8f4669f8c7cf293d5f1b34e3f588ba6
--- /dev/null
+++ b/packages/client/src/components/ToastWrapper.tsx
@@ -0,0 +1,13 @@
+import { useTheme } from "next-themes";
+import { ToastContainer } from "react-toastify";
+
+export const ToastWrapper = () => {
+ const { theme } = useTheme()
+
+ return (
+
+ );
+};
\ No newline at end of file
diff --git a/packages/client/src/components/Toolbar/Palette.scss b/packages/client/src/components/Toolbar/Palette.scss
index 424ceebf9eb37020b733a7343407e9d55e108c46..95c463dc6cf0c257c8aeee55517e8f857b7011e3 100644
--- a/packages/client/src/components/Toolbar/Palette.scss
+++ b/packages/client/src/components/Toolbar/Palette.scss
@@ -12,8 +12,6 @@
z-index: 10;
position: relative;
- background-color: #fff;
-
.pallete-colors {
// display: flex;
// width: 100%;
@@ -42,7 +40,6 @@
vertical-align: top;
font-size: 2rem;
line-height: 1;
- color: #000;
border: 0;
background: transparent;
@@ -51,7 +48,7 @@
.pallete-color {
width: 36px;
height: 36px;
- border: 2px solid #000;
+ border: 2px solid;
border-radius: 3px;
transition: transform 0.25s;
cursor: pointer;
diff --git a/packages/client/src/components/Toolbar/Palette.tsx b/packages/client/src/components/Toolbar/Palette.tsx
index 056b02ff23962834ac822292a9f1d762264d5efc..b3f9a3a666e5fca760889f493cafb1d75e085f0a 100644
--- a/packages/client/src/components/Toolbar/Palette.tsx
+++ b/packages/client/src/components/Toolbar/Palette.tsx
@@ -29,7 +29,7 @@ export const Palette = () => {
}, []);
return (
-
+
)}
diff --git a/packages/client/src/index.tsx b/packages/client/src/index.tsx
index fc201d96f5c35d6d82355da6a740c7f1782d58d6..0f899443a98a8819071b5fc09934101f89c8a389 100644
--- a/packages/client/src/index.tsx
+++ b/packages/client/src/index.tsx
@@ -1,6 +1,7 @@
import React from "react";
import { createRoot } from "react-dom/client";
import { NextUIProvider } from "@nextui-org/react";
+import { ThemeProvider } from 'next-themes'
import App from "./components/App";
import Bugsnag from "@bugsnag/js";
@@ -26,7 +27,11 @@ root.render(
-
+
+
+
diff --git a/packages/client/src/style.scss b/packages/client/src/style.scss
index 5b1d2eea6d2f69c452898d09b36e9aad62186756..8eb97cc86a57d85966c67a211df019b096153709 100644
--- a/packages/client/src/style.scss
+++ b/packages/client/src/style.scss
@@ -10,8 +10,6 @@ html,
body {
overscroll-behavior: contain;
touch-action: none;
-
- background-color: #ddd !important;
}
header#main-header {
@@ -150,8 +148,6 @@ main {
position: fixed;
top: 0;
z-index: 9998;
- background-color: #fff;
- color: #000;
height: 100%;
min-width: 20rem;