diff --git a/frontend/src/app/pages/Dashboard/cards/DashboardViewCard.tsx b/frontend/src/app/pages/Dashboard/cards/DashboardViewCard.tsx index 221989cc..a3b39b2c 100644 --- a/frontend/src/app/pages/Dashboard/cards/DashboardViewCard.tsx +++ b/frontend/src/app/pages/Dashboard/cards/DashboardViewCard.tsx @@ -645,16 +645,6 @@ const DashboardViewCard: React.FC = ({ const dockActive = !!dockRect && !dragging && !localResize && !isTiled && !isMinimized; const tiledSize = useTiledCard({ cardId: cardKey, zone: tileZone, active: !isMinimized, originX: displayX, originY: displayY, getCamera: getCanvasState }); - // Same identity math as the dock and Applications window, shrunk to chrome size. - const appHue = ((): number => { - let h = 0; - const name = output.name || '?'; - for (let i = 0; i < name.length; i++) h = (h * 31 + name.charCodeAt(i)) >>> 0; - return h % 360; - })(); - const p_glyph = (output.icon || '').trim(); - const appGlyph = p_glyph && p_glyph.length <= 3 ? p_glyph : (output.name || '?').trim().charAt(0).toUpperCase(); - // The old 8-icon header cluster, demoted behind one kebab: view switcher, new window, toolbar // collapse, then the same rows the card's right-click menu carries. const headerKebabRows = (): CardMenuRow[] => ([ @@ -817,29 +807,6 @@ const DashboardViewCard: React.FC = ({ e.stopPropagation()} sx={{ display: 'flex', alignItems: 'center', flexShrink: 0, mr: 0.25 }}> handleRemove()} onMinimize={onMinimize} onTile={onTile} tiled={!!tileZone} /> - {/* Centered identity: the app's own monogram tile, no name (bare-chrome grammar shared with Settings/Marketplace; the tile matches the dock and Applications window). */} - - - {appGlyph} - - {instance > 1 && ( - #{instance} - )} - {showControls && ( diff --git a/frontend/src/app/pages/Dashboard/desktop/DockTileIcon.tsx b/frontend/src/app/pages/Dashboard/desktop/DockTileIcon.tsx index c1453376..0bf35eff 100644 --- a/frontend/src/app/pages/Dashboard/desktop/DockTileIcon.tsx +++ b/frontend/src/app/pages/Dashboard/desktop/DockTileIcon.tsx @@ -2,11 +2,21 @@ import React, { useState } from 'react'; import Box from '@mui/material/Box'; import type { DockEntry } from './dockEntries'; -/** A tile shows its site favicon OR the generic glyph, never the glyph peeking out from behind the favicon. */ +/** A tile shows its real image (site favicon, app thumbnail) OR the generic SVG glyph, never + * letters and never the glyph peeking out from behind an image. */ export function DockTileIcon({ entry }: { entry: DockEntry }): React.ReactElement { - const [faviconFailed, setFaviconFailed] = useState(false); - if (!entry.faviconUrl || faviconFailed) return <>{entry.icon}; - return ( - setFaviconFailed(true)} sx={{ borderRadius: '6px' }} /> - ); + const [imageFailed, setImageFailed] = useState(false); + if (entry.faviconUrl && !imageFailed) { + return ( + setImageFailed(true)} sx={{ borderRadius: '6px' }} /> + ); + } + // An app's own screenshot fills the whole tile: the most personalized mark it can carry. + if (entry.kind === 'view' && entry.thumbnail && !imageFailed) { + return ( + setImageFailed(true)} + sx={{ position: 'absolute', inset: 0, width: '100%', height: '100%', objectFit: 'cover' }} /> + ); + } + return <>{entry.icon}; }