feat: rename link color to --color-link and add dark/light theme support

- Rename CSS variable from --link-color to --color-link
- Add linkColorDark and linkColorLight settings (replacing single linkColor)
- Add --color-link to dark and light theme CSS variables
- Use CSS var() references to automatically switch based on theme
- Update settings UI to show separate color pickers for dark and light themes
- Default: dark=#38bdf8 (sky-400), light=#3b82f6 (blue-500)
- Update all CSS references to use new variable name
This commit is contained in:
Gigi
2025-11-07 22:34:46 +01:00
parent 36659ad2cc
commit 286d5df5b8
7 changed files with 34 additions and 11 deletions

View File

@@ -51,7 +51,8 @@ const DEFAULT_SETTINGS: UserSettings = {
ttsDetectContentLanguage: true, ttsDetectContentLanguage: true,
ttsLanguageMode: 'content', ttsLanguageMode: 'content',
ttsDefaultSpeed: 2.1, ttsDefaultSpeed: 2.1,
linkColor: '#38bdf8', linkColorDark: '#38bdf8',
linkColorLight: '#3b82f6',
} }
interface SettingsProps { interface SettingsProps {

View File

@@ -110,11 +110,22 @@ const ReadingDisplaySettings: React.FC<ReadingDisplaySettingsProps> = ({ setting
</div> </div>
<div className="setting-group setting-inline"> <div className="setting-group setting-inline">
<label className="setting-label">Link Color</label> <label className="setting-label">Link Color (Dark)</label>
<div className="setting-control"> <div className="setting-control">
<ColorPicker <ColorPicker
selectedColor={settings.linkColor || '#38bdf8'} selectedColor={settings.linkColorDark || '#38bdf8'}
onColorChange={(color) => onUpdate({ linkColor: color })} onColorChange={(color) => onUpdate({ linkColorDark: color })}
colors={LINK_COLORS}
/>
</div>
</div>
<div className="setting-group setting-inline">
<label className="setting-label">Link Color (Light)</label>
<div className="setting-control">
<ColorPicker
selectedColor={settings.linkColorLight || '#3b82f6'}
onColorChange={(color) => onUpdate({ linkColorLight: color })}
colors={LINK_COLORS} colors={LINK_COLORS}
/> />
</div> </div>
@@ -191,7 +202,8 @@ const ReadingDisplaySettings: React.FC<ReadingDisplaySettingsProps> = ({ setting
fontSize: `${settings.fontSize || 21}px`, fontSize: `${settings.fontSize || 21}px`,
'--highlight-rgb': hexToRgb(settings.highlightColor || '#ffff00'), '--highlight-rgb': hexToRgb(settings.highlightColor || '#ffff00'),
'--paragraph-alignment': settings.paragraphAlignment || 'justify', '--paragraph-alignment': settings.paragraphAlignment || 'justify',
'--link-color': settings.linkColor || '#38bdf8' '--color-link-dark': settings.linkColorDark || '#38bdf8',
'--color-link-light': settings.linkColorLight || '#3b82f6'
} as React.CSSProperties} } as React.CSSProperties}
> >
<h3>The Quick Brown Fox</h3> <h3>The Quick Brown Fox</h3>

View File

@@ -68,8 +68,13 @@ export function useSettings({ relayPool, eventStore, pubkey, accountManager }: U
root.setProperty('--highlight-color-friends', settings.highlightColorFriends || '#f97316') root.setProperty('--highlight-color-friends', settings.highlightColorFriends || '#f97316')
root.setProperty('--highlight-color-nostrverse', settings.highlightColorNostrverse || '#9333ea') root.setProperty('--highlight-color-nostrverse', settings.highlightColorNostrverse || '#9333ea')
// Set link color // Set link colors for dark and light themes
root.setProperty('--link-color', settings.linkColor || '#38bdf8') // Store both values on root - CSS will use the appropriate one based on theme
const darkLinkColor = settings.linkColorDark || '#38bdf8'
const lightLinkColor = settings.linkColorLight || '#3b82f6'
root.setProperty('--color-link-dark', darkLinkColor)
root.setProperty('--color-link-light', lightLinkColor)
// Set paragraph alignment // Set paragraph alignment
root.setProperty('--paragraph-alignment', settings.paragraphAlignment || 'justify') root.setProperty('--paragraph-alignment', settings.paragraphAlignment || 'justify')

View File

@@ -74,8 +74,9 @@ export interface UserSettings {
ttsLanguageMode?: 'system' | 'content' | string // default: 'content', can also be language code like 'en', 'es', etc. ttsLanguageMode?: 'system' | 'content' | string // default: 'content', can also be language code like 'en', 'es', etc.
// Text-to-Speech settings // Text-to-Speech settings
ttsDefaultSpeed?: number // default: 2.1 ttsDefaultSpeed?: number // default: 2.1
// Link color for article content // Link color for article content (theme-specific)
linkColor?: string // default: #38bdf8 (sky-400) linkColorDark?: string // default: #38bdf8 (sky-400)
linkColorLight?: string // default: #3b82f6 (blue-500)
} }
/** /**

View File

@@ -57,6 +57,7 @@
--color-text-muted: #71717a; /* zinc-500 */ --color-text-muted: #71717a; /* zinc-500 */
--color-primary: #6366f1; /* indigo-500 */ --color-primary: #6366f1; /* indigo-500 */
--color-primary-hover: #4f46e5; /* indigo-600 */ --color-primary-hover: #4f46e5; /* indigo-600 */
--color-link: var(--color-link-dark, #38bdf8); /* sky-400 */
} }
/* Light theme */ /* Light theme */
@@ -73,6 +74,7 @@
--color-text-muted: #6b7280; /* gray-500 */ --color-text-muted: #6b7280; /* gray-500 */
--color-primary: #4f46e5; /* indigo-600 */ --color-primary: #4f46e5; /* indigo-600 */
--color-primary-hover: #4338ca; /* indigo-700 */ --color-primary-hover: #4338ca; /* indigo-700 */
--color-link: var(--color-link-light, #3b82f6); /* blue-500 */
/* Highlight colors for light theme - use same Tailwind colors */ /* Highlight colors for light theme - use same Tailwind colors */
--highlight-color-mine: #fde047; /* yellow-300 */ --highlight-color-mine: #fde047; /* yellow-300 */
@@ -97,6 +99,7 @@
--color-text-muted: #71717a; --color-text-muted: #71717a;
--color-primary: #6366f1; --color-primary: #6366f1;
--color-primary-hover: #4f46e5; --color-primary-hover: #4f46e5;
--color-link: var(--color-link-dark, #38bdf8);
} }
} }
@@ -112,6 +115,7 @@
--color-text-muted: #6b7280; --color-text-muted: #6b7280;
--color-primary: #4f46e5; --color-primary: #4f46e5;
--color-primary-hover: #4338ca; --color-primary-hover: #4338ca;
--color-link: var(--color-link-light, #3b82f6);
/* Standard highlight colors */ /* Standard highlight colors */
--highlight-color-mine: #fde047; --highlight-color-mine: #fde047;

View File

@@ -44,7 +44,7 @@
text-align: var(--paragraph-alignment, justify); text-align: var(--paragraph-alignment, justify);
} }
.preview-content a { .preview-content a {
color: var(--link-color, #38bdf8); color: var(--color-link);
text-decoration: none; text-decoration: none;
} }
.preview-content a:hover { .preview-content a:hover {

View File

@@ -160,7 +160,7 @@
opacity: 0.69; opacity: 0.69;
margin: 2.5rem 0; margin: 2.5rem 0;
} }
.reader-markdown a { color: var(--link-color, #38bdf8); text-decoration: none; } .reader-markdown a { color: var(--color-link); text-decoration: none; }
.reader-markdown a:hover { text-decoration: underline; } .reader-markdown a:hover { text-decoration: underline; }
.reader-markdown code { background: var(--color-bg-subtle); border: 1px solid var(--color-border); border-radius: 4px; padding: 0.15rem 0.4rem; font-size: 0.9em; font-family: 'Monaco', 'Menlo', 'Consolas', 'Courier New', monospace; } .reader-markdown code { background: var(--color-bg-subtle); border: 1px solid var(--color-border); border-radius: 4px; padding: 0.15rem 0.4rem; font-size: 0.9em; font-family: 'Monaco', 'Menlo', 'Consolas', 'Courier New', monospace; }
.reader-markdown pre { background: var(--color-bg-subtle); border: 1px solid var(--color-border); border-radius: 8px; padding: 1rem; overflow-x: auto; margin: 1rem 0; line-height: 1.5; font-family: 'Monaco', 'Menlo', 'Consolas', 'Courier New', monospace; } .reader-markdown pre { background: var(--color-bg-subtle); border: 1px solid var(--color-border); border-radius: 8px; padding: 1rem; overflow-x: auto; margin: 1rem 0; line-height: 1.5; font-family: 'Monaco', 'Menlo', 'Consolas', 'Courier New', monospace; }