Skip to content

Commit e77dea3

Browse files
committed
feat: primer color schemes
Signed-off-by: Adam Setch <[email protected]>
1 parent 1f90a1e commit e77dea3

File tree

9 files changed

+75
-87
lines changed

9 files changed

+75
-87
lines changed

src/renderer/__mocks__/state-mocks.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import {
88
type Link,
99
OpenPreference,
1010
type SettingsState,
11-
ThemeMode,
11+
Theme,
1212
type Token,
1313
} from '../types';
1414
import type { EnterpriseAccount } from '../utils/auth/types';
@@ -81,7 +81,7 @@ export const mockAuth: AuthState = {
8181
export const mockToken = 'token-123-456' as Token;
8282

8383
const mockAppearanceSettings = {
84-
themeMode: ThemeMode.SYSTEM,
84+
theme: Theme.SYSTEM,
8585
zoomPercentage: 100,
8686
detailedNotifications: true,
8787
showPills: true,

src/renderer/components/settings/AppearanceSettings.test.tsx

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -34,13 +34,11 @@ describe('renderer/routes/components/settings/AppearanceSettings.tsx', () => {
3434
);
3535
});
3636

37-
const select = screen.getByTestId(
38-
'settings-theme-mode',
39-
) as HTMLSelectElement;
40-
fireEvent.change(select, { target: { value: 'LIGHT_DEFAULT' } });
37+
const select = screen.getByTestId('settings-theme') as HTMLSelectElement;
38+
fireEvent.change(select, { target: { value: 'LIGHT' } });
4139

4240
expect(updateSetting).toHaveBeenCalledTimes(1);
43-
expect(updateSetting).toHaveBeenCalledWith('themeMode', 'LIGHT_DEFAULT');
41+
expect(updateSetting).toHaveBeenCalledWith('theme', 'LIGHT');
4442
});
4543

4644
it('should update the zoom value when using CMD + and CMD -', async () => {

src/renderer/components/settings/AppearanceSettings.tsx

Lines changed: 17 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ import {
2323

2424
import { namespacedEvent } from '../../../shared/events';
2525
import { AppContext } from '../../context/App';
26-
import { Size, ThemeMode } from '../../types';
26+
import { Size, Theme } from '../../types';
2727
import { hasMultipleAccounts } from '../../utils/auth/utils';
2828
import {
2929
DEFAULT_DAY_COLOR_SCHEME,
@@ -49,8 +49,8 @@ export const AppearanceSettings: FC = () => {
4949
useEffect(() => {
5050
ipcRenderer.on(
5151
namespacedEvent('update-theme'),
52-
(_, updatedTheme: ThemeMode) => {
53-
if (settings.themeMode === ThemeMode.SYSTEM) {
52+
(_, updatedTheme: Theme) => {
53+
if (settings.theme === Theme.SYSTEM) {
5454
const mode = isDayScheme(updatedTheme) ? 'day' : 'night';
5555
setColorMode('auto');
5656
setDayScheme(DEFAULT_DAY_COLOR_SCHEME);
@@ -59,7 +59,7 @@ export const AppearanceSettings: FC = () => {
5959
}
6060
},
6161
);
62-
}, [settings.themeMode, setColorMode, setDayScheme, setNightScheme]);
62+
}, [settings.theme, setColorMode, setDayScheme, setNightScheme]);
6363

6464
window.addEventListener('resize', () => {
6565
// clear the timeout
@@ -81,45 +81,37 @@ export const AppearanceSettings: FC = () => {
8181

8282
<Select
8383
id="theme"
84-
value={settings.themeMode}
85-
onChange={(evt) =>
86-
updateSetting('themeMode', evt.target.value as ThemeMode)
87-
}
88-
data-testid="settings-theme-mode"
84+
value={settings.theme}
85+
onChange={(evt) => updateSetting('theme', evt.target.value as Theme)}
86+
data-testid="settings-theme"
8987
>
9088
<Select.OptGroup label="System">
91-
<Select.Option value={ThemeMode.SYSTEM}>System</Select.Option>
89+
<Select.Option value={Theme.SYSTEM}>System</Select.Option>
9290
</Select.OptGroup>
9391
<Select.OptGroup label="Light">
94-
<Select.Option value={ThemeMode.LIGHT_DEFAULT}>
95-
Light default
96-
</Select.Option>
97-
<Select.Option value={ThemeMode.LIGHT_HIGH_CONTRAST}>
92+
<Select.Option value={Theme.LIGHT}>Light default</Select.Option>
93+
<Select.Option value={Theme.LIGHT_HIGH_CONTRAST}>
9894
Light high contrast
9995
</Select.Option>
100-
<Select.Option value={ThemeMode.LIGHT_COLOR_BLIND}>
96+
<Select.Option value={Theme.LIGHT_COLORBLIND}>
10197
Light Protanopia & Deuteranopia
10298
</Select.Option>
103-
<Select.Option value={ThemeMode.LIGHT_TRITANOPIA}>
99+
<Select.Option value={Theme.LIGHT_TRITANOPIA}>
104100
Light Tritanopia
105101
</Select.Option>
106102
</Select.OptGroup>
107103
<Select.OptGroup label="Dark">
108-
<Select.Option value={ThemeMode.DARK_DEFAULT}>
109-
Dark default
110-
</Select.Option>
111-
<Select.Option value={ThemeMode.DARK_HIGH_CONTRAST}>
104+
<Select.Option value={Theme.DARK}>Dark default</Select.Option>
105+
<Select.Option value={Theme.DARK_HIGH_CONTRAST}>
112106
Dark high contrast
113107
</Select.Option>
114-
<Select.Option value={ThemeMode.DARK_COLOR_BLIND}>
108+
<Select.Option value={Theme.DARK_COLORBLIND}>
115109
Dark Protanopia & Deuteranopia
116110
</Select.Option>
117-
<Select.Option value={ThemeMode.DARK_TRITANOPIA}>
111+
<Select.Option value={Theme.DARK_TRITANOPIA}>
118112
Dark Tritanopia
119113
</Select.Option>
120-
<Select.Option value={ThemeMode.DARK_DIMMED}>
121-
Dark dimmed
122-
</Select.Option>
114+
<Select.Option value={Theme.DARK_DIMMED}>Dark dimmed</Select.Option>
123115
</Select.OptGroup>
124116
</Select>
125117
</div>

src/renderer/context/App.tsx

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ import {
2323
type SettingsState,
2424
type SettingsValue,
2525
type Status,
26-
ThemeMode,
26+
Theme,
2727
} from '../types';
2828
import type { Notification } from '../typesGitHub';
2929
import { headNotifications } from '../utils/api/client';
@@ -66,7 +66,7 @@ export const defaultAuth: AuthState = {
6666
};
6767

6868
const defaultAppearanceSettings = {
69-
themeMode: ThemeMode.SYSTEM,
69+
theme: Theme.SYSTEM,
7070
zoomPercentage: 100,
7171
detailedNotifications: true,
7272
showPills: true,
@@ -150,9 +150,9 @@ export const AppProvider = ({ children }: { children: ReactNode }) => {
150150
}, []);
151151

152152
useEffect(() => {
153-
const colorScheme = mapThemeModeToColorScheme(settings.themeMode);
153+
const colorScheme = mapThemeModeToColorScheme(settings.theme);
154154

155-
if (isDayScheme(settings.themeMode)) {
155+
if (isDayScheme(settings.theme)) {
156156
setDayScheme(colorScheme ?? DEFAULT_DAY_COLOR_SCHEME);
157157
setColorMode('day');
158158
setScrollbarTheme('day');
@@ -161,7 +161,7 @@ export const AppProvider = ({ children }: { children: ReactNode }) => {
161161
setColorMode('night');
162162
setScrollbarTheme('night');
163163
}
164-
}, [settings.themeMode, setDayScheme, setNightScheme]);
164+
}, [settings.theme, setColorMode, setDayScheme, setNightScheme]);
165165

166166
// biome-ignore lint/correctness/useExhaustiveDependencies: We only want fetchNotifications to be called for account changes
167167
useEffect(() => {

src/renderer/routes/__snapshots__/Settings.test.tsx.snap

Lines changed: 5 additions & 5 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/renderer/types.ts

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -59,15 +59,15 @@ export type SettingsValue =
5959
| GroupBy
6060
| OpenPreference
6161
| Reason[]
62-
| ThemeMode;
62+
| Theme;
6363

6464
export type SettingsState = AppearanceSettingsState &
6565
NotificationSettingsState &
6666
SystemSettingsState &
6767
FilterSettingsState;
6868

6969
interface AppearanceSettingsState {
70-
themeMode: ThemeMode;
70+
theme: Theme;
7171
zoomPercentage: number;
7272
detailedNotifications: boolean;
7373
showAccountHeader: boolean;
@@ -104,15 +104,15 @@ export interface GitifyState {
104104
settings?: SettingsState;
105105
}
106106

107-
export enum ThemeMode {
107+
export enum Theme {
108108
SYSTEM = 'SYSTEM',
109-
LIGHT_DEFAULT = 'LIGHT_DEFAULT',
109+
LIGHT = 'LIGHT',
110110
LIGHT_HIGH_CONTRAST = 'LIGHT_HIGH_CONTRAST',
111-
LIGHT_COLOR_BLIND = 'LIGHT_COLOR_BLIND',
111+
LIGHT_COLORBLIND = 'LIGHT_COLORBLIND',
112112
LIGHT_TRITANOPIA = 'LIGHT_TRITANOPIA',
113-
DARK_DEFAULT = 'LIGHT_DARK_DEFAULT',
113+
DARK = 'DARK',
114114
DARK_HIGH_CONTRAST = 'DARK_HIGH_CONTRAST',
115-
DARK_COLOR_BLIND = 'DARK_COLOR_BLIND',
115+
DARK_COLORBLIND = 'DARK_COLORBLIND',
116116
DARK_TRITANOPIA = 'DARK_TRITANOPIA',
117117
DARK_DIMMED = 'DARK_DIMMED',
118118
}

src/renderer/utils/storage.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ describe('renderer/utils/storage.ts', () => {
1818
},
1919
],
2020
},
21-
settings: { themeMode: 'DARK_DEFAULT' },
21+
settings: { theme: 'DARK_DEFAULT' },
2222
}),
2323
);
2424
const result = loadState();
@@ -35,7 +35,7 @@ describe('renderer/utils/storage.ts', () => {
3535
expect(result.auth.token).toBeUndefined();
3636
expect(result.auth.enterpriseAccounts).toBeUndefined();
3737
expect(result.auth.user).toBeUndefined();
38-
expect(result.settings.themeMode).toBe('DARK_DEFAULT');
38+
expect(result.settings.theme).toBe('DARK_DEFAULT');
3939
});
4040

4141
it('should load the state from localstorage - empty', () => {

src/renderer/utils/theme.test.ts

Lines changed: 15 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { ThemeMode } from '../types';
1+
import { Theme } from '../types';
22
import {
33
getTheme,
44
mapThemeModeToColorScheme,
@@ -14,12 +14,12 @@ describe('renderer/utils/theme.ts', () => {
1414

1515
it('should change to light mode', () => {
1616
setScrollbarTheme('day');
17-
expect(getTheme()).toBe(ThemeMode.LIGHT_DEFAULT);
17+
expect(getTheme()).toBe(Theme.LIGHT);
1818
});
1919

2020
it('should change to dark mode', () => {
2121
setScrollbarTheme('night');
22-
expect(getTheme()).toBe(ThemeMode.DARK_DEFAULT);
22+
expect(getTheme()).toBe(Theme.DARK);
2323
});
2424

2525
it("should use the system's mode - light", () => {
@@ -30,7 +30,7 @@ describe('renderer/utils/theme.ts', () => {
3030
})),
3131
});
3232
setScrollbarTheme();
33-
expect(getTheme()).toBe(ThemeMode.LIGHT_DEFAULT);
33+
expect(getTheme()).toBe(Theme.LIGHT);
3434
});
3535

3636
it("should use the system's mode - dark", () => {
@@ -41,33 +41,31 @@ describe('renderer/utils/theme.ts', () => {
4141
})),
4242
});
4343
setScrollbarTheme();
44-
expect(getTheme()).toBe(ThemeMode.DARK_DEFAULT);
44+
expect(getTheme()).toBe(Theme.DARK);
4545
});
4646

4747
it('should map theme mode to github primer provider', () => {
48-
expect(mapThemeModeToColorScheme(ThemeMode.LIGHT_DEFAULT)).toBe('light');
49-
expect(mapThemeModeToColorScheme(ThemeMode.LIGHT_HIGH_CONTRAST)).toBe(
48+
expect(mapThemeModeToColorScheme(Theme.LIGHT)).toBe('light');
49+
expect(mapThemeModeToColorScheme(Theme.LIGHT_HIGH_CONTRAST)).toBe(
5050
'light_high_contrast',
5151
);
52-
expect(mapThemeModeToColorScheme(ThemeMode.LIGHT_COLOR_BLIND)).toBe(
52+
expect(mapThemeModeToColorScheme(Theme.LIGHT_COLORBLIND)).toBe(
5353
'light_colorblind',
5454
);
55-
expect(mapThemeModeToColorScheme(ThemeMode.LIGHT_TRITANOPIA)).toBe(
55+
expect(mapThemeModeToColorScheme(Theme.LIGHT_TRITANOPIA)).toBe(
5656
'light_tritanopia',
5757
);
58-
expect(mapThemeModeToColorScheme(ThemeMode.DARK_DEFAULT)).toBe('dark');
59-
expect(mapThemeModeToColorScheme(ThemeMode.DARK_HIGH_CONTRAST)).toBe(
58+
expect(mapThemeModeToColorScheme(Theme.DARK)).toBe('dark');
59+
expect(mapThemeModeToColorScheme(Theme.DARK_HIGH_CONTRAST)).toBe(
6060
'dark_high_contrast',
6161
);
62-
expect(mapThemeModeToColorScheme(ThemeMode.DARK_COLOR_BLIND)).toBe(
62+
expect(mapThemeModeToColorScheme(Theme.DARK_COLORBLIND)).toBe(
6363
'dark_colorblind',
6464
);
65-
expect(mapThemeModeToColorScheme(ThemeMode.DARK_TRITANOPIA)).toBe(
65+
expect(mapThemeModeToColorScheme(Theme.DARK_TRITANOPIA)).toBe(
6666
'dark_tritanopia',
6767
);
68-
expect(mapThemeModeToColorScheme(ThemeMode.DARK_DIMMED)).toBe(
69-
'dark_dimmed',
70-
);
71-
expect(mapThemeModeToColorScheme(ThemeMode.SYSTEM)).toBe(null);
68+
expect(mapThemeModeToColorScheme(Theme.DARK_DIMMED)).toBe('dark_dimmed');
69+
expect(mapThemeModeToColorScheme(Theme.SYSTEM)).toBe(null);
7270
});
7371
});

0 commit comments

Comments
 (0)