Compare commits

...

12 Commits

19 changed files with 190 additions and 34 deletions

BIN
bun.lockb

Binary file not shown.

View File

@@ -31,8 +31,8 @@
"@types/chroma-js": "^2.4.4",
"@types/events": "^3.0.3",
"@types/ramda": "^0.30.1",
"@types/react": "^18.2.15",
"@types/react-dom": "^18.2.7",
"@types/react": "^18.3.3",
"@types/react-dom": "^18.3.0",
"@vitejs/plugin-react": "^4.2.1",
"typescript": "^5.2.2",
"vite": "^5.3.1"

View File

@@ -2,7 +2,9 @@
"$schema": "../gen/schemas/desktop-schema.json",
"identifier": "default",
"description": "Capability for the main window",
"windows": ["main"],
"windows": [
"main"
],
"permissions": [
"path:default",
"event:default",
@@ -12,6 +14,7 @@
"resources:default",
"menu:default",
"tray:default",
"shell:allow-open"
"shell:allow-open",
"window:allow-start-dragging"
]
}

View File

@@ -13,7 +13,13 @@
{
"title": "BugWork",
"width": 1200,
"height": 800
"height": 800,
"minWidth": 1200,
"minHeight": 800,
"titleBarStyle": "Overlay",
"decorations": true,
"hiddenTitle": true,
"transparent": false
}
],
"security": {

View File

@@ -0,0 +1,26 @@
import { Spacer } from "@/foundations";
import { flex, mq } from "@/style-predefines";
import { css } from "@emotion/react";
import styled from "@emotion/styled";
import chroma from "chroma-js";
const NavigationContainer = styled.div(
({ theme }) => css`
height: 100%;
width: ${theme.spacings.xxs * 36}px;
padding-top: ${theme.spacings.xxs * 24}px;
background-color: ${chroma(theme.backgroundColor.light).darken(0.3).hex()};
${flex(theme, "column", "flex-start", "stretch", "sm")}
${mq.dark} {
background-color: ${chroma(theme.backgroundColor.dark).brighten(0.3).hex()};
}
`
);
export function NavigationBar() {
return (
<NavigationContainer>
<Spacer />
</NavigationContainer>
);
}

View File

@@ -0,0 +1,17 @@
import { css } from "@emotion/react";
import styled from "@emotion/styled";
const Handler = styled.div(
({ theme }) => css`
position: fixed;
top: 0;
left: 0;
right: 0;
height: ${theme.spacings.xxs * 24}px;
z-index: 1;
`
);
export function WindowMoveHandler() {
return <Handler data-tauri-drag-region />;
}

View File

@@ -0,0 +1,2 @@
export { NavigationBar } from "./NavigationBar";
export { WindowMoveHandler } from "./WindowMoveHandler";

View File

@@ -0,0 +1,42 @@
import { flex } from "@/style-predefines";
import { css, useTheme } from "@emotion/react";
import styled from "@emotion/styled";
import { __, always, cond, includes, T } from "ramda";
import { PropsWithChildren } from "react";
type AvatarProps = {
size?: "xs" | "sm" | "md" | "lg" | "xl" | "xxl";
square?: boolean;
bgColor?: string;
};
const AvatarContainer = styled("div")<AvatarProps>(({ theme, size, square }) => {
const radiusSize = cond([
[includes(__, ["xs", "sm", "md"]), always("xxs")],
[T, always("xs")],
])(size);
return css`
height: ${theme.spacings[size]};
width: ${theme.spacings[size]};
border-radius: ${theme.radius[square ? "none" : radiusSize]};
overflow: hidden;
${flex(theme, "row", "center", "center")}
.child {
overflow: hidden;
}
`;
});
export function Avatar({
size = "md",
square = false,
bgColor,
children,
}: PropsWithChildren<AvatarProps>) {
const theme = useTheme();
return (
<AvatarContainer size={size} square={square}>
<div className="child">{children}</div>
</AvatarContainer>
);
}

View File

@@ -0,0 +1,10 @@
import { css } from "@emotion/react";
import styled from "@emotion/styled";
export const Spacer = styled.div(
() => css`
flex-grow: 1;
flex-shrink: 0;
align-self: stretch;
`
);

View File

@@ -0,0 +1 @@
export { Spacer } from "./Spacer";

View File

@@ -1,20 +1,33 @@
import { css } from "@emotion/react";
import { css, Theme } from "@emotion/react";
import { mq } from "./style-predefines";
export const globalStyle = (theme) =>
css({
[":root"]: {
colorScheme: "light dark",
fontFamily: "Inter, Avenir, Helvetica, Arial, sans-serif",
fontSize: 0.625,
fontSynthesis: "none",
textRendering: "optimizeLegibility",
WebkitFontSmoothing: "antialiased",
MozOsxFontSmoothing: "grayscale",
WebkitTextSizeAdjust: "100%",
backgroundColor: theme.backgroundColor.light,
[mq.dark]: {
backgroundColor: theme.backgroundColor.dark,
},
},
});
export const globalStyle = (theme: Theme) => css`
:root {
color-scheme: light dark;
font-family: Inter, Avenir, Helvetica, Arial, sans-serif;
font-size: 0.625;
font-synthesis: none;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
-webkit-text-size-adjust: 100%;
color: ${theme.foregroundColor.light};
background-color: ${theme.backgroundColor.light};
overflow: hidden;
height: 100vh;
width: 100vw;
${mq.dark} {
color: ${theme.foregroundColor.dark};
background-color: ${theme.backgroundColor.dark};
}
}
body {
height: inherit;
width: inherit;
overflow: hidden;
#root {
height: inherit;
width: inherit;
}
}
`;

0
src/hooks/index.tsx Normal file
View File

View File

@@ -4,7 +4,7 @@ import React from "react";
import ReactDOM from "react-dom/client";
import { RouterProvider } from "react-router-dom";
import { globalStyle } from "./global-style";
import { routes } from "./pages/routes";
import { routes } from "./pages";
import { theme } from "./theme";
ReactDOM.createRoot(document.getElementById("root") as HTMLElement).render(

View File

@@ -0,0 +1,27 @@
import { NavigationBar, WindowMoveHandler } from "@/components";
import { flex } from "@/style-predefines";
import { css } from "@emotion/react";
import styled from "@emotion/styled";
const LayoutContainer = styled.div(
({ theme }) => css`
height: 100%;
width: 100%;
overflow: hidden;
${flex(theme, "row", "flex-start", "stretch")}
.main-content {
flex-grow: 1;
overflow: hidden;
}
`
);
export function MainLayout() {
return (
<LayoutContainer>
<WindowMoveHandler />
<NavigationBar />
<div className="main-content">Main Content</div>
</LayoutContainer>
);
}

View File

@@ -0,0 +1,2 @@
export { MainLayout } from "./MainLayout";
export { routes } from "./routes";

View File

@@ -1,3 +1,9 @@
import { createBrowserRouter } from "react-router-dom";
import { MainLayout } from "./MainLayout";
export const routes = createBrowserRouter([]);
export const routes = createBrowserRouter([
{
path: "/",
element: <MainLayout />,
},
]);

0
src/states/index.tsx Normal file
View File

View File

@@ -35,8 +35,8 @@ export function flex(
direction: Property.FlexDirection = "row",
justify: Property.JustifyContent = "flex-start",
align: Property.AlignItems = "start",
wrap: Property.FlexWrap = "nowrap",
gap: MeasureUnit = "none"
gap: MeasureUnit = "none",
wrap: Property.FlexWrap = "nowrap"
) {
return css({
display: "flex",

View File

@@ -1,4 +1,5 @@
import type { Theme } from "@emotion/react";
import chroma from "chroma-js";
import { generatePalette } from "./style-predefines";
const colors: Theme["colors"] = {
@@ -9,7 +10,7 @@ const colors: Theme["colors"] = {
grape: generatePalette("#f8f0fc", "#862e9c"),
violet: generatePalette("#f3f0ff", "#5f3dc4"),
indigo: generatePalette("#edf2ff", "#364fc7"),
bllue: generatePalette("#e7f5ff", "#1864ab"),
blue: generatePalette("#e7f5ff", "#1864ab"),
cyan: generatePalette("#e3fafc", "#0b7285"),
teal: generatePalette("#e6fcf5", "#087f5b"),
green: generatePalette("#ebfbee", "#2b8a3e"),
@@ -23,12 +24,12 @@ export const theme: Partial<Theme> = {
white: "#ffffff",
black: "#000000",
foregroundColor: {
light: chroma.hsl(0, 0, 0.06).hex(),
dark: chroma.hsl(0, 0, 0.88).hex(),
light: chroma.hsl(0, 0, 0.12).hex(),
dark: chroma.hsl(0, 0, 0.82).hex(),
},
backgroundColor: {
light: chroma.hsl(0, 0, 0.96).hex(),
dark: chroma.hsl(0, 0, 0.18).hex(),
light: chroma.hsl(0, 0, 0.94).hex(),
dark: chroma.hsl(0, 0, 0.098).hex(),
},
successColor: {
light: colors.green[5],