The spreadsheet engine parsed typed input with the invariant culture while
displaying values with the current culture, breaking the edit round-trip on
non-en-US hosts and making comma-decimal entry (10,50) impossible.
Workbook gains a Culture property (defaults to CurrentCulture) which the
component stamps from its inherited Culture parameter. It drives:
- Cell input parsing (CellData type inference), including day-month date
handling for cultures where the group and date separators collide (de-DE)
- Edit text and display rendering (GetValue, GetValueAsString, GetDisplayText)
- Number format rendering - format codes stay canonical invariant tokens while
separators, month names, and AM/PM designators follow the culture
- Formula entry and display via the new FormulaLocalizer (Excel FormulaLocal
semantics: ';' argument separators and ',' decimals in comma-decimal
cultures, lenient comma acceptance where unambiguous, canonical invariant
storage)
- Dialog input (data validation, conditional format, filter) via shared
conversion helpers on SpreadsheetDialogBase
XLSX and CSV files read and write canonical invariant values regardless of
the workbook culture, including autofit column widths. Malformed formulas now
surface as error trees instead of an unhandled lexer exception. Number format
parsing is cached (hard-bounded) since CellView reparsed per render.
Includes localization demos for the Spreadsheet and Document Processing
sections and culture test suites.
Note: headless code on non-en-US hosts now parses string values with the
host culture; set Workbook.Culture explicitly (or to InvariantCulture) for
host-independent processing.
Pull the freshest and flagship categories up: DataGrid, Data Visualization
(Updated, 48 new chart types, was buried at #20), Forms, Spreadsheet, then the
New categories; push utility pages (Accessibility) down. Keep Overview/Get
Started/AI/Support at the top. Remove the New flag from the AI category.
Titles/meta/intros were already strong; this adds the missing layer. New
GetSpreadsheetPages + cluster branch in SeoSchema (Home > Spreadsheet > feature)
-> TechArticle + BreadcrumbList on all 18, FAQPage on Overview (5) + 7 key
features, related cross-links throughout. Aligned the two '| Radzen' titles to
the standard '| Free UI Components by Radzen' suffix.
- CompilerService: global-qualify Radzen.CompositeFilterDescriptor and
Radzen.Blazor.PagingInformation in the generated type-inference helper
(same workaround already used for Radzen.Group); the runtime Razor
compiler emits them without global:: inside the __Blazor.* namespace,
causing CS0234. Fixes the DataFilter and DataGridPagerApi demos.
- DataGridCheckBoxListLookupFilter: initialize the lookup in OnInitialized
instead of a constructor named after the page class, which becomes an
invalid (return-type-less) method when the runtime compiler renames the
class to DynamicComponent (CS1520).
All 1052 demos now compile under the trimmed online editor.
Two follow-up fixes for compiling demos in Edit Source / Playground:
- CompilerService: raise the parse language version from C# 10 to Latest
so demos using collection expressions and primary constructors compile
(previously failed with CS8936).
- linker.xml: preserve System.Math, DisplayAttribute and Radzen.Colors,
which are referenced only by demo source compiled at runtime and were
otherwise removed by trimming (Math.PI, [Display(Description=...)],
@Colors.* respectively).
Verified against a trimmed publish: demo compile failures drop from 20 to 5
out of 1052 (remaining 5 are a separate Razor type-inference codegen issue).
Add /markdown to standalone SEO pages (TechArticle + breadcrumb + FAQPage);
keyword title/intro framed accurately as a renderer (not an editor), with
related links to html-editor and textarea. Nav placement left top-level.
Add GetPivotDataGridPages + a cluster branch in SeoSchema (Home > Pivot DataGrid
> variant). Primary title now leads with 'Pivot Table' to capture the larger
query; fixed copy-pasted descriptions on the LoadData/OData pages; added FAQ,
related links, and keyword intros.
- Add /themes to standalone SEO pages (schema + FAQ + related); tightened intro.
- Refer to the library as 'Radzen Blazor', never 'Radzen' alone: fix themes and
dashboard copy, and drop the trailing ', from Radzen' from 14 chart descriptions.
Add /dashboard to standalone SEO pages; title now 'Sample Blazor Dashboard',
H1 'Blazor Dashboard', keyword intro/meta, one FAQ, and related links
(tile-layout, datagrid, charts).
Dropped from DataGrid, Scheduler, and DropDown - the question adds no useful
content (the free/MIT message already lives on the home and gallery pages).
Add /icon to the standalone SEO pages so it emits TechArticle + BreadcrumbList +
FAQPage; keyword intro/meta and related links. Title kept (already ranks well).
Add a reusable standalone-page branch to SeoSchema (Home > Page breadcrumb) and
optimize /scheduler: title and intro now lead with 'Calendar' to capture the
larger 'blazor calendar' query, plus a calendar-focused FAQ and related links.
Keyword-aligned titles (capture 'select'/'multiselect'), SEO intros, FAQ on
high-traffic pages, and family cross-links for the 8 DropDown pages. Also fixes
the DemoSeo related-links heading from 'Related charts' to a neutral 'Related'
(it was already mislabeled on the DataGrid pages).
Forms has no single hub page, so each component (DropDown, Button, ...) acts
as its own breadcrumb root. GetFormsComponentHubs maps every Forms page to its
component's primary page; single-page components hub on themselves, grouped ones
(DropDown, HtmlEditor) on their first child. Refactored leaf collection into a
shared CollectLeaves helper reused by GetDataGridPages.
The Upload component demo was served at /example-upload because the demo
host's UploadController owned the /upload URL space. Move the controller's
endpoints under api/upload/* to free /upload, point the demo page and every
consumer (Upload and HtmlEditor demos) at the new paths, switch the page
route and ExampleService path to /upload, and add a permanent 301 redirect
from /example-upload (and the legacy docs URL) to /upload.
- Turn /datagrid into a dedicated DataGrid overview: keyword-rich intro
(IQueryable, Entity Framework, OData, ...), flagship live grid, 12
feature cards linking to each demo, and an FAQ. Matches the overview
pattern Telerik/DevExpress/Infragistics/Syncfusion use for the head term.
- Move the IQueryable/EF demo to /datagrid-iqueryable (first under the
Data-binding nav group); /datagrid keeps its URL/authority.
- Generalize SeoSchema for multiple clusters; add GetDataGridPages so every
DataGrid page emits TechArticle + BreadcrumbList (Home > DataGrid > Page),
the overview also FAQPage.
- Fix TitleFor to honor an explicit Title on an "Overview"-named entry.
Extend the chart SEO work to the 15 chart configuration and feature
demo pages (axis, legend, tooltip, interpolation, data labels,
crosshair, etc.):
- GetChartConfigPages() + SeoSchema treats these pages as article-
eligible (TechArticle + BreadcrumbList + FAQPage), without adding
them to the /charts gallery ItemList
- Human-readable intros, "how do I..." FAQs, and related links per page
Enrich all 58 chart/dataviz demo pages on blazor.radzen.com for search
and AI discovery:
- JSON-LD via a new head-schemas section + SeoSchema/DemoSeo, emitted
once per page from MainLayout (CollectionPage+ItemList on /charts,
TechArticle+BreadcrumbList+FAQPage on each chart page)
- Human-readable intros, 1-3 FAQs, and related-chart links per page,
sourced once from ExampleService (rendered on-page and as FAQPage)
- Complete OG/Twitter tags; corrected gallery copy (30+ chart types /
40+ data-visualization components); dropped "native" wording
- Rename chart-spline/-histogram/-pareto to {type}-chart
Adds RadzenBlazorDemos/Services/SeoSchema.cs and Shared/DemoSeo.razor.
Ship satellite resource files (RadzenStrings.{de,fr,es,it,ja}.resx) with all
535 strings translated, so components localize out of the box via the standard
.NET ResourceManager.
Make culture handling reactive everywhere:
- RadzenDatePicker rebuilds its month/year lists when Culture or the
DefaultCulture cascade changes (previously cached at init).
- Scheduler views, HtmlEditor tools and the spreadsheet ChartOverlay localize
through their parent component's UICulture instead of CurrentUICulture;
spreadsheet dialogs honor a DefaultUICulture cascade. UICulture is added to
IScheduler/ISpreadsheet as default interface members, so this is non-breaking.
Update the Localization demo with an interactive language switcher (cascading
DefaultUICulture + DefaultCulture) backed by an ILocalizer so it works in-place
on Blazor WebAssembly.
DataSheet<T> tried to expose a virtualized IQueryable view as a Worksheet
but the abstraction leaked in several places: a fixed (100, 100) size
unrelated to the source, an implicit header row, async fetches inside
the cell getter with no re-render signal, one-way mappings (no edit
write-back), and no XLSX round-trip story. That role belongs to
RadzenDataGrid, not the document model. Drop it before release.
Demo: three-section page covering ReadOnly (whole-spreadsheet lockdown),
Allow* and Show* flags wired to a switch panel, and CommandExecuting with
an async role check via PreventDefault. Cross-links to the Protection demo.
Fixes discovered while testing it:
- Formula bar honoured ReadOnly: SheetEditor now takes a ReadOnly parameter
that flips the contenteditable attribute; FormulaEditor wires it to the
Editing feature check via the cascading ISpreadsheet.
- Context menus respect the per-feature flags: cell / row / column menus
build their items conditionally so Cut/Paste/Clear/Sort/Insert/Delete/
Hide/Unhide/Convert-table/Delete-table all disappear when their feature
is disabled. In ReadOnly mode only Copy stays.
- AllowClipboard now genuinely gates Copy as well as Cut and Paste, and is
decoupled from ReadOnly so view-only users can still copy data unless
the host explicitly opts out. Test asserting "ReadOnly turns OFF all
features" updated to reflect the new contract; new test added for the
AllowClipboard=false case.
The spreadsheet has two distinct sets of tab-like UI: the toolbar at the
top (groupings of tools) and the sheet strip at the bottom (worksheet
picker). The public API mixed both as 'Tab'. Settle terms:
- toolbar (singular) — the whole top strip; ShowToolbar already owned this
- toolset — one named section of tools inside the toolbar (was 'tab')
- sheet tab — the bottom worksheet picker; ShowSheetTabs unchanged
Renames:
- SelectedTabIndex/-Changed → SelectedToolsetIndex/-Changed
- TableDesignTab component → TableDesignToolset (file + usages)
- Doc comments and demo description that said 'ribbon' now say 'toolbar'
(the term 'ribbon' is reserved for a future RadzenRibbon component)
Two-section page showing how to compose a custom ribbon via ChildContent:
predefined tools in a custom layout, and a custom tool that dispatches an
undoable ICommand declaring a SpreadsheetFeature.