refactor: update theme handling in TabContainer and Sidebar components (#8816)

* refactor: update theme handling in TabContainer and Sidebar components

* refactor: replace setTheme with toggleTheme and update theme state management
* feat: add Monitor icon for additional theme state in both components

* feat(DisplaySettings): replace theme icons with lucide icons for improved visual representation

* updated light and dark theme icons to use Sun and Moon from lucide
* replaced SyncOutlined with Monitor icon for system theme option

* format code

* feat(TabContainer): add tooltip for theme toggle button with translation support

* integrated Tooltip component to provide contextual information for the theme toggle button
* utilized useTranslation hook for internationalization of tooltip text
* imported getThemeModeLabel to enhance theme description
This commit is contained in:
beyondkmp 2025-08-04 16:50:34 +08:00 committed by GitHub
parent 90c1fff54a
commit e8b3d44400
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 35 additions and 14 deletions

View File

@ -3,19 +3,21 @@ import { isLinux, isMac, isWin } from '@renderer/config/constant'
import { useTheme } from '@renderer/context/ThemeProvider'
import { useFullscreen } from '@renderer/hooks/useFullscreen'
import { useMinappPopup } from '@renderer/hooks/useMinappPopup'
import { getTitleLabel } from '@renderer/i18n/label'
import { getThemeModeLabel, getTitleLabel } from '@renderer/i18n/label'
import tabsService from '@renderer/services/TabsService'
import { useAppDispatch, useAppSelector } from '@renderer/store'
import type { Tab } from '@renderer/store/tabs'
import { addTab, removeTab, setActiveTab } from '@renderer/store/tabs'
import { ThemeMode } from '@renderer/types'
import { classNames } from '@renderer/utils'
import { Tooltip } from 'antd'
import {
FileSearch,
Folder,
Home,
Languages,
LayoutGrid,
Monitor,
Moon,
Palette,
Settings,
@ -25,6 +27,7 @@ import {
X
} from 'lucide-react'
import { useCallback, useEffect } from 'react'
import { useTranslation } from 'react-i18next'
import { useLocation, useNavigate } from 'react-router-dom'
import styled from 'styled-components'
@ -69,8 +72,9 @@ const TabsContainer: React.FC<TabsContainerProps> = ({ children }) => {
const tabs = useAppSelector((state) => state.tabs.tabs)
const activeTabId = useAppSelector((state) => state.tabs.activeTabId)
const isFullscreen = useFullscreen()
const { theme, setTheme } = useTheme()
const { settedTheme, toggleTheme } = useTheme()
const { hideMinappPopup } = useMinappPopup()
const { t } = useTranslation()
const getTabId = (path: string): string => {
if (path === '/') return 'home'
@ -162,9 +166,20 @@ const TabsContainer: React.FC<TabsContainerProps> = ({ children }) => {
</AddTabButton>
<RightButtonsContainer>
<TopNavbarOpenedMinappTabs />
<ThemeButton onClick={() => setTheme(theme === ThemeMode.dark ? ThemeMode.light : ThemeMode.dark)}>
{theme === ThemeMode.dark ? <Moon size={16} /> : <Sun size={16} />}
</ThemeButton>
<Tooltip
title={t('settings.theme.title') + ': ' + getThemeModeLabel(settedTheme)}
mouseEnterDelay={0.8}
placement="bottom">
<ThemeButton onClick={toggleTheme}>
{settedTheme === ThemeMode.dark ? (
<Moon size={16} />
) : settedTheme === ThemeMode.light ? (
<Sun size={16} />
) : (
<Monitor size={16} />
)}
</ThemeButton>
</Tooltip>
<SettingsButton onClick={handleSettingsClick} $active={activeTabId === 'settings'}>
<Settings size={16} />
</SettingsButton>

View File

@ -21,6 +21,7 @@ import {
Languages,
LayoutGrid,
MessageSquare,
Monitor,
Moon,
Palette,
Settings,
@ -44,7 +45,7 @@ const Sidebar: FC = () => {
const { pathname } = useLocation()
const navigate = useNavigate()
const { theme, setTheme } = useTheme()
const { theme, settedTheme, toggleTheme } = useTheme()
const avatar = useAvatar()
const { t } = useTranslation()
@ -105,11 +106,17 @@ const Sidebar: FC = () => {
</Icon>
</Tooltip>
<Tooltip
title={t('settings.theme.title') + ': ' + getThemeModeLabel(theme)}
title={t('settings.theme.title') + ': ' + getThemeModeLabel(settedTheme)}
mouseEnterDelay={0.8}
placement="right">
<Icon theme={theme} onClick={() => setTheme(theme === ThemeMode.dark ? ThemeMode.light : ThemeMode.dark)}>
{theme === ThemeMode.dark ? <Moon size={20} className="icon" /> : <Sun size={20} className="icon" />}
<Icon theme={theme} onClick={toggleTheme}>
{settedTheme === ThemeMode.dark ? (
<Moon size={20} className="icon" />
) : settedTheme === ThemeMode.light ? (
<Sun size={20} className="icon" />
) : (
<Monitor size={20} className="icon" />
)}
</Icon>
</Tooltip>
<Tooltip title={t('settings.title')} mouseEnterDelay={0.8} placement="right">

View File

@ -1,4 +1,3 @@
import { SyncOutlined } from '@ant-design/icons'
import CodeEditor from '@renderer/components/CodeEditor'
import { HStack } from '@renderer/components/Layout'
import TextBadge from '@renderer/components/TextBadge'
@ -19,7 +18,7 @@ import {
} from '@renderer/store/settings'
import { ThemeMode } from '@renderer/types'
import { Button, ColorPicker, Segmented, Switch } from 'antd'
import { Minus, Plus, RotateCcw } from 'lucide-react'
import { Minus, Monitor, Moon, Plus, RotateCcw, Sun } from 'lucide-react'
import { FC, useCallback, useEffect, useMemo, useState } from 'react'
import { useTranslation } from 'react-i18next'
import styled from 'styled-components'
@ -108,7 +107,7 @@ const DisplaySettings: FC = () => {
value: ThemeMode.light,
label: (
<div style={{ display: 'flex', alignItems: 'center', gap: '5px' }}>
<i className="iconfont icon-theme icon-theme-light" />
<Sun size={16} />
<span>{t('settings.theme.light')}</span>
</div>
)
@ -117,7 +116,7 @@ const DisplaySettings: FC = () => {
value: ThemeMode.dark,
label: (
<div style={{ display: 'flex', alignItems: 'center', gap: '5px' }}>
<i className="iconfont icon-theme icon-dark1" />
<Moon size={16} />
<span>{t('settings.theme.dark')}</span>
</div>
)
@ -126,7 +125,7 @@ const DisplaySettings: FC = () => {
value: ThemeMode.system,
label: (
<div style={{ display: 'flex', alignItems: 'center', gap: '5px' }}>
<SyncOutlined />
<Monitor size={16} />
<span>{t('settings.theme.system')}</span>
</div>
)