Skip to content

fix(renderers): add icon name overrides for v0.9 renderers#1146

Open
ppazosp wants to merge 5 commits intogoogle:mainfrom
ppazosp:fix/v09-icon-name-overrides
Open

fix(renderers): add icon name overrides for v0.9 renderers#1146
ppazosp wants to merge 5 commits intogoogle:mainfrom
ppazosp:fix/v09-icon-name-overrides

Conversation

@ppazosp
Copy link
Copy Markdown
Contributor

@ppazosp ppazosp commented Apr 11, 2026

Description

Adds an icon name override map to all three v0.9 renderers (React, Angular, Lit) for A2UI spec icon names that don't match their Material Symbols ligatures after camelCase-to-snake_case conversion.

The four overrides:

Spec name Material Symbols
play play_arrow
rewind fast_rewind
favoriteOff favorite_border
starOff star_border

Additionally, the Lit v0.9 renderer was missing camelCase-to-snake_case conversion entirely, so that is also added here.

Follow-up to #1031 as discussed in #1031 (comment).

Pre-launch Checklist

ppazosp added 2 commits April 11, 2026 03:50
Some A2UI spec icon names don't match Material Symbols ligatures
(play, rewind, favoriteOff, starOff). Add a lookup table to all
three v0.9 renderers (React, Angular, Lit) that maps these names
to their correct Material Symbols equivalents before falling back
to camelCase-to-snake_case conversion.
Test that the 4 icon name overrides (play, rewind, favoriteOff,
starOff) resolve to their correct Material Symbols ligatures, and
that camelCase-to-snake_case conversion works for multi-word icons.
Copy link
Copy Markdown
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces icon name overrides and camelCase to snake_case conversion across the Angular, Lit, and React renderers to ensure compatibility with Material Symbols. It also includes comprehensive tests for these changes. The review feedback identifies a logic error in the Lit and React implementations where the conversion function is incorrectly applied to SVG path strings, potentially corrupting the data. Additionally, suggestions were provided to optimize the string replacement logic in those renderers for better performance and consistency with the Angular implementation.

Comment on lines +38 to +40
const rawName =
typeof props.name === 'string' ? props.name : (props.name as {path?: string})?.path;
const iconName = rawName ? toSnakeCase(rawName) : undefined;
const iconName = rawName ? toMaterialSymbol(rawName) : undefined;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The toMaterialSymbol function (which performs snake_case conversion) is being applied to the icon name even when it represents an SVG path string. This occurs because rawName extracts the path string from the object before the conversion check. This is incorrect for SVG paths and inefficient.

Suggested change
const rawName =
typeof props.name === 'string' ? props.name : (props.name as {path?: string})?.path;
const iconName = rawName ? toSnakeCase(rawName) : undefined;
const iconName = rawName ? toMaterialSymbol(rawName) : undefined;
const iconName = typeof props.name === 'string'
? toMaterialSymbol(props.name)
: (props.name as {path?: string})?.path;

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 805fb5d. Now only applies toMaterialSymbol when props.name is a string.

Comment on lines +44 to +46
const name =
typeof props.name === "string" ? props.name : (props.name as any)?.path;
const iconName = name ? toMaterialSymbol(name) : name;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Similar to the React implementation, toMaterialSymbol should not be applied to SVG path strings. The conversion logic should only be triggered when the input is a string (representing an icon name).

Suggested change
const name =
typeof props.name === "string" ? props.name : (props.name as any)?.path;
const iconName = name ? toMaterialSymbol(name) : name;
const iconName = typeof props.name === "string"
? toMaterialSymbol(props.name)
: (props.name as any)?.path;

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 805fb5d. Same approach as the React fix.

function toSnakeCase(str: string): string {
return str.replace(/([A-Z])/g, '_$1').toLowerCase();
function toMaterialSymbol(str: string): string {
return ICON_NAME_OVERRIDES[str] ?? str.replace(/([A-Z])/g, '_$1').toLowerCase();
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Consider using a more targeted replacement function to avoid capturing groups and lowercasing the entire string, aligning with the implementation in the Angular renderer for better efficiency.

Suggested change
return ICON_NAME_OVERRIDES[str] ?? str.replace(/([A-Z])/g, '_$1').toLowerCase();
return ICON_NAME_OVERRIDES[str] ?? str.replace(/[A-Z]/g, (letter) => "_" + letter.toLowerCase());

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 805fb5d. Aligned all three renderers to use the same regex pattern.


function toMaterialSymbol(name: string): string {
if (ICON_NAME_OVERRIDES[name]) return ICON_NAME_OVERRIDES[name];
return name.replace(/([A-Z])/g, "_$1").toLowerCase();
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Consider using a more targeted replacement function for consistency with other renderers and slightly better performance by avoiding a global lowercase call.

Suggested change
return name.replace(/([A-Z])/g, "_$1").toLowerCase();
return name.replace(/[A-Z]/g, (letter) => "_" + letter.toLowerCase());

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 805fb5d.

ppazosp and others added 2 commits April 11, 2026 04:08
Only apply toMaterialSymbol when props.name is a string icon name,
not when it's an SVG path object. Also align regex pattern across
all three renderers for consistency.
@jacobsimionato
Copy link
Copy Markdown
Collaborator

This looks great - thank you!! Please just fix the prettier errors in React that are causing CI to fail.

@ppazosp
Copy link
Copy Markdown
Contributor Author

ppazosp commented Apr 14, 2026

Done, sorry for that!!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Todo

Development

Successfully merging this pull request may close these issues.

2 participants