From fb0416c72409671264bed5642a1c5d0b54167253 Mon Sep 17 00:00:00 2001 From: Cursor Agent Date: Wed, 2 Sep 2026 17:07:22 +0000 Subject: [PATCH 1/3] =?UTF-8?q?fix(ui):=20visual=20audit=20batch=20?= =?UTF-8?q?=E2=80=94=20light=20skeletons,=20toast,=20tab=20focus?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Use theme fill tokens for SVG skeleton shimmer so chat loading is not hardcoded dark in light mode. Top-align toast/banner content and tighten body line-height. Replace default link/tab focus color with design-system focus styles. Sentinel pending copy already reads "Running"; no change there. Co-authored-by: Anna Nguyen --- js/console/src/components/utils/Link.tsx | 10 ++++++- .../src/components/utils/SkeletonLoaders.tsx | 29 +++++++++++++------ js/console/src/components/utils/Tabs.tsx | 8 +++++ js/console/src/index.css | 3 +- js/design-system/src/components/Banner.tsx | 5 ++-- js/design-system/src/components/Tab.tsx | 6 ++++ js/design-system/src/components/TabList.tsx | 9 +++++- 7 files changed, 56 insertions(+), 14 deletions(-) diff --git a/js/console/src/components/utils/Link.tsx b/js/console/src/components/utils/Link.tsx index 02b96dd4f3..5fa5cf1fa8 100644 --- a/js/console/src/components/utils/Link.tsx +++ b/js/console/src/components/utils/Link.tsx @@ -2,8 +2,16 @@ import { Link } from 'react-router-dom' import styled from 'styled-components' export const UnstyledLink = styled(Link)<{ $extendStyle?: object }>( - ({ $extendStyle }) => ({ + ({ theme, $extendStyle }) => ({ textDecoration: 'none', + color: 'inherit', + '&:focus, &:focus-visible': { + outline: 'none', + color: 'inherit', + }, + '&:focus-visible': { + ...theme.partials.focus.default, + }, ...$extendStyle, }) ) diff --git a/js/console/src/components/utils/SkeletonLoaders.tsx b/js/console/src/components/utils/SkeletonLoaders.tsx index f2e6644ef2..b34ee8a1a2 100644 --- a/js/console/src/components/utils/SkeletonLoaders.tsx +++ b/js/console/src/components/utils/SkeletonLoaders.tsx @@ -16,13 +16,13 @@ import { CSSPseudos } from 'styled-components/dist/types' const shimmerKeyframes = keyframes` 0% { - stop-color: #2D3037; + stop-color: var(--skeleton-from); } 50% { - stop-color: #393C44; + stop-color: var(--skeleton-to); } 100% { - stop-color: #2D3037; + stop-color: var(--skeleton-from); } ` const LinearGradient = styled.linearGradient` @@ -31,6 +31,13 @@ const LinearGradient = styled.linearGradient` } ` +function skeletonCssVars(theme: ReturnType): CSSProperties { + return { + '--skeleton-from': theme.colors['fill-two'], + '--skeleton-to': theme.colors['fill-three'], + } as CSSProperties +} + // pretty much deprecated in favor of "loading" prop on tables export function TableSkeleton({ width = 870, @@ -70,6 +77,7 @@ export function TableSkeleton({ viewBox={`0 0 ${width + theme.spacing.large * (numColumns - 1)} ${height}`} fill="none" xmlns="http://www.w3.org/2000/svg" + style={skeletonCssVars(theme)} > {Array.from({ length: numRows * numColumns }, (_, i) => ( ))} @@ -110,12 +118,15 @@ export function TableSkeleton({ } export function ChartSkeleton({ scale = 1 }: { scale?: number }) { + const theme = useTheme() + return ( diff --git a/js/console/src/components/utils/Tabs.tsx b/js/console/src/components/utils/Tabs.tsx index 6a16760a6f..4ea7c3a5ad 100644 --- a/js/console/src/components/utils/Tabs.tsx +++ b/js/console/src/components/utils/Tabs.tsx @@ -45,5 +45,13 @@ export const LinkTabWrap = styled(LinkTabWrapUnstyled)<{ }>(({ theme, vertical, subTab, $extendStyle }) => ({ ...(vertical ? { width: '100%' } : {}), ...(subTab ? { borderRadius: theme.borderRadiuses.medium } : {}), + color: 'inherit', + '&:focus, &:focus-visible': { + outline: 'none', + color: 'inherit', + }, + '&:focus-visible': { + ...theme.partials.focus.default, + }, ...$extendStyle, })) diff --git a/js/console/src/index.css b/js/console/src/index.css index 6fc4051f75..b974b3b9d8 100644 --- a/js/console/src/index.css +++ b/js/console/src/index.css @@ -37,7 +37,8 @@ code { source-code-pro, Menlo, Monaco, Consolas, 'Courier New', monospace; } -/* Undo mysterious global :focus-visible styles set by (probably) honorable */ +/* Undo mysterious global :focus / :focus-visible styles set by (probably) honorable */ +html :focus, html :focus-visible { background-color: unset; color: unset; diff --git a/js/design-system/src/components/Banner.tsx b/js/design-system/src/components/Banner.tsx index d1fbd4dd2a..02509b2163 100644 --- a/js/design-system/src/components/Banner.tsx +++ b/js/design-system/src/components/Banner.tsx @@ -61,7 +61,7 @@ const BannerOuter: any = styled.div<{ $fullWidth?: boolean }>(({ $borderColorKey, $fullWidth, theme }) => ({ display: 'inline-flex', - align: 'flex-start', + alignItems: 'flex-start', padding: theme.spacing.medium, backgroundColor: theme.mode === 'light' @@ -103,7 +103,7 @@ const BannerAction = styled(Span)(({ theme }) => ({ const Content = styled.p<{ $hasHeading: boolean }>( ({ $hasHeading: $heading, theme }) => ({ - ...theme.partials.text.body2LooseLineHeight, + ...theme.partials.text.body2, marginTop: $heading ? theme.spacing.xxsmall : theme.spacing.xxxsmall, marginBottom: 0, color: theme.colors['text-light'], @@ -141,6 +141,7 @@ function Banner({ $borderColorKey={borderColorKey} $fullWidth={fullWidth} as={Flex} + align="flex-start" {...props} > diff --git a/js/design-system/src/components/Tab.tsx b/js/design-system/src/components/Tab.tsx index 803710e9be..58aaf85d3e 100644 --- a/js/design-system/src/components/Tab.tsx +++ b/js/design-system/src/components/Tab.tsx @@ -38,6 +38,7 @@ function Tab({ body2 display="block" textDecoration="none" + color="inherit" tabIndex={0} userSelect="none" cursor="pointer" @@ -58,9 +59,14 @@ function Tab({ : undefined } {...borderRadiuses} + _focus={{ + outline: 'none', + color: 'inherit', + }} _focusVisible={{ zIndex: theme.zIndexes.base + 1, ...theme.partials.focus.default, + color: 'inherit', }} {...props} > diff --git a/js/design-system/src/components/TabList.tsx b/js/design-system/src/components/TabList.tsx index f10861c047..5beffec072 100644 --- a/js/design-system/src/components/TabList.tsx +++ b/js/design-system/src/components/TabList.tsx @@ -177,6 +177,7 @@ const TabClone = styled( position: 'relative', '&:focus, &:focus-visible': { outline: 'none', + color: 'inherit', zIndex: theme.zIndexes.base + 1, }, '&:focus-visible': { @@ -219,9 +220,15 @@ function TabRenderer({ item, state, stateProps, stateRef }: TabRendererProps) { { ...{ cursor: 'pointer', - _focusVisible: { ...theme.partials.focus.default }, + _focus: { outline: 'none', color: 'inherit' }, + _focusVisible: { + ...theme.partials.focus.default, + color: 'inherit', + }, position: 'relative', '&:focus, &:focus-visible': { + outline: 'none', + color: 'inherit', zIndex: theme.zIndexes.base + 1, }, }, From 60d3a014923dd5c059a0c4b2fd6954383d4d37df Mon Sep 17 00:00:00 2001 From: Cursor Agent Date: Wed, 2 Sep 2026 17:12:07 +0000 Subject: [PATCH 2/3] fix(ui): use React CSSProperties for skeleton CSS vars Avoid a styled-components vs React CSSProperties mismatch on the SVG style prop. Co-authored-by: Anna Nguyen --- js/console/src/components/utils/SkeletonLoaders.tsx | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/js/console/src/components/utils/SkeletonLoaders.tsx b/js/console/src/components/utils/SkeletonLoaders.tsx index b34ee8a1a2..e3212ecb9c 100644 --- a/js/console/src/components/utils/SkeletonLoaders.tsx +++ b/js/console/src/components/utils/SkeletonLoaders.tsx @@ -6,6 +6,7 @@ import { SidecarItem, } from '@pluralsh/design-system' import chroma from 'chroma-js' +import { type CSSProperties as ReactCSSProperties } from 'react' import styled, { CSSObject, CSSProperties, @@ -31,11 +32,13 @@ const LinearGradient = styled.linearGradient` } ` -function skeletonCssVars(theme: ReturnType): CSSProperties { +function skeletonCssVars( + theme: ReturnType +): ReactCSSProperties { return { '--skeleton-from': theme.colors['fill-two'], '--skeleton-to': theme.colors['fill-three'], - } as CSSProperties + } } // pretty much deprecated in favor of "loading" prop on tables From 978cf6aafa27a8f07e5d4548fe7e766877dce2d2 Mon Sep 17 00:00:00 2001 From: Anna Nguyen Date: Wed, 16 Sep 2026 15:27:11 -0400 Subject: [PATCH 3/3] fix(ui): normalize banner severity icons and title alignment Scale info and error glyphs to match check optical size, use a fixed 20px icon slot, and nudge icon padding for body1 line height. Co-authored-by: Cursor --- js/design-system/src/components/Banner.tsx | 21 +++++++++--- .../src/components/icons/ErrorIcon.tsx | 32 +++++++++++-------- .../src/components/icons/InfoIcon.tsx | 30 ++++++++++------- .../src/components/icons/WarningIcon.tsx | 1 + 4 files changed, 54 insertions(+), 30 deletions(-) diff --git a/js/design-system/src/components/Banner.tsx b/js/design-system/src/components/Banner.tsx index 02509b2163..85545bb9f2 100644 --- a/js/design-system/src/components/Banner.tsx +++ b/js/design-system/src/components/Banner.tsx @@ -81,10 +81,22 @@ const BannerInner = styled.div(({ theme }) => ({ alignItems: 'flex-start', })) -const IconWrap = styled.div((_) => ({ +const BANNER_ICON_SIZE = 20 + +const IconWrap = styled.div(({ theme }) => ({ display: 'flex', - paddingTop: 2, - paddingBottom: 2, + flexShrink: 0, + width: BANNER_ICON_SIZE, + height: BANNER_ICON_SIZE, + alignItems: 'flex-start', + justifyContent: 'center', + paddingTop: 4, + boxSizing: 'content-box', + marginRight: theme.spacing.medium, + '& svg': { + width: BANNER_ICON_SIZE, + height: BANNER_ICON_SIZE, + }, })) const Heading = styled.div<{ $bold: boolean }>(({ $bold, theme }) => ({ @@ -147,9 +159,8 @@ function Banner({
diff --git a/js/design-system/src/components/icons/ErrorIcon.tsx b/js/design-system/src/components/icons/ErrorIcon.tsx index a388662dc8..796c20e7fb 100644 --- a/js/design-system/src/components/icons/ErrorIcon.tsx +++ b/js/design-system/src/components/icons/ErrorIcon.tsx @@ -1,24 +1,30 @@ import createIcon from './createIcon' +// Match CheckRoundedIcon optical size (14px glyph in 16 viewBox). +const OPTICAL_INSET_SCALE = 14 / 16 + export default createIcon(({ size, color, secondaryColor = 'transparent' }) => ( - - + + + + )) diff --git a/js/design-system/src/components/icons/InfoIcon.tsx b/js/design-system/src/components/icons/InfoIcon.tsx index 48fef95797..c7d5922906 100644 --- a/js/design-system/src/components/icons/InfoIcon.tsx +++ b/js/design-system/src/components/icons/InfoIcon.tsx @@ -1,23 +1,29 @@ import createIcon from './createIcon' +// Match CheckRoundedIcon optical size (14px glyph in 16 viewBox). +const OPTICAL_INSET_SCALE = 14 / 16 + export default createIcon(({ size, color, secondaryColor = 'transparent' }) => ( - - + + + + )) diff --git a/js/design-system/src/components/icons/WarningIcon.tsx b/js/design-system/src/components/icons/WarningIcon.tsx index 1f6de5caa1..e4f0bf6d0c 100644 --- a/js/design-system/src/components/icons/WarningIcon.tsx +++ b/js/design-system/src/components/icons/WarningIcon.tsx @@ -8,6 +8,7 @@ export default createIcon(({ size, color, secondaryColor = 'transparent' }) => { return (