mirror of
https://github.com/stablyai/orca.git
synced 2026-09-22 00:02:31 +00:00
Add task provider icon setting (#1128)
This commit is contained in:
@@ -64,6 +64,7 @@ function createSettings(overrides: Partial<GlobalSettings> = {}): GlobalSettings
|
||||
openLinksInApp: false,
|
||||
rightSidebarOpenByDefault: true,
|
||||
showTitlebarAgentActivity: true,
|
||||
showTaskProviderIcons: true,
|
||||
diffDefaultView: 'inline',
|
||||
notifications: {
|
||||
enabled: true,
|
||||
|
||||
@@ -58,6 +58,7 @@ function createSettings(overrides: Partial<GlobalSettings> = {}): GlobalSettings
|
||||
openLinksInApp: false,
|
||||
rightSidebarOpenByDefault: true,
|
||||
showTitlebarAgentActivity: true,
|
||||
showTaskProviderIcons: true,
|
||||
diffDefaultView: 'inline',
|
||||
notifications: {
|
||||
enabled: true,
|
||||
|
||||
@@ -77,6 +77,7 @@ describe('Store', () => {
|
||||
expect(settings.terminalFontSize).toBe(14)
|
||||
expect(settings.terminalFontWeight).toBe(500)
|
||||
expect(settings.rightSidebarOpenByDefault).toBe(true)
|
||||
expect(settings.showTaskProviderIcons).toBe(true)
|
||||
})
|
||||
|
||||
it('returns default UI state when no data file exists', async () => {
|
||||
@@ -144,6 +145,7 @@ describe('Store', () => {
|
||||
expect(store.getSettings().editorAutoSaveDelayMs).toBe(1000)
|
||||
expect(store.getSettings().refreshLocalBaseRefOnWorktreeCreate).toBe(false)
|
||||
expect(store.getSettings().rightSidebarOpenByDefault).toBe(true)
|
||||
expect(store.getSettings().showTaskProviderIcons).toBe(true)
|
||||
// repos should be loaded
|
||||
expect(store.getRepos()).toHaveLength(1)
|
||||
})
|
||||
|
||||
@@ -32,6 +32,11 @@ export const APPEARANCE_PANE_SEARCH_ENTRIES: SettingsSearchEntry[] = [
|
||||
title: 'Titlebar Agent Activity',
|
||||
description: 'Show the number of active agents in the titlebar.',
|
||||
keywords: ['titlebar', 'agent', 'badge', 'active', 'count', 'status']
|
||||
},
|
||||
{
|
||||
title: 'Task Provider Icons',
|
||||
description: 'Show GitHub and Linear icons in the Tasks sidebar button.',
|
||||
keywords: ['tasks', 'sidebar', 'github', 'linear', 'icons', 'badges']
|
||||
}
|
||||
]
|
||||
|
||||
@@ -47,7 +52,8 @@ export function AppearancePane({
|
||||
const themeEntries = APPEARANCE_PANE_SEARCH_ENTRIES.slice(0, 1)
|
||||
const zoomEntries = APPEARANCE_PANE_SEARCH_ENTRIES.slice(1, 2)
|
||||
const layoutEntries = APPEARANCE_PANE_SEARCH_ENTRIES.slice(2, 3)
|
||||
const titlebarEntries = APPEARANCE_PANE_SEARCH_ENTRIES.slice(3)
|
||||
const titlebarEntries = APPEARANCE_PANE_SEARCH_ENTRIES.slice(3, 4)
|
||||
const sidebarEntries = APPEARANCE_PANE_SEARCH_ENTRIES.slice(4)
|
||||
|
||||
const visibleSections = [
|
||||
matchesSettingsSearch(searchQuery, themeEntries) ? (
|
||||
@@ -187,6 +193,46 @@ export function AppearancePane({
|
||||
</button>
|
||||
</SearchableSetting>
|
||||
</section>
|
||||
) : null,
|
||||
matchesSettingsSearch(searchQuery, sidebarEntries) ? (
|
||||
<section key="sidebar" className="space-y-4">
|
||||
<div className="space-y-1">
|
||||
<h3 className="text-sm font-semibold">Sidebar</h3>
|
||||
<p className="text-xs text-muted-foreground">Tune the left sidebar chrome.</p>
|
||||
</div>
|
||||
|
||||
<SearchableSetting
|
||||
title="Task Provider Icons"
|
||||
description="Show GitHub and Linear icons in the Tasks sidebar button."
|
||||
keywords={['tasks', 'sidebar', 'github', 'linear', 'icons', 'badges']}
|
||||
className="flex items-center justify-between gap-4 px-1 py-2"
|
||||
>
|
||||
<div className="space-y-0.5">
|
||||
<Label>Task Provider Icons</Label>
|
||||
<p className="text-xs text-muted-foreground">
|
||||
Show GitHub and Linear icons next to the Tasks button.
|
||||
</p>
|
||||
</div>
|
||||
<button
|
||||
role="switch"
|
||||
aria-checked={settings.showTaskProviderIcons}
|
||||
onClick={() =>
|
||||
updateSettings({
|
||||
showTaskProviderIcons: !settings.showTaskProviderIcons
|
||||
})
|
||||
}
|
||||
className={`relative inline-flex h-5 w-9 shrink-0 cursor-pointer items-center rounded-full border border-transparent transition-colors ${
|
||||
settings.showTaskProviderIcons ? 'bg-foreground' : 'bg-muted-foreground/30'
|
||||
}`}
|
||||
>
|
||||
<span
|
||||
className={`pointer-events-none block size-3.5 rounded-full bg-background shadow-sm transition-transform ${
|
||||
settings.showTaskProviderIcons ? 'translate-x-4' : 'translate-x-0.5'
|
||||
}`}
|
||||
/>
|
||||
</button>
|
||||
</SearchableSetting>
|
||||
</section>
|
||||
) : null
|
||||
].filter(Boolean)
|
||||
|
||||
|
||||
@@ -20,6 +20,7 @@ const SidebarNav = React.memo(function SidebarNav() {
|
||||
const repos = useAppStore((s) => s.repos)
|
||||
const repoMap = useRepoMap()
|
||||
const canBrowseTasks = repos.some((repo) => isGitRepoKind(repo))
|
||||
const showTaskProviderIcons = useAppStore((s) => s.settings?.showTaskProviderIcons !== false)
|
||||
|
||||
// Why: warm the GitHub work-item cache on hover/focus so by the time the
|
||||
// user's click finishes the round-trip has either completed or is already
|
||||
@@ -74,36 +75,38 @@ const SidebarNav = React.memo(function SidebarNav() {
|
||||
>
|
||||
<List className="size-4 shrink-0" strokeWidth={2.25} />
|
||||
<span className="flex-1">Tasks</span>
|
||||
<span className="flex items-center gap-1">
|
||||
<span
|
||||
role="button"
|
||||
tabIndex={-1}
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
if (!canBrowseTasks) {
|
||||
return
|
||||
}
|
||||
openTaskPage({ taskSource: 'github' })
|
||||
}}
|
||||
className="rounded p-0.5 text-muted-foreground/70 transition-colors hover:text-foreground"
|
||||
>
|
||||
<Github className="size-3.5" aria-hidden />
|
||||
{showTaskProviderIcons ? (
|
||||
<span className="flex items-center gap-1">
|
||||
<span
|
||||
role="button"
|
||||
tabIndex={-1}
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
if (!canBrowseTasks) {
|
||||
return
|
||||
}
|
||||
openTaskPage({ taskSource: 'github' })
|
||||
}}
|
||||
className="rounded p-0.5 text-muted-foreground/70 transition-colors hover:text-foreground"
|
||||
>
|
||||
<Github className="size-3.5" aria-hidden />
|
||||
</span>
|
||||
<span
|
||||
role="button"
|
||||
tabIndex={-1}
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
if (!canBrowseTasks) {
|
||||
return
|
||||
}
|
||||
openTaskPage({ taskSource: 'linear' })
|
||||
}}
|
||||
className="rounded p-0.5 text-muted-foreground/70 transition-colors hover:text-foreground"
|
||||
>
|
||||
<LinearIcon className="size-3.5" />
|
||||
</span>
|
||||
</span>
|
||||
<span
|
||||
role="button"
|
||||
tabIndex={-1}
|
||||
onClick={(e) => {
|
||||
e.stopPropagation()
|
||||
if (!canBrowseTasks) {
|
||||
return
|
||||
}
|
||||
openTaskPage({ taskSource: 'linear' })
|
||||
}}
|
||||
className="rounded p-0.5 text-muted-foreground/70 transition-colors hover:text-foreground"
|
||||
>
|
||||
<LinearIcon className="size-3.5" />
|
||||
</span>
|
||||
</span>
|
||||
) : null}
|
||||
</button>
|
||||
</div>
|
||||
)
|
||||
|
||||
@@ -150,6 +150,7 @@ export function getDefaultSettings(homedir: string): GlobalSettings {
|
||||
openLinksInApp: true,
|
||||
rightSidebarOpenByDefault: true,
|
||||
showTitlebarAgentActivity: true,
|
||||
showTaskProviderIcons: true,
|
||||
notifications: getDefaultNotificationSettings(),
|
||||
diffDefaultView: 'inline',
|
||||
promptCacheTimerEnabled: false,
|
||||
|
||||
@@ -811,6 +811,9 @@ export type GlobalSettings = {
|
||||
rightSidebarOpenByDefault: boolean
|
||||
/** Whether to show the live agent activity count badge in the titlebar. */
|
||||
showTitlebarAgentActivity: boolean
|
||||
/** Why: the Tasks sidebar label can be kept cleaner for users who do not
|
||||
* actively use the GitHub/Linear integrations behind it. */
|
||||
showTaskProviderIcons: boolean
|
||||
diffDefaultView: 'inline' | 'side-by-side'
|
||||
notifications: NotificationSettings
|
||||
/** When true, a countdown timer is shown after a Claude agent becomes idle,
|
||||
|
||||
Reference in New Issue
Block a user