Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions BitFun-Installer/src/theme/installerThemesData.ts
Original file line number Diff line number Diff line change
Expand Up @@ -140,10 +140,10 @@ export const THEMES: InstallerTheme[] = [
type: 'dark',
colors: {
background: { primary: '#1a1c1e', secondary: '#1a1c1e', tertiary: '#1a1c1e', quaternary: '#32363a', elevated: '#1a1c1e', workbench: '#1a1c1e', flowchat: '#1a1c1e', tooltip: 'rgba(42, 45, 48, 0.96)' },
text: { primary: '#e4e6e8', secondary: '#b8bbc0', muted: '#8a8d92', disabled: '#5a5d62' },
accent: { '50': 'rgba(107, 155, 213, 0.04)', '100': 'rgba(107, 155, 213, 0.08)', '200': 'rgba(107, 155, 213, 0.15)', '300': 'rgba(107, 155, 213, 0.25)', '400': 'rgba(107, 155, 213, 0.4)', '500': '#6b9bd5', '600': '#5a8bc4', '700': 'rgba(90, 139, 196, 0.8)', '800': 'rgba(90, 139, 196, 0.9)' },
purple: { '50': 'rgba(165, 180, 252, 0.04)', '100': 'rgba(165, 180, 252, 0.08)', '200': 'rgba(165, 180, 252, 0.15)', '300': 'rgba(165, 180, 252, 0.25)', '400': 'rgba(165, 180, 252, 0.4)', '500': '#a5b4fc', '600': '#8b9adb', '700': 'rgba(139, 154, 219, 0.8)', '800': 'rgba(139, 154, 219, 0.9)' },
semantic: { success: '#7fb899', warning: '#d4a574', error: '#c9878d', info: '#6b9bd5', highlight: '#d4d6d8', highlightBg: 'rgba(212, 214, 216, 0.12)' },
text: { primary: '#eef0f3', secondary: '#c8ccd2', muted: '#9ea4ab', disabled: '#65696f' },
accent: { '50': 'rgba(122, 176, 238, 0.04)', '100': 'rgba(122, 176, 238, 0.08)', '200': 'rgba(122, 176, 238, 0.15)', '300': 'rgba(122, 176, 238, 0.25)', '400': 'rgba(122, 176, 238, 0.4)', '500': '#7ab0ee', '600': '#689ad8', '700': 'rgba(104, 154, 216, 0.8)', '800': 'rgba(104, 154, 216, 0.9)' },
purple: { '50': 'rgba(184, 198, 255, 0.04)', '100': 'rgba(184, 198, 255, 0.08)', '200': 'rgba(184, 198, 255, 0.15)', '300': 'rgba(184, 198, 255, 0.25)', '400': 'rgba(184, 198, 255, 0.4)', '500': '#b8c4ff', '600': '#9dacf5', '700': 'rgba(157, 172, 245, 0.8)', '800': 'rgba(157, 172, 245, 0.9)' },
semantic: { success: '#7fb899', warning: '#d4a574', error: '#c9878d', info: '#7ab0ee', highlight: '#e2e4e7', highlightBg: 'rgba(212, 214, 216, 0.12)' },
border: { subtle: 'rgba(255, 255, 255, 0.12)', base: 'rgba(255, 255, 255, 0.18)', medium: 'rgba(255, 255, 255, 0.24)', strong: 'rgba(255, 255, 255, 0.32)', prominent: 'rgba(255, 255, 255, 0.45)' },
element: { subtle: 'rgba(255, 255, 255, 0.06)', soft: 'rgba(255, 255, 255, 0.10)', base: 'rgba(255, 255, 255, 0.13)', medium: 'rgba(255, 255, 255, 0.17)', strong: 'rgba(255, 255, 255, 0.21)', elevated: 'rgba(255, 255, 255, 0.25)' },
},
Expand Down
40 changes: 12 additions & 28 deletions src/web-ui/src/app/components/NavPanel/NavPanel.scss
Original file line number Diff line number Diff line change
Expand Up @@ -549,7 +549,7 @@ $_section-header-height: 24px;
padding: 0 $size-gap-2;
margin: 0 $size-gap-2;
border-radius: 4px;
opacity: 0.72;
opacity: 0.92;
transition: background $motion-fast $easing-standard,
opacity $motion-fast $easing-standard;

Expand All @@ -561,7 +561,7 @@ $_section-header-height: 24px;
background: var(--element-bg-soft);

.bitfun-nav-panel__section-label {
color: var(--color-text-secondary);
color: var(--color-text-primary);
}
}

Expand All @@ -582,7 +582,7 @@ $_section-header-height: 24px;
font-weight: 700;
letter-spacing: 0.06em;
text-transform: uppercase;
color: var(--color-text-secondary);
color: var(--color-text-primary);
flex: 1;
white-space: nowrap;
overflow: hidden;
Expand Down Expand Up @@ -627,7 +627,7 @@ $_section-header-height: 24px;
border: none;
border-radius: 10px;
background: transparent;
color: var(--color-text-secondary);
color: var(--color-text-primary);
cursor: pointer;
transition: background $motion-fast $easing-standard,
color $motion-fast $easing-standard,
Expand Down Expand Up @@ -664,13 +664,6 @@ $_section-header-height: 24px;
font-size: 13px;
font-weight: 500;
line-height: 1.1;
opacity: 0.72;
transition: opacity $motion-fast $easing-standard;

.bitfun-nav-panel__assistant-entry:hover &,
.bitfun-nav-panel__assistant-entry.is-active & {
opacity: 1;
}
}

&__miniapp-entry-wrap {
Expand All @@ -687,7 +680,7 @@ $_section-header-height: 24px;
border: none;
border-radius: 10px;
background: transparent;
color: var(--color-text-secondary);
color: var(--color-text-primary);
cursor: pointer;
text-align: left;
transition: background $motion-fast $easing-standard,
Expand Down Expand Up @@ -750,13 +743,6 @@ $_section-header-height: 24px;
font-size: 13px;
font-weight: 500;
line-height: 1.1;
opacity: 0.72;
transition: opacity $motion-fast $easing-standard;

.bitfun-nav-panel__miniapp-entry:hover &,
.bitfun-nav-panel__miniapp-entry.is-active & {
opacity: 1;
}
}

&__miniapp-entry-apps {
Expand Down Expand Up @@ -798,7 +784,7 @@ $_section-header-height: 24px;

&--more {
background: color-mix(in srgb, var(--element-bg-medium) 92%, transparent);
color: var(--color-text-secondary);
color: var(--color-text-primary);
font-size: 10px;
font-weight: 700;
letter-spacing: 0.01em;
Expand Down Expand Up @@ -1125,21 +1111,21 @@ $_section-header-height: 24px;
border: none;
border-radius: 4px;
background: transparent;
color: var(--color-text-muted);
color: var(--color-text-primary);
cursor: pointer;
text-align: left;
font-size: $font-size-sm;
font-weight: 400;
width: 100%;
position: relative;
opacity: 0.4;
opacity: 1;
transition: color $motion-fast $easing-standard,
background $motion-fast $easing-standard,
opacity $motion-fast $easing-standard;

&:hover {
opacity: 1;
color: var(--color-text-secondary);
color: var(--color-text-primary);
background: var(--element-bg-soft);
}

Expand Down Expand Up @@ -1191,12 +1177,12 @@ $_section-header-height: 24px;
display: flex;
align-items: center;
flex-shrink: 0;
opacity: 0.5;
opacity: 0.78;
transition: opacity $motion-fast $easing-standard,
color $motion-fast $easing-standard;

.bitfun-nav-panel__item:hover & {
opacity: 0.75;
opacity: 1;
}
}

Expand Down Expand Up @@ -1846,7 +1832,7 @@ $_section-header-height: 24px;
border: none;
border-radius: $size-radius-base;
background: transparent;
color: var(--color-text-secondary);
color: var(--color-text-primary);
font-size: 12.5px;
font-weight: 500;
cursor: pointer;
Expand Down Expand Up @@ -1965,13 +1951,11 @@ $_section-header-height: 24px;
transform-origin: center;
transition: background $motion-fast $easing-standard,
color $motion-fast $easing-standard,
box-shadow $motion-fast $easing-standard,
transform $motion-fast $easing-standard;

.bitfun-nav-panel__top-action-btn:hover & {
background: var(--element-bg-strong);
color: var(--color-primary);
box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--color-primary) 28%, transparent);
transform: scale(1.07);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@
border: none;
border-radius: 4px;
background: transparent;
color: var(--color-text-secondary);
color: var(--color-text-primary);
font-size: 13px;
font-weight: 400;
cursor: pointer;
Expand Down Expand Up @@ -137,17 +137,17 @@

&__inline-item-icon {
flex-shrink: 0;
opacity: 0.6;
opacity: 0.78;
display: flex;
align-items: center;
color: var(--color-text-muted);
color: color-mix(in srgb, var(--color-text-primary) 72%, var(--color-text-muted));

&.is-code {
color: color-mix(in srgb, var(--color-primary) 70%, var(--color-text-muted));
color: color-mix(in srgb, var(--color-primary) 70%, var(--color-text-primary));
}

&.is-cowork {
color: color-mix(in srgb, var(--color-accent-500) 70%, var(--color-text-muted));
color: color-mix(in srgb, var(--color-accent-500) 70%, var(--color-text-primary));
}

&.is-running {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@
align-items: center;
justify-content: space-between;
gap: $size-gap-1;
color: var(--color-text-muted);
color: var(--color-text-primary);
font-size: 10px;
font-weight: 700;
letter-spacing: 0.06em;
Expand Down Expand Up @@ -153,7 +153,7 @@
width: 100%;
min-height: 30px;
border-radius: 6px;
color: var(--color-text-secondary);
color: var(--color-text-primary);
transition: color $motion-fast $easing-standard,
background $motion-fast $easing-standard;

Expand Down Expand Up @@ -296,7 +296,7 @@
&__workspace-item-icon-toggle {
opacity: 0;
transform: scale(0.7);
color: var(--color-text-secondary);
color: var(--color-text-primary);

svg {
transition: transform $motion-fast $easing-standard;
Expand Down
4 changes: 4 additions & 0 deletions src/web-ui/src/app/components/SceneBar/SceneBar.scss
Original file line number Diff line number Diff line change
Expand Up @@ -227,6 +227,10 @@ $_tab-v-margin: 6px; // symmetric top/bottom gap inside SceneBar
}
}

[data-theme='bitfun-slate'] .bitfun-scene-tab__icon {
opacity: 0.94;
}

@media (prefers-reduced-motion: reduce) {
.bitfun-scene-tab {
transition: none;
Expand Down
1 change: 1 addition & 0 deletions src/web-ui/src/app/components/SceneBar/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ export type SceneTabId =
| 'assistant'
| 'insights'
| 'shell'
| 'panel-view'
| `miniapp:${string}`;

/** Static definition (from registry) for a scene tab type */
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,12 +22,15 @@ export interface ContentCanvasProps {
onInteraction?: (itemId: string, userInput: string) => Promise<void>;
/** Before-close callback */
onBeforeClose?: (content: any) => Promise<boolean>;
/** Disable pop-out and panel-close controls (used in panel-view scene) */
disablePopOut?: boolean;
}

export const ContentCanvas: React.FC<ContentCanvasProps> = ({
workspacePath,
mode = 'agent',
onInteraction,
disablePopOut = false,
}) => {
// Store state
const {
Expand Down Expand Up @@ -102,7 +105,7 @@ export const ContentCanvas: React.FC<ContentCanvasProps> = ({
const renderContent = () => {
// Show empty state when primary group has no visible tabs
if (!hasPrimaryVisibleTabs) {
return <EmptyState onClose={collapsePanel} />;
return <EmptyState onClose={disablePopOut ? undefined : collapsePanel} />;
}

return (
Expand All @@ -115,6 +118,7 @@ export const ContentCanvas: React.FC<ContentCanvasProps> = ({
onInteraction={onInteraction}
onTabCloseWithDirtyCheck={handleCloseWithDirtyCheck}
onTabCloseAllWithDirtyCheck={handleCloseAllWithDirtyCheck}
disablePopOut={disablePopOut}
/>
</div>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ export interface EditorAreaProps {
onInteraction?: (itemId: string, userInput: string) => Promise<void>;
onTabCloseWithDirtyCheck?: (tabId: string, groupId: EditorGroupId) => Promise<boolean>;
onTabCloseAllWithDirtyCheck?: (groupId: EditorGroupId) => Promise<boolean>;
disablePopOut?: boolean;
}

export const EditorArea: React.FC<EditorAreaProps> = ({
Expand All @@ -23,6 +24,7 @@ export const EditorArea: React.FC<EditorAreaProps> = ({
onInteraction,
onTabCloseWithDirtyCheck,
onTabCloseAllWithDirtyCheck,
disablePopOut = false,
}) => {
const containerRef = useRef<HTMLDivElement>(null);
const topRowRef = useRef<HTMLDivElement>(null);
Expand Down Expand Up @@ -142,6 +144,7 @@ export const EditorArea: React.FC<EditorAreaProps> = ({
onOpenMissionControl={groupId === 'primary' ? onOpenMissionControl : undefined}
onCloseAllTabs={handleCloseAllTabs(groupId)}
onInteraction={onInteraction}
disablePopOut={disablePopOut}
/>
);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import { useTranslation } from 'react-i18next';
import { TabBar } from '../tab-bar';
import { DropZone } from './DropZone';
import FlexiblePanel from '../../base/FlexiblePanel';
import { usePanelViewCanvasStore } from '../stores';
import { useSceneStore } from '../../../../stores/sceneStore';
import type {
EditorGroupId,
EditorGroupState,
Expand Down Expand Up @@ -41,6 +43,7 @@ export interface EditorGroupProps {
onOpenMissionControl?: () => void;
onCloseAllTabs?: () => Promise<void> | void;
onInteraction?: (itemId: string, userInput: string) => Promise<void>;
disablePopOut?: boolean;
}

export const EditorGroup: React.FC<EditorGroupProps> = ({
Expand All @@ -66,6 +69,7 @@ export const EditorGroup: React.FC<EditorGroupProps> = ({
onOpenMissionControl,
onCloseAllTabs,
onInteraction,
disablePopOut = false,
}) => {
const { t } = useTranslation('components');
const visibleTabs = useMemo(() => group.tabs.filter(t => !t.isHidden), [group.tabs]);
Expand Down Expand Up @@ -119,6 +123,13 @@ export const EditorGroup: React.FC<EditorGroupProps> = ({
}
}, [group.activeTabId, onDirtyStateChange]);

const handleTabPopOut = useCallback((tabId: string) => {
const tab = group.tabs.find(t => t.id === tabId);
if (!tab || !tab.content) return;
usePanelViewCanvasStore.getState().addTab(tab.content as PanelContent, 'active');
useSceneStore.getState().openScene('panel-view');
}, [group.tabs]);

const isDragging = draggingTabId !== null;

return (
Expand All @@ -142,6 +153,7 @@ export const EditorGroup: React.FC<EditorGroupProps> = ({
onReorderTab={onReorderTab}
onOpenMissionControl={onOpenMissionControl}
onCloseAllTabs={onCloseAllTabs}
onTabPopOut={disablePopOut ? undefined : handleTabPopOut}
/>

<DropZone
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ export type { ContentCanvasProps } from './ContentCanvas';
export * from './types';

// Store
export { useCanvasStore } from './stores';
export { useCanvasStore, CanvasStoreModeContext } from './stores';

// Context
export * from './context';
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1070,7 +1070,7 @@ const createCanvasStoreHook = () => create<CanvasStore>()(
}))
);

export type CanvasStoreMode = 'agent' | 'project' | 'git';
export type CanvasStoreMode = 'agent' | 'project' | 'git' | 'panel-view';

/**
* Selects which canvas store instance is used by the current subtree.
Expand All @@ -1081,10 +1081,12 @@ export const CanvasStoreModeContext = createContext<CanvasStoreMode>('agent');
export const useAgentCanvasStore = createCanvasStoreHook();
export const useProjectCanvasStore = createCanvasStoreHook();
export const useGitCanvasStore = createCanvasStoreHook();
export const usePanelViewCanvasStore = createCanvasStoreHook();

const pickStoreByMode = (mode: CanvasStoreMode) => {
if (mode === 'project') return useProjectCanvasStore;
if (mode === 'git') return useGitCanvasStore;
if (mode === 'panel-view') return usePanelViewCanvasStore;
return useAgentCanvasStore;
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ export {
useAgentCanvasStore,
useProjectCanvasStore,
useGitCanvasStore,
usePanelViewCanvasStore,
useGroupTabs,
useActiveTabId,
useLayout,
Expand Down
Loading
Loading