1
0
mirror of https://github.com/coder/coder.git synced 2025-03-15 10:17:09 +00:00

refactor: consolidate purple theme code and fix navigation styling

- Refactored purple theme to extend dark theme where possible
- Reduced code duplication by inheriting common styles from dark theme
- Fixed navigation item highlighting by adding contrast between active and inactive items
- Applied inheritance pattern to all theme components: roles, experimental, monaco, mui, and branding
- Improved maintainability by only overriding purple-specific styles

🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
Ben Potter
2025-03-11 00:46:16 +00:00
parent 5b50b46fa6
commit 07966c2ae9
6 changed files with 49 additions and 200 deletions

@ -78,7 +78,7 @@
}
.purple {
--content-primary: 0 0% 100%;
--content-secondary: 0 0% 100%;
--content-secondary: 270 50% 80%;
--content-link: 270 100% 80%;
--content-invert: 270 10% 4%;
--content-disabled: 270 5% 60%;

@ -1,8 +1,13 @@
import tw from "../tailwindColors";
import type { Branding } from "../branding";
import darkBranding from "../dark/branding";
// Purple theme branding
// Create purple branding by extending dark branding
const branding: Branding = {
// Start with dark branding
...darkBranding,
// Override with purple-specific branding
enterprise: {
background: tw.purple[800],
divider: tw.purple[600],

@ -1,8 +1,13 @@
import type { NewTheme } from "../experimental";
import tw from "../tailwindColors";
import darkExperimental from "../dark/experimental";
// Using the dark experimental theme as a basis but with purple colors
// Create purple experimental theme by extending dark theme
const experimental: NewTheme = {
// Start with dark theme
...darkExperimental,
// Override with purple-specific styles
l1: {
background: tw.purple[950],
outline: tw.purple[700],

@ -1,37 +1,26 @@
import type * as monaco from "monaco-editor";
import darkMonaco from "../dark/monaco";
import muiTheme from "./mui";
export default {
base: "vs-dark",
inherit: true,
rules: [
{
token: "comment",
foreground: "6B737C",
},
{
token: "type",
foreground: "C4A7F5", // Lighter purple for types
},
{
token: "string",
foreground: "9DB1C5",
},
{
token: "variable",
foreground: "DDDDDD",
},
{
token: "identifier",
foreground: "C4A7F5", // Lighter purple for identifiers
},
{
token: "delimiter.curly",
foreground: "EBB325",
},
],
// Create a purple monaco theme based on dark monaco theme
const purpleMonacoTheme: monaco.editor.IStandaloneThemeData = {
...darkMonaco,
// Override only the rules that need purple styling
rules: darkMonaco.rules.map(rule => {
// Apply purple colors to type and identifier tokens
if (rule.token === "type" || rule.token === "identifier") {
return {
...rule,
foreground: "C4A7F5" // Lighter purple for types and identifiers
};
}
return rule;
}),
colors: {
"editor.foreground": "#eeeeee",
...darkMonaco.colors,
"editor.foreground": muiTheme.palette.text.primary,
"editor.background": muiTheme.palette.background.paper,
},
} satisfies monaco.editor.IStandaloneThemeData as monaco.editor.IStandaloneThemeData;
}
};
export default purpleMonacoTheme;

@ -1,13 +1,15 @@
// biome-ignore lint/nursery/noRestrictedImports: createTheme
import { createTheme } from "@mui/material/styles";
import { BODY_FONT_FAMILY, borderRadius } from "../constants";
import { components } from "../mui";
import darkTheme from "../dark/mui";
import tw from "../tailwindColors";
// Create a simple purple theme based on the dark theme structure
// Create a purple theme based on the dark theme
// This significantly reduces code duplication
const muiTheme = createTheme({
...darkTheme,
palette: {
mode: "dark", // Using dark mode as the base
...darkTheme.palette,
// Override with purple-specific colors
primary: {
main: tw.purple[500],
contrastText: tw.white,
@ -29,27 +31,6 @@ const muiTheme = createTheme({
disabled: tw.purple[500],
},
divider: tw.purple[700],
warning: {
light: tw.amber[500],
main: tw.amber[800],
dark: tw.amber[950],
},
success: {
main: tw.green[500],
dark: tw.green[600],
},
info: {
light: tw.blue[400],
main: tw.blue[600],
dark: tw.blue[950],
contrastText: tw.white,
},
error: {
light: tw.red[400],
main: tw.red[500],
dark: tw.red[950],
contrastText: tw.white,
},
action: {
hover: tw.purple[600],
active: tw.purple[500],
@ -57,30 +38,11 @@ const muiTheme = createTheme({
disabledBackground: tw.purple[800],
selected: tw.purple[600],
},
neutral: {
main: tw.zinc[50],
},
dots: tw.purple[500],
},
typography: {
fontFamily: BODY_FONT_FAMILY,
allVariants: {
color: tw.white,
},
body1: {
fontSize: "1rem",
lineHeight: "160%",
},
body2: {
fontSize: "0.875rem",
lineHeight: "160%",
},
},
shape: {
borderRadius,
},
components: {
...components,
...darkTheme.components,
// Override only the components that need purple-specific styling
MuiMenuItem: {
styleOverrides: {
root: {
@ -154,15 +116,6 @@ const muiTheme = createTheme({
},
},
},
MuiChip: {
styleOverrides: {
root: {
"& .MuiChip-label": {
textTransform: "none",
},
},
},
},
},
});

@ -1,67 +1,14 @@
import type { Roles } from "../roles";
import colors from "../tailwindColors";
import darkRoles from "../dark/roles";
// Create a purple theme by extending the dark theme roles
// This maintains consistency with dark theme and reduces duplication
const roles: Roles = {
danger: {
background: colors.orange[950],
outline: colors.orange[500],
text: colors.orange[50],
fill: {
solid: colors.orange[500],
outline: colors.orange[400],
text: colors.white,
},
disabled: {
background: colors.orange[950],
outline: colors.orange[800],
text: colors.orange[200],
fill: {
solid: colors.orange[800],
outline: colors.orange[800],
text: colors.white,
},
},
hover: {
background: colors.orange[900],
outline: colors.orange[500],
text: colors.white,
fill: {
solid: colors.orange[500],
outline: colors.orange[500],
text: colors.white,
},
},
},
error: {
background: colors.red[950],
outline: colors.red[600],
text: colors.red[50],
fill: {
solid: colors.red[400],
outline: colors.red[400],
text: colors.white,
},
},
warning: {
background: colors.amber[950],
outline: colors.amber[300],
text: colors.amber[50],
fill: {
solid: colors.amber[500],
outline: colors.amber[500],
text: colors.white,
},
},
notice: {
background: colors.blue[950],
outline: colors.blue[400],
text: colors.blue[50],
fill: {
solid: colors.blue[500],
outline: colors.blue[600],
text: colors.white,
},
},
// Reuse all common role definitions from dark theme
...darkRoles,
// Override only the roles that need purple styling
info: {
background: colors.purple[950],
outline: colors.purple[400],
@ -72,36 +19,6 @@ const roles: Roles = {
text: colors.white,
},
},
success: {
background: colors.green[950],
outline: colors.green[500],
text: colors.green[50],
fill: {
solid: colors.green[600],
outline: colors.green[600],
text: colors.white,
},
disabled: {
background: colors.green[950],
outline: colors.green[800],
text: colors.green[200],
fill: {
solid: colors.green[800],
outline: colors.green[800],
text: colors.white,
},
},
hover: {
background: colors.green[900],
outline: colors.green[500],
text: colors.white,
fill: {
solid: colors.green[500],
outline: colors.green[500],
text: colors.white,
},
},
},
active: {
background: colors.purple[950],
outline: colors.purple[500],
@ -132,26 +49,6 @@ const roles: Roles = {
},
},
},
inactive: {
background: colors.zinc[950],
outline: colors.zinc[500],
text: colors.zinc[50],
fill: {
solid: colors.zinc[400],
outline: colors.zinc[400],
text: colors.white,
},
},
preview: {
background: colors.violet[950],
outline: colors.violet[500],
text: colors.violet[50],
fill: {
solid: colors.violet[400],
outline: colors.violet[400],
text: colors.white,
},
},
};
export default roles;