diff --git a/.github/skills/syncfusion-blazor-toolkit-buttons/SKILL.md b/.github/skills/syncfusion-blazor-toolkit-buttons/SKILL.md
new file mode 100644
index 0000000..580ae55
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-buttons/SKILL.md
@@ -0,0 +1,229 @@
+---
+name: syncfusion-blazor-toolkit-buttons
+description: Implement interactive Blazor button components with Syncfusion Toolkit. Covers SfButton, SfButtonGroup with styling and accessibility.
+compatibility: .NET Core 3.1+, .NET 5+, .NET 6+, .NET 7+, .NET 8+
+metadata:
+ author: "Syncfusion Inc"
+ version: "1.0.0"
+---
+
+# Syncfusion Blazor Toolkit Buttons
+
+## Component Overview
+
+The Syncfusion Blazor Toolkit provides a comprehensive suite of button components for building interactive user interfaces. From basic buttons to button groups, these components support rich content, events, accessibility, and extensive customization.
+
+**Components Included:**
+- **SfButton** — Core interactive button component
+- **SfButtonGroup** — Group multiple buttons with selection modes
+
+When you need interactive buttons, use the appropriate component from this skill based on your UI requirements.
+
+---
+
+## Documentation and Navigation Guide
+
+### Getting Started
+📄 **Read:** [references/getting-started.md](references/getting-started.md)
+- Installation and package setup
+- Adding button component to your project
+- First button implementation
+- Basic click event handling
+- Content property usage
+- Testing in samples
+
+**When to read:** Start here for your first button component or to understand project setup.
+
+### Button Fundamentals
+📄 **Read:** [references/button-fundamentals.md](references/button-fundamentals.md)
+- Button states (enabled, disabled)
+- Disabled state implementation
+- Primary vs standard button styling
+- CSS class combinations
+- HTML attributes capture
+- Styling with CssClass property
+- Common styling patterns
+
+**When to read:** Need to style buttons, set disabled state, or apply custom CSS classes.
+
+### Icons and Content
+📄 **Read:** [references/icons-and-content.md](references/icons-and-content.md)
+- Icon CSS classes and icon library
+- Icon positioning (left, right, top, bottom)
+- Content vs ChildContent properties
+- Complex content patterns
+- SVG and custom icons
+- Icon-only buttons
+- Practical icon examples
+
+**When to read:** Want to add icons, position them, or create complex button content.
+
+### Events and Callbacks
+📄 **Read:** [references/events-and-callbacks.md](references/events-and-callbacks.md)
+- Click event handling
+- Created lifecycle event
+- EventCallback usage
+- Async event handling patterns
+- State management with events
+- Two-way binding
+- Debugging event issues
+
+**When to read:** Need to handle button clicks, lifecycle events, or implement event-driven logic.
+
+### Button Groups
+📄 **Read:** [references/button-group.md](references/button-group.md)
+- SfButtonGroup component
+- Selection modes (single, multiple)
+- SelectedChanged event
+- Button child component
+- Default selection
+- Real-world patterns
+
+**When to read:** Need to group buttons or implement selection patterns (radio group, multi-select toolbar).
+
+---
+
+## Quick Start Example
+
+### Basic Button
+```razor
+
+```
+
+### Button with Click Handler
+```razor
+
+
+@code {
+ private void OnClickHandler(MouseEventArgs args)
+ {
+ Console.WriteLine("Button clicked!");
+ }
+}
+```
+
+### Button with Icon
+```razor
+
+```
+
+### Button with Form Integration
+```razor
+
+
+
+@code {
+ private async Task SubmitForm(MouseEventArgs args)
+ {
+ // Handle form submission logic
+ Console.WriteLine("Form submitted!");
+ }
+}
+```
+
+### Primary Button with Event
+```razor
+
+
+@code {
+ private async Task SaveData(MouseEventArgs args)
+ {
+ // Handle save logic
+ }
+}
+```
+
+---
+
+## Common Patterns
+
+### Pattern 1: Disabled State Management
+```razor
+
+
+@code {
+ private bool isProcessing = false;
+
+ private async Task Submit(MouseEventArgs args)
+ {
+ isProcessing = true;
+ await Task.Delay(2000); // Simulate work
+ isProcessing = false;
+ }
+}
+```
+
+### Pattern 2: Icon Positioning
+```razor
+
+
+
+
+
+
+
+
+```
+
+### Pattern 3: Button Group Selection
+```razor
+
+ Bold
+ Italic
+ Underline
+
+```
+
+---
+
+## Key Properties Summary
+
+| Component | Key Property | Purpose | Type | Default |
+|-----------|--------------|---------|------|---------|
+| SfButton | Content | Button text | string | "" |
+| SfButton | Disabled | Enable/disable | bool | false |
+| SfButton | IsPrimary | Primary styling | bool | false |
+| SfButton | IconCss | Icon classes | string | "" |
+| SfButton | IconPosition | Icon placement | IconPosition | Left |
+| SfButton | CssClass | Custom CSS | string | "" |
+| SfButton | Type | Form button type | ButtonType | Button |
+| SfButton | HtmlAttributes | Capture HTML attributes | Dictionary | {} |
+| SfButtonGroup | Mode | Selection type | SelectionMode | None |
+| SfButtonGroup | IsVertical | Vertical layout | bool | false |
+
+---
+
+## Button Component Decision Tree
+
+```
+Need a button?
+├─ Simple clickable button?
+│ └─ Use SfButton with Content and OnClick
+└─ Multiple related buttons?
+ └─ Use SfButtonGroup with Mode
+```
+
+---
+
+## Accessibility Considerations
+
+All button components support accessibility best practices:
+
+- **Keyboard Navigation:** All buttons are keyboard accessible via Tab, Enter, and Space
+- **ARIA Support:** Proper ARIA attributes are applied automatically
+- **Screen Reader Support:** Buttons announce their content and state to screen readers
+- **Focus Indicators:** Clear focus indicators for keyboard navigation
+- **Disabled State:** Disabled buttons are properly announced and not focusable
+
+When implementing custom HTML attributes or complex content, ensure you maintain these accessibility standards.
+
+---
+
+## Next Steps
+
+1. **Start Simple:** Read [getting-started.md](references/getting-started.md) to create your first button
+2. **Style and Configure:** Explore [button-fundamentals.md](references/button-fundamentals.md) for styling options
+3. **Add Interactivity:** Learn event handling in [events-and-callbacks.md](references/events-and-callbacks.md)
+4. **Expand:** Explore [button-group.md](references/button-group.md) for grouping buttons
+
+**Documentation:** Syncfusion Blazor Toolkit official documentation at https://www.syncfusion.com/blazor-components/
diff --git a/.github/skills/syncfusion-blazor-toolkit-buttons/references/button-fundamentals.md b/.github/skills/syncfusion-blazor-toolkit-buttons/references/button-fundamentals.md
new file mode 100644
index 0000000..644224d
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-buttons/references/button-fundamentals.md
@@ -0,0 +1,558 @@
+# Button Fundamentals
+
+## Table of Contents
+1. [Button States](#button-states)
+2. [Disabled State](#disabled-state)
+3. [Primary Button Styling](#primary-button-styling)
+4. [CSS Class Combinations](#css-class-combinations)
+5. [HTML Attributes](#html-attributes)
+6. [Icon Support](#icon-support)
+7. [Toggle Button](#toggle-button)
+8. [Form Button Types](#form-button-types)
+9. [Standard vs Primary](#standard-vs-primary)
+10. [Practical Examples](#practical-examples)
+
+## Button States
+
+A button can exist in different states depending on user interaction and application logic:
+
+- **Enabled:** Normal state, user can interact
+- **Disabled:** User cannot click or interact
+- **Hover:** Visual feedback when mouse hovers
+- **Pressed/Active:** Feedback during click
+
+The Syncfusion button component automatically handles hover and pressed states through CSS.
+
+## Disabled State
+
+### Basic Disabled Button
+```razor
+
+```
+
+When a button is disabled (`Disabled="true"`):
+- Cannot be clicked
+- Cannot receive focus via Tab key
+- Appears grayed out with reduced opacity
+- Screen readers announce it as disabled
+
+### Conditional Disabled State
+```razor
+
+
+@code {
+ private bool isProcessing = false;
+
+ private async Task OnSubmit(MouseEventArgs args)
+ {
+ isProcessing = true;
+ try
+ {
+ await PerformOperation();
+ }
+ finally
+ {
+ isProcessing = false;
+ }
+ }
+
+ private async Task PerformOperation()
+ {
+ await Task.Delay(2000); // Simulate work
+ }
+}
+```
+
+### Multi-button Coordination
+```razor
+
+
+@code {
+ private string formData = "";
+ private bool hasChanges = false;
+ private bool isProcessing = false;
+
+ private void HandleInput(ChangeEventArgs e)
+ {
+ formData = e.Value?.ToString() ?? "";
+ hasChanges = true;
+ }
+
+ private async Task Save(MouseEventArgs args)
+ {
+ isProcessing = true;
+ await Task.Delay(1000);
+ isProcessing = false;
+ hasChanges = false;
+ formData = "";
+ }
+
+ private void Reset(MouseEventArgs args)
+ {
+ hasChanges = false;
+ formData = "";
+ }
+
+ private async Task Delete(MouseEventArgs args)
+ {
+ isProcessing = true;
+ await Task.Delay(1000);
+ isProcessing = false;
+ }
+}
+```
+
+## Primary Button Styling
+
+### Standard Button
+```razor
+
+```
+
+### Primary Button
+```razor
+
+```
+
+The `IsPrimary` property applies prominent styling to indicate the primary action:
+- Darker background color
+- Higher contrast
+- Often used for "Save", "Submit", "Continue" actions
+- Should typically be only one per action area
+
+### Best Practice: Primary Actions
+```razor
+
+
+
+
+
+```
+
+## CSS Class Combinations
+
+### Using CssClass Property
+```razor
+
+```
+
+The `CssClass` property accepts space-separated CSS class names that apply to the button element.
+
+### Syncfusion Built-in Classes
+
+| Class | Purpose |
+|-------|---------|
+| `e-primary` | Primary button styling |
+| `e-success` | Success/positive action styling |
+| `e-warning` | Warning action styling |
+| `e-danger` | Destructive action styling |
+| `e-info` | Informational button styling |
+
+### Combining Multiple Classes
+```razor
+
+
+
+
+
+
+
+
+```
+
+### Custom CSS with Built-in Classes
+```razor
+
+
+
+```
+
+## HTML Attributes
+
+### Capturing HTML Attributes
+The `HtmlAttributes` parameter captures unmatched HTML attributes:
+
+```razor
+
+```
+
+These attributes are applied to the underlying `` HTML element.
+
+### Accessibility Attributes
+```razor
+
+Saves current form data
+```
+
+### Data Attributes for JavaScript
+```razor
+
+```
+
+## Icon Support
+
+The `IconCss` property allows you to add icons to buttons for better visual representation of actions.
+
+### Icon with Text
+```razor
+
+
+
+```
+
+### Icon Position
+
+Use `IconPosition` to control icon placement.
+
+```razor
+
+
+
+```
+
+### Icon Only Button
+```razor
+
+
+```
+
+### Best Practice:
+- Always include `aria-label` for icon-only buttons
+
+## Toggle Button
+
+The `IsToggle` property enables a button to act as a toggle (two-state button).
+
+### Basic Toggle
+```razor
+
+ Toggle Me
+
+
+@code {
+ private bool isOn;
+
+ private void ToggleState(MouseEventArgs args)
+ {
+ isOn = !isOn;
+ }
+}
+```
+
+---
+
+### Toggle with Visual State
+```razor
+
+ @(isBold ? "Bold On" : "Bold Off")
+
+
+@code {
+ private bool isBold;
+
+ private void ToggleBold(MouseEventArgs args)
+ {
+ isBold = !isBold;
+ }
+}
+```
+
+---
+
+### Icon-only Toggle
+```razor
+
+
+
+@code {
+ private bool isSettingsOn;
+
+ private void ToggleSettings(MouseEventArgs args)
+ {
+ isSettingsOn = !isSettingsOn;
+ }
+}
+```
+
+## Form Button Types
+
+The `Type` property controls how the button behaves in HTML forms. It accepts values from the `ButtonType` enumeration.
+
+### Button Types
+
+| Type | Description |
+|------|-------------|
+| `ButtonType.Button` | Standard button, no form interaction (default) |
+| `ButtonType.Submit` | Submits the form when clicked |
+| `ButtonType.Reset` | Resets form fields to their initial values |
+
+### Submit Button
+```razor
+
+
+
+
+
+@code {
+ private FormModel formModel = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Form submitted: {formModel.Name}");
+ }
+
+ public class FormModel
+ {
+ public string Name { get; set; } = "";
+ }
+}
+```
+
+### Reset Button
+```razor
+
+
+
+
+
+
+@code {
+ private FormModel formModel = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Form submitted: {formModel.Name}");
+ }
+
+ private void HandleReset()
+ {
+ formModel = new FormModel();
+ Console.WriteLine("Form reset");
+ }
+
+ public class FormModel
+ {
+ public string Name { get; set; } = "";
+ }
+}
+```
+
+### Default Button Type
+```razor
+
+
+
+```
+
+**Best Practice:** Always specify `ButtonType.Submit` for form submission buttons to ensure proper form handling.
+
+## Standard vs Primary
+
+### Visual Comparison
+```razor
+
+
+
+
+
+
+
+
+
+
+```
+
+### When to Use Each
+
+**Standard Button:**
+- Secondary actions
+- Cancel operations
+- Navigation without save
+- Optional actions
+
+**Primary Button:**
+- Main action in a dialog
+- Submit forms
+- Confirm important operations
+- Single action to emphasize
+
+## Practical Examples
+
+### Form Submit Pattern
+```razor
+
+
+@code {
+ private string formData = "";
+
+ private void OnCancel(MouseEventArgs args)
+ {
+ formData = "";
+ }
+
+ private void OnSubmit(MouseEventArgs args)
+ {
+ Console.WriteLine($"Submitted: {formData}");
+ formData = "";
+ }
+}
+```
+
+### Status-Based Button Styling
+```razor
+
+
+@code {
+ private string status = "active"; // active, inactive, locked
+
+ private string GetButtonText()
+ {
+ return status switch
+ {
+ "active" => "Active - Click Me",
+ "inactive" => "Inactive",
+ "locked" => "Locked",
+ _ => "Unknown"
+ };
+ }
+
+ private string GetStatusClass()
+ {
+ return status switch
+ {
+ "active" => "e-success",
+ "inactive" => "",
+ "locked" => "e-danger",
+ _ => ""
+ };
+ }
+}
+```
+
+### Action Button Group
+```razor
+
+
+
+
+
+
+
+@code {
+ private void OnAction(string action, MouseEventArgs args)
+ {
+ Console.WriteLine($"Action: {action}");
+ }
+}
+```
+
+## Edge Cases and Gotchas
+
+### Gotcha 1: Disable While Processing
+```razor
+
+
+
+
+
+
+@code {
+ private bool isProcessing = false;
+
+ private async Task ProcessWithState(MouseEventArgs args)
+ {
+ isProcessing = true;
+ await ProcessAsync();
+ isProcessing = false;
+ }
+
+ private async Task ProcessAsync()
+ {
+ // Simulate async operation (e.g., API call, database query)
+ await Task.Delay(2000);
+ Console.WriteLine("Processing complete!");
+ }
+}
+```
+
+### Gotcha 2: Multiple Primary Buttons
+Avoid this pattern - confuses user about what's the main action:
+```razor
+
+
+
+
+
+
+
+
+
+```
+
+### Gotcha 3: CSS Class Specificity
+Custom CSS might not override Syncfusion styles due to specificity:
+```razor
+
+
+
+
+
+
+
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-buttons/references/button-group.md b/.github/skills/syncfusion-blazor-toolkit-buttons/references/button-group.md
new file mode 100644
index 0000000..7977778
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-buttons/references/button-group.md
@@ -0,0 +1,804 @@
+# Button Group
+
+## Table of Contents
+1. [SfButtonGroup Overview](#sfbuttongroup-overview)
+2. [Selection Modes](#selection-modes)
+3. [Vertical Orientation](#vertical-orientation)
+4. [Button Component](#button-component)
+5. [IconCss and Icons](#iconcss-and-icons)
+6. [CssClass and Styling](#cssclass-and-styling)
+7. [Disabled State](#disabled-state)
+8. [Toggle Button](#toggle-button)
+9. [Single Selection Pattern](#single-selection-pattern)
+10. [Multiple Selection Pattern](#multiple-selection-pattern)
+11. [Real-World Use Cases](#real-world-use-cases)
+
+## SfButtonGroup Overview
+
+The `SfButtonGroup` component groups multiple buttons together, supporting single or multiple selection modes. It's perfect for:
+- Toggle groups
+- Radio button alternatives
+- Formatting toolbars
+- Filter collections
+- Option selectors
+
+### Basic Button Group
+```razor
+
+ Left
+ Center
+ Right
+
+```
+
+Each button in the group is a `Button` child component.
+
+### Group with Default Selection
+```razor
+
+ One
+ Two
+ Three
+
+```
+
+## Selection Modes
+
+### Single Selection
+```razor
+
+ Light
+ Dark
+ Auto
+
+```
+
+With `Single` mode:
+- Only one button can be selected at a time
+- Clicking a button deselects the previously selected button
+- Useful for mutually exclusive options
+
+### Multiple Selection
+```razor
+
+ Bold
+ Italic
+ Underline
+
+```
+
+With `Multiple` mode:
+- Multiple buttons can be selected simultaneously
+- Each button toggles independently
+- Useful for combined options
+
+### No Selection
+```razor
+
+
+ Action 1
+ Action 2
+
+
+@code {
+ private void DoAction1(bool selected) { /* ... */ }
+ private void DoAction2(bool selected) { /* ... */ }
+}
+```
+
+Without explicit `SelectionMode`, buttons work as a styled group without selection state.
+
+### SfButtonGroup Properties
+
+| Property | Type | Purpose |
+|----------|------|---------|
+| `Mode` | SelectionMode | Selection behavior (None, Single, Multiple). Default: `None` |
+| `IsVertical` | bool | Vertical layout arrangement |
+| `CssClass` | string | Custom CSS classes |
+| `HtmlAttributes` | Dictionary | Capture additional HTML attributes |
+
+### Group with HTML Attributes
+```razor
+
+ Option 1
+ Option 2
+
+```
+
+### Group with Lifecycle Event
+```razor
+
+ Left
+ Right
+
+
+@code {
+ private void OnGroupCreated(object args)
+ {
+ Console.WriteLine("ButtonGroup has been created");
+ }
+}
+```
+
+## Vertical Orientation
+
+The `IsVertical` property stacks buttons vertically instead of horizontally. This is useful for sidebar navigation, vertical toolbars, or option lists.
+
+### Basic Vertical Group
+```razor
+
+ Option 1
+ Option 2
+ Option 3
+
+```
+
+### Vertical with Single Selection
+```razor
+
+ Small
+ Medium
+ Large
+
+
+@code {
+ private string selectedSize = "Medium";
+
+ private void OnSizeSelected(bool selected, string size)
+ {
+ if (selected)
+ selectedSize = size;
+ }
+}
+```
+
+### Vertical with Multiple Selection
+```razor
+
+ Generate Report
+ Export Data
+ Print
+
+
+Selected Actions: @string.Join(", ", activeOptions)
+
+@code {
+ private List activeOptions = new();
+
+ private void OnOptionToggled(string option, bool selected)
+ {
+ if (selected)
+ activeOptions.Add(option);
+ else
+ activeOptions.Remove(option);
+ }
+}
+```
+
+## Button Component
+
+### Basic Button
+```razor
+
+ Option A
+ Option B
+
+```
+
+### Properties
+
+| Property | Type | Purpose |
+|----------|------|---------|
+| `Content` | string | Button text |
+| `IconCss` | string | Icon CSS classes |
+| `CssClass` | string | Custom CSS classes |
+| `Disabled` | bool | Enable/disable state |
+| `Selected` | bool | Current selection state |
+| `Name` | string | Name attribute for underlying input |
+| `Value` | string | Value attribute for form submission |
+| `IconPosition` | IconPosition | Icon placement (Left, Right, Top, Bottom) |
+| `IsToggle` | bool | Enable toggle behavior |
+| `HtmlAttributes` | Dictionary | Capture additional HTML attributes |
+
+### Complete Example
+```razor
+
+ Bold
+ Italic
+ Underline
+ Strikethrough
+
+```
+
+### Button with Name and Value for Form Submission
+```razor
+
+ Low Priority
+ Medium Priority
+ High Priority
+
+```
+
+## IconCss and Icons
+
+The `IconCss` property allows you to add icons to buttons using CSS icon classes. You can use icon-only buttons, icons with text, or combine icons with other styling options for visual communication.
+
+### Icon-Only Buttons
+```razor
+Icon-Only Button Group
+
+
+
+
+
+```
+
+**Best Practice**: Always include an `aria-label` on icon-only buttons for accessibility.
+
+### Icon with Text
+```razor
+Icon with Text
+
+ Left
+ Center
+ Right
+
+```
+
+### Icon with Position
+```razor
+
+ Save
+ Edit
+ Upload
+ Download
+
+```
+
+### Formatting Toolbar with Icons
+```razor
+Text Formatting Toolbar
+
+
+
+
+
+
+
+@code {
+ private List activeFormats = new();
+
+ private void OnFormatToggled(string format, bool selected)
+ {
+ if (selected)
+ activeFormats.Add(format);
+ else
+ activeFormats.Remove(format);
+ }
+}
+```
+
+### Icon Colors and Styling
+```razor
+Colored Icons with CssClass
+
+ Save
+ Close
+ Undo
+ Done
+
+```
+
+### Common Icon Classes Reference
+
+Common icon classes available for use (these are examples):
+- **Text Formatting**: `e-bold`, `e-italic`, `e-underline`, `e-strikethrough`
+- **Alignment**: `e-align-left`, `e-align-center`, `e-align-right`, `e-justify`
+- **Navigation**: `e-home`, `e-user`, `e-settings`, `e-help`
+- **Actions**: `e-save`, `e-close`, `e-undo`, `e-redo`, `e-check`, `e-delete`
+- **Media**: `e-play`, `e-pause`, `e-stop`
+
+## CssClass and Styling
+
+The `CssClass` property allows you to apply custom CSS classes to individual buttons for styling, theming, and visual hierarchy. You can combine multiple classes for different effects.
+
+### Semantic Color Classes
+```razor
+
+ Primary
+ Success
+ Warning
+ Info
+ Danger
+
+```
+
+### Flat Button Style
+```razor
+
+ Day
+ Week
+ Month
+
+```
+
+### Outlined Button Style
+```razor
+
+ Day
+ Week
+ Month
+
+```
+
+### Rounded Corners
+```razor
+
+ Option 1
+ Option 2
+ Option 3
+
+```
+
+### Mixed Styling in Single Group
+```razor
+
+ Primary Action
+ Success Action
+ Warning Action
+
+
+@code {
+ private bool selected1, selected2, selected3;
+
+ private void OnToggle(bool value, ref bool state)
+ {
+ state = value;
+ }
+}
+```
+
+### Custom CSS Classes
+```razor
+
+
+
+ Button 1
+ Button 2
+ Button 3
+
+```
+
+## Disabled State
+
+The `Disabled` property disables individual buttons or an entire button group. Disabled buttons cannot be interacted with and are visually distinct.
+
+### Mixed Enabled and Disabled Buttons
+```razor
+
+ Enabled
+ Disabled
+ Enabled
+
+```
+
+### All Buttons Disabled
+```razor
+
+ Option 1
+ Option 2
+ Option 3
+
+```
+
+## Toggle Button
+
+The `IsToggle` property enables individual buttons within a group to act as toggle buttons, allowing them to switch between selected and unselected states.
+
+### Toggle Button in Group
+```razor
+
+
+ Bold
+
+
+ Italic
+
+
+ Underline
+
+
+
+@code {
+ private bool isBold;
+ private bool isItalic;
+ private bool isUnderline;
+
+ private void OnToggleChanged(string style, bool selected)
+ {
+ switch (style)
+ {
+ case "Bold":
+ isBold = selected;
+ break;
+ case "Italic":
+ isItalic = selected;
+ break;
+ case "Underline":
+ isUnderline = selected;
+ break;
+ }
+ }
+}
+```
+
+### Icon Toggle Buttons
+```razor
+
+
+
+
+
+
+
+
+
+@code {
+ private bool isBoldIcon;
+ private bool isItalicIcon;
+ private bool isUnderlineIcon;
+}
+```
+
+## Single Selection Pattern
+
+### Radio Button Replacement
+```razor
+Choose Theme:
+
+ Light
+ Dark
+ System
+
+
+
+ Current Theme: @selectedTheme
+
+
+@code {
+ private string selectedTheme = "Light";
+
+ private void OnThemeSelected(bool selected, string theme)
+ {
+ if (selected)
+ selectedTheme = theme;
+ }
+}
+```
+
+### Size Selection
+```razor
+Select Size:
+
+ S
+ M
+ L
+ XL
+
+
+Selected Size: @selectedSize (@GetSizeDescription(selectedSize))
+
+@code {
+ private string selectedSize = "M";
+
+ private void OnSizeSelected(bool selected, string size)
+ {
+ if (selected)
+ selectedSize = size;
+ }
+
+ private string GetSizeDescription(string size)
+ {
+ return size switch
+ {
+ "S" => "Small",
+ "M" => "Medium",
+ "L" => "Large",
+ "XL" => "Extra Large",
+ _ => "Unknown"
+ };
+ }
+}
+```
+
+## Multiple Selection Pattern
+
+### Formatting Toolbar
+```razor
+Text Formatting:
+
+ Bold
+ Italic
+ Underline
+
+
+
+ Preview Text with Applied Formatting
+
+
+@code {
+ private List activeFormats = new();
+
+ private void OnFormatToggled(string format, bool selected)
+ {
+ if (selected)
+ activeFormats.Add(format);
+ else
+ activeFormats.Remove(format);
+ }
+
+ private string GetTextStyle()
+ {
+ var style = "";
+ if (activeFormats.Contains("Bold"))
+ style += "font-weight: bold; ";
+ if (activeFormats.Contains("Italic"))
+ style += "font-style: italic; ";
+ if (activeFormats.Contains("Underline"))
+ style += "text-decoration: underline; ";
+ return style;
+ }
+}
+```
+
+### Filter Collection
+```razor
+Filter Posts:
+
+ Tech
+ Travel
+ Food
+ Sports
+
+
+Posts:
+
+ @foreach (var post in GetFilteredPosts())
+ {
+ @post.Title (@post.Category)
+ }
+
+
+@code {
+ private List activeCategories = new();
+
+ private List allPosts = new()
+ {
+ new() { Title = "AI Trends", Category = "Tech" },
+ new() { Title = "Paris Guide", Category = "Travel" },
+ new() { Title = "Italian Food", Category = "Food" },
+ new() { Title = "World Cup", Category = "Sports" },
+ };
+
+ private void OnFilterChanged(string category, bool selected)
+ {
+ if (selected)
+ activeCategories.Add(category);
+ else
+ activeCategories.Remove(category);
+ }
+
+ private List GetFilteredPosts()
+ {
+ if (activeCategories.Count == 0)
+ return allPosts;
+
+ return allPosts.Where(p => activeCategories.Contains(p.Category)).ToList();
+ }
+
+ private class Post
+ {
+ public string Title { get; set; }
+ public string Category { get; set; }
+ }
+}
+```
+
+## Real-World Use Cases
+
+### Sort Options
+```razor
+Sort By:
+
+ Date
+ Name
+ Rating
+
+
+@code {
+ private string currentSort = "Date";
+
+ private void OnSortChanged(bool selected, string sortOption)
+ {
+ if (selected)
+ currentSort = sortOption;
+ // Apply sorting logic here
+ }
+}
+```
+
+### View Mode Toggle
+```razor
+View:
+
+ List
+ Grid
+
+
+@code {
+ private string viewMode = "List";
+
+ private void OnViewModeChanged(bool selected, string mode)
+ {
+ if (!selected) return;
+
+ viewMode = mode;
+ }
+}
+```
+
+### Alignment Buttons
+```razor
+Text Alignment:
+
+ Left
+ Center
+ Right
+ Justify
+
+
+@code {
+ private string alignment = "Left";
+
+ private void OnAlignmentChanged(bool selected, string newAlignment)
+ {
+ if (!selected) return;
+
+ alignment = newAlignment;
+ }
+}
+```
+
+### Time Range Selection
+```razor
+Select Period:
+
+ Today
+ Week
+ Month
+ Year
+
+
+Showing data for: @selectedPeriod
+
+@code {
+ private string selectedPeriod = "Week";
+ private bool isToday, isWeek = true, isMonth, isYear;
+
+ private void OnPeriodChanged(bool selected, string period)
+ {
+ if (!selected) return;
+
+ selectedPeriod = period;
+ // Fetch data for selected period
+ isToday = period == "Today";
+ isWeek = period == "Week";
+ isMonth = period == "Month";
+ isYear = period == "Year";
+ }
+}
+```
+
+## Edge Cases and Gotchas
+
+### Gotcha 1: No Initial Selection with Single Mode
+```razor
+
+
+ Option 1
+ Option 2
+
+
+
+
+ Option 1
+ Option 2
+
+
+@code {
+ private int selectedOption = 0;
+ private bool isOpt1 = true, isOpt2;
+
+ private void OnSelect(bool selected, int option)
+ {
+ if (!selected) return;
+
+ selectedOption = option;
+ // One will always be "selected" through your tracking
+ isOpt1 = option == 1;
+ isOpt2 = option == 2;
+ }
+}
+```
+
+### Gotcha 2: Multiple Selection Confusion
+```razor
+
+
+ A
+ B
+
+
+
+
+
Select one or more options:
+
+ A
+ B
+
+
Selected: @string.Join(", ", selectedOptions)
+
+
+@code {
+ private List selectedOptions = new();
+
+ private void ToggleSelection(string option, bool selected)
+ {
+ if (selected)
+ selectedOptions.Add(option);
+ else
+ selectedOptions.Remove(option);
+ }
+}
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-buttons/references/events-and-callbacks.md b/.github/skills/syncfusion-blazor-toolkit-buttons/references/events-and-callbacks.md
new file mode 100644
index 0000000..444ab4c
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-buttons/references/events-and-callbacks.md
@@ -0,0 +1,561 @@
+# Events and Callbacks
+
+## Table of Contents
+1. [Click Event Handling](#click-event-handling)
+2. [EventCallback Parameter](#eventcallback-parameter)
+3. [Created Event Lifecycle](#created-event-lifecycle)
+4. [Async Event Handling](#async-event-handling)
+5. [Event Arguments](#event-arguments)
+6. [State Management with Events](#state-management-with-events)
+7. [Debugging Events](#debugging-events)
+
+## Click Event Handling
+
+### Basic Click Handler
+```razor
+
+
+@code {
+ private void OnClick(MouseEventArgs args)
+ {
+ Console.WriteLine("Button clicked!");
+ }
+}
+```
+
+When the button is clicked, the `OnClick` method executes.
+
+### Click with Event Arguments
+```razor
+
+
+@code {
+ private void OnClickWithArgs(MouseEventArgs e)
+ {
+ Console.WriteLine($"Button clicked at X:{e.ClientX}, Y:{e.ClientY}");
+ Console.WriteLine($"Button: {e.Button}");
+ Console.WriteLine($"CtrlKey: {e.CtrlKey}");
+ }
+}
+```
+
+### Multiple Buttons with Different Handlers
+```razor
+
+
+
+
+@code {
+ private void OnSave(MouseEventArgs args)
+ {
+ Console.WriteLine("Saving...");
+ }
+
+ private void OnCancel(MouseEventArgs args)
+ {
+ Console.WriteLine("Cancelled");
+ }
+
+ private void OnDelete(MouseEventArgs args)
+ {
+ Console.WriteLine("Deleting...");
+ }
+}
+```
+
+### Click with Lambda Expression
+```razor
+
+Count: @count
+
+@code {
+ private int count = 0;
+}
+```
+
+### Click with Parameters
+```razor
+
+
+Selected: @selectedId
+
+@code {
+ private int selectedId = 0;
+
+ private void SelectItem(int id)
+ {
+ selectedId = id;
+ }
+}
+```
+
+## EventCallback Parameter
+
+### Understanding EventCallback
+`EventCallback` is Blazor's mechanism for component communication. In buttons, it enables:
+- Parent-to-child event propagation
+- Proper change detection
+- Support for async handlers
+
+### Creating a Button Component Wrapper
+```razor
+
+@inherits ComponentBase
+
+
+
+@code {
+ [Parameter]
+ public string Content { get; set; } = "Button";
+
+ [Parameter]
+ public bool IsPrimary { get; set; } = false;
+
+ [Parameter]
+ public EventCallback OnClick { get; set; }
+
+ private async Task HandleClick(MouseEventArgs e)
+ {
+ await OnClick.InvokeAsync(e);
+ }
+}
+```
+
+Usage:
+```razor
+
+
+@code {
+ private async Task HandleMyClick(MouseEventArgs e)
+ {
+ Console.WriteLine("Button clicked via callback");
+ }
+}
+```
+
+## Created Event Lifecycle
+
+### Created Event
+```razor
+
+
+@code {
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("SfButton component rendering is complete");
+ }
+}
+```
+
+The `Created` event fires after the component has finished rendering in the DOM.
+
+### Using Created for Initialization
+```razor
+
+
+@code {
+ private string buttonLabel = "Loading...";
+
+ private async void OnButtonCreated(object args)
+ {
+ // Perform initialization after render
+ await Task.Delay(500);
+ buttonLabel = "Ready!";
+
+ await InvokeAsync(StateHasChanged);
+ }
+}
+```
+
+### Lifecycle Order
+```razor
+
+
+
+@code {
+ protected override void OnInitialized()
+ {
+ Console.WriteLine("1. OnInitialized");
+ }
+
+ protected override async Task OnInitializedAsync()
+ {
+ Console.WriteLine("2. OnInitializedAsync");
+ }
+
+ protected override void OnParametersSet()
+ {
+ Console.WriteLine("3. OnParametersSet");
+ }
+
+ protected override async Task OnParametersSetAsync()
+ {
+ Console.WriteLine("4. OnParametersSetAsync");
+ }
+
+ protected override void OnAfterRender(bool firstRender)
+ {
+ Console.WriteLine($"5. OnAfterRender (firstRender: {firstRender})");
+ }
+
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("6. Created event");
+ }
+
+ private void OnClick(MouseEventArgs args)
+ {
+ Console.WriteLine("7. Click event");
+ }
+}
+```
+
+## Async Event Handling
+
+### Async Click Handler
+```razor
+
+
+@code {
+ private bool isLoading = false;
+
+ private async Task LoadDataAsync(MouseEventArgs args)
+ {
+ isLoading = true;
+ try
+ {
+ // Simulate API call
+ await Task.Delay(2000);
+ Console.WriteLine("Data loaded!");
+ }
+ finally
+ {
+ isLoading = false;
+ }
+ }
+}
+```
+
+### Async with Error Handling
+```razor
+
+
+ @(errorMessage ?? successMessage)
+
+
+@code {
+ private bool isProcessing = false;
+ private string? errorMessage;
+ private string? successMessage;
+
+ private async Task SubmitAsync(MouseEventArgs args)
+ {
+ isProcessing = true;
+ errorMessage = null;
+ successMessage = null;
+
+ try
+ {
+ await Task.Delay(1000);
+
+ // Simulate potential error (10% chance)
+ if (new Random().Next(10) == 0)
+ throw new Exception("Submission failed");
+
+ successMessage = "Submitted successfully!";
+ }
+ catch (Exception ex)
+ {
+ errorMessage = $"Error: {ex.Message}";
+ }
+ finally
+ {
+ isProcessing = false;
+ }
+ }
+}
+```
+
+### Async with Timeout
+```razor
+
+@message
+
+@code {
+ private string message = "";
+
+ private async Task FetchWithTimeout(MouseEventArgs args)
+ {
+ message = "Fetching...";
+
+ try
+ {
+ using (var cts = new CancellationTokenSource(TimeSpan.FromSeconds(5)))
+ {
+ await SimulateApiCallAsync(cts.Token);
+ message = "Success!";
+ }
+ }
+ catch (OperationCanceledException)
+ {
+ message = "Request timed out after 5 seconds";
+ }
+ catch (Exception ex)
+ {
+ message = $"Error: {ex.Message}";
+ }
+ }
+
+ private async Task SimulateApiCallAsync(CancellationToken ct)
+ {
+ await Task.Delay(3000, ct); // Simulates work
+ }
+}
+```
+
+## Event Arguments
+
+### MouseEventArgs Properties
+The `MouseEventArgs` object contains:
+
+| Property | Type | Description |
+|----------|------|-------------|
+| `ClientX` | double | Mouse X position relative to viewport |
+| `ClientY` | double | Mouse Y position relative to viewport |
+| `Button` | long | Mouse button (0=left, 1=middle, 2=right) |
+| `Buttons` | long | Pressed buttons (bitmask) |
+| `CtrlKey` | bool | Ctrl key pressed |
+| `ShiftKey` | bool | Shift key pressed |
+| `AltKey` | bool | Alt key pressed |
+| `MetaKey` | bool | Meta/Command key pressed |
+
+### Using MouseEventArgs
+```razor
+
+@clickInfo
+
+@code {
+ private string clickInfo = "";
+
+ private void ShowClickInfo(MouseEventArgs e)
+ {
+ clickInfo = $"Button: {e.Button}, Ctrl: {e.CtrlKey}, Shift: {e.ShiftKey}";
+ }
+}
+```
+
+## State Management with Events
+
+### Simple State Update
+```razor
+
+State: @(isVisible ? "Visible" : "Hidden")
+
+@code {
+ private bool isVisible = false;
+
+ private void ToggleState(MouseEventArgs args)
+ {
+ isVisible = !isVisible;
+ }
+}
+```
+
+### List State Management
+```razor
+
+
+
+
+ @foreach (var item in items)
+ {
+ @item
+ }
+
+
+@code {
+ private List items = new();
+ private int itemCount = 0;
+
+ private void AddItem(MouseEventArgs args)
+ {
+ items.Add($"Item {++itemCount}");
+ }
+
+ private void ClearItems(MouseEventArgs args)
+ {
+ items.Clear();
+ itemCount = 0;
+ }
+}
+```
+
+### Parent-Child State Sharing
+```razor
+
+
+
+
Parent sees: @count
+
+
+@code {
+ private int count = 0;
+
+ private void UpdateCount(int newCount)
+ {
+ count = newCount;
+ }
+}
+
+
+@inherits ComponentBase
+
+Child: @LocalCount
+
+
+@code {
+ [Parameter]
+ public int InitialCount { get; set; }
+
+ [Parameter]
+ public EventCallback OnCountChanged { get; set; }
+
+ private int LocalCount { get; set; }
+
+ protected override void OnInitialized()
+ {
+ LocalCount = InitialCount;
+ }
+
+ private async Task IncrementAsync(MouseEventArgs args)
+ {
+ LocalCount++;
+ await OnCountChanged.InvokeAsync(LocalCount);
+ }
+}
+```
+
+## Debugging Events
+
+### Console Logging
+```razor
+
+
+@code {
+ private void DebugClick(MouseEventArgs args)
+ {
+ Console.WriteLine("Click event fired");
+ Console.WriteLine($"Timestamp: {DateTime.Now:HH:mm:ss.fff}");
+ }
+}
+```
+
+### Event Tracking
+```razor
+
+
+
Event Log:
+
+ @foreach (var log in eventLog)
+ {
+ @log
+ }
+
+
+
+@code {
+ private List eventLog = new();
+
+ private void TrackEvent(MouseEventArgs args)
+ {
+ eventLog.Add($"[{DateTime.Now:HH:mm:ss}] Click event");
+
+ // Keep only last 10 events
+ if (eventLog.Count > 10)
+ eventLog.RemoveAt(0);
+ }
+}
+```
+
+### Conditional Event Logging
+```razor
+
+
+@code {
+ private int clickCount = 0;
+ private bool debugMode = false;
+
+ private void ConditionalLog()
+ {
+ clickCount++;
+
+ if (debugMode)
+ {
+ Console.WriteLine($"Click #{clickCount}");
+ Console.WriteLine($"Stack: {Environment.StackTrace}");
+ }
+ }
+}
+```
+
+## Edge Cases and Gotchas
+
+### Gotcha 1: Async Void Handlers
+```razor
+
+
+
+
+
+
+@code {
+ private async void BadAsyncVoidHandler(MouseEventArgs args) // ❌ Bad
+ {
+ await Task.Delay(1000);
+ }
+
+ private async Task GoodAsyncTaskHandler(MouseEventArgs args) // ✅ Good
+ {
+ await Task.Delay(1000);
+ }
+}
+```
+
+### Gotcha 2: StaleClosures
+```razor
+
+@for (int i = 0; i < 3; i++)
+{
+
+}
+
+
+@for (int i = 0; i < 3; i++)
+{
+ int index = i;
+
+}
+
+@code {
+ private void OnClick(int buttonIndex)
+ {
+ Console.WriteLine($"Clicked button {buttonIndex}");
+ }
+}
+```
+
+### Gotcha 3: Not Awaiting EventCallback
+```razor
+
+private async Task HandleClick()
+{
+ await OnClick.InvokeAsync(null); // ✅ Correct: await
+ // Next code runs after callback completes
+}
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-buttons/references/getting-started.md b/.github/skills/syncfusion-blazor-toolkit-buttons/references/getting-started.md
new file mode 100644
index 0000000..72aa1a3
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-buttons/references/getting-started.md
@@ -0,0 +1,255 @@
+# Getting Started with Syncfusion Blazor Buttons
+
+## Table of Contents
+1. [Installation Requirements](#installation-requirements)
+2. [Adding to Your Project](#adding-to-your-project)
+3. [First Button Component](#first-button-component)
+4. [Basic Click Handling](#basic-click-handling)
+5. [Form Integration](#form-integration)
+6. [Using the Content Property](#using-the-content-property)
+7. [Testing in Samples](#testing-in-samples)
+8. [Common Setup Issues](#common-setup-issues)
+
+## Installation Requirements
+
+The Syncfusion Blazor Toolkit button components are part of the main toolkit package. Ensure you have:
+
+- **.NET SDK:** .NET Core 3.1 or later
+- **Blazor Project:** WebAssembly or Server-side
+- **NuGet Package:** `Syncfusion.Blazor.Toolkit` latest version
+- **CSS Files:** Theme CSS imported in your layout
+
+## Adding to Your Project
+
+### 1. Install via NuGet
+```bash
+dotnet add package Syncfusion.Blazor.Toolkit
+```
+
+### 2. Register in Program.cs (Blazor Server)
+```csharp
+builder.Services.AddSyncfusionBlazorToolkit();
+```
+
+Or for Blazor WebAssembly:
+```csharp
+builder.Services.AddSyncfusionBlazorToolkit();
+```
+
+### 3. Add Theme CSS in Layout
+In `_Host.cshtml` or `index.html`, add the theme stylesheet:
+```html
+
+```
+
+### 4. Add Global Imports
+In `_Imports.razor`, add:
+```razor
+@using Syncfusion.Blazor
+@using Syncfusion.Blazor.Toolkit
+```
+
+## First Button Component
+
+### Minimal Button
+```razor
+
+```
+
+This renders a standard button with default styling. The button is clickable but doesn't perform any action without an event handler.
+
+### Button with Text Only
+```razor
+
+
+
+```
+
+The `Content` property accepts any string value and displays it as button text.
+
+## Basic Click Handling
+
+### Simple Click Handler
+```razor
+
+
+@code {
+ private void OnClick(MouseEventArgs args)
+ {
+ Console.WriteLine("Button was clicked!");
+ }
+}
+```
+
+### Async Click Handler
+```razor
+
+
+@code {
+ private async Task LoadDataAsync(MouseEventArgs args)
+ {
+ await Task.Delay(1000); // Simulate API call
+ Console.WriteLine("Data loaded!");
+ }
+}
+```
+
+### Click with Parameter
+```razor
+
+
+
+@code {
+ private void DeleteItem(int id)
+ {
+ Console.WriteLine($"Deleting item {id}");
+ }
+}
+```
+
+## Form Integration
+
+### Button Types for Forms
+```razor
+
+
+
+
+ Name:
+
+
+
+
+
+
+
+
+
+@code {
+ private FormModel formModel = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Form submitted: {formModel.Name}");
+ }
+
+ public class FormModel
+ {
+ public string Name { get; set; } = "";
+ }
+}
+```
+
+**Note:** The `Type` property accepts `ButtonType.Button` (default), `ButtonType.Submit`, or `ButtonType.Reset`.
+
+## Using the Content Property
+
+### String Content
+```razor
+
+
+@code {
+ private string currentLabel = "Click Here";
+}
+```
+
+### Dynamic Content
+```razor
+
+
+@code {
+ private bool isLoading = false;
+}
+```
+
+### Content from Variables
+```razor
+
+
+@code {
+ private string GetButtonText()
+ {
+ return DateTime.Now.Hour < 12 ? "Good Morning" : "Good Afternoon";
+ }
+}
+```
+
+## Testing in Samples
+
+### Running the Sample App
+```bash
+cd samples/Blazor.Toolkit.Samples
+dotnet watch run
+```
+
+The application starts at `https://localhost:7145` (or similar port).
+
+### Adding a Test Page
+1. Create `Pages/ButtonTest.razor`
+2. Add button examples
+3. Navigate to `/button-test` to test
+
+### Example Test Page
+```razor
+@page "/button-test"
+
+Button Component Tests
+
+
+
Basic Button
+
+
+
+
+
Button with Click Handler
+
+
@clickMessage
+
+
+@code {
+ private string clickMessage = "";
+
+ private void OnSubmit(MouseEventArgs args)
+ {
+ clickMessage = "Submitted at " + DateTime.Now.ToString("HH:mm:ss");
+ }
+}
+```
+
+## Common Setup Issues
+
+### Issue 1: Button Not Rendering
+**Symptom:** No button appears on page
+**Solution:**
+- Verify `@using` statement includes `Syncfusion.Blazor.Toolkit.Buttons`
+- Check that services are registered in `Program.cs`
+- Ensure CSS file is imported in layout
+
+### Issue 2: Styling Looks Wrong
+**Symptom:** Button appears unstyled or broken
+**Solution:**
+- Verify theme CSS is loaded: Check browser DevTools Network tab
+- Confirm correct theme CSS path: ` ` Replace fluent.min.css with the relevant stylesheet (bootstrap.min.css, material.min.css, tailwind.min.css, etc.) depending on the theme you’re using.
+- Ensure theme matches your layout expectations
+
+### Issue 3: Click Handler Not Firing
+**Symptom:** Button clicks don't trigger handler
+**Solution:**
+- Verify `OnClick` directive is present
+- Check handler method has correct signature
+- For async handlers, use `OnClick="OnClickAsync"` with `async Task` return type
+- Ensure button is not disabled
+
+### Issue 4: Content Not Updating
+**Symptom:** Button text doesn't change when variable changes
+**Solution:**
+- Wrap content in `@(...)` expression for binding
+- Use `StateHasChanged()` if manual refresh needed
+- Verify variable is not hardcoded
+
+## Next Steps
+
+- Learn styling in **button-fundamentals.md**
+- Add icons in **icons-and-content.md**
+- Handle events in **events-and-callbacks.md**
+- Explore button groups in **button-group.md**
diff --git a/.github/skills/syncfusion-blazor-toolkit-buttons/references/icons-and-content.md b/.github/skills/syncfusion-blazor-toolkit-buttons/references/icons-and-content.md
new file mode 100644
index 0000000..0a2b7bf
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-buttons/references/icons-and-content.md
@@ -0,0 +1,370 @@
+# Icons and Content
+
+## Table of Contents
+1. [Icon CSS Classes](#icon-css-classes)
+2. [Icon Positioning](#icon-positioning)
+3. [Syncfusion Icon Library](#syncfusion-icon-library)
+4. [Content vs ChildContent](#content-vs-childcontent)
+5. [Complex Content Patterns](#complex-content-patterns)
+6. [SVG and Custom Icons](#svg-and-custom-icons)
+7. [Icon-Only Buttons](#icon-only-buttons)
+
+## Icon CSS Classes
+
+### Basic Icon Button
+```razor
+
+```
+
+The `IconCss` property accepts space-separated CSS class names for icon styling:
+
+- First class typically identifies the icon library (`e-icons`)
+- Second class specifies the icon (`e-plus`, `e-save`, `e-close`, `e-refresh` etc.)
+
+### Icon Library Classes
+
+| Library | Class | Usage |
+|---------|-------|-------|
+| Syncfusion | `e-icons` | Built-in Syncfusion icon set |
+| Font Awesome | `fa fa-*` | Font Awesome icon library |
+| Bootstrap | `bi bi-*` | Bootstrap icon library |
+
+### Common Syncfusion Icons
+
+| Icon | Class |
+|------|-------|
+| Add | `e-icons e-plus` |
+| Edit | `e-icons e-edit` |
+| Delete | `e-icons e-delete` |
+| Save | `e-icons e-save` |
+| Close | `e-icons e-close` |
+| Search | `e-icons e-search` |
+| Filter | `e-icons e-filter` |
+| Refresh | `e-icons e-refresh` |
+
+## Icon Positioning
+
+### Position Enum Values
+The `IconPosition` parameter accepts:
+- `Left` — Icon before text (default)
+- `Right` — Icon after text
+- `Top` — Icon above text
+- `Bottom` — Icon below text
+
+### Examples by Position
+
+#### Left Position
+```razor
+
+```
+Renders: **[icon] Edit Item**
+
+#### Right Position
+```razor
+
+```
+Renders: **Next [icon]**
+
+#### Top Position
+```razor
+
+```
+Renders: Icon above text
+
+#### Bottom Position
+```razor
+
+```
+Renders: Icon below text
+
+### Choosing Position
+
+**Left position** — Best for action buttons (Edit, Delete, Add)
+```razor
+
+
+```
+
+**Right position** — Best for navigation/direction (Next, Previous, Continue)
+```razor
+
+```
+
+**Top/Bottom** — Best for mobile or icon-focused layouts
+```razor
+
+```
+
+## Syncfusion Icon Library
+
+### Icon Library Integration
+The Syncfusion icon library is included with theme CSS. To use icons:
+
+1. Ensure theme CSS is imported (contains icon font)
+2. Use `e-icons` class with specific icon class
+3. Icons render as font-based glyphs (scalable)
+
+### Complete Icon Examples
+```razor
+
+
+
+
+
+
+
+
+
+```
+
+## Content vs ChildContent
+
+### Content Property (Text Only)
+```razor
+
+
+
+```
+
+Use `Content` for:
+- Simple text labels
+- Dynamic text from variables
+- Simple expressions
+
+### ChildContent (Complex HTML)
+```razor
+
+
+ Bold and Italic
+
+```
+
+ChildContent allows:
+- HTML elements and tags
+- Complex formatting
+- Nested components
+- Mixed text and elements
+
+### Practical Comparison
+
+```razor
+
+
+
+
+
+
+ Advanced Button
+
+
+
+
+
+
+ Edit This Item
+
+```
+
+### When to Use Each
+
+**Use Content:**
+- Simple text buttons
+- Performance-critical scenarios
+- Dynamic text binding
+
+**Use ChildContent:**
+- Formatted text
+- Icon + text combinations
+- Complex styling
+- Custom elements
+
+## Complex Content Patterns
+
+### Icon with Styled Text
+```razor
+
+
+ Download Report
+
+```
+
+### Badge with Button
+```razor
+
+ Notifications
+
+ 3
+
+
+```
+
+### Multi-line Button Content
+```razor
+
+
+ Click Me
+
+ Additional description goes here
+
+
+
+```
+
+### Status Indicator Button
+```razor
+
+
+
+ @(isActive ? "Online" : "Offline")
+
+
+
+@code {
+ private bool isActive = true;
+}
+```
+
+## SVG and Custom Icons
+
+### Using SVG Icons
+```razor
+
+
+
+
+ SVG Icon Button
+
+```
+
+### Font Awesome Icons
+```razor
+
+
+
+
+
+ Favorite
+
+```
+
+### Bootstrap Icons
+```razor
+
+
+
+
+
+ Download
+
+```
+
+## Icon-Only Buttons
+
+### Icon Without Text
+```razor
+
+
+
+
+```
+
+Always include `title` attribute for accessibility with icon-only buttons.
+
+### Icon Button Sizing
+```razor
+
+
+
+
+
+
+
+
+```
+
+### Icon Button Group
+```razor
+
+
+
+
+
+```
+
+### Icon Toolbar Pattern
+```razor
+
+
+
+
+
+
+
+
+```
+
+## Edge Cases and Gotchas
+
+### Gotcha 1: Icon Class Spacing
+```razor
+
+
+
+
+
+```
+
+### Gotcha 2: Icon Library Must Be Loaded
+```razor
+
+
+
+
+
+```
+
+### Gotcha 3: ChildContent Replaces Content
+```razor
+
+
+
+ Custom Content Here
+
+
+
+
+
+ Edit
+
+```
+
+### Gotcha 4: Accessibility with Icons
+```razor
+
+
+
+
+
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/SKILL.md b/.github/skills/syncfusion-blazor-toolkit-inputs/SKILL.md
new file mode 100644
index 0000000..15afeec
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/SKILL.md
@@ -0,0 +1,331 @@
+---
+name: syncfusion-blazor-toolkit-inputs
+description: Implement Syncfusion Blazor Toolkit input components. Comprehensive guide for TextBox, TextArea, NumericTextBox, Uploader, CheckBox, RadioButton, and Switch. Covers component usage, event handling, validation, styling, accessibility, and real-world patterns.
+compatibility: .NET 8+, Blazor WebAssembly/Server
+metadata:
+ author: "Syncfusion Inc"
+ version: "1.0.0"
+---
+
+# Syncfusion Blazor Toolkit - Input Components
+
+The Syncfusion Blazor Toolkit provides a comprehensive collection of input components for building rich, interactive forms and data entry experiences. From basic text inputs to file uploaders, the Inputs namespace offers solutions for data input scenarios.
+
+## Component Overview
+
+| Component | Purpose | Use Case |
+|-----------|---------|----------|
+| **SfTextBox** | Single-line text input | General text entry, search fields, usernames |
+| **SfTextArea** | Multi-line text input | Comments, descriptions, feedback, long-form content |
+| **SfNumericTextBox** | Numeric input with formatting | Prices, quantities, ages, measurements |
+| **SfUploader** | File upload with validation | Document upload, image upload, bulk file handling |
+| **SfCheckBox** | Boolean selection (multiple) | Agreement checkboxes, multi-select options |
+| **SfRadioButton** | Boolean selection (single) | Exclusive choice options, single selection groups |
+| **SfSwitch** | Toggle boolean state | Feature toggles, on/off switches, preferences |
+
+## Documentation and Navigation Guide
+
+### Getting Started
+📄 **Read:** [references/getting-started-inputs.md](references/getting-started-inputs.md)
+- Installation and package setup
+- CSS imports and theming
+- Basic component initialization
+- Common event patterns
+- State management basics
+
+### Basic Input Controls
+📄 **Read:** [references/textbox-textarea.md](references/textbox-textarea.md)
+- SfTextBox component properties and events
+- SfTextArea for multi-line input
+- Floating labels and placeholders
+- Focus and blur event handling
+- Input validation and error states
+
+📄 **Read:** [references/numeric-currency.md](references/numeric-currency.md)
+- SfNumericTextBox generic implementation
+- Currency and percentage formatting
+- Min/Max constraints and step values
+- Decimal place handling
+- Spin button behavior
+- Practical examples with real-world scenarios
+
+### Specialized Input Components
+📄 **Read:** [references/uploader.md](references/uploader.md)
+- SfUploader complete workflow
+- Auto upload and async settings
+- Multiple file selection and restrictions
+- File type and size validation
+- Upload events and progress tracking
+- Error handling and retry logic
+- Drag-and-drop support
+
+### Selection Controls
+📄 **Read:** [references/checkbox-radio-switch.md](references/checkbox-radio-switch.md)
+- SfCheckBox states and binding
+- SfRadioButton grouping and selection
+- SfSwitch toggle behavior
+- Label positioning and text
+- Change event handling
+- Grouped and conditional patterns
+
+### Advanced Features & Best Practices
+📄 **Read:** [references/input-accessibility.md](references/input-accessibility.md)
+- WCAG compliance principles
+- Keyboard navigation across all inputs
+- ARIA attributes and label associations
+- Focus management and indicators
+- Error messaging and validation
+- Screen reader support
+- Component-specific accessibility notes
+
+## Quick Start Example
+
+### Basic Text Input
+```razor
+@page "/inputs-demo"
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+Basic Inputs Demo
+
+
+ Username:
+
+
+
+
+
+ Email:
+
+
+
+
+
+ Comments:
+
+
+
+
+@code {
+ private SfTextBox usernameBox;
+ private string username = "";
+ private string email = "";
+ private string comments = "";
+
+ private void OnUsernameChange(ChangedEventArgs args)
+ {
+ username = args.Value;
+ Console.WriteLine($"Username changed: {username}");
+ }
+
+ private void OnEmailChange(ChangedEventArgs args)
+ {
+ email = args.Value;
+ Console.WriteLine($"Email changed: {email}");
+ }
+}
+```
+
+### NumericTextBox with Currency
+```razor
+
+ Price:
+
+
+
+
+@code {
+ private decimal price = 29.99m;
+}
+```
+
+### CheckBox and Switch
+```razor
+
+
+
+
+
+ Enable Notifications:
+
+
+
+@code {
+ private bool rememberMe = false;
+ private bool notificationsEnabled = true;
+}
+```
+
+## Common Patterns Across All Inputs
+
+### 1. Two-Way Data Binding
+All input components support two-way binding with `@bind-Value`:
+```razor
+
+
+
+
+@code {
+ private string myText = "";
+ private int myNumber = 0;
+ private bool myBool = false;
+}
+```
+
+### 2. Event Handling Pattern
+Components emit change events for tracking modifications:
+```razor
+
+
+@code {
+ private void OnValueChanged(ChangedEventArgs args)
+ {
+ Console.WriteLine($"New value: {args.Value}");
+ }
+}
+```
+
+### 3. Validation and Error States
+Use CascadingParameter with EditContext for form validation:
+```razor
+@using Syncfusion.Blazor.Toolkit.Inputs
+@using System.ComponentModel.DataAnnotations
+
+
+
+
+
+ Email:
+
+
+
+
+
+ Submit
+
+
+@code {
+ private LoginModel formModel = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Email: {formModel.Email}");
+ }
+
+ public class LoginModel
+ {
+ [Required(ErrorMessage = "Email is required")]
+ [EmailAddress(ErrorMessage = "Invalid email format")]
+ public string Email { get; set; } = "";
+ }
+}
+```
+
+### 4. Disabled and ReadOnly States
+All inputs support disabled and read-only configurations:
+```razor
+
+
+
+```
+
+### 5. Event Binding for Multiple Inputs
+Handle focus, blur, and input events:
+```razor
+
+
+@code {
+ private void OnFocus(FocusInEventArgs args)
+ {
+ Console.WriteLine("Focused");
+ }
+
+ private void OnBlur(FocusOutEventArgs args)
+ {
+ Console.WriteLine("Blurred");
+ }
+
+ private void OnInput(InputEventArgs args)
+ {
+ Console.WriteLine($"Input: {args.Value}");
+ }
+}
+```
+
+## Key Props & Events Summary
+
+### Universal Input Props
+- `Disabled`: Disable user input (bool)
+- `ReadOnly`: Prevent modification (bool)
+- `Placeholder`: Hint text (string)
+- `CssClass`: Custom CSS classes (string)
+- `HtmlAttributes`: Additional HTML attributes (Dictionary)
+
+### Common Value Props
+- `Value`: Current component value (varies by type)
+- `ValueChange`: Event fired when value changes (callback)
+- `@bind-Value`: Two-way binding helper
+
+### Focus & Blur Events
+- `OnFocus`: Fired when component gains focus
+- `OnBlur`: Fired when component loses focus
+
+### Input-Specific Props (See references for details)
+- **TextBox**: `Type`, `FloatLabelType`
+- **TextArea**: `RowCount`, `ColumnCount`, `MaxLength`
+- **NumericTextBox**: `Format`, `Min`, `Max`, `Step`, `Decimals`
+- **Uploader**: `AllowedExtensions`, `MaxFileSize`, `AutoUpload`
+
+## Component Selection Guide
+
+**Use SfTextBox when:**
+- Need simple text input
+- Collecting usernames, passwords, search queries
+- Want email/URL/number type validation
+
+**Use SfTextArea when:**
+- Accepting multi-line content
+- Building comment sections, feedback forms
+- Need customizable rows/columns
+
+**Use SfNumericTextBox when:**
+- Input must be numeric
+- Need currency/percentage formatting
+- Require min/max constraints and step values
+
+**Use SfUploader when:**
+- Need file upload functionality
+- Require file validation (type, size)
+- Want progress tracking and error handling
+
+**Use SfCheckBox when:**
+- Need multiple independent selections
+- Building agreement/terms checkboxes
+- Want multiple boolean flags
+
+**Use SfRadioButton when:**
+- Need mutually exclusive selection
+- Building single-choice option groups
+- Want dependent form fields
+
+**Use SfSwitch when:**
+- Need simple on/off toggle
+- Building preference/feature switches
+- Want visual toggle indicator
+
+---
+
+**👉 Start with [references/getting-started-inputs.md](references/getting-started-inputs.md) for installation and basic setup, then navigate to your specific component reference.**
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/references/checkbox-radio-switch.md b/.github/skills/syncfusion-blazor-toolkit-inputs/references/checkbox-radio-switch.md
new file mode 100644
index 0000000..489b9fa
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/references/checkbox-radio-switch.md
@@ -0,0 +1,882 @@
+# Checkbox, RadioButton, and Switch Components - Selection Controls
+
+## Table of Contents
+- [SfCheckBox Overview](#sfcheckbox-overview)
+- [CheckBox Properties](#checkbox-properties)
+- [CheckBox Events](#checkbox-events)
+- [SfRadioButton Overview](#sfradiobutton-overview)
+- [RadioButton Properties](#radiobutton-properties)
+- [RadioButton Events](#radiobutton-events)
+- [SfSwitch Overview](#sfswitch-overview)
+- [Switch Properties](#switch-properties)
+- [Switch Events](#switch-events)
+- [Practical Examples](#practical-examples)
+
+## SfCheckBox Overview
+
+**SfCheckBox** allows multiple independent selections. It's generic to support any value type and provides checked, unchecked, and indeterminate states.
+
+**When to use SfCheckBox:**
+- Multiple independent options (select many)
+- Agreement/terms acceptance
+- Feature toggles with multiple choices
+- Preference selections
+- Bulk actions (select all)
+
+### Basic Implementation
+
+```razor
+
+```
+
+### With Label
+
+```razor
+
+
+@code {
+ private bool agreeTerms = false;
+}
+```
+
+## CheckBox Properties
+
+### Essential Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `Checked` | `TChecked` | `default(TChecked)` | Checked state |
+| `Indeterminate` | `bool` | `false` | Indeterminate state |
+| `Label` | `string` | `""` | Label text |
+| `Disabled` | `bool` | `false` | Disable checkbox |
+| `LabelPosition` | `LabelPosition` | `Before` | Label placement |
+| `EnableTriState` | `bool` | `false` | Enable three-state-mode |
+| `CssClass` | `string` | `""` | Custom CSS classes |
+
+### Checkbox States
+
+Common CheckBox states include `Checked`, `Unchecked`, `Disabled`, and `Indeterminate`. Use Disabled to prevent interaction, and enable tri‑state using `EnableTriState` to support the Indeterminate state.
+
+**Note:** For proper tri-state behavior, use `bool?` (nullable bool) as the generic type `TChecked`. The `bool` type only supports binary checked/unchecked states.
+
+```razor
+
+
+
+
+@code {
+ private bool? tIndeterminate = null; // null = indeterminate state
+}
+```
+
+### Label Positioning
+
+```razor
+
+
Label Positions
+
+
+
+
+
+
+
+
+
+
+
+```
+
+### CheckBox Customization
+
+Customize the appearance of the CheckBox using built‑in theme color classes or fully custom CSS.
+
+```razor
+
+
+@code {
+ private bool isPrimary = true;
+}
+
+
+```
+
+### Grouping
+
+Bind the checked state using Blazor’s `bind-Checked` for two‑way binding. When you need custom logic during updates, use the explicit pattern with `Checked` and `CheckedChanged`.
+
+```razor
+
+
+
+@for (int i = 0; i < notifItems.Count; i++)
+{
+ var idx = i;
+
+
+
+}
+
+
+
+
+ Selected: @notifSelectedCount of @notifItems.Count
+
+
+
+@code {
+ private bool? notifParentState = false;
+ private bool indeterminateWhenAllSelected = false;
+
+ private class Pick { public string Name { get; set; } = ""; public bool Selected { get; set; } }
+
+ private List notifItems = new()
+ {
+ new Pick { Name = "Product updates", Selected = true },
+ new Pick { Name = "Security alerts", Selected = true },
+ new Pick { Name = "Promotions", Selected = false },
+ new Pick { Name = "Surveys", Selected = false },
+ };
+
+ private int notifSelectedCount => notifItems.Count(i => i.Selected);
+
+ protected override void OnInitialized()
+ {
+ UpdateNotifParentState();
+ }
+
+ private void UpdateNotifParentState()
+ {
+ int total = notifItems.Count;
+ int selected = notifItems.Count(i => i.Selected);
+
+ if (selected == 0)
+ notifParentState = false;
+ else if (selected == total)
+ notifParentState = indeterminateWhenAllSelected ? null : true;
+ else
+ notifParentState = null;
+ }
+
+ private void OnNotifChildChanged()
+ {
+ UpdateNotifParentState();
+ }
+
+ private void OnNotifParentClicked(bool? valueFromUI)
+ {
+ bool target = notifItems.Any(i => !i.Selected); // if any unchecked -> check all; else uncheck all
+
+ if (valueFromUI == true) target = true;
+ else if (valueFromUI == false) target = false;
+
+ foreach (var it in notifItems)
+ it.Selected = target;
+
+ UpdateNotifParentState();
+ }
+}
+```
+
+## CheckBox Events
+
+### ValueChange Event
+
+```razor
+
+
+
+@newsletterStatus
+
+@code {
+ private bool newsletter = false;
+ private string newsletterStatus = "Not subscribed";
+
+ private void OnNewsletterChanged(CheckedChangeEventArgs args)
+ {
+ newsletter = args.Checked;
+ newsletterStatus = args.Checked ? "Subscribed to newsletter" : "Unsubscribed from newsletter";
+ }
+}
+```
+
+### Created Event
+
+```razor
+
+
+@code {
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("CheckBox created");
+ }
+}
+```
+
+## SfRadioButton Overview
+
+**SfRadioButton** allows single selection from a group. All radio buttons in a group must share the same `Name` attribute.
+
+**When to use SfRadioButton:**
+- Single selection from multiple options
+- Mutually exclusive choices
+- Gender/marital status
+- Shipping method selection
+- Survey questions
+
+### Basic Implementation
+
+```razor
+
+
+
+@code {
+ private string gender = "";
+}
+```
+
+## RadioButton Properties
+
+### Essential Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `Label` | `string` | `null` | Label text |
+| `Disabled` | `bool` | `false` | Disable radio button |
+| `LabelPosition` | `LabelPosition` | `Before` | Label placement |
+| `Name` | `string` | `""` | Groups radio buttons together |
+| `Value` | `string?` | `null` | Value associated with this radio option |
+| `CssClass` | `string` | `""` | Custom CSS classes |
+
+### Radio Button Labels and States
+
+The `Label` property provides contextual text next to the Radio Button. Use the `LabelPosition` property to place the label either `Before` or `After` the radio. Radio Buttons support common selection states including `Checked`, `Unchecked`, and `Disabled`.
+
+```razor
+
+
+
+@code {
+ private string? labelPosPick = "After";
+}
+
+```
+
+### Radio Button Color Customization
+
+Customize the appearance of Radio Buttons using built‑in theme color classes such as `e-success`, `e-info`, `e-warning`, and `e-danger`. These semantic color utilities help visually differentiate important selections or highlight specific actions. Additional styling can be applied using custom CSS targeting the Radio Button wrapper and its state indicators.
+
+```razor
+
+
+
+@code {
+ private string? colorPick = "Success";
+}
+
+
+```
+
+### Radio Button Groups
+
+```razor
+
+
Select Shipping Method:
+
+
+
+
+
+
+
+
+
+
+
Selected: @selectedShipping
+
+
+@code {
+ private string selectedShipping = "standard";
+}
+```
+
+### Disabled Radio Buttons
+
+Disabled radio buttons prevent user selection, typically used for unavailable options:
+
+```razor
+
+
Select Payment Method:
+
+
+
+
+
+
+
+
+
+
+
Selected: @selectedPayment
+
+
+@code {
+ private string selectedPayment = "credit-card";
+}
+```
+
+### Radio Buttons with Data
+
+```razor
+
+
Select Plan:
+
+ @foreach (var plan in plans)
+ {
+
+
+
+
@plan.Price/month
+
+ }
+
+
+@code {
+ private string selectedPlanId = "basic";
+
+ private List plans = new()
+ {
+ new Plan { Id = "basic", Name = "Basic Plan", Price = "$9.99" },
+ new Plan { Id = "pro", Name = "Professional", Price = "$19.99" },
+ new Plan { Id = "enterprise", Name = "Enterprise", Price = "Custom" }
+ };
+
+ private class Plan
+ {
+ public string Id { get; set; }
+ public string Name { get; set; }
+ public string Price { get; set; }
+ }
+}
+```
+
+## RadioButton Events
+
+### ValueChange Event
+
+```razor
+
+
+
+
+
+
+Selected method: @paymentMethod
+
+@code {
+ private string paymentMethod = "credit-card";
+
+ private void OnPaymentChanged(ChangeArgs args)
+ {
+ paymentMethod = args.Value;
+ Console.WriteLine($"Payment method changed to: {paymentMethod}");
+ }
+}
+
+```
+
+## SfSwitch Overview
+
+**SfSwitch** is a toggle control for binary on/off states. It provides visual feedback and supports checked/unchecked states.
+
+**When to use SfSwitch:**
+- Feature toggles (on/off)
+- Notifications (enable/disable)
+- Settings (active/inactive)
+- Dark mode
+- Two-state preferences
+
+### Basic Implementation
+
+```razor
+
+
+@code {
+ private bool darkMode = false;
+}
+```
+
+### With Label
+
+```razor
+
+ Email Notifications:
+
+
+
+@code {
+ private bool notifications = true;
+}
+```
+
+## Switch Properties
+
+### Essential Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `Checked` | `bool` | `false` | Checked state |
+| `OnLabel` | `string` | `null` | Text when switch is ON |
+| `OffLabel` | `string` | `null` | Text when switch is OFF |
+| `Disabled` | `bool` | `false` | Disable switch |
+| `CssClass` | `string` | `""` | Custom CSS classes |
+
+### Switch with Labels
+
+```razor
+
+
Feature Toggles
+
+
+ Email Notifications:
+
+
+
+
+ Push Notifications:
+
+
+
+
+ Two-Factor Authentication:
+
+
+
+
+@code {
+ private bool emailNotifications = true;
+ private bool pushNotifications = false;
+ private bool twoFactorAuth = true;
+}
+```
+
+### Disabled Switch
+
+Disabled switches prevent user interaction, typically used when a feature is unavailable based on subscription tier or other conditions:
+
+```razor
+
+
Subscription Features
+
+
+ Cloud Storage (50GB):
+
+
+
+
+ Advanced Analytics:
+
+ (Premium feature)
+
+
+
+ Priority Support:
+
+ (Enterprise only)
+
+
+
+@code {
+ private bool cloudStorage = true;
+ private bool advancedAnalytics = false;
+ private bool prioritySupport = false;
+}
+```
+
+## Switch Events
+
+### CheckedChanged Event
+
+Use `CheckedChanged` for explicit two-way binding when you need custom logic during updates:
+
+```razor
+
+ Dark Mode:
+
+
+
+@themeStatus
+
+@code {
+ private bool darkMode = false;
+ private string themeStatus = "Light mode active";
+
+ private async Task OnDarkModeChanged(bool value)
+ {
+ darkMode = value;
+ themeStatus = value ? "Dark mode enabled" : "Light mode enabled";
+ }
+}
+```
+
+### ValueChange Event
+
+```razor
+
+ Dark Mode:
+
+
+
+@themeStatus
+
+@code {
+ private bool darkMode = false;
+ private string themeStatus = "Light mode active";
+
+ private void OnDarkModeToggled(CheckedChangeEventArgs args)
+ {
+ darkMode = args.Checked;
+ themeStatus = args.Checked ? "Dark mode enabled" : "Light mode enabled";
+ }
+}
+```
+
+### Reactive Updates with Switch
+
+```razor
+
+
Settings Panel
+
+
+ Show Advanced Options:
+
+
+
+ @if (advancedMode)
+ {
+
+
Advanced Options:
+
+
+
+
+ }
+
+
+@code {
+ private bool advancedMode = false;
+
+ private void OnAdvancedModeChanged(CheckedChangeEventArgs args)
+ {
+ advancedMode = args.Checked;
+ Console.WriteLine($"Advanced mode: {advancedMode}");
+ }
+}
+```
+
+## Practical Examples
+
+### Terms and Conditions Form
+
+```razor
+@using System.ComponentModel.DataAnnotations
+
+
+
+@code {
+ private SignUpModel signUpModel = new();
+
+ private void HandleSignUp()
+ {
+ Console.WriteLine($"Sign up: {signUpModel.Email}, Newsletter: {signUpModel.NewsletterOptIn}");
+ }
+
+ private class SignUpModel
+ {
+ [Required(ErrorMessage = "Email is required")]
+ [EmailAddress(ErrorMessage = "Invalid email format")]
+ public string Email { get; set; } = "";
+ public bool AgreeTerms { get; set; }
+ public bool NewsletterOptIn { get; set; }
+ }
+}
+```
+
+### Survey with Multiple Question Types
+
+```razor
+
+
+@code {
+ private string satisfaction = "";
+ private bool[] features = new bool[3];
+ private bool wouldRecommend = false;
+
+ private void SubmitSurvey()
+ {
+ var usedFeatures = string.Join(", ",
+ new[] { "A", "B", "C" }
+ .Where((f, i) => features[i])
+ .ToArray());
+ Console.WriteLine($"Survey: Satisfaction={satisfaction}, Features={usedFeatures}, Recommend={wouldRecommend}");
+ }
+}
+```
+
+### Settings Dashboard
+
+```razor
+
+
Account Settings
+
+
+
Notifications
+
+
+ Email Notifications:
+
+
+
+
+ Push Notifications:
+
+
+
+
+ SMS Alerts:
+
+
+
+
+
+
Privacy
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Theme
+
+
+
+
+
+
+
+
+
+
+
+
+
Save Settings
+
@settingsMessage
+
+
+@code {
+ private bool emailNotifications = true;
+ private bool pushNotifications = false;
+ private bool smsAlerts = true;
+ private bool profilePublic = true;
+ private bool allowMessages = true;
+ private string theme = "light";
+ private string settingsMessage = "";
+
+ private void OnSettingChanged(CheckedChangeEventArgs args)
+ {
+ settingsMessage = "Settings updated (unsaved)";
+ }
+
+ private void OnThemeChanged(ChangeArgs args)
+ {
+ theme = args.Value;
+ settingsMessage = $"Theme changed to {theme}";
+ }
+
+ private void SaveSettings()
+ {
+ settingsMessage = "All settings saved successfully!";
+ }
+}
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/references/getting-started-inputs.md b/.github/skills/syncfusion-blazor-toolkit-inputs/references/getting-started-inputs.md
new file mode 100644
index 0000000..3182aed
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/references/getting-started-inputs.md
@@ -0,0 +1,414 @@
+# Getting Started with Syncfusion Blazor Toolkit Inputs
+
+## Table of Contents
+- [Installation & Setup](#installation--setup)
+- [CSS Imports and Theming](#css-imports-and-theming)
+- [Basic Component Initialization](#basic-component-initialization)
+- [Common Event Patterns](#common-event-patterns)
+- [State Management Basics](#state-management-basics)
+- [Namespace & Using Statements](#namespace--using-statements)
+
+## Installation & Setup
+
+### Step 1: Add NuGet Package
+
+The Syncfusion Blazor Toolkit is available via NuGet. Add it to your Blazor project:
+
+```bash
+dotnet add package Syncfusion.Blazor.Toolkit
+```
+
+**Version Compatibility:**
+- Syncfusion Blazor Toolkit: Latest stable version
+- .NET: 8.0 or higher
+- Blazor: WebAssembly or Server
+
+### Step 2: Register Services
+
+In your `Program.cs` (Blazor Server or WebAssembly), register Syncfusion services:
+
+```csharp
+// Program.cs
+using Syncfusion.Blazor;
+
+var builder = WebApplication.CreateBuilder(args);
+
+builder.Services.AddRazorComponents();
+
+// Register Syncfusion Blazor service
+builder.Services.AddSyncfusionBlazorToolkit();
+
+var app = builder.Build();
+app.Run();
+```
+
+**For Blazor Server:**
+```csharp
+services.AddSyncfusionBlazorToolkit();
+```
+
+**For Blazor WebAssembly:**
+```csharp
+builder.Services.AddSyncfusionBlazorToolkit();
+```
+
+## CSS Imports and Theming
+
+### Required CSS Files
+
+Add Syncfusion CSS files to your HTML head. In `_Layout.cshtml` (Blazor Server) or `index.html` (Blazor WebAssembly):
+
+```html
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+### Available Themes
+
+| Theme | Use Case |
+|-------|----------|
+| **fluent.css** | Modern, minimal design (default) |
+| **bootstrap5.css** | Bootstrap-compatible styling |
+| **material.css** | Material Design principles |
+| **tailwind.css** | Tailwind CSS integration |
+| **highcontrast.css** | Accessibility-focused |
+
+### Custom Theming
+
+Override Syncfusion CSS variables in your custom CSS file:
+
+```css
+/* app.css */
+:root {
+ --sf-primary: #0078d4;
+ --sf-surface: #ffffff;
+ --sf-surface-variant: #f3f3f3;
+ --sf-outline: #d0d0d0;
+ --sf-error: #d32f2f;
+}
+
+body {
+ font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
+}
+```
+
+Reference this file after the Syncfusion CSS:
+
+```html
+
+
+```
+
+## Basic Component Initialization
+
+### Minimal Component Setup
+
+Every input component requires at minimum:
+
+```razor
+@page "/basic-input"
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+
+ Text Input:
+
+
+```
+
+### Component with Value Binding
+
+```razor
+
+
+@code {
+ private string userInput = "";
+}
+```
+
+### Component with Initial Value
+
+```razor
+
+```
+
+### Component with Reference
+
+Store a component reference for programmatic access:
+
+```razor
+
+
+Focus Input
+
+@code {
+ private SfTextBox myTextBox;
+
+ private async Task FocusInput()
+ {
+ await myTextBox.FocusAsync();
+ }
+}
+```
+
+## Common Event Patterns
+
+### Change Event Handler
+
+Triggered when the component value changes:
+
+```razor
+
+
+@code {
+ private void OnTextChanged(ChangedEventArgs args)
+ {
+ Console.WriteLine($"New value: {args.Value}");
+ Console.WriteLine($"Previous value: {args.PreviousValue}");
+ }
+}
+```
+
+### Focus and Blur Events
+
+```razor
+
+
+
+@code {
+ private void OnFocus(FocusInEventArgs args)
+ {
+ Console.WriteLine("Input focused");
+ }
+
+ private void OnBlur(FocusOutEventArgs args)
+ {
+ Console.WriteLine("Input blurred");
+ }
+}
+```
+
+### Input Event (Real-time Typing)
+
+```razor
+
+
+@code {
+ private void OnInput(InputEventArgs args)
+ {
+ // Fires on every keystroke
+ Console.WriteLine($"Current input: {args.Value}");
+ }
+}
+```
+
+### Combining Multiple Events
+
+```razor
+
+
+
+@code {
+ private string text = "";
+
+ private void OnValueChanged(ChangedEventArgs args)
+ {
+ Console.WriteLine($"Value changed: {args.Value}");
+ }
+
+ private void OnFocused(FocusInEventArgs args)
+ {
+ Console.WriteLine("Focused");
+ }
+
+ private void OnBlurred(FocusOutEventArgs args)
+ {
+ Console.WriteLine("Blurred");
+ }
+}
+```
+
+## State Management Basics
+
+### Simple Component State
+
+```razor
+@page "/counter"
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+
+
+@code {
+ private int count = 0;
+}
+```
+
+### Form State Management
+
+```razor
+@page "/form"
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+
+
+@code {
+ private FormModel formData = new();
+
+ private void SubmitForm()
+ {
+ Console.WriteLine($"Name: {formData.Name}, Email: {formData.Email}, Age: {formData.Age}");
+ }
+
+ public class FormModel
+ {
+ public string Name { get; set; } = "";
+ public string Email { get; set; } = "";
+ public int? Age { get; set; }
+ }
+}
+```
+
+### Conditional State Management
+
+```razor
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+
+
+ Show Advanced Options:
+
+
+
+ @if (isEnabled)
+ {
+
+
+
+ }
+
+
+@code {
+ private bool isEnabled = false;
+ private string advancedOption = "";
+}
+```
+
+### Reactive Updates with StateHasChanged
+
+```razor
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+
+
+@code {
+ private string message = "";
+
+ private async Task OnInputChange(ChangedEventArgs args)
+ {
+ message = $"You entered: {args.Value}";
+ await Task.Delay(2000);
+ message = "";
+ StateHasChanged();
+ }
+}
+```
+
+## Namespace & Using Statements
+
+### Required Namespaces
+
+Add these using statements to your Razor components:
+
+```csharp
+// Input components
+using Syncfusion.Blazor.Toolkit.Inputs;
+```
+
+### Global Imports (_Imports.razor)
+
+Add to your `_Imports.razor` to avoid repeating using statements:
+
+```razor
+@using Syncfusion.Blazor.Toolkit
+```
+
+### Complete Setup Example
+
+```razor
+@* _Imports.razor *@
+@using System.Globalization
+@using Microsoft.AspNetCore.Components
+@using Syncfusion.Blazor.Toolkit
+
+@* Counter.razor *@
+@page "/counter"
+@using Syncfusion.Blazor.Toolkit.Inputs
+
+
+
Counter Component
+
Current value: @count
+
+
+
+
+
+1
+
-1
+
+
+@code {
+ private int count = 0;
+
+ private void Increment() => count++;
+ private void Decrement() => count--;
+}
+```
+
+## Next Steps
+
+- **Basic Inputs:** See [textbox-textarea.md](textbox-textarea.md) for TextBox and TextArea
+- **Numeric Input:** See [numeric-currency.md](numeric-currency.md) for NumericTextBox with formatting
+- **Selection Controls:** See [checkbox-radio-switch.md](checkbox-radio-switch.md) for CheckBox, RadioButton, and Switch
+- **Accessibility:** See [input-accessibility.md](input-accessibility.md) for WCAG compliance
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/references/input-accessibility.md b/.github/skills/syncfusion-blazor-toolkit-inputs/references/input-accessibility.md
new file mode 100644
index 0000000..86572b0
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/references/input-accessibility.md
@@ -0,0 +1,699 @@
+# Input Component Accessibility - WCAG Compliance Guide
+
+## Table of Contents
+- [Accessibility Overview](#accessibility-overview)
+- [Keyboard Navigation](#keyboard-navigation)
+- [ARIA Attributes](#aria-attributes)
+- [Focus Management](#focus-management)
+- [Labels and Instructions](#labels-and-instructions)
+- [Error Messaging](#error-messaging)
+- [Component-Specific Guidelines](#component-specific-guidelines)
+- [Testing Accessibility](#testing-accessibility)
+
+## Accessibility Overview
+
+Accessibility ensures that all users, including those with disabilities, can interact with input components effectively. This includes users with:
+- **Visual impairments** (blind, low vision) - screen reader users
+- **Motor impairments** - keyboard-only navigation, speech input
+- **Cognitive impairments** - clear instructions, consistent patterns
+- **Hearing impairments** - visual feedback not sound-dependent
+
+### WCAG 2.1 Level AA Compliance
+
+Syncfusion input components support WCAG 2.1 Level AA standards:
+- **Principle 1: Perceivable** - Information visible to all users
+- **Principle 2: Operable** - All functionality keyboard accessible
+- **Principle 3: Understandable** - Clear, predictable interface
+- **Principle 4: Robust** - Compatible with assistive technologies
+
+## Keyboard Navigation
+
+### Tab Order and Focus
+
+```razor
+
+
Tab Order Example
+
+ Name:
+
+
+
+ Email:
+
+
+
+
+ Submit
+
+
+@code {
+ private SfTextBox nameInput;
+
+ protected override async Task OnAfterRenderAsync(bool firstRender)
+ {
+ if (firstRender && nameInput != null)
+ {
+ // Focus first input on page load
+ await nameInput.FocusAsync();
+ }
+ }
+}
+```
+
+### Keyboard Access for All Components
+
+| Component | Keyboard Shortcuts |
+|-----------|-------------------|
+| **TextBox/TextArea** | Tab: navigate, Shift+Tab: back, Enter: submit (form) |
+| **NumericTextBox** | Arrow Up/Down: increment/decrement by step |
+| **CheckBox** | Space: toggle, Tab: navigate |
+| **RadioButton** | Arrow keys: navigate group, Space: select, Tab: next group |
+
+### Keyboard Event Handling
+
+```razor
+
+
+
+@code {
+ private string searchText = "";
+ private List searchHistory = new();
+
+ private void OnSearchKeyDown(KeyboardEventArgs args)
+ {
+ if (args.Key == "ArrowUp" && searchHistory.Count > 0)
+ {
+ // Navigate search history upward
+ searchText = searchHistory.Last();
+ }
+ else if (args.Key == "ArrowDown")
+ {
+ // Navigate search history downward
+ searchText = "";
+ }
+ else if (args.Key == "Enter")
+ {
+ // Execute search
+ searchHistory.Add(searchText);
+ }
+ }
+}
+```
+
+## ARIA Attributes
+
+### ARIA Labels and Descriptions
+
+```razor
+
+
Form with Proper ARIA
+
+ Username:
+
+
+ Must be at least 3 characters
+
+ Password:
+
+
+
+```
+
+### ARIA Live Regions
+
+```razor
+
+
Real-time Validation Feedback
+
+
+
+
+
+ @emailValidationMessage
+
+
+
+@code {
+ private string email = "";
+ private string emailValidationMessage = "";
+
+ private void OnEmailInput(InputEventArgs args)
+ {
+ // Validation happens, aria-live region updates automatically
+ if (string.IsNullOrEmpty(email))
+ {
+ emailValidationMessage = "Email is required";
+ }
+ else if (!email.Contains("@"))
+ {
+ emailValidationMessage = "Please enter a valid email";
+ }
+ else
+ {
+ emailValidationMessage = "Email format is valid";
+ }
+ }
+}
+```
+
+### ARIA for Form Groups
+
+```razor
+
+ Select Your Preferences
+
+
+
Notification Options:
+
+
+
+ Receive updates via email
+
+
+
+ Receive alerts on your device
+
+
+
+ Receive text messages
+
+
+
+@code {
+ private bool emailNotif = false;
+ private bool pushNotif = false;
+ private bool smsNotif = false;
+}
+```
+
+## Focus Management
+
+### Visible Focus Indicators
+
+```razor
+
+
+
+
+```
+
+### Programmatic Focus
+
+```razor
+@using System.ComponentModel.DataAnnotations
+
+
+
Form Validation with Focus
+
+
+
+
+
+ First Name (required):
+
+
+
+
+
+
+ Age:
+
+
+
+
+ Submit
+
+
+
+@code {
+ private SfTextBox firstNameInput;
+ private FormModel formModel = new();
+
+ private async Task HandleSubmit()
+ {
+ // Focus returns to first field if validation fails
+ if (formModel.FirstName?.Length < 2)
+ {
+ await firstNameInput.FocusAsync();
+ }
+ }
+
+ private class FormModel
+ {
+ public string FirstName { get; set; }
+ public int Age { get; set; }
+ }
+}
+```
+
+### Focus Trap for Modals
+
+```razor
+
+
Confirm Action
+
+
Are you sure you want to proceed?
+
+
+
+ Confirm
+
+
+
+ Cancel
+
+
+
+
+@code {
+ private ElementReference confirmButton;
+ private ElementReference cancelButton;
+
+ private async Task OnModalKeyDown(KeyboardEventArgs args)
+ {
+ if (args.Key == "Tab")
+ {
+ // Trap focus within modal
+ args.PreventDefault();
+ // Focus next button or wrap to first
+ }
+ }
+
+ private void OnConfirm() => Console.WriteLine("Confirmed");
+ private void OnCancel() => Console.WriteLine("Cancelled");
+}
+```
+
+## Labels and Instructions
+
+### Explicit Label Association
+
+```razor
+
+
Properly Associated Labels
+
+
+ Email Address:
+
+
+
+
+
+
+
+```
+
+### Help Text and Instructions
+
+```razor
+
+
Form with Clear Instructions
+
+
+
+```
+
+## Error Messaging
+
+### Accessible Error Messages
+
+```razor
+@using System.ComponentModel.DataAnnotations
+
+
+
Form with Error Messages
+
+
+
+
+
+
+ Submit
+
+
+
+@code {
+ private ErrorModel errorModel = new();
+
+ private void SubmitForm()
+ {
+ Console.WriteLine("Form submitted");
+ }
+
+ private class ErrorModel
+ {
+ [Required(ErrorMessage = "Email is required")]
+ [EmailAddress(ErrorMessage = "Please enter a valid email")]
+ public string Email { get; set; }
+ }
+}
+```
+
+### Real-time Validation Feedback
+
+```razor
+
+
+
+
+ @if (!string.IsNullOrEmpty(usernameError))
+ {
+
+ ❌ @usernameError
+
+ }
+ else if (usernameValid)
+ {
+
+ ✓ Username is available
+
+ }
+
+
+@code {
+ private string username = "";
+ private string usernameError = "";
+ private bool usernameValid = false;
+
+ private void OnUsernameInput(ChangeEventArgs args)
+ {
+ username = args.Value.ToString();
+
+ if (username.Length < 3)
+ {
+ usernameError = "Username must be at least 3 characters";
+ usernameValid = false;
+ }
+ else
+ {
+ usernameError = "";
+ // Check availability (mock)
+ usernameValid = !new[] { "admin", "user", "root" }.Contains(username);
+ }
+ }
+
+ private void OnUsernameBlur(FocusOutEventArgs args)
+ {
+ // Ensure error message is announced when focus leaves
+ }
+}
+```
+
+## Component-Specific Guidelines
+
+### TextBox and TextArea Accessibility
+
+```razor
+
+
+ Full Name:
+
+
+ Enter your first and last name
+
+
+
+ Biography:
+
+
+ @bio.Length / 500 characters
+
+
+
+@code {
+ private string fullName = "";
+ private string bio = "";
+}
+```
+
+### Checkbox and RadioButton Accessibility
+
+```razor
+
+ Contact Preferences
+
+
+
How often would you like to hear from us?
+
+
+
+
+
+
+
+
+
+
+
+
+ Notification Types (Select all that apply):
+
+
+
+ Get updates via email
+
+
+
+ Get alerts on your device
+
+
+
+@code {
+ private string frequency = "weekly";
+ private bool notifEmail = true;
+ private bool notifPush = false;
+}
+```
+
+### NumericTextBox Accessibility
+
+```razor
+
+ Quantity:
+
+
+ Minimum 1, Maximum 100. Use arrow keys to adjust.
+
+
+@code {
+ private int quantity = 1;
+}
+```
+
+## Testing Accessibility
+
+### Manual Testing Checklist
+
+- [ ] **Keyboard Navigation**: Tab through all inputs in logical order
+- [ ] **Focus Visibility**: All interactive elements show clear focus indicator
+- [ ] **Screen Reader**: Test with NVDA/JAWS/VoiceOver
+- [ ] **Labels**: All inputs have associated labels
+- [ ] **Error Messages**: Errors announced with aria-live
+- [ ] **Color Contrast**: Text contrast ≥ 4.5:1 for normal text, ≥ 3:1 for large text
+- [ ] **Touch Targets**: Clickable areas ≥ 44×44 pixels
+- [ ] **Zoom**: Content remains usable at 200% zoom
+
+### Automated Testing Example
+
+```csharp
+// Using AxeCore accessibility testing in Blazor
+[TestClass]
+public class AccessibilityTests
+{
+ [TestMethod]
+ public async Task TextBoxFormShouldBeAccessible()
+ {
+ // Setup component with accessibility attributes
+ var formComponent = new FormComponent();
+
+ // Run AxeCore scan
+ var results = await formComponent.RunAccessibilityAudit();
+
+ // Assert no accessibility violations
+ Assert.AreEqual(0, results.Violations.Count,
+ "Form should have no accessibility violations");
+ }
+}
+```
+
+### Screen Reader Testing Commands
+
+**NVDA (Windows):**
+```
+- Insert + F7: View element list
+- Insert + F: Find mode
+- h: Next heading
+- l: Next list
+- g: Next graphic
+```
+
+**JAWS (Windows):**
+```
+- Ins + F6: Settings
+- Ins + ; (semicolon): List of links
+- Ins + ' (apostrophe): List of headings
+- Ins + ? : Help
+```
+
+**VoiceOver (Mac/iOS):**
+```
+- Control + Option + U: Web rotor
+- Control + Option + Right Arrow: Navigate
+- Control + Option + Space: Activate
+```
+
+### Accessibility Best Practices Summary
+
+1. **Always use semantic HTML** (label, fieldset, legend)
+2. **Provide clear, descriptive labels** for all inputs
+3. **Make keyboard navigation obvious** and logical
+4. **Test with actual assistive technologies**
+5. **Use ARIA only when HTML semantics insufficient**
+6. **Provide sufficient color contrast** (≥ 4.5:1)
+7. **Don't rely on color alone** to convey information
+8. **Make error messages clear and associated** with inputs
+9. **Use aria-live for dynamic updates**
+10. **Test with real users** who use assistive technologies
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/references/numeric-currency.md b/.github/skills/syncfusion-blazor-toolkit-inputs/references/numeric-currency.md
new file mode 100644
index 0000000..f37cee7
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/references/numeric-currency.md
@@ -0,0 +1,679 @@
+# NumericTextBox Component - Numeric and Currency Formatting
+
+## Table of Contents
+- [SfNumericTextBox Overview](#sfdnumerictextbox-overview)
+- [Generic Type Implementation](#generic-type-implementation)
+- [Basic Properties](#basic-properties)
+- [Currency Formatting](#currency-formatting)
+- [Percentage Formatting](#percentage-formatting)
+- [Min/Max Constraints](#minmax-constraints)
+- [Step and Spinner](#step-and-spinner)
+- [Decimal Places](#decimal-places)
+- [Events and Validation](#events-and-validation)
+- [Practical Examples](#practical-examples)
+
+## SfNumericTextBox Overview
+
+**SfNumericTextBox** is a typed numeric input component for entering and formatting numbers. It supports currency, percentage, decimals, and custom formatting with built-in validation and spinner controls.
+
+**When to use SfNumericTextBox:**
+- Currency amounts and prices
+- Percentages and rates
+- Measurements and quantities
+- Age, ratings, or count inputs
+- Any numeric data with formatting
+
+### Basic Implementation
+
+```razor
+
+```
+
+### With Value Binding
+
+```razor
+
+
+@code {
+ private int quantity = 1;
+}
+```
+
+## Generic Type Implementation
+
+**SfNumericTextBox** requires a generic type parameter. The `TValue` can be:
+
+| Type | Use Case | Example |
+|------|----------|---------|
+| `int` | Whole numbers | Product quantities |
+| `long` | Large whole numbers | Big amounts |
+| `float` | Single-precision decimals | Measurements |
+| `double` | Double-precision decimals | Scientific values |
+| `decimal` | Currency precision | Money amounts |
+| `int?` | Nullable integer | Optional counts |
+| `decimal?` | Nullable decimal | Optional prices |
+
+### Type-Specific Examples
+
+```razor
+@* Whole number *@
+
+
+@* Decimal for currency *@
+
+
+@* Nullable for optional input *@
+
+
+@* Double for precision *@
+
+```
+
+## Basic Properties
+
+### Essential Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `Value` | `T` | `default(T)` | Current numeric value |
+| `Min` | `T` | Varies by type | Minimum allowed value |
+| `Max` | `T` | Varies by type | Maximum allowed value |
+| `Step` | `T` | Varies by type | Increment/decrement step |
+| `Disabled` | `bool` | `false` | Disable input |
+| `Readonly` | `bool` | `false` | Prevent modification |
+| `Placeholder` | `string` | `null` | Placeholder text |
+| `Format` | `string` | `"n2"` | Number format string |
+
+### Display Properties
+
+| Property | Type | Description |
+|----------|------|-------------|
+| `ShowSpinButton` | `bool` | Show +/- spinner buttons |
+| `ShowClearButton` | `bool` | Show clear button |
+| `Decimals` | `int?` | Number of decimal places to display |
+| `FloatLabelType` | `FloatLabelType` | Floating label behavior |
+
+### Currency and Validation Properties
+
+| Property | Type | Description |
+|----------|------|-------------|
+| `Currency` | `string?` | ISO 4217 currency code (e.g., "USD", "EUR") |
+| `ValidateDecimalOnType` | `bool` | Validate decimals during typing |
+| `StrictMode` | `bool` | Restrict values between Min/Max (default: true) |
+| `AllowMouseWheel` | `bool` | Enable mouse wheel increment/decrement |
+
+## Currency Formatting
+
+### Basic Currency Format
+
+```razor
+
+ Price (USD):
+
+
+
+```
+
+**Format String Reference:**
+- `C` or `C2` - Currency with 2 decimals ($29.99)
+- `C0` - Currency with no decimals ($30)
+- `C3` - Currency with 3 decimals ($29.990)
+
+### Currency with Value Binding
+
+```razor
+
+
+@code {
+ private decimal productPrice = 29.99m;
+ private int quantity = 1;
+}
+```
+
+### Multiple Currency Formats
+
+```razor
+
+
Currency Formatting
+
+
+ USD (C2):
+
+
+
+
+ Percentage (P):
+
+
+
+
+ Number (N):
+
+
+
+
+ Fixed decimals (F3):
+
+
+
+```
+
+## Percentage Formatting
+
+### Percentage Input
+
+```razor
+
+ Discount Rate:
+
+
+
+```
+
+**Note:** Percentage format expects decimal values (0.15 = 15%)
+
+### Tax Calculator with Percentages
+
+```razor
+
+
Tax Calculator
+
+
+ Subtotal:
+
+
+
+
+
+ Tax Rate (%):
+
+
+
+
+
+ Tax Amount:
+
+
+
+
+
+ Total: @($"{(subtotal + subtotal * taxRate):C2}")
+
+
+
+@code {
+ private decimal subtotal = 100m;
+ private decimal taxRate = 0.08m;
+}
+```
+
+## Min/Max Constraints
+
+### Setting Boundaries
+
+```razor
+
+ Age (18-120):
+
+
+
+
+@code {
+ private int age = 25;
+}
+```
+
+### Dynamic Min/Max
+
+```razor
+
+
+@code {
+ private int minValue = 10;
+ private int maxValue = 100;
+}
+```
+
+## Step and Spinner
+
+### Spinner Buttons
+
+The spinner buttons allow increment/decrement by the step value:
+
+```razor
+
+ Quantity:
+
+
+
+
+@code {
+ private int quantity = 1;
+}
+```
+
+### Custom Step Values
+
+```razor
+
+
Different Step Values
+
+
+ By 1:
+
+
+
+
+ By 5:
+
+
+
+
+ By 0.01 (decimal):
+
+
+
+
+ By 10% (percentage):
+
+
+
+```
+
+## Decimal Places
+
+### Decimals Property
+
+Forces a fixed number of decimal places:
+
+```razor
+
+
Decimal Places
+
+
+ 2 Decimal Places (Currency):
+
+
+
+
+
+ 4 Decimal Places (Scientific):
+
+
+
+
+
+ 0 Decimal Places (Whole):
+
+
+
+
+```
+
+## Events and Validation
+
+### ValueChange Event
+
+```razor
+
+
+
+@code {
+ private int myNumber = 0;
+
+ private void OnValueChanged(ChangeEventArgs args)
+ {
+ Console.WriteLine($"Old value: {args.PreviousValue}");
+ Console.WriteLine($"New value: {args.Value}");
+ }
+}
+```
+
+### OnInput Event
+
+Real-time event fired on every value change during typing:
+
+```razor
+
+
+
+@code {
+ private int myNumber = 0;
+
+ private void OnInput(ChangeEventArgs args)
+ {
+ Console.WriteLine($"Input: {args.Value}");
+ }
+}
+```
+
+### Created Event
+
+```razor
+
+
+@code {
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("NumericTextBox created");
+ }
+}
+```
+
+### Destroyed Event
+
+```razor
+
+
+@code {
+ private void OnDestroyed(object args)
+ {
+ Console.WriteLine("NumericTextBox destroyed");
+ }
+}
+```
+
+### Focus and Blur Events
+
+```razor
+
+
+@validationMessage
+
+@code {
+ private decimal price = 0m;
+ private string validationMessage = "";
+
+ private void OnFocus(NumericFocusEventArgs args)
+ {
+ validationMessage = "Enter a valid price";
+ }
+
+ private void OnBlur(NumericBlurEventArgs args)
+ {
+ if (price <= 0)
+ {
+ validationMessage = "❌ Price must be greater than 0";
+ }
+ else
+ {
+ validationMessage = "✓ Valid price";
+ }
+ }
+}
+```
+
+### Form Validation with DataAnnotations
+
+```razor
+@using System.ComponentModel.DataAnnotations
+
+
+
+
+
+ Product Name:
+
+
+
+
+
+ Price:
+
+
+
+
+
+ Save Product
+
+
+@code {
+ private ProductModel product = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Product: {product.Name}, Price: {product.Price}");
+ }
+
+ public class ProductModel
+ {
+ [Required(ErrorMessage = "Product name is required")]
+ public string Name { get; set; } = "";
+
+ [Required(ErrorMessage = "Price is required")]
+ [Range(0.01, 999999.99, ErrorMessage = "Price must be between 0.01 and 999999.99")]
+ public decimal Price { get; set; }
+ }
+}
+```
+
+## Practical Examples
+
+### Shopping Cart Price Calculator
+
+```razor
+
+
+@code {
+ private List cartItems = new()
+ {
+ new CartItem { Name = "Item 1", UnitPrice = 29.99m, Quantity = 1 },
+ new CartItem { Name = "Item 2", UnitPrice = 49.99m, Quantity = 2 },
+ };
+
+ private decimal subtotal = 0m;
+ private decimal tax = 0m;
+ private decimal total = 0m;
+
+ private void RecalculateTotal(ChangeEventArgs args)
+ {
+ subtotal = cartItems.Sum(x => x.UnitPrice * x.Quantity);
+ tax = subtotal * 0.08m;
+ total = subtotal + tax;
+ }
+
+ private void OnQuantityChanged(ChangeEventArgs args)
+ {
+ subtotal = cartItems.Sum(x => x.UnitPrice * x.Quantity);
+ tax = subtotal * 0.08m;
+ total = subtotal + tax;
+ }
+
+ public class CartItem
+ {
+ public string Name { get; set; }
+ public decimal UnitPrice { get; set; }
+ public int Quantity { get; set; }
+ }
+}
+```
+
+### Rating with Score
+
+```razor
+
+
+@code {
+ private decimal rating = 3m;
+}
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/references/textbox-textarea.md b/.github/skills/syncfusion-blazor-toolkit-inputs/references/textbox-textarea.md
new file mode 100644
index 0000000..67cf436
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/references/textbox-textarea.md
@@ -0,0 +1,799 @@
+# TextBox and TextArea Components
+
+## Table of Contents
+- [SfTextBox Overview](#sftextbox-overview)
+- [SfTextBox Properties](#sftextbox-properties)
+- [SfTextBox Events](#sftextbox-events)
+- [Floating Labels](#floating-labels)
+- [Placeholders and Hints](#placeholders-and-hints)
+- [Focus and Blur Handling](#focus-and-blur-handling)
+- [Input Validation](#input-validation)
+- [SfTextArea Component](#sftextarea-component)
+- [Practical Examples](#practical-examples)
+
+## SfTextBox Overview
+
+**SfTextBox** is the fundamental single-line text input component. It provides a styled alternative to standard HTML input elements with additional features like floating labels, custom styling, and event handling.
+
+**When to use SfTextBox:**
+- General text input (names, usernames, search queries)
+- Email, URL, or password fields
+- Search/filter inputs
+- Labels with floating animation
+- Custom styling and themes
+
+### Basic Implementation
+
+```razor
+
+```
+
+### With Value Binding
+
+```razor
+
+
+@code {
+ private string myText = "";
+}
+```
+
+## SfTextBox Properties
+
+### Essential Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `Value` | `string` | `""` | Current text value |
+| `Placeholder` | `string` | `""` | Placeholder text when empty |
+| `Type` | `InputType` | `Text` | Input type (Text, Email, Password, URL, Number) |
+| `Autocomplete` | `AutoComplete` | `On` | Browser autocomplete behavior (On, Off) |
+| `Disabled` | `bool` | `false` | Disable user input |
+| `ReadOnly` | `bool` | `false` | Prevent modification |
+| `CssClass` | `string` | `""` | Custom CSS classes |
+| `Multiline` | `bool` | `false` | Allow multiple lines (for multi-line text) |
+
+### Appearance Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `FloatLabelType` | `FloatLabelType` | `Never` | Floating label mode (Never, Always, Auto) |
+| `ShowClearButton` | `bool` | `false` | Display clear/reset button |
+| `Width` | `string?` | `null` (100%) | Width of the TextBox component |
+| `TabIndex` | `int` | `0` | Tab order of the TextBox |
+| `HtmlAttributes` | `Dictionary?` | `null` | Additional HTML attributes for wrapper element |
+| `InputAttributes` | `Dictionary` | `{}` | Additional HTML attributes for input element |
+| `CssClass` | `string` | `""` | Custom CSS classes |
+
+### Input Type Examples
+
+```razor
+@* Regular text input *@
+
+
+@* Email validation *@
+
+
+@* Password field *@
+
+
+@* URL input *@
+
+
+@* Phone number *@
+
+```
+
+### Autocomplete Property
+
+The `Autocomplete` property controls the browser's built-in autocomplete suggestions:
+
+```razor
+@* Autocomplete enabled (default) *@
+
+
+@* Autocomplete disabled - suitable for sensitive fields *@
+
+```
+
+### SfTextBox Variants
+The TextBox component offers two visual variants: `Filled`, and `Outlined`
+
+```razor
+
+
+```
+
+### TextBox with Disabled State
+
+```razor
+
+
+
+@code {
+ private string disabledValue = "Cannot be modified";
+}
+```
+
+### TextBox with ReadOnly State
+
+```razor
+
+
+
+@code {
+ private string readonlyValue = "View only - cannot edit";
+}
+```
+
+### Multi-line TextBox
+
+Use the `Multiline` property for multi-line text input (textarea behavior):
+
+```razor
+
+
+@code {
+ private string notes = "";
+}
+```
+
+## SfTextBox Events
+
+### ValueChange Event
+
+Fired when the text value changes:
+
+```razor
+
+
+@code {
+ private void OnTextChanged(ChangedEventArgs args)
+ {
+ Console.WriteLine($"New value: {args.Value}");
+ Console.WriteLine($"Previous value: {args.PreviousValue}");
+ }
+}
+```
+
+### Input Event
+
+Real-time event firing on every keystroke:
+
+```razor
+
+
+@code {
+ private void OnInputChange(InputEventArgs args)
+ {
+ Console.WriteLine($"Character count: {args.Value?.Length}");
+ }
+}
+```
+
+### Focus and Blur Events
+
+```razor
+
+
+
+@code {
+ private void OnFocus(FocusInEventArgs args)
+ {
+ Console.WriteLine("TextBox focused");
+ }
+
+ private void OnBlur(FocusOutEventArgs args)
+ {
+ Console.WriteLine("TextBox blurred, value: " + args.Value);
+ }
+}
+```
+
+## Floating Labels
+
+Floating labels improve UX by providing context when users interact with inputs. The label animates up when focused or filled.
+
+### FloatLabelType Options
+
+| Option | Behavior |
+|--------|----------|
+| `Never` | Label fixed at placeholder position |
+| `Always` | Label always floats above input |
+| `Auto` | Label floats when focused or has value |
+
+### Implementation
+
+```razor
+
+
+
+
+
+
+
+
+
+
+@code {
+ private string email = "";
+ private string password = "";
+}
+```
+
+## Placeholders and Hints
+
+### Basic Placeholder
+
+```razor
+
+```
+
+### Placeholder with Helper Text
+
+```razor
+
+
+ We'll never share your email
+
+```
+
+### Using ClearButton
+
+```razor
+
+
+
+@code {
+ private string searchText = "";
+
+ private void OnSearchChanged(ChangedEventArgs args)
+ {
+ Console.WriteLine($"Searching for: {args.Value}");
+ }
+}
+```
+
+## Focus and Blur Handling
+
+### Focus Management
+
+```razor
+
+
+Focus Input
+Blur Input
+
+@code {
+ private SfTextBox textboxRef;
+
+ private async Task FocusInput()
+ {
+ await textboxRef.FocusAsync(); // Focus programmatically
+ }
+
+ private async Task BlurInput()
+ {
+ await textboxRef.FocusOutAsync(); // Blur programmatically
+ }
+}
+```
+
+### Focus Event with Validation
+
+```razor
+
+
+
+@validationMessage
+
+@code {
+ private string username = "";
+ private string validationMessage = "";
+
+ private void OnInputFocused(FocusInEventArgs args)
+ {
+ validationMessage = "Username must be 3-20 characters";
+ }
+
+ private void OnInputBlurred(FocusOutEventArgs args)
+ {
+ if (username.Length < 3)
+ {
+ validationMessage = "❌ Username too short";
+ }
+ else if (username.Length > 20)
+ {
+ validationMessage = "❌ Username too long";
+ }
+ else
+ {
+ validationMessage = "✓ Username valid";
+ }
+ }
+}
+```
+
+## Input Validation
+
+### Basic Validation
+
+```razor
+@using System.ComponentModel.DataAnnotations
+
+
+
+
+
+ Email:
+
+
+
+
+
+ Submit
+
+
+@code {
+ private LoginModel model = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Email: {model.Email}");
+ }
+
+ public class LoginModel
+ {
+ [Required(ErrorMessage = "Email is required")]
+ [EmailAddress(ErrorMessage = "Invalid email format")]
+ public string Email { get; set; } = "";
+ }
+}
+```
+
+### Custom Validation
+
+```razor
+
+
+
+@usernameError
+
+@code {
+ private string username = "";
+ private string usernameError = "";
+
+ private void ValidateUsername(FocusOutEventArgs args)
+ {
+ if (username.Length < 3)
+ {
+ usernameError = "Username too short (min 3 characters)";
+ }
+ else if (username.Length > 20)
+ {
+ usernameError = "Username too long (max 20 characters)";
+ }
+ else
+ {
+ usernameError = "";
+ }
+ }
+}
+```
+
+### Real-time Character Count
+
+```razor
+
+
+@code {
+ private string comment = "";
+ private Dictionary MaxLengthAttrs => new() { { "maxlength", "200" } };
+
+ private void OnCommentInput(InputEventArgs args)
+ {
+ // Character count updates in real-time
+ Console.WriteLine($"Remaining: {200 - comment.Length}");
+ }
+}
+```
+
+## SfTextArea Component
+
+**SfTextArea** is for multi-line text input. It's ideal for comments, descriptions, feedback, and long-form content.
+
+### Basic TextArea
+
+The `RowCount` property defines the initial number of visible text lines in the TextArea and `ColumnCount` property specifies the TextArea's initial width in terms of the approximate number of characters per line,
+
+```razor
+
+
+```
+
+### TextArea with Value Binding
+
+```razor
+
+
+
+Characters entered: @feedback.Length
+
+@code {
+ private string feedback = "";
+}
+```
+
+### TextArea Properties
+
+| Property | Type | Description |
+|----------|------|-------------|
+| `Placeholder` | `string` | Placeholder text |
+| `Width` | `string?` | Width of the TextArea component |
+| `RowCount` | `int` | Number of visible rows |
+| `ColumnCount` | `int` | Number of visible columns |
+| `MaxLength` | `int` | Maximum character length (-1 for unlimited) |
+| `ResizeMode` | `Resize` | Resizing direction (Both, Horizontal, Vertical, None) |
+| `Disabled` | `bool` | Disable input |
+| `ReadOnly` | `bool` | Read-only mode |
+| `TabIndex` | `int` | Tab order of the TextArea |
+| `HtmlAttributes` | `Dictionary?` | Additional HTML attributes for wrapper element |
+| `InputAttributes` | `Dictionary` | Additional HTML attributes for input element |
+
+### Appearance Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `FloatLabelType` | `FloatLabelType` | `Never` | Floating label mode (Never, Always, Auto) |
+
+### TextArea with Resizing
+
+The TextArea component offers flexible resizing options through the ResizeMode property, including `Both`, `Horizontal`, `Vertical`, and `None`. This option enables the TextArea to be resized in any direction.
+
+```razor
+
+```
+
+### TextArea with Disabled State
+
+```razor
+
+
+
+@code {
+ private string disabledFeedback = "This cannot be modified";
+}
+```
+
+### TextArea with ReadOnly State
+
+```razor
+
+
+@code {
+ private string termsText = "Terms and conditions: Lorem ipsum dolor sit amet, consectetur adipiscing elit...";
+}
+```
+
+### TextArea with Variants
+
+The TextArea component offers two visual variants — `Filled`, and `Outlined`
+
+```razor
+
+
+```
+
+### TextArea with Float Label
+
+The floating label functionality supports three modes: `Never`, `Auto`, and `Always`.
+
+```razor
+
+
+```
+
+### TextArea with MaxLength
+
+Use the `MaxLength` property to enforce a maximum character limit in the TextArea.
+
+```razor
+
+```
+
+### TextArea Events
+
+The TextArea component supports the following events: `Created`, `OnInput`, `ValueChange`, `OnFocus`, and `OnBlur`.
+
+#### Created Event
+
+Fired when the TextArea component is initialized:
+
+```razor
+
+
+@code {
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("TextArea component created");
+ }
+}
+```
+
+#### OnInput Event
+
+Real-time event firing on every keystroke:
+
+```razor
+
+
+@code {
+ private void OnTextInput(TextAreaInputEventArgs args)
+ {
+ Console.WriteLine($"Input value: {args.Value}");
+ Console.WriteLine($"Character count: {args.Value?.Length ?? 0}");
+ }
+}
+```
+
+#### ValueChange Event
+
+Fired when the text value changes:
+
+```razor
+
+
+@code {
+ private void OnValueChanged(TextAreaValueChangeEventArgs args)
+ {
+ Console.WriteLine($"New value: {args.Value}");
+ Console.WriteLine($"Previous value: {args.PreviousValue}");
+ }
+}
+```
+
+#### OnFocus Event
+
+Fired when the TextArea receives focus:
+
+```razor
+
+
+@code {
+ private void OnFocus(TextAreaFocusInEventArgs args)
+ {
+ Console.WriteLine("TextArea focused");
+ Console.WriteLine($"Event source: {args.Event}");
+ }
+}
+```
+
+#### OnBlur Event
+
+Fired when the TextArea loses focus:
+
+```razor
+
+
+@code {
+ private void OnBlur(TextAreaFocusOutEventArgs args)
+ {
+ Console.WriteLine("TextArea blurred");
+ Console.WriteLine($"Current value: {args.Value}");
+ }
+}
+```
+
+#### Complete TextArea Events Example
+
+```razor
+
+
+
+
Event: "@_eventMessage"
+
+@code {
+ private string _eventMessage = string.Empty;
+
+ private void CreatedHandler(object args)
+ {
+ _eventMessage = "Created event triggered";
+ }
+
+ private void InputHandler(TextAreaInputEventArgs args)
+ {
+ _eventMessage = "Input event triggered";
+ }
+
+ private void ChangeHandler(TextAreaValueChangeEventArgs args)
+ {
+ _eventMessage = "Changed event triggered";
+ }
+
+ private void BlurHandler(TextAreaFocusOutEventArgs args)
+ {
+ _eventMessage = "FocusOut event triggered";
+ }
+
+ private void FocusHandler(TextAreaFocusInEventArgs args)
+ {
+ _eventMessage = "FocusIn event triggered";
+ }
+}
+```
+
+## Practical Examples
+
+### Login Form
+
+```razor
+
+
+@code {
+ private string username = "";
+ private string password = "";
+
+ private void HandleLogin()
+ {
+ Console.WriteLine($"Login: {username}");
+ }
+}
+```
+
+### Comment Form
+
+```razor
+
+
+@code {
+ private CommentModel commentData = new();
+ private Dictionary NameAttrs => new() { { "maxlength", "100" } };
+ private Dictionary EmailAttrs => new() { { "maxlength", "100" } };
+
+ private void SubmitComment()
+ {
+ Console.WriteLine($"Comment from {commentData.Name}: {commentData.Comment}");
+ }
+
+ public class CommentModel
+ {
+ public string Name { get; set; } = "";
+ public string Email { get; set; } = "";
+ public string Comment { get; set; } = "";
+ }
+}
+```
+
+### Search Bar
+
+```razor
+
+
+
+
+ @if (!string.IsNullOrEmpty(searchQuery))
+ {
+
+
Searching for: @searchQuery
+
+ }
+
+
+@code {
+ private string searchQuery = "";
+
+ private async Task OnSearchInput(InputEventArgs args)
+ {
+ searchQuery = args.Value ?? "";
+ // Perform search operation
+ await PerformSearch(searchQuery);
+ }
+
+ private async Task PerformSearch(string query)
+ {
+ // Search logic here
+ Console.WriteLine($"Searching for: {query}");
+ }
+}
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-inputs/references/uploader.md b/.github/skills/syncfusion-blazor-toolkit-inputs/references/uploader.md
new file mode 100644
index 0000000..8b1d3c6
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-inputs/references/uploader.md
@@ -0,0 +1,833 @@
+# Uploader Component - File Upload and Management
+
+## Table of Contents
+- [SfUploader Overview](#sfuploader-overview)
+- [Basic File Upload](#basic-file-upload)
+- [Preloaded Files](#preloaded-files)
+- [Auto Upload Configuration](#auto-upload-configuration)
+- [File Validation](#file-validation)
+- [Directory and Sequential Upload](#directory-and-sequential-upload)
+- [Drag and Drop](#drag-and-drop)
+- [UI Customization](#ui-customization)
+- [Uploader Templates](#uploader-templates)
+- [Upload Events](#upload-events)
+- [Progress and Cancellation](#progress-and-cancellation)
+- [Error Handling](#error-handling)
+- [Practical Examples](#practical-examples)
+
+## SfUploader Overview
+
+**SfUploader** provides a complete file upload solution with validation, progress tracking, and async upload capabilities. It supports single/multiple files, drag-and-drop, and extensive customization.
+
+**When to use SfUploader:**
+- Document upload
+- Image upload
+- Bulk file handling
+- File management interfaces
+- Profile picture upload
+
+### Uploader Properties
+
+| Property | Type | Default | Description |
+|----------|------|---------|-------------|
+| `ID` | `string` | `""` | Unique identifier for the component |
+| `AutoUpload` | `bool` | `true` | Upload files immediately after selection |
+| `AllowMultiple` | `bool` | `true` | Allow multiple file selection |
+| `AllowedExtensions` | `string` | `""` | File extensions to allow (e.g., ".jpg,.png,.pdf") |
+| `MaxFileSize` | `double` | `30000000` | Maximum file size in bytes |
+| `MinFileSize` | `double` | `0` | Minimum file size in bytes |
+| `DirectoryUpload` | `bool` | `false` | Enable folder upload |
+| `SequentialUpload` | `bool` | `false` | Upload files sequentially |
+| `DropArea` | `string?` | `null` | Custom drop target element selector |
+| `DropEffect` | `DropEffect` | `Default` | Drag-drop effect (Copy, Move, Link, None) |
+| `CssClass` | `string` | `""` | Custom CSS classes |
+| `Disabled` | `bool` | `false` | Disable the uploader |
+| `ShowFileList` | `bool` | `true` | Display file list |
+| `ShowProgressBar` | `bool` | `true` | Show progress bar during upload |
+| `EnableHtmlSanitizer` | `bool` | `true` | Sanitize filenames for XSS |
+| `EnablePersistence` | `bool` | `false` | Persist upload state across page reloads |
+| `TabIndex` | `int` | `0` | Tab order |
+| `HttpClientInstance` | `HttpClient` | `new()` | Custom HttpClient for upload requests |
+
+### Basic Implementation
+
+```razor
+
+```
+
+### With Upload URL
+
+```razor
+
+
+
+```
+
+## Basic File Upload
+
+### Single File Upload
+
+```razor
+
+
Upload Single File
+
+
+
+```
+
+### Multiple File Upload
+
+```razor
+
+
Upload Multiple Files
+
+
+
+```
+
+## Preloaded Files
+
+### Display Preloaded Files
+
+The FileUpload component supports displaying a list of files that are already available on the server as `UploadedFile`. This is useful for editing scenarios where users need to see and potentially remove existing files before uploading new ones.
+
+```razor
+
+
+
+
+
+
+
+```
+
+## Auto Upload Configuration
+
+### Enable Auto Upload
+
+```razor
+
+
+
+```
+
+### Async Upload Settings
+
+```razor
+
+
+
+```
+
+## File Validation
+
+### Allowed Extensions
+
+```razor
+
+
File Type Validation
+
+
+ Images only:
+
+
+
+
+
+ Documents only:
+
+
+
+
+
+ All common formats:
+
+
+
+
+```
+
+### File Size Validation
+
+```razor
+
+
File Size Validation
+
+
+ Max 5 MB:
+
+
+
+
+
+ Max 50 MB:
+
+
+
+
+```
+
+### Minimum File Size
+
+```razor
+
+
+```
+
+## Directory and Sequential Upload
+
+### Directory Upload
+
+Enable directory upload to allow uploading entire folders:
+
+```razor
+
+
+```
+
+### Sequential Upload
+
+Upload files one at a time in sequence when multiple files are selected:
+
+```razor
+
+
+```
+
+When `SequentialUpload` is set to `true`, files are uploaded one after another instead of simultaneously. This is useful for servers with limited bandwidth or when you want to track individual file upload progress more precisely.
+
+## Drag and Drop
+
+### Default Drop Effect
+
+```razor
+
+```
+
+### Custom Drop Area
+
+Specify a custom drop target element:
+
+```razor
+
+
+
Drag and drop files here
+
+
+
+```
+
+## UI Customization
+
+### Custom CSS Classes
+
+Apply custom styling to the uploader:
+
+```razor
+
+
+```
+
+### Disabled State
+
+Disable the uploader to prevent uploads:
+
+```razor
+
+
+
+
+
+```
+
+### Show/Hide File List
+
+Control whether the file list is displayed:
+
+```razor
+
+
With File List (default):
+
+
+ Without File List:
+
+
+```
+
+### Show/Hide Progress Bar
+
+Control whether the progress bar is displayed:
+
+```razor
+
+
With Progress Bar:
+
+
+ Without Progress Bar:
+
+
+```
+
+## Uploader Templates
+
+### File List Template
+
+The File Upload component allows for the customization of the file list items by using a template:
+
+```razor
+
+
+
+
+
+
File Name : @context.Name
+
File Size : @context.Size
+
File Status : @context.Status
+
+
+
+
+```
+
+## Upload Events
+
+### OnValueChange Event
+
+Fired when files are selected:
+
+```razor
+
+
+
+@code {
+ private void OnFilesChanged(UploadChangeEventArgs args)
+ {
+ Console.WriteLine($"Files changed:");
+ foreach (var file in args.Files)
+ {
+ Console.WriteLine($" - {file.FileInfo.Name} ({file.FileInfo.Size} bytes)");
+ }
+ }
+}
+```
+
+### Uploading Event
+
+Fired before uploading starts:
+
+```razor
+
+
+
+
+@code {
+ private void OnUploading(UploadingEventArgs args)
+ {
+ Console.WriteLine($"Uploading {args.FileData.Name}");
+ }
+}
+```
+
+### Success Event
+
+Fired when upload completes successfully:
+
+```razor
+
+
+
+
+@code {
+ private void OnUploadSuccess(SuccessEventArgs args)
+ {
+ Console.WriteLine($"Upload successful: {args.File.Name}");
+ }
+}
+```
+
+### Failure Event
+
+Fired when upload fails:
+
+```razor
+
+
+
+
+@errorMessage
+
+@code {
+ private string errorMessage = "";
+
+ private void OnUploadFailure(FailureEventArgs args)
+ {
+ errorMessage = $"Upload failed: {args.File.Name}";
+ Console.WriteLine(errorMessage);
+ }
+}
+```
+
+## Progress and Cancellation
+
+### Progress Tracking
+
+```razor
+
+
+
+
+
+
+
Uploaded: @uploadedPercent%
+
+
+
+
+@code {
+ private SfUploader uploader = new();
+ private int uploadedPercent = 0;
+
+ private void OnUploadProgress(Syncfusion.Blazor.Toolkit.Inputs.ProgressEventArgs args)
+ {
+ if (args.Total > 0)
+ {
+ uploadedPercent = (int)((args.Loaded / args.Total) * 100);
+ }
+ Console.WriteLine($"Progress: {uploadedPercent}%");
+ }
+}
+```
+
+### Pause and Resume
+
+```razor
+
+
+
+
+
+ Pause
+ Resume
+ Cancel
+
+
+@code {
+ private SfUploader uploader = new();
+
+ private void OnPaused(PauseResumeEventArgs args)
+ {
+ Console.WriteLine($"Upload paused: {args.File.Name}");
+ }
+
+ private void OnResumed(PauseResumeEventArgs args)
+ {
+ Console.WriteLine($"Upload resumed: {args.File.Name}");
+ }
+
+ private async Task PauseUpload()
+ {
+ await uploader.PauseAsync();
+ }
+
+ private async Task ResumeUpload()
+ {
+ await uploader.ResumeAsync();
+ }
+
+ private async Task CancelUpload()
+ {
+ await uploader.CancelAsync();
+ }
+}
+```
+
+### OnChunkUploadStart Event
+
+Fired when each chunk upload starts (requires ChunkSize to be set):
+
+```razor
+
+
+
+
+@code {
+ private void OnChunkStart(UploadingEventArgs args)
+ {
+ Console.WriteLine($"Chunk upload started for: {args.FileData.Name}");
+ // Pass custom data with chunk
+ // args.CustomFormData = new List { new { Authorization = "token" } };
+ }
+}
+```
+
+### OnChunkSuccess Event
+
+Fired when each chunk uploads successfully:
+
+```razor
+
+
+
+
+@code {
+ private void OnChunkSuccess(SuccessEventArgs args)
+ {
+ Console.WriteLine($"Chunk uploaded successfully: {args.File.Name}");
+ }
+}
+```
+
+### OnChunkFailure Event
+
+Fired when a chunk upload fails:
+
+```razor
+
+
+
+
+@code {
+ private void OnChunkFailure(FailureEventArgs args)
+ {
+ Console.WriteLine($"Chunk upload failed: {args.File.Name}");
+ }
+}
+```
+
+### OnActionComplete Event
+
+Fired when all upload/remove operations complete:
+
+```razor
+
+
+
+
+@code {
+ private void OnComplete(ActionCompleteEventArgs args)
+ {
+ foreach (var file in args.FileData)
+ {
+ Console.WriteLine($"File completed: {file.Name} - Status: {file.Status}");
+ }
+ }
+}
+```
+
+### Created Event
+
+Fired when the uploader component is created:
+
+```razor
+
+
+
+
+@code {
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("Uploader created");
+ }
+}
+```
+
+### OnClear Event
+
+Fired before clearing all files from the list:
+
+```razor
+
+
+
+
+@code {
+ private void OnClear(ClearingEventArgs args)
+ {
+ Console.WriteLine($"Clearing {args.FilesData.Count} files");
+ }
+}
+```
+
+## Error Handling
+
+### Validation Error Handling
+
+Use the `FileSelected` event to validate files when they are selected. Set `args.Cancel = true` to reject invalid files:
+
+```razor
+
+
+
+
+ @if (!string.IsNullOrEmpty(validationError))
+ {
+
@validationError
+ }
+
+
+@code {
+ private string validationError = "";
+
+ private void OnFileSelected(SelectedEventArgs args)
+ {
+ validationError = "";
+
+ foreach (var file in args.FilesData)
+ {
+ // Check file size
+ if (file.Size > 5242880)
+ {
+ validationError = $"File {file.Name} exceeds 5MB limit";
+ args.Cancel = true;
+ return;
+ }
+
+ // Check extension
+ var validExtensions = new[] { ".jpg", ".png", ".pdf" };
+ var extension = System.IO.Path.GetExtension(file.Name);
+ if (!validExtensions.Contains(extension.ToLower()))
+ {
+ validationError = $"File type {extension} not allowed";
+ args.Cancel = true;
+ return;
+ }
+ }
+ }
+}
+```
+
+### Server-Side Error Handling
+
+```razor
+
+
+
+
+
+
Status: @statusMessage
+
@errorMessage
+
+
+@code {
+ private string statusMessage = "";
+ private string errorMessage = "";
+
+ private void OnUploadFailure(FailureEventArgs args)
+ {
+ statusMessage = "Upload failed";
+ errorMessage = $"Error uploading {args.File?.Name}: {args.StatusText}";
+ Console.WriteLine(errorMessage);
+ }
+}
+```
+
+## Practical Examples
+
+### Profile Picture Upload
+
+```razor
+
+
Upload Profile Picture
+
+
+ @if (!string.IsNullOrEmpty(profilePictureUrl))
+ {
+
+ }
+ else
+ {
+
No image uploaded
+ }
+
+
+
+
+
+
+
+@code {
+ private string profilePictureUrl = "";
+
+ private void OnProfilePictureUploaded(SuccessEventArgs args)
+ {
+ profilePictureUrl = $"/uploads/profile/{args.File.Name}";
+ Console.WriteLine($"Profile picture uploaded: {profilePictureUrl}");
+ }
+}
+```
+
+### Bulk Image Upload with Preview
+
+```razor
+
+
Bulk Image Upload
+
+
+
+
+
+
+
Uploaded Images:
+
+ @foreach (var image in uploadedImages)
+ {
+
+
+
@image.Name
+
+ }
+
+
+
+
+@code {
+ private List uploadedImages = new();
+
+ private void OnImageUploaded(SuccessEventArgs args)
+ {
+ uploadedImages.Add(new ImageInfo
+ {
+ Name = args.File.Name,
+ Url = $"/uploads/images/{args.File.Name}"
+ });
+ }
+
+ public class ImageInfo
+ {
+ public string Name { get; set; }
+ public string Url { get; set; }
+ }
+}
+```
+
+### Form with File Upload
+
+```razor
+
+
+@code {
+ private SupportModel supportModel = new();
+
+ private void HandleSubmit()
+ {
+ Console.WriteLine($"Support ticket: {supportModel.Title}");
+ }
+
+ private class SupportModel
+ {
+ public string Title { get; set; } = "";
+ public string Description { get; set; } = "";
+ }
+}
+```
diff --git a/.github/skills/syncfusion-blazor-toolkit-popups/SKILL.md b/.github/skills/syncfusion-blazor-toolkit-popups/SKILL.md
new file mode 100644
index 0000000..4b6d2c1
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-popups/SKILL.md
@@ -0,0 +1,244 @@
+---
+name: syncfusion-blazor-toolkit-popups
+description: Implement interactive popup components with Syncfusion Blazor Toolkit. Covers SfDialog (modal windows) and SfTooltip (hover-based help text). Includes positioning, animations, event handling, accessibility, and real-world integration patterns. Use this skill when building modals, confirmation dialogs, contextual menus, informational overlays, or help tooltips in Blazor applications.
+metadata:
+ author: "Syncfusion Inc"
+ version: "1.0.0"
+---
+
+# Syncfusion Blazor Toolkit: Popups
+
+## Component Ecosystem Overview
+
+The Syncfusion Blazor Toolkit provides a comprehensive set of popup components for creating interactive, user-friendly interfaces. These components handle common UI patterns like modal dialogs, context menus, and help tooltips.
+
+### Components in This Skill
+
+| Component | Purpose | Key Use Cases |
+|-----------|---------|---|
+| **SfDialog** | Modal windows with configurable buttons, drag, resize, and animations | Confirmation dialogs, forms, alerts, full-screen modals |
+| **SfTooltip** | Hover-based informational text with positioning and animations | Help text, keyboard shortcut hints, status indicators |
+
+---
+
+## When to Use Each Component
+
+### Dialog (SfDialog)
+**Use SfDialog when you need:**
+- Modal or modeless dialog windows
+- User confirmations ("Are you sure?")
+- Form input collection
+- Full-screen overlays with controlled interactions
+- Drag, resize, and positioning capabilities
+- Button actions with event handling
+- Custom animation effects
+
+**Example Scenarios:**
+- "Save changes?" confirmation before navigation
+- Registration or login form popup
+- Settings configuration modal
+- Alert notification with user acknowledgment
+
+### Tooltip (SfTooltip)
+**Use SfTooltip when you need:**
+- Hover-based help text
+- Brief explanatory messages
+- Keyboard shortcut hints
+- Icon descriptions
+- Status or error messages on hover
+- Automatic positioning and arrow indicators
+
+**Example Scenarios:**
+- Help icon with explanation on hover
+- "Ctrl+S" keyboard shortcut hint
+- "Invalid email format" tooltip on input field
+- Icon button description tooltip
+
+---
+
+## Documentation and Navigation Guide
+
+### Getting Started with Dialogs
+📄 **Read:** [references/dialog-basics.md](references/dialog-basics.md)
+- Installation and initial setup
+- Creating your first dialog
+- Basic dialog configuration
+- Dialog types (modal, modeless)
+- Animation and effects
+- Button configuration
+- Basic event handling
+- content allowprerender and closeonescape apis
+- programatic methods in dialog
+
+### Advanced Dialog Features
+📄 **Read:** [references/dialog-advanced.md](references/dialog-advanced.md)
+- Dialog positioning and collision handling
+- Drag and resize functionality
+- Custom templates and content rendering
+- Dialog service and provider pattern
+- Complex event handling
+- Dynamic dialog creation
+- State management patterns
+
+### Tooltip Implementation
+📄 **Read:** [references/tooltip-implementation.md](references/tooltip-implementation.md)
+- Tooltip content configuration
+- Position and arrow indicators
+- Animation settings
+- open modes (hover, focus, click)
+- Event handling and lifecycle
+- tooltip programmatic methods
+- keyboard accessibility
+- real world examples
+
+---
+
+## Quick Start Examples
+
+### Quick Dialog Example
+```razor
+Open Dialog
+
+
+
+ Are you sure you want to proceed?
+
+
+
+
+
+
+
+
+@code {
+ private bool isVisible = false;
+ private void OpenDialog()
+ {
+ isVisible = true;
+ }
+
+ private async Task OnOkClick()
+ {
+ // Handle OK action
+ isVisible = false;
+ }
+
+ private async Task OnCancelClick()
+ {
+ isVisible = false;
+ }
+}
+```
+
+### Quick Tooltip Example
+```razor
+
+
+
+```
+
+---
+
+## Common Patterns
+
+### Modal Confirmation Dialog
+A reusable pattern for asking user confirmation:
+```razor
+Open Dialog
+
+
+
+ @confirmMessage
+
+
+
+
+
+
+
+
+@code {
+ private SfDialog confirmDialog;
+ private bool showConfirm = false;
+ private string confirmMessage = "";
+ private Func onConfirmCallback;
+ private void OpenDialog()
+ {
+ showConfirm = true;
+ }
+
+ public async Task ShowConfirmation(string message, Func callback)
+ {
+ confirmMessage = message;
+ onConfirmCallback = callback;
+ showConfirm = true;
+ }
+
+ private async Task OnConfirmYes()
+ {
+ showConfirm = false;
+ }
+
+ private void OnConfirmNo()
+ {
+ showConfirm = false;
+ }
+}
+```
+
+---
+
+## Key Properties and Methods
+
+### SfDialog Key Properties
+- `Visible` - Show/hide the dialog
+- `Header` - Dialog header text
+- `Width` / `Height` - Dialog dimensions
+- `IsModal` - Modal vs modeless behavior
+- `AllowDragging` - Enable/disable dragging
+- `EnableResize` - Enable/disable resizing
+- `DialogAnimationSettings` - Animation configuration
+
+### SfTooltip Key Properties
+- `Content` - Tooltip text or template
+- `Position` - Tooltip position
+- `OpensOn` - Trigger mode (Auto, Hover, Click, Focus, Custom)
+- `TooltipAnimationSettings` - Animation configuration
+- `TipPointerPosition` - Arrow position
+
+---
+
+## Accessibility and Best Practices
+
+✅ **DO:**
+- Use semantic HTML within dialogs and popups
+- Provide proper ARIA labels for interactive elements
+- Ensure keyboard navigation support
+- Use sufficient color contrast in tooltips
+- Include descriptive headers and footers
+- Test with screen readers
+- Provide alternative text for images in popups
+
+❌ **DON'T:**
+- Overuse dialogs for simple messages (use tooltips)
+- Hide critical information in tooltips only
+- Create dialogs without close buttons
+- Ignore keyboard accessibility
+- Create modals that trap focus improperly
+
+---
+
+## Next Steps
+
+1. **Start with basics:** Read [dialog-basics.md](references/dialog-basics.md) to understand core dialog usage
+2. **Explore advanced features:** Check [dialog-advanced.md](references/dialog-advanced.md) for complex scenarios
+3. **Implement tooltips:** Follow [tooltip-implementation.md](references/tooltip-implementation.md) for help text
+
+For additional help, refer to official Syncfusion documentation or check the referenced files for specific implementation details.
diff --git a/.github/skills/syncfusion-blazor-toolkit-popups/references/dialog-advanced.md b/.github/skills/syncfusion-blazor-toolkit-popups/references/dialog-advanced.md
new file mode 100644
index 0000000..f520f4d
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-popups/references/dialog-advanced.md
@@ -0,0 +1,828 @@
+# Dialog Advanced Features
+
+## Table of Contents
+- [Positioning](#positioning)
+- [Drag and Resize Functionality](#drag-and-resize-functionality)
+- [Custom Templates and Content](#custom-templates-and-content)
+- [Dialog Service and Providers](#dialog-service-and-providers)
+- [Complex Event Handling](#complex-event-handling)
+- [Dynamic Dialog Creation](#dynamic-dialog-creation)
+- [State Management Patterns](#state-management-patterns)
+- [Advanced Scenarios](#advanced-scenarios)
+
+---
+
+## Positioning
+
+
+
+### Dialog Positioning - Keyword Alignment
+
+Positions the dialog using predefined alignment keywords such as `top`, `center`, or `right`.
+
+```razor
+
+
+
+
+
+
+ Dialog aligned with keywords
+
+
+
+
+
+
+
+
+@code {
+ private bool KeywordVisibility { get; set; } = false;
+
+ private void OpenKeywordDialog()
+ {
+ KeywordVisibility = true;
+ }
+}
+```
+
+### Preset Positions
+
+```razor
+// Center on screen
+private DialogPositionData centerPosition = new()
+{
+ X = "center",
+ Y = "center"
+};
+
+// Top-left corner
+private DialogPositionData topLeftPosition = new()
+{
+ X = "0",
+ Y = "0"
+};
+
+// Top-center
+private DialogPositionData topCenterPosition = new()
+{
+ X = "center",
+ Y = "0"
+};
+
+// Bottom-right
+private DialogPositionData bottomRightPosition = new()
+{
+ X = "right",
+ Y = "bottom"
+};
+```
+
+## Drag and Resize Functionality
+
+### Resizing Dialog and ResizeHandles property
+
+The `EnableResize` property allows users to dynamically adjust the size of a dialog, making it easier to view content in expanded mode. When this feature is enabled, resize handles appear along the dialog’s edges or corners, providing interactive grip areas that can be dragged to change its dimensions. The `ResizeHandles` property further refines this behavior by specifying which sides or corners of the dialog can be resized, giving developers precise control over the resizing experience.
+
+```razor
+
+
+
+
+@code {
+ private bool IsResizeVisible { get; set; } = false;
+ private ResizeDirection[] dialogResizeDirections { get; set; } = new ResizeDirection[] { ResizeDirection.All };
+ private void OpenResizeDialog()
+ {
+ this.IsResizeVisible = true;
+ }
+ private void OnResizeStart(MouseEventArgs args)
+ {
+ Console.WriteLine("Resize started");
+ }
+
+ private void OnResizing(MouseEventArgs args)
+ {
+ // Resizing in progress - real-time updates
+ Console.WriteLine($"Resizing at X: {args.ClientX}, Y: {args.ClientY}");
+ }
+
+ private void OnResizeStop(MouseEventArgs args)
+ {
+ Console.WriteLine("Resize stopped");
+ }
+}
+```
+
+### Draggable Dialog
+
+To enable dragging capabilities, set the `AllowDragging` property to true on the Dialog component. When enabled, users can drag the Dialog by clicking and holding the Dialog header area.
+
+```razor
+
+
+
+
+@code {
+ private bool IsDraggableVisible { get; set; } = false;
+
+ private void OpenDraggableDialog()
+ {
+ IsDraggableVisible = true;
+ }
+
+ private void OnDragStart(Syncfusion.Blazor.Toolkit.Popups.DragStartEventArgs args)
+ {
+ Console.WriteLine($"Drag started at X: {args.Event.ClientX}, Y: {args.Event.ClientY}");
+ }
+
+ private void OnDrag(Syncfusion.Blazor.Toolkit.Popups.DragEventArgs args)
+ {
+ Console.WriteLine($"Dragging at X: {args.Event.ClientX}, Y: {args.Event.ClientY}");
+ }
+
+ private void OnDragStop(Syncfusion.Blazor.Toolkit.Popups.DragStopEventArgs args)
+ {
+ Console.WriteLine($"Drag stopped at X: {args.Event.ClientX}, Y: {args.Event.ClientY}");
+ }
+}
+```
+
+---
+
+## Custom Templates and Content
+
+### Header and Footer Templates
+
+You can set the Header and FooterTemplate of the SfDialog in two different ways. For simple cases, you can assign them directly as string or HTML properties, which is quick and useful when you only need plain text or a small snippet of markup.
+
+```razor
+
+
+
+ Dialog content
+
+
+
+
+@code {
+ private bool Visibility { get; set; } = true;
+ private string HeaderText { get; set; } = "Simple Header";
+ private string FooterHtml { get; set; } = "Simple Footer
";
+}
+```
+
+When you need more complex layouts — such as multiple elements, styled sections, or action buttons — you should use render fragments inside `DialogTemplates`.
+
+```razor
+
+
+
+
+
+
+
Dialog Content
+
This is custom content with full HTML support
+
+
+ Info Box: Dialog supports complex content
+
+
+
+
+
+
+ Save
+ Cancel
+
+
+
+
+
+@code {
+ private bool isDialogOpen = true;
+}
+```
+
+### Form Content Template
+
+```razor
+
+
showFormDialog = true)" />
+
+
+
+
+ User Registration Form
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ @if (!string.IsNullOrEmpty(validationError))
+ {
+
+ @validationError
+
+ }
+
+
+
+
+
+
+
+
+
+
+
+@code {
+ private bool showFormDialog = false;
+ private string validationError = "";
+
+ private class FormData
+ {
+ public string FullName { get; set; } = "";
+ public string Email { get; set; } = "";
+ public string Message { get; set; } = "";
+ }
+
+ private FormData formData = new();
+
+ private async Task OnSubmit()
+ {
+ validationError = "";
+
+ if (string.IsNullOrWhiteSpace(formData.FullName))
+ {
+ validationError = "Full Name is required";
+ return;
+ }
+
+ if (string.IsNullOrWhiteSpace(formData.Email))
+ {
+ validationError = "Email is required";
+ return;
+ }
+
+ Console.WriteLine($"Form submitted: {formData.FullName}, {formData.Email}");
+ showFormDialog = false;
+ formData = new();
+ }
+
+ private void OnCancel()
+ {
+ validationError = "";
+ formData = new();
+ showFormDialog = false;
+ }
+}
+```
+
+
+## Complex Event Handling
+
+### Preventing Dialog Close
+
+```razor
+
+
+
+ You have unsaved changes!
+
+
+
+
+
+
+
+@code {
+ private bool isOpen = true;
+
+ private void OnCloseHandler(BeforeCloseEventArgs args)
+ {
+ // Prevent dialog from closing
+ args.Cancel = true;
+ }
+}
+```
+
+### Handling Overlay Click
+
+When the modal overlay (backdrop) is clicked, `OnOverlayModalClick` is triggered. It provides an opportunity to respond to overlay clicks, which commonly involves closing the dialog or showing confirmation messages. This event is only applicable when the dialog is configured as a modal dialog using the `IsModal` property.
+
+```razor
+
+
+
+
+ Click the backdrop.
+
+
+
+
+@code {
+ private bool isOpen = true;
+
+ private void OnOverlayClick(OverlayModalClickEventArgs args)
+ {
+ Console.WriteLine("Overlay was clicked");
+ }
+}
+```
+
+### Multi-Step Dialog
+
+```razor
+
+
+
+ Setup Wizard - Step @currentStep of 3
+
+
+
+ @if (currentStep == 1)
+ {
+
+
Step 1: Enter Name
+
+
+ }
+ else if (currentStep == 2)
+ {
+
+
Step 2: Enter Email
+
+
+ }
+ else if (currentStep == 3)
+ {
+
+
Step 3: Confirm Details
+
Name: @wizardData.Name
+
Email: @wizardData.Email
+
+ }
+
+
+
+
+ @if (currentStep > 1)
+ {
+
+ }
+
+ @if (currentStep < 3)
+ {
+
+ }
+ else
+ {
+
+ }
+
+
+
+
+
+@code {
+ private bool isDialogOpen = true;
+ private int currentStep = 1;
+
+ private class WizardData
+ {
+ public string Name { get; set; } = "";
+ public string Email { get; set; } = "";
+ }
+
+ private WizardData wizardData = new();
+
+ private void NextStep()
+ {
+ if (currentStep < 3) currentStep++;
+ }
+
+ private void PreviousStep()
+ {
+ if (currentStep > 1) currentStep--;
+ }
+
+ private async Task FinishWizard()
+ {
+ Console.WriteLine($"Wizard completed: {wizardData.Name}, {wizardData.Email}");
+ isDialogOpen = false;
+ currentStep = 1;
+ }
+
+ private void CancelWizard()
+ {
+ isDialogOpen = false;
+ currentStep = 1;
+ wizardData = new();
+ }
+}
+```
+
+---
+
+## Dynamic Dialog Creation
+
+
+
+---
+
+## State Management Patterns
+
+### Dialog State in Parent Component
+
+```razor
+@page "/state-management"
+
+
+
+
+
+ Name:
+
+
+
+
+ Email:
+
+
+
+
+
+
+
+
+
+
+
+ Name: @formData.Name
+ Email: @formData.Email
+
+
+
+
+
+
+
+@code {
+ private bool showPreview = false;
+
+ private class FormModel
+ {
+ public string Name { get; set; } = "";
+ public string Email { get; set; } = "";
+ }
+
+ private FormModel formData = new();
+
+ private void ShowPreview()
+ {
+ showPreview = true;
+ }
+
+ private async Task SaveForm()
+ {
+ Console.WriteLine($"Saved: {formData.Name}, {formData.Email}");
+ }
+}
+```
+
+---
+
+## Advanced Scenarios
+
+### Nested Dialogs
+
+```razor
+
+
+
+
+
+
+ This is the first dialog
+ showDialog2 = true">
+ Open Dialog 2
+
+
+
+
+
+
+
+
+
+
+
+
+ This is a nested dialog
+
+
+
+
+
+
+
+@code {
+ private bool showDialog1 = false;
+ private bool showDialog2 = false;
+}
+
+### Dialog with Loading State
+
+```razor
+
+
+
+
+
+
+ @if (isLoading)
+ {
+ Processing your request...
+ }
+ else
+ {
+ @resultMessage
+ }
+
+
+
+
+
+
+
+@code {
+ private bool showDialog = false;
+ private bool isLoading = false;
+ private string resultMessage = "";
+
+ private async Task SimulateLoading()
+ {
+ showDialog = true;
+ isLoading = true;
+ resultMessage = "";
+
+ await Task.Delay(2000); // simulate work
+
+ isLoading = false;
+ resultMessage = "Operation completed!";
+ }
+}
+```
+---
+
+## Key Takeaways
+
+✅ **DO:**
+- Use positioning for better UX
+- Implement drag and resize for flexibility
+- Handle OnClose for data validation
+- Use templates for complex content
+- Implement multi-step workflows for complex processes
+
+❌ **DON'T:**
+- Create deeply nested dialogs (hard to navigate)
+- Ignore resize constraints (can break UI)
+- Use service for every dialog (prefer direct binding)
+- Forget to cleanup dialog state
+- Create inaccessible forms in dialogs
+
+---
+
+## Next: Popups and Positioning
+
+See [popup-positioning.md](popup-positioning.md) for lightweight popup positioning and targeting.
diff --git a/.github/skills/syncfusion-blazor-toolkit-popups/references/dialog-basics.md b/.github/skills/syncfusion-blazor-toolkit-popups/references/dialog-basics.md
new file mode 100644
index 0000000..f3b0727
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-popups/references/dialog-basics.md
@@ -0,0 +1,848 @@
+# Dialog Basics
+
+## Table of Contents
+- [What is SfDialog?](#what-is-sfdialog)
+- [Installation and Setup](#installation-and-setup)
+- [Creating Your First Dialog](#creating-your-first-dialog)
+- [Dialog Configuration](#dialog-configuration)
+- [Modal vs Modeless](#modal-vs-modeless)
+- [Animation and Effects](#animation-and-effects)
+- [Button Configuration](#button-configuration)
+- [Basic Event Handling](#basic-event-handling)
+- [Content,AllowPrerender and CloseOnEscape APIs](#content-allowprerender-closeonescape-apis)
+- [Programmatic Methods in Dialog](#programmatic-methods-in-dialog)
+- [Common Scenarios](#common-scenarios)
+
+---
+
+## What is SfDialog?
+
+SfDialog is a versatile modal or modeless dialog component from Syncfusion Blazor Toolkit. It displays content in a separate window that can be dragged, resized, and positioned. Dialogs are ideal for:
+
+- Confirming user actions
+- Collecting form input
+- Displaying alerts or notifications
+- Creating settings panels
+- Showing detailed information
+
+**Key Characteristics:**
+- Fully customizable header, content, and footer
+- Built-in buttons with event handling
+- Drag and resize capabilities
+- Animation support
+- Modal and modeless variants
+- Responsive sizing
+
+---
+
+## Installation and Setup
+
+### 1. Import the Component
+In your Razor component or `_Imports.razor`:
+
+```csharp
+@using Syncfusion.Blazor.Toolkit.Popups
+```
+
+### 2. Register the Component
+In `Program.cs`:
+
+```csharp
+using Syncfusion.Blazor.Toolkit;
+
+builder.Services.AddSyncfusionBlazorToolkit();
+```
+
+### 3. Include CSS
+In `_Host.cshtml` or `App.razor`:
+
+```html
+
+```
+
+---
+
+## Creating Your First Dialog
+
+### Minimal Dialog Example
+
+```razor
+@page "/dialog-demo"
+@using Syncfusion.Blazor.Toolkit.Popups
+@using Syncfusion.Blazor.Toolkit.Buttons
+
+
+
+
+
+ This is a simple dialog.
+
+
+
+
+Open Dialog
+
+@code {
+ private bool isDialogOpen = false;
+
+ private void OpenDialog()
+ {
+ isDialogOpen = true;
+ }
+}
+```
+
+**What's happening:**
+- `@bind-Visible="isDialogOpen"` - Binds dialog visibility to a boolean variable
+- `Width` and `Height` - Set dialog dimensions
+- `DialogTemplates` - Contains Header, Content, and Footer sections
+- Button click opens the dialog by setting `isDialogOpen = true`
+
+---
+
+## Dialog Configuration
+
+### Essential Properties
+
+```razor
+
+
+
+ Dialog content goes here
+
+
+
+
+```
+
+### Dialog with HtmlAttribute
+
+```razor
+
+
+
+ This dialog has HtmlAttributes applied.
+
+
+
+
+
+
+@code {
+ private bool Visibility { get; set; } = false;
+
+ // Simple HtmlAttributes dictionary
+ private Dictionary DialogAttributes = new()
+ {
+ { "title", "My Simple Dialog" }
+ };
+}
+```
+
+**Property Details:**
+
+| Property | Type | Default | Purpose |
+|----------|------|---------|---------|
+| `Visible` | bool | false | Show/hide the dialog |
+| `Header` | string | "Dialog" | Dialog header text |
+| `Width` | string | "100%" | Dialog width (px, %, em, etc.) |
+| `Height` | string | "auto" | Dialog height |
+| `AllowDragging` | bool | false | Enable dragging the dialog |
+| `EnableResize` | bool | false | Enable resizing the dialog |
+| `AllowPrerender` | bool | false | Keep DOM when closed (performance optimization) |
+| `CloseOnEscape` | bool | true | Allow closing with Escape key |
+| `IsModal` | bool | false | Modal overlay behind dialog |
+| `ZIndex` | int | 1000 | Stacking order |
+| `CssClass` | string | String.Empty | Custom CSS class |
+| `MinHeight` | string | String.Empty | Minimum height constraint |
+| `Target` | string | null | Container element for dialog display |
+| `ShowCloseIcon` | bool | false | Display close icon in header |
+| `VisibleChanged` | EventCallback | - | Two-way binding callback, invoked when Visible changes |
+| `Created` | EventCallback | - | Component created event |
+| `Destroyed` | EventCallback | - | Component destroyed event |
+| `EnablePersistence` | bool | false | Persist dialog position and size to localStorage |
+| `ID` | string | null | seful for targeting the dialog element with CSS or JavaScript |
+| `HtmlAttributes` | Dictionary | null | allows to add custom attributes like id, title, or aria- attributes to the dialog element |
+
+### Sizing Options
+
+**Fixed Size:**
+```razor
+
+```
+
+**Responsive Size:**
+```razor
+
+```
+
+**Auto Height:**
+```razor
+
+```
+
+**Min Dimensions:**
+```razor
+
+
+@code {
+ private SfDialog dialog;
+}
+```
+
+---
+
+## Modal vs Modeless
+
+### Modal Dialog (Default)
+User cannot interact with background content while dialog is open:
+
+```razor
+
+
+
+ Modal dialog - background is disabled
+
+
+
+Open Dialog
+
+@code {
+ private bool isDialogOpen = false;
+
+ private void OpenDialog()
+ {
+ isDialogOpen = true;
+ }
+}
+```
+
+**Use Cases:**
+- Critical confirmations
+- Important forms
+- Alerts that need user attention
+
+### Modeless Dialog
+User can interact with background content:
+
+```razor
+
+
+
+ Modeless dialog - background is interactive
+
+
+
+Open Dialog
+
+@code {
+ private bool isDialogOpen = false;
+
+ private void OpenDialog()
+ {
+ isDialogOpen = true;
+ }
+}
+```
+
+**Use Cases:**
+- Help panels
+- Notes or scratch pads
+- Docked panels
+- Tool palettes
+
+---
+
+## Animation and Effects
+
+### Basic Animation
+
+```razor
+
+
+
+
+ Dialog content
+
+
+
+
+
+
+Open Dialog
+
+@code {
+ private bool isDialogOpen = false;
+
+ private void OpenDialog()
+ {
+ isDialogOpen = true;
+ }
+}
+```
+
+### Available Effects
+
+| Effect | Behavior |
+|--------|----------|
+| `DialogEffect.Fade` | Gradual opacity transition |
+| `DialogEffect.FadeZoom` | Combined fade and zoom effect |
+| `DialogEffect.FlipLeftDown` | Flip animation from left to down |
+| `DialogEffect.FlipLeftUp` | Flip animation from left to up |
+| `DialogEffect.FlipRightDown` | Flip animation from right to down |
+| `DialogEffect.FlipRightUp` | Flip animation from right to up |
+| `DialogEffect.FlipXDown` | Horizontal flip with downward motion |
+| `DialogEffect.FlipXUp` | Horizontal flip with upward motion |
+| `DialogEffect.FlipYLeft` | Vertical flip with leftward motion |
+| `DialogEffect.FlipYRight` | Vertical flip with rightward motion |
+| `DialogEffect.SlideBottom` | Slide in/out from bottom |
+| `DialogEffect.SlideLeft` | Slide in/out from left |
+| `DialogEffect.SlideRight` | Slide in/out from right |
+| `DialogEffect.SlideTop` | Slide in/out from top |
+| `DialogEffect.Zoom` | Scale-based zoom effect |
+| `DialogEffect.None` | No animation effect |
+
+### Custom Animation
+
+```razor
+
+
+
+ Custom animation
+
+
+
+
+@code {
+ private DialogAnimationSettings customAnimation = new()
+ {
+ Effect = DialogEffect.Zoom,
+ Duration = 800,
+ Delay = 100
+ };
+}
+```
+
+---
+
+## Button Configuration
+
+### Dialog Buttons
+
+```razor
+
+
+
+ Do you want to continue?
+
+
+
+
+
+
+
+
+
+@code {
+ private bool isDialogOpen = true;
+
+ private async Task OnYesClick()
+ {
+ isDialogOpen = false;
+ }
+
+ private async Task OnNoClick()
+ {
+ isDialogOpen = false;
+ }
+
+ private async Task OnCancelClick()
+ {
+ isDialogOpen = false;
+ }
+}
+```
+
+### Button Properties
+
+```razor
+private DialogButton submitButton = new()
+{
+ Content = "Submit",
+ IsPrimary = true,
+ CssClass = "custom-button",
+ Disabled = false,
+ IconCss = "e-icons e-save"
+};
+```
+
+---
+
+## Basic Event Handling
+
+```razor
+
+
+
+ Event handling demo
+
+
+
+
+Open Dialog
+
+@code {
+ private bool isDialogOpen = false;
+
+ private void OpenDialog()
+ {
+ isDialogOpen = true;
+ }
+
+ private async Task OnDialogOpen(BeforeOpenEventArgs args)
+ {
+ Console.WriteLine("Dialog is about to open");
+ // Cancel opening if needed: args.Cancel = true;
+ }
+
+ private async Task OnDialogClose(BeforeCloseEventArgs args)
+ {
+ Console.WriteLine("Dialog is about to close");
+ // Prevent closing if needed: args.Cancel = true;
+ }
+}
+```
+
+### Created and Destroyed Events
+
+The `Created` event fires when the dialog component is fully rendered, and `Destroyed` fires when it's being disposed:
+
+```razor
+
+
+ Lifecycle events demo
+
+
+
+@code {
+ private bool isDialogOpen = true;
+
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("Dialog has been created and rendered");
+ }
+
+ private void OnDestroyed(object args)
+ {
+ Console.WriteLine("Dialog is being destroyed and removed from DOM");
+ }
+}
+```
+
+### Event Arguments
+
+**BeforeOpenEventArgs:**
+```csharp
+public class BeforeOpenEventArgs
+{
+ public bool Cancel { get; set; } // Cancel opening
+ public string MaxHeight { get; set; } // Override max height before open
+}
+```
+
+**OpenEventArgs:**
+```csharp
+public class OpenEventArgs
+{
+ public bool Cancel { get; set; } // Not typically used
+ public string Name { get; set; } // Event name ("Opened")
+ public bool PreventFocus { get; set; } // Prevent auto-focus on first element
+}
+```
+
+**BeforeCloseEventArgs:**
+```csharp
+public class BeforeCloseEventArgs
+{
+ public bool Cancel { get; set; } // Cancel closing
+ public string ClosedBy { get; set; } // "CloseIcon", "Escape", etc.
+ public EventArgs Event { get; set; } // MouseEventArgs or KeyboardEventArgs
+ public bool IsInteracted { get; set; } // User-initiated close
+ public bool PreventFocus { get; set; } // Prevent focus restoration
+}
+```
+
+**CloseEventArgs:**
+```csharp
+public class CloseEventArgs
+{
+ public bool Cancel { get; set; } // Not typically used
+ public string ClosedBy { get; set; } // Source of close action
+ public EventArgs Event { get; set; } // Original event
+ public bool IsInteracted { get; set; } // User-initiated close
+ public string Name { get; set; } // Event name ("Closed")
+}
+```
+
+### Drag Event Args
+
+**DragStartEventArgs:**
+```csharp
+public class DragStartEventArgs
+{
+ public MouseEventArgs Event { get; set; } // Mouse event data
+ public string Name { get; set; } // "OnDragStart"
+}
+```
+
+**DragEventArgs:**
+```csharp
+public class DragEventArgs
+{
+ public MouseEventArgs Event { get; set; } // Current mouse position
+ public string Name { get; set; } // "OnDrag"
+}
+```
+
+**DragStopEventArgs:**
+```csharp
+public class DragStopEventArgs
+{
+ public MouseEventArgs Event { get; set; } // Final mouse position
+ public string Name { get; set; } // "OnDragStop"
+}
+```
+
+### Overlay Event Args
+
+**OverlayModalClickEventArgs:**
+```csharp
+public class OverlayModalClickEventArgs
+{
+ public MouseEventArgs Event { get; set; } // Click event data
+ public bool PreventFocus { get; set; } // Prevent auto-focus
+}
+```
+---
+
+## Content,AllowPrerender and CloseOnEscape APIs
+
+### Content property
+
+For simple text content, you can use the `Content` property instead of `DialogTemplates`:
+
+```razor
+
+
+
+@code {
+ private bool isDialogOpen = false;
+}
+```
+
+### AllowPrerender for Performance
+
+When `AllowPrerender` is set to `true`, the dialog's DOM elements remain in the page when closed (hidden via CSS) instead of being removed. This improves performance for frequently opened/closed dialogs:
+
+```razor
+
+
+
+ This dialog's DOM stays in the page when closed.
+
+
+
+@code {
+ private bool isDialogOpen = false;
+}
+```
+
+### CloseOnEscape Configuration
+
+By default, pressing the Escape key closes the dialog. Set `CloseOnEscape="false"` to disable this behavior:
+
+```razor
+
+
+ Press Escape key - this dialog won't close!
+
+
+
+@code {
+ private bool isDialogOpen = true;
+}
+```
+
+---
+
+## Programmatic Methods in Dialog
+
+
+SfDialog provides several async methods for programmatic control:
+
+### Showing and Hiding Dialogs
+
+```razor
+
+
+ Programmatic control demo
+
+
+
+
+
+
+
+@code {
+ private SfDialog dialog;
+
+ private async Task ShowDialog()
+ {
+ await dialog.ShowAsync();
+ }
+
+ private async Task HideDialog()
+ {
+ await dialog.HideAsync();
+ }
+
+ private async Task ToggleFullscreen()
+ {
+ await dialog.ShowAsync(true); // true = fullscreen mode
+ }
+}
+```
+
+### Getting Dialog Dimensions using GetDimensionAsync method
+
+```razor
+
+
+
+ This is a sample dialog.
+
+
+
+
+
+
+
+@code {
+ private SfDialog? dialog;
+ private bool showDialog = false;
+ private async Task GetDimensions()
+ {
+ if (dialog is not null)
+ {
+ var dimensions = await dialog.GetDimensionAsync();
+ Console.WriteLine($"Width: {dimensions.Width}, Height: {dimensions.Height}");
+ }
+ else
+ {
+ Console.WriteLine("Dialog reference is null — make sure it's rendered.");
+ }
+ }
+}
+```
+
+
+### GetButton
+Returns the specific DialogButton instance at the specified index.
+
+```csharp
+SfDialog dialog;
+DialogButton firstButton = dialog.GetButton(0);
+DialogButton secondButton = dialog.GetButton(1);
+```
+
+### GetButtonItems
+Returns the complete collection of DialogButton instances.
+
+```csharp
+SfDialog dialog;
+List allButtons = dialog.GetButtonItems();
+if (allButtons is not null)
+{
+ foreach (var button in allButtons)
+ {
+ Console.WriteLine($"Button: {button.Content}");
+ }
+}
+```
+
+---
+
+## Common Scenarios
+
+### Simple Alert Dialog
+
+```razor
+
+
+
+
+ @alertMessage
+
+
+
+
+
+
+
+Show Alert
+
+@code {
+ private bool showAlert = false;
+ private string alertMessage = "This is an alert message";
+
+ private void ShowAlert()
+ {
+ alertMessage = "Something important happened!";
+ showAlert = true;
+ }
+}
+```
+
+### Confirmation Dialog
+
+```razor
+
+
+
+
+ Are you sure you want to delete this item?
+ This action cannot be undone.
+
+
+
+
+
+
+
+Show Alert
+
+@code {
+ private bool showConfirm = false;
+
+ private async Task OnConfirmDelete()
+ {
+ // Perform delete action
+ showConfirm = false;
+ }
+ private void ShowPopup()
+ {
+ showConfirm = true; // open the dialog
+ }
+}
+```
+
+### Information Dialog with Multiple Sections
+
+```razor
+
+
+
+
+
+
Product Details
+
Name: Syncfusion Blazor Toolkit
+
Version: 1.0.0
+
License: Commercial
+
+
Features
+
+ Rich component library
+ Full responsive support
+ Accessibility compliant
+
+
+
+
+
+
+
+
+
+ showInfo = true">Show Info
+
+@code {
+ private bool showInfo = false;
+}
+```
+
+---
+
+## Key Takeaways
+
+✅ **DO:**
+- Use Modal="true" for critical user confirmations
+- Provide clear header and footer for context
+- Include descriptive button labels
+- Handle BeforeClose event for unsaved changes validation
+- Use animations sparingly for better UX
+
+❌ **DON'T:**
+- Create dialogs without clear close mechanisms
+- Use dialogs for simple messages (use tooltips instead)
+- Trap users in dialogs without escape option
+- Overuse animations (performance impact)
+- Hide important information in dialog content only
+
+---
+
+## Next: Advanced Dialog Features
+
+For more complex scenarios like drag, resize, dynamic creation, and advanced templating, see [dialog-advanced.md](dialog-advanced.md).
diff --git a/.github/skills/syncfusion-blazor-toolkit-popups/references/tooltip-implementation.md b/.github/skills/syncfusion-blazor-toolkit-popups/references/tooltip-implementation.md
new file mode 100644
index 0000000..fa6967c
--- /dev/null
+++ b/.github/skills/syncfusion-blazor-toolkit-popups/references/tooltip-implementation.md
@@ -0,0 +1,835 @@
+# Tooltip Implementation and Styling
+
+## Table of Contents
+- [What is SfTooltip?](#what-is-sftooltip)
+- [Basic Tooltip Setup](#basic-tooltip-setup)
+- [Content Configuration](#content-configuration)
+- [Position and Arrow Indicators](#position-and-arrow-indicators)
+- [Animation Settings](#animation-settings)
+- [Open Modes](#Open-modes)
+- [Sticky Mode and Mouse Trail](#sticky-mode-and-mouse-trail)
+- [Delays, Window Collision and TargetContainer APIs](#Delays, Window Collision and TargetContainer APIs)
+- [Event Handling](#event-handling)
+- [Tooltip Programmatic Methods](#tooltip-programmatic-methods)
+- [Keyboard Accessibility](#keyboard-accessibility)
+- [Styling and Theming](#styling-and-theming)
+- [Real-World Examples](#real-world-examples)
+
+---
+
+## What is SfTooltip?
+
+SfTooltip is a lightweight component that displays contextual help text or information on hover, focus, or click. It's ideal for:
+
+- Icon descriptions
+- Keyboard shortcut hints
+- Status or validation messages
+- Brief explanations
+- Accessibility enhancements
+
+**Key Characteristics:**
+- Multiple positioning options
+- Arrow indicators pointing to target
+- Customizable open modes
+- Animation support
+- RTL support
+- Accessibility compliant (WCAG)
+
+---
+
+## Basic Tooltip Setup
+
+### Minimal Tooltip Example
+
+```razor
+@using Syncfusion.Blazor.Popups
+
+
+ Hover over me
+
+```
+
+### With Target Element
+
+```razor
+
+
+ ❓
+
+
+```
+
+### With Container
+
+```razor
+
+
+
+
+
+```
+
+### CSS Import
+
+Ensure Syncfusion CSS is included in `_Host.cshtml` or `App.razor`:
+
+```html
+
+```
+
+---
+
+## Content Configuration
+
+### Text Content
+
+```razor
+
+ Help
+
+```
+
+### HTML Template
+
+```razor
+
+
+
+
+
+
+
+
Tooltip Title
+
This tooltip contains HTML content
+
+
+
+```
+
+### Dynamic Content
+
+```razor
+
+
+
+
+ Selected: @DynamicContent
+
+
+
+ DynamicContent = "Wireless")">
+ DynamicContent = "Device")">
+ DynamicContent = "Personal")">
+
+
+
+
+@code {
+ private SfTooltip? tooltipInstance;
+ private string DynamicContent = "Wireless";
+}
+```
+
+---
+
+## Position and Arrow Indicators
+
+### Position Options
+
+```razor
+
+ @foreach(var position in positions)
+ {
+
+
+ @position
+
+
+ }
+
+
+@code {
+ private Position[] positions =
+ {
+ Position.TopCenter,
+ Position.TopLeft,
+ Position.TopRight,
+ Position.BottomCenter,
+ Position.BottomLeft,
+ Position.BottomRight,
+ Position.LeftCenter,
+ Position.LeftTop,
+ Position.LeftBottom,
+ Position.RightCenter,
+ Position.RightTop,
+ Position.RightBottom
+ };
+}
+```
+
+### Arrow Positioning
+
+```razor
+
+
+ Arrow points to end
+
+
+
+
+
+ Arrow points to middle
+
+
+
+@code {
+}
+```
+
+### Show/Hide Tip Pointer
+
+```razor
+
+
+
+
+
+```
+
+
+
+---
+
+## Animation Settings
+
+### Basic Animation
+
+```razor
+
+
+
+@code
+{
+ public AnimationModel Animation { get; set; } = new AnimationModel
+ {
+ Open = new TooltipAnimationSettings {Delay = 0, Duration = 500, Effect = Effect.ZoomIn },
+ Close = new TooltipAnimationSettings{Delay=0,Duration=500,Effect=Effect.ZoomOut}
+ };
+}
+```
+
+### Available Effects
+
+The available effects include fade, slide, zoom, and other predefined animation types.
+
+---
+
+## Open Modes
+
+The `OpensOn` property determines the event that triggers the Tooltip to appear. The supported values are: `Auto` , `Hover`, `Click`, `Focus` and `Custom`.
+
+### Hover
+
+```razor
+
+
+ Hover over me
+
+
+```
+
+### Click
+
+```razor
+
+
+ Click me
+
+
+```
+
+### Focus (for keyboard navigation)
+
+```razor
+
+
+
+```
+
+### Auto Mode (Default)
+
+```razor
+
+
+ Hover or click me
+
+
+```
+
+### Custom Trigger (Programmatic)
+
+```razor
+
+
+ Show Tooltip
+
+
+
+
+ Hide Tooltip
+
+
+@code {
+ private SfTooltip tooltip;
+
+ private async Task ShowTooltip()
+ {
+ await tooltip.OpenAsync();
+ }
+
+ private async Task HideTooltip()
+ {
+ await tooltip.CloseAsync();
+ }
+}
+```
+
+---
+
+## Sticky Mode and Mouse Trail
+
+### Sticky Tooltip
+
+```razor
+
+ Click to open sticky tooltip
+
+```
+
+### Mouse Trail
+
+```razor
+
+
+ Move mouse here to see trail effect
+
+
+```
+
+---
+
+## Delays, Window Collision and TargetContainer APIs
+
+### Open and Close Delays
+
+```razor
+
+
+ Hover - wait 1 second
+
+
+
+
+
+ Hover and then leave
+
+
+```
+
+### Window Collision
+
+```razor
+
+
+ Hover near edges
+
+
+```
+
+### Target Container
+
+```razor
+
+
+ Button 1
+ Button 2
+ Button 3
+
+
+```
+
+---
+
+## Event Handling
+
+### Lifecycle Events
+
+```razor
+
+
+ Hover to see events
+
+
+
+
+
Event Log:
+ @foreach(var evt in eventLog.TakeLast(5))
+ {
+
@evt
+ }
+
+
+@code {
+ private List eventLog = new();
+
+ private async Task OnBeforeOpen(TooltipEventArgs args)
+ {
+ eventLog.Add($"[{DateTime.Now:HH:mm:ss}] BeforeOpen - Can cancel with args.Cancel");
+ }
+
+ private async Task OnTooltipOpened(TooltipEventArgs args)
+ {
+ eventLog.Add($"[{DateTime.Now:HH:mm:ss}] Opened");
+ }
+
+ private async Task OnBeforeClose(TooltipEventArgs args)
+ {
+ eventLog.Add($"[{DateTime.Now:HH:mm:ss}] BeforeClose - Can cancel with args.Cancel");
+ }
+
+ private async Task OnTooltipClosed(TooltipEventArgs args)
+ {
+ eventLog.Add($"[{DateTime.Now:HH:mm:ss}] Closed");
+ }
+}
+```
+
+### Collision Detection
+
+```razor
+
+
+ Hover to see collision handling
+
+
+
+@code {
+ private void OnCollision(TooltipEventArgs args)
+ {
+ // Contains collision information for custom positioning logic
+ Console.WriteLine($"Collision at: {args.Left}, {args.Top}");
+ }
+}
+```
+
+### OnRender Event
+
+```razor
+
+
+ Hover to see render event
+
+
+
+@code {
+ private bool someCondition = false;
+
+ private void OnTooltipRender(TooltipEventArgs args)
+ {
+ // Called before tooltip is added to DOM
+ if (someCondition)
+ {
+ // Cancel showing the tooltip
+ args.Cancel = true;
+ }
+ else
+ {
+ // Dynamically change the content before render
+ Console.WriteLine("Tooltip rendered");
+ }
+ }
+}
+```
+
+### Creation and Destruction Events
+
+```razor
+
+
+ Hover to see lifecycle
+
+
+
+@code {
+ private void OnCreated(object args)
+ {
+ Console.WriteLine("Tooltip created");
+ }
+
+ private void OnDestroyed(object args)
+ {
+ Console.WriteLine("Tooltip destroyed");
+ }
+}
+```
+
+---
+
+## Tooltip Programmatic Methods
+
+### OpenAsync and CloseAsync
+
+These methods allow programmatic control over showing and hiding the tooltip with optional animation settings and target element specification.
+
+```razor
+
+
+ Show Tooltip
+
+
+
+
+ Hide Tooltip
+
+
+@code {
+ private SfTooltip? tooltip;
+
+ private async Task ShowTooltip()
+ {
+ var fadeIn = new TooltipAnimationSettings
+ {
+ Effect = Effect.FadeIn,
+ Duration = 300
+ };
+
+ if (tooltip is not null)
+ await tooltip.OpenAsync(null, fadeIn);
+ }
+
+ private async Task HideTooltip()
+ {
+ var fadeOut = new TooltipAnimationSettings
+ {
+ Effect = Effect.FadeOut,
+ Duration = 500
+ };
+
+ if (tooltip is not null)
+ await tooltip.CloseAsync(fadeOut);
+ }
+}
+```
+
+### PreventRender
+Controls the re-rendering behavior of the Tooltip component.
+
+```csharp
+// Prevent tooltip from re-rendering (default behavior)
+tooltip.PreventRender(true);
+
+// Allow tooltip to re-render again
+tooltip.PreventRender(false);
+```
+
+### RefreshAsync
+Asynchronously refreshes the entire Tooltip component to synchronize with dynamic DOM changes and target element updates.
+
+```csharp
+// After adding new elements dynamically
+await AddNewElementsToPage();
+await tooltipComponent.RefreshAsync();
+
+// After modifying existing target elements
+await UpdateTargetElementAttributes();
+await tooltipComponent.RefreshAsync();
+```
+
+### RefreshPositionAsync
+Recalculates and updates the tooltip’s position when the layout changes, keeping it aligned with its target element. Useful after resizing, scrolling, or moving elements dynamically.
+
+```csharp
+// Refresh position with default target
+await tooltip.RefreshPositionAsync();
+
+// Refresh position for a specific element
+await tooltip.RefreshPositionAsync(targetElement);
+```
+
+---
+
+## Keyboard Accessibility
+
+### Keyboard Support
+
+```razor
+
+
+ Keyboard Shortcut
+ Description
+
+
+
+
+
+
+ Shift + Tab
+
+
+
+ Navigate backwards
+
+
+
+
+
+
+ Tab
+
+
+
+ Navigate forwards
+
+
+
+
+
+
+ Enter / Space
+
+
+
+ Activate element
+
+
+```
+
+### Accessible Tooltips
+
+```razor
+
+
+ 💾 Save
+
+
+
+
+
+ 🗑️ Delete
+
+
+
+@code {
+}
+```
+
+---
+
+## Styling and Theming
+
+### CSS Classes
+
+The `CssClass` property is used to apply custom CSS class names that define specific user-defined styles and themes to be applied to the Tooltip element. Multiple class names can be specified by separating them with a space.
+
+```razor
+
+
+
+
+
+```
+
+---
+
+## Real-World Examples
+
+### Icon Button Tooltip
+
+```razor
+
+
+
+ 💾
+
+
+
+
+
+ ↶
+
+
+
+
+
+ ↷
+
+
+
+
+
+ 🗑️
+
+
+
+
+
+```
+
+### Data Cell Tooltip
+
+```razor
+
+
+
+ Name
+ Email
+ Status
+
+
+
+ @foreach(var user in users)
+ {
+
+ @user.Name
+
+
+
+ @(user.Email.Length > 15 ? user.Email.Substring(0, 12) + "..." : user.Email)
+
+
+
+
+
+
+ @user.Status
+
+
+
+
+ }
+
+
+
+@code {
+ private class User
+ {
+ public string Name { get; set; }
+ public string Email { get; set; }
+ public string Status { get; set; }
+ }
+
+ private List users = new()
+ {
+ new() { Name = "John Doe", Email = "john@example.com", Status = "Active" },
+ new() { Name = "Jane Smith", Email = "jane@example.com", Status = "Inactive" },
+ new() { Name = "Bob Wilson", Email = "bob@example.com", Status = "Pending" }
+ };
+
+ private string GetStatusDescription(string status) => status switch
+ {
+ "Active" => "User is currently active",
+ "Inactive" => "User account is inactive",
+ "Pending" => "User account approval pending",
+ _ => ""
+ };
+
+ private string GetStatusColor(string status) => status switch
+ {
+ "Active" => "#4caf50",
+ "Inactive" => "#999",
+ "Pending" => "#ff9800",
+ _ => "#999"
+ };
+}
+```
+
+## Key Takeaways
+
+✅ **DO:**
+- Use tooltips for help and clarification, not critical information
+- Keep tooltip text concise and clear
+- Include keyboard shortcut hints in tooltips
+- Test tooltip positioning at different screen sizes
+- Use appropriate Open modes for different contexts
+- Use `IsSticky` for tooltips that should stay open until manually closed
+- Use `MouseTrail` for following mouse movement during demos
+- Use `OpenDelay` and `CloseDelay` to prevent tooltip flashing during quick mouse movements
+- Use `WindowCollision` when tooltip should avoid viewport edges
+
+❌ **DON'T:**
+- Hide critical information in tooltips only
+- Use tooltips as a replacement for proper labeling
+- Create tooltips with excessive text (use dialogs instead)
+- Overuse animations (performance impact)
+- Forget to make tooltips accessible (keyboard support)
+- Use `Position.Custom` as there's no custom positioning enum value
diff --git a/README.md b/README.md
index f446c8b..95668c4 100644
--- a/README.md
+++ b/README.md
@@ -1,40 +1,116 @@
# Syncfusion® Toolkit for Blazor
-The **Syncfusion® Toolkit for Blazor** is a high-performance, open-source collection of lightweight UI components designed to accelerate Blazor application development (Server and WebAssembly). These controls help developers build modern, responsive, and feature-rich web applications faster, with clean code and excellent performance.
+The [**Syncfusion® Toolkit for Blazor**](https://www.syncfusion.com/blazor-toolkit) is a high-performance, open-source collection of lightweight UI components designed to accelerate Blazor application development (Server and WebAssembly). These controls help developers build modern, responsive, and feature-rich web applications faster, with clean code and excellent performance.
-Built with community collaboration in mind, the toolkit incorporates user feedback and contributions to deliver practical, high-quality components that integrate seamlessly with the broader Syncfusion Blazor ecosystem.
+Built with community collaboration in mind, the toolkit incorporates user feedback and contributions to deliver practical, high-quality components that integrate seamlessly with the broader Syncfusion Blazor ecosystem. We welcome contributions across components, documentation, tests, accessibility, and performance.
[](https://www.nuget.org/packages/Syncfusion.Blazor.Toolkit)
[](https://github.com/syncfusion/blazor-toolkit/blob/main/LICENSE)
[](https://github.com/syncfusion/blazor-toolkit/stargazers)
+
+
+## Quick Contributor Start
+
+```bash
+git clone https://github.com/syncfusion/blazor-toolkit.git
+cd blazor-toolkit
+```
+Run these commands to build the solution:
+```bash
+dotnet restore
+dotnet build ./Syncfusion.Blazor.Toolkit.slnx
+```
+To run the samples,
+- Open the `samples/Blazor.Toolkit.Samples.slnx` file in Visual Studio.
+- Set the desired sample project as the startup project and run.
+
+## Ways to Contribute
+
+We welcome contributions of all sizes:
+
+- **Bug fixes** — Help us ship cleaner, more correct components
+- **Documentation** — Improve XML docs, examples, and usage guides
+- **Test coverage** — Add bUnit tests for components with low coverage
+- **Accessibility** — Improve ARIA attributes, keyboard navigation, and screen reader support
+- **Performance** — Profile rendering, reduce allocations, tighten JS interop
+- **API review** — Give feedback on component APIs and patterns
+- **Feature proposals** — Open a discussion before opening a PR for large changes
+
+Not sure where to start? Look for issues labeled [`good first issue`](https://github.com/syncfusion/blazor-toolkit/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22) or [`help wanted`](https://github.com/syncfusion/blazor-toolkit/issues?q=is%3Aopen+is%3Aissue+label%3Ahelp+wanted).
+
+## Good First Issues
+
+Looking for a place to start? Here are some examples of contributions we regularly accept:
+
+- Fix incomplete or incorrect XML documentation on public API members
+- Add bUnit tests for components with low test coverage
+- Improve accessibility labels and ARIA attributes on existing components
+- Tighten JavaScript interop scoping (reduce unnecessary `IJSRuntime` surface exposure)
+- Refactor large enums or constants into domain-specific files
+- Add missing `` blocks in XML documentation comments
+
+For a full list, see [open issues labeled good first issue](https://github.com/syncfusion/blazor-toolkit/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22).
+
+## Repository Structure
+
+```
+blazor-toolkit/
+├── src/
+│ ├── Base/ # Shared infrastructure (ComponentBase, event callbacks, utilities)
+│ ├── Components/ # UI components by domain (Buttons/, Calendars/, Charts/, Inputs/, Popups/, Spinner/)
+│ │ └── / # Each component has its own folder (SfButton/, SfChart/, etc.)
+│ └── wwwroot/ # Static assets: JavaScript, CSS, and generated theme files
+│ └── styles/ # Theme CSS generated by gulp — do not edit by hand
+├── samples/ # Sample browser application
+├── tests/ # Test suites
+│ ├── BUnitTest/ # Component unit tests (bUnit + xUnit)
+│ └── Playwright.Test/ # Browser automation and visual regression tests
+└── .github/ # Architecture, coding standards, and development documentation
+```
+
+## Development Workflow
+
+1. **Branch** — Create a branch from `main` blazor toolkit repository
+2. **Change** — Make your change. All PRs target the `main` branch
+3. **Test** — Run `dotnet test` and confirm no linter warnings before opening a PR
+4. **PR** — Open a pull request against `main`. Fill out the PR template completely
+5. **Review** — Two maintainers review. We aim to respond within 5 business days
+6. **Merge** — PRs are merged after approval and passing CI checks
+
+For full details on commit style, PR requirements, and review criteria, see the [Contributing Guide](./.github/CONTRIBUTING.md).
## Getting Started
- [Install .NET](https://dotnet.microsoft.com/download) (8.0 or later recommended)
-- [Syncfusion Blazor Toolkit Documentation](https://blazor.syncfusion.com/documentation/toolkit/overview) *(update when live)*
-- [Development Guide](/.github/DEVELOPMENT.md)
-
-## Controls List
-
-| **Category** | **Control** | **Description** |
-|----------------|----------------------------|---------------------------------------------------------------------------------|
-| Data Viz | Charts | Versatile charting component for rendering interactive data visualizations like line, bar, pie, and more with zooming, tooltips, and legends. |
-| Buttons | Button | Customizable button with support for icons, predefined styles (primary, success, etc.), sizes, and states like disabled or loading. |
-| Buttons | ButtonGroup | Groups multiple buttons together for unified styling and actions, ideal for toolbars or segmented controls. |
-| Buttons | Checkbox | Toggleable input for single or grouped selections with customizable labels, states, and indeterminate mode. |
-| Buttons | Radio Button | Grouped selection control allowing single choice from options, with customizable appearance and accessibility support. |
-| Buttons | Toggle Switch Button | On/off toggle control (like a switch) for boolean inputs, with customizable labels and states. |
-| Calendars | Calendar | Interactive monthly calendar view for date selection with navigation, multi-select, and range highlighting. |
-| Calendars | DatePicker | Popup calendar input for selecting single dates with formatting, validation, and culture support. |
-| Calendars | DateTime Picker | Combined date and time selector with calendar popup and time spinner for precise datetime input. |
-| Calendars | TimePicker | Time selection input with spinner or list view, supporting 12/24-hour formats and intervals. |
-| Inputs | File Upload | Drag-and-drop or browse file input with progress tracking, multiple file support, and validation. |
-| Inputs | Numeric TextBox | Input for numeric values with formatting, spin buttons, decimals, min/max ranges, and culture support. |
-| Inputs | TextArea | Multi-line text input with auto-resize, character counter, and floating label support. |
-| Inputs | Textbox | Single-line text input with floating labels, icons, validation states, and clear button. |
-| Layout | Dialog | Modal/popup window for alerts, forms, or confirmations with drag, resize, and animation support. |
-| Layout | Tooltip | Lightweight popup that displays contextual information when users hover over, focus on, or interact with a target element, with customizable positioning and animation support. |
-| Notification | Spinner | Loading indicator with customizable size, type, and overlay for async operations. |
+- [Syncfusion Blazor Toolkit Documentation](https://blazor.syncfusion.com/documentation/toolkit/overview) (in active development — contributor-focused docs in [DEVELOPMENT.md](./.github/DEVELOPMENT.md))
+- [Development Guide](./.github/DEVELOPMENT.md)
+
+## Components
+
+| Category | Control | Description |
+|----------|---------|-------------|
+| Data Viz | Chart | Versatile charting component for rendering interactive data visualizations like line, bar, pie, and more with zooming, tooltips, and legends. |
+| Buttons | Button | Customizable button with support for icons, predefined styles (primary, success, etc.), sizes, and states like disabled or loading. |
+| Buttons | ButtonGroup | Groups multiple buttons together for unified styling and actions, ideal for toolbars or segmented controls. |
+| Buttons | Checkbox | Toggleable input for single or grouped selections with customizable labels, states, and indeterminate mode. |
+| Buttons | Radio Button | Grouped selection control allowing single choice from options, with customizable appearance and accessibility support. |
+| Buttons | Toggle Switch | On/off toggle control (like a switch) for boolean inputs, with customizable labels and states. |
+| Calendars | Calendar | Interactive monthly calendar view for date selection with navigation, multi-select, and range highlighting. |
+| Calendars | DatePicker | Popup calendar input for selecting single dates with formatting, validation, and culture support. |
+| Calendars | DateTime Picker | Combined date and time selector with calendar popup and time spinner for precise datetime input. |
+| Calendars | TimePicker | Time selection input with spinner or list view, supporting 12/24-hour formats and intervals. |
+| Inputs | File Upload | Drag-and-drop or browse file input with progress tracking, multiple file support, and validation. |
+| Inputs | Numeric TextBox | Input for numeric values with formatting, spin buttons, decimals, min/max ranges, and culture support. |
+| Inputs | TextArea | Multi-line text input with auto-resize, character counter, and floating label support. |
+| Inputs | Textbox | Single-line text input with floating labels, icons, validation states, and clear button. |
+| Layout | Dialog | Modal/popup window for alerts, forms, or confirmations with drag, resize, and animation support. |
+| Layout | Tooltip | Lightweight popup that displays contextual information when users hover over, focus on, or interact with a target element, with customizable positioning and animation support. |
+| Notification | Spinner | Loading indicator with customizable size, type, and overlay for async operations. |
## Installation
@@ -52,7 +128,7 @@ Alternatively, add it directly in your `.csproj` file:
## Setup in Your Blazor App
-To use the Syncfusion® Blazor Toolkit, register the Syncfusion Blazor services in your `Program.cs` file as follows:
+To use the [Syncfusion® Blazor Toolkit](https://www.syncfusion.com/blazor-toolkit), register the Syncfusion Blazor Toolkit services in your `Program.cs` file as follows:
**Program.cs**
@@ -79,7 +155,6 @@ var app = builder.Build();
Add the following imports to your `_Imports.razor` file:
```razor
-@using Syncfusion.Blazor
@using Syncfusion.Blazor.Toolkit
```
@@ -88,7 +163,7 @@ Add the following imports to your `_Imports.razor` file:
Add the Syncfusion Blazor Toolkit styles to the `` section of your `App.razor` file:
```html
-@* Add syncfusion blazor toolkit style reference *@
+@* Add syncfusion blazor toolkit style reference *@
```
@@ -96,7 +171,7 @@ Add the Syncfusion Blazor Toolkit styles to the `` section of your `App.ra
Here's a quick example to get you started with one of the controls, such as the Chart:
-The following Razor code demonstrates how to set up a basic `SfChart` using the Syncfusion® Blazor Toolkit. This code snippet should be included in a `.razor` page of your Blazor project. It sets up the necessary namespaces, binds data to the component, and configures the `SfChart` with two spline area series for comparing Online vs Retail sales data.
+The following Razor code demonstrates how to set up a basic `SfChart` using the [Syncfusion® Blazor Toolkit](https://www.syncfusion.com/blazor-toolkit). This code snippet should be included in a `.razor` page of your Blazor project. It sets up the necessary namespaces, binds data to the component, and configures the `SfChart` with two spline area series for comparing Online vs Retail sales data.
**Pages/ChartExample.razor**
@@ -109,7 +184,7 @@ The following Razor code demonstrates how to set up a basic `SfChart` using the
-
+
+ Opacity="0.5" />
@@ -182,14 +257,26 @@ public class ChartDataPoint
## Support
-For any other queries, reach our [Syncfusion support team](https://blazortoolkit.syncfusion.com/support/tickets/) through ticket.
+### Community Support (Open Source)
+
+- **[GitHub Issues](https://github.com/syncfusion/blazor-toolkit/issues)** — Bug reports and bug-fix PRs
+- **[GitHub Discussions](https://github.com/syncfusion/blazor-toolkit/discussions)** — Ideas, questions, and feature proposals before opening a PR
+
+Response time for community channels is best-effort; we aim to acknowledge within 5 business days.
+
+### Commercial Support
+
+- **[Syncfusion Blazor Components](https://www.syncfusion.com/blazor-components)** — Licensed commercial components with additional enterprise features and dedicated support.
+- **Toolkit-specific inquiries** — For paid support, licensing, and toolkit-specific questions: [submit a ticket](https://blazortoolkit.syncfusion.com/support/tickets/).
## Contributing
-Contributions are welcome! If you'd like to contribute, please check out our [contributing guide](./.github/CONTRIBUTING.md) for details on how to get started. Whether you find a bug, have a feature request, or want to submit code, we appreciate your help in improving the toolkit.
+Contributions are welcome! If you'd like to contribute, check out our [contributing guide](./.github/CONTRIBUTING.md) for details on how to get started. Whether you find a bug, have a feature request, or want to submit code, we appreciate your help in improving the toolkit.
See the [Development Guide](./.github/DEVELOPMENT.md) for more details about this repository and project structure.
+Review our [Code of Conduct](./.github/CODE_OF_CONDUCT.md) — all community interactions are expected to follow it.
+
## About Syncfusion®
Founded in 2001 and headquartered in Research Triangle Park, N.C., Syncfusion® has more than 35,000 customers and more than 1 million users, including large financial institutions, Fortune 500 companies, and global IT consultancies.
diff --git a/samples/Blazor.Toolkit.Samples.Client/Layout/NavMenu.razor b/samples/Blazor.Toolkit.Samples.Client/Layout/NavMenu.razor
index 3f70e37..670d9e1 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Layout/NavMenu.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Layout/NavMenu.razor
@@ -36,13 +36,13 @@
Right-To-Left
- State Persistence
+ State Persistence
- Globalization
+ Globalization
- Component Test Matrix
+ Component Test Matrix
@@ -129,7 +129,7 @@
Dialog
- Tooltip
+ Tooltip
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonGroup.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonGroup.razor
index f008687..ee2662b 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonGroup.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonGroup.razor
@@ -30,7 +30,7 @@
Vertical Orientation
- Set the ButtonGroup orientation to vertical by using the property IsVertical="true". This stacks the buttons vertically and can be combined with variants such as e-flat and e-outline.
+ Set the ButtonGroup orientation to vertical by using the property IsVertical . This stacks the buttons vertically and can be combined with variants such as e-flat and e-outline.
@@ -66,7 +66,7 @@
Selection Type
- ButtonGroup can behave like a segmented control with single or multiple selection using the built-in selection model.
+ ButtonGroup can behave like a segmented control with single or multiple selection using the built-in Mode selection model.
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonPage.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonPage.razor
index 8833d35..4293626 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonPage.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Buttons/ButtonPage.razor
@@ -15,7 +15,7 @@
Blazor Toolkit Button Component
- The Button component enables user interactions such as submitting forms, toggling states, and invoking actions.
+ The Button component enables user interactions such as submitting forms, toggling states, and invoking actions.
This sample demonstrates all Button features, including visual variants, semantic colors, sizes, icons,
toggle functionality, disabled states, and form integration. The default Button renders without any styling
classes and is suitable for simple or secondary actions.
@@ -46,6 +46,7 @@
This visual type is ideal for secondary actions or providing visual distinction while maintaining a clean, modern appearance.
You can combine the outline style with semantic color classes like e-info, e-success,
e-warning, and e-danger to communicate the intent of the action.
+ Customize the appearance using the CssClass property.
@@ -149,7 +150,7 @@
Icons
- Add visual meaning to actions using icons via the IconCss property. Position icons on the left,
+ Add visual meaning to actions using icons via the IconCss property. Position icons on the left,
right, top, or bottom of the Button with IconPosition. For icon‑only Buttons, include an
accessible aria-label.
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/Calendar.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/Calendar.razor
index b3cdc02..7ac0a7c 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/Calendar.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/Calendar.razor
@@ -9,7 +9,7 @@
Blazor Toolkit Calendar Component
- The Blazor Calendar component provides an intuitive interface for date selection and navigation. It offers a comprehensive set of features including multiple view modes, multi-selection, week number and accessibility support for building robust date-picking experiences.
+ The Blazor Calendar component provides an intuitive interface for date selection and navigation. It offers a comprehensive set of features including multiple view modes, multi-selection, week number and accessibility support for building robust date-picking experiences.
@@ -24,7 +24,7 @@
Year And Decade Views
- The Calendar component supports multiple view modes including month, year, and decade views. Users can switch between different views using the Start and Depth properties to control the initial view and navigation depth.
+ The Calendar component supports multiple view modes including month, year, and decade views. Users can switch between different views using the Start and Depth properties to control the initial view and navigation depth.
@@ -48,7 +48,7 @@
Date Range
- The Min and Max properties used to control date selection by setting minimum and maximum selectable dates. This ensures users can only select dates within the specified range, making it ideal for booking systems and date-restricted scenarios.
+ The Min and Max properties used to control date selection by setting minimum and maximum selectable dates. This ensures users can only select dates within the specified range, making it ideal for booking systems and date-restricted scenarios.
@@ -63,7 +63,7 @@
Multi Selection
- The IsMultiSelection property enable users to select multiple non-consecutive dates. This is useful for scheduling events, selecting date ranges, or marking multiple important dates.
+ The IsMultiSelection property enable users to select multiple non-consecutive dates. This is useful for scheduling events, selecting date ranges, or marking multiple important dates.
@@ -78,7 +78,7 @@
Special Dates
- Customize specific dates in a Blazor Calendar by handling the DayCellRendering event. This event fires for each day cell as it is created, allowing the addition of CSS classes and, if needed, disabling particular dates. The following example highlights two sets of days in the current month with custom styles using the personal-appointment and official-appointment classes, and updates a label on selection via ValueChange event.
+ Customize specific dates in a Blazor Calendar by handling the DayCellRendering event. This event fires for each day cell as it is created, allowing the addition of CSS classes and, if needed, disabling particular dates. The following example highlights two sets of days in the current month with custom styles using the personal-appointment and official-appointment classes, and updates a label on selection via ValueChange event.
@@ -98,7 +98,7 @@
Islamic Calendar
- The Blazor Calendar component supports displaying the Islamic (Hijri) Calendar. The Hijri Calendar is a lunar Calendar with 12 months and 354 or 355 days per year. To render the Islamic Calendar, set the CalendarMode property to CalendarType.Islamic. This switches the Calendar system used for display and selection.
+ The Blazor Calendar component supports displaying the Islamic (Hijri) Calendar. The Hijri Calendar is a lunar Calendar with 12 months and 354 or 355 days per year. To render the Islamic Calendar, set the CalendarMode property to CalendarType.Islamic. This switches the Calendar system used for display and selection.
@@ -113,7 +113,7 @@
Week Number
- The WeekNumber property is used to display week numbers alongside the Calendar dates. This feature is particularly useful for business applications that reference ISO week numbers for planning and reporting purposes. Configure how the first week of the year is determined by using the WeekRule property (aligned with .NET CalendarWeekRule semantics).
+ The WeekNumber property is used to display week numbers alongside the Calendar dates. This feature is particularly useful for business applications that reference ISO week numbers for planning and reporting purposes. Configure how the first week of the year is determined by using the WeekRule property (aligned with .NET CalendarWeekRule semantics).
@@ -128,7 +128,7 @@
First Day Of Week
- The Calendar provides an option to change the first day of the week by using the FirstDayOfWeek property. Generally, the day of the week starts from 0 (Sunday) and ends with 6 (Saturday).
+ The Calendar provides an option to change the first day of the week by using the FirstDayOfWeek property. Generally, the day of the week starts from 0 (Sunday) and ends with 6 (Saturday).
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DatePicker.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DatePicker.razor
index b1cd030..cc44a17 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DatePicker.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DatePicker.razor
@@ -9,7 +9,7 @@
Blazor Toolkit Date Picker Component
- The Blazor DatePicker component provides an intuitive interface for date selection and navigation. It offers a comprehensive set of features including multiple view modes, date range restrictions, custom rendering, and accessibility support for building robust date-picking experiences.
+ The Blazor DatePicker component provides an intuitive interface for date selection and navigation. It offers a comprehensive set of features including multiple view modes, date range restrictions, custom rendering, and accessibility support for building robust date-picking experiences.
@@ -24,7 +24,7 @@
Two-Way Binding
- Two-way binding can be achieved by using bind-Value attribute, which supports string, int, Enum, DateTime, bool types. If the component value has been changed, it will affect all places where the variable is bound for the bind-value attribute.
+ Two-way binding can be achieved by using bind-Value attribute, which supports string, int, Enum, DateTime, bool types. If the component value has been changed, it will affect all places where the variable is bound for the bind-value attribute.
@@ -44,7 +44,7 @@
Date Format
- The Format property allows you to define how the selected date is displayed in the input field. Additionally, the InputFormats property defines a list of custom formats that the DatePicker accepts when a user manually enters a date, providing flexibility for different date entry styles.
+ The Format property allows you to define how the selected date is displayed in the input field. Additionally, the InputFormats property defines a list of custom formats that the DatePicker accepts when a user manually enters a date, providing flexibility for different date entry styles.
@@ -59,7 +59,7 @@
Date Range
- The Min and Max properties allow you to restrict the range of dates that a user can select. Any dates outside of this range will be disabled in the calendar popup, and manual entry of out-of-range dates will be invalidated.
+ The Min and Max properties allow you to restrict the range of dates that a user can select. Any dates outside of this range will be disabled in the calendar popup, and manual entry of out-of-range dates will be invalidated.
@@ -74,7 +74,7 @@
Strict Mode
- By default, the DatePicker allows users to enter any date, but if the entered date is outside the Min and Max range, it will be automatically reset to the nearest valid date when StrictMode is enabled. This ensures the component always holds a value within the specified boundaries.
+ By default, the DatePicker allows users to enter any date, but if the entered date is outside the Min and Max range, it will be automatically reset to the nearest valid date when StrictMode is enabled. This ensures the component always holds a value within the specified boundaries.
@@ -89,7 +89,7 @@
Start And Depth View
- The Start property specifies the initial view when the calendar is opened (e.g., Year, Decade), while the Depth property restricts the view navigation level (e.g., to Month, Year). This allows for quick selection of years or decades without drilling down to specific days.
+ The Start property specifies the initial view when the calendar is opened (e.g., Year, Decade), while the Depth property restricts the view navigation level (e.g., to Month, Year). This allows for quick selection of years or decades without drilling down to specific days.
@@ -104,7 +104,7 @@
Floating Label
- Enable floating labels by setting the FloatLabelType property. Floating labels move above the input field when focused or filled, providing a clean interface that saves vertical space.
+ Enable floating labels by setting the FloatLabelType property. Floating labels move above the input field when focused or filled, providing a clean interface that saves vertical space.
@@ -119,7 +119,7 @@
Mask Support
- The masking feature allows users to enter a date in the correct format, as specified by the Format property. This helps to ensure that the date is entered correctly and can also make it easier for users to understand how to enter the date. The EnableMask property in the DatePicker component allows you to enable or disable the masking functionality. When enabled, the input field will be displayed as masked with a specific date format pattern for entering the date.
+ The masking feature allows users to enter a date in the correct format, as specified by the Format property. This helps to ensure that the date is entered correctly and can also make it easier for users to understand how to enter the date. The EnableMask property in the DatePicker component allows you to enable or disable the masking functionality. When enabled, the input field will be displayed as masked with a specific date format pattern for entering the date.
@@ -136,7 +136,7 @@
Islamic Mode
- The DatePicker control supports displaying the Islamic calendar (Hijri calendar). Islamic calendar or Hijri calendar is a lunar calendar consisting of 12 months in a year of 354 or 355 days.Users can either select a date from the Islamic calendar or manually enter a date. Additionally, you can use the ConvertToHijri and ConvertToGregorian methods to parse dates.
+ The DatePicker control supports displaying the Islamic calendar (Hijri calendar). Islamic calendar or Hijri calendar is a lunar calendar consisting of 12 months in a year of 354 or 355 days.Users can either select a date from the Islamic calendar or manually enter a date. Additionally, you can use the ConvertToHijri and ConvertToGregorian methods to parse dates.
@@ -151,7 +151,7 @@
Week Number
- You can enable WeekNumber in the DatePicker by using the WeekNumber property. Configure how the first week of the year is determined by using the WeekRule property (aligned with .NET CalendarWeekRule semantics).
+ You can enable WeekNumber in the DatePicker by using the WeekNumber property. Configure how the first week of the year is determined by using the WeekRule property (aligned with .NET CalendarWeekRule semantics).
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DateTimePicker.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DateTimePicker.razor
index 6fa81a6..10816a8 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DateTimePicker.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/DateTimePicker.razor
@@ -10,7 +10,7 @@
Blazor Toolkit DateTimePicker Component
- The Blazor DateTimePicker component provides a seamless interface for choosing both date and time in a single, unified control. It supports multiple display modes, customizable formats, validation rules, and accessibility features for precise date‑time input.
+ The Blazor DateTimePicker component provides a seamless interface for choosing both date and time in a single, unified control. It supports multiple display modes, customizable formats, validation rules, and accessibility features for precise date‑time input.
@@ -29,7 +29,7 @@
This sample demonstrates disabled dates functionality in the DateTimePicker component. All weekends (Saturday and Sunday) of a month are disabled and restricted from selection.
- The Disabled Dates example shows how to disable specific dates in the DateTimePicker using the DayCellRendering event. This event triggers on each day cell element creation, allowing customization or disabling of specific dates.
+ The Disabled Dates example shows how to disable specific dates in the DateTimePicker using the DayCellRendering event. This event triggers on each day cell element creation, allowing customization or disabling of specific dates.
In this example, weekend dates are disabled using the DayCellRendering event by adding appropriate CSS classes to restrict selection.
@@ -50,7 +50,7 @@
This sample demonstrates how to highlight specific dates in the calendar popup of the DateTimePicker component with custom styling.
- The Special Dates example shows how to customize specific dates using the DayCellRendering event. This event triggers on each day cell element creation, allowing custom styling and customization.
+ The Special Dates example shows how to customize specific dates using the DayCellRendering event. This event triggers on each day cell element creation, allowing custom styling and customization.
In this example, weekend dates are disabled using the DayCellRendering event by adding appropriate CSS classes to restrict selection.
@@ -74,11 +74,11 @@
This sample demonstrates date and time range selection in the DateTimePicker component.
- Date and time selection is restricted within specific ranges defined by the Min, Max, MinTime, and MaxTime properties.
+ Date and time selection is restricted within specific ranges defined by the Min , Max , MinTime , and MaxTime properties.
All other dates and times are out of range and restricted.
- In this example, the DateTimePicker range is restricted from 7th to 27th days of current month and the time is restriced from 10:00 AM to 7:00 PM.
+ In this example, the DateTimePicker range is restricted from 7th to 27th days of current month and the time is restriced from 10:00 AM to 8:30 PM.
@@ -97,7 +97,7 @@
The display format defines how the date and time value is shown (and parsed) in the DateTimePicker.
By default, the DateTimePicker’s format is based on the current culture.
- You can also apply a custom or standard .NET date and time format by using the Format property.
+ You can also apply a custom or standard .NET date and time format by using the Format property.
@@ -114,8 +114,8 @@
- The masking feature guides users to enter date and time values that match the display format defined by the Format property.
- Enable or disable masking using the EnableMask property.
+ The masking feature guides users to enter date and time values that match the display format defined by the Format property.
+ Enable or disable masking using the EnableMask property.
When enabled, the input shows a mask pattern derived from the configured format and the current culture (including localized separators and literals).
@@ -152,39 +152,39 @@
- Blur
+ Blur
Triggers when the input loses focus.
- ValueChange
+ ValueChange
Triggers when the DateTimePicker value is changed.
- OnClose
+ OnClose
Triggers when the DateTimePicker popup is closed.
- OnOpen
+ OnOpen
Triggers when the DateTimePicker popup is opened.
- Created
+ Created
Triggers when the DateTimePicker component is created.
- Destroyed
+ Destroyed
Triggers when the DateTimePicker component is destroyed.
- Focus
+ Focus
Triggers when the input element gets focus.
- Navigated
+ Navigated
Triggers when the the Calendar is navigated to another level or within the same level of view.
- DayCellRendering
+ DayCellRendering
Triggers before each day cell is rendered in the calendar.
@@ -217,7 +217,7 @@
The DateTimePicker retains its core features in Islamic mode, such as minimum and maximum date constraints, week numbers, first day of the week, right-to-left (RTL) support, start and depth views, localization, and the ability to highlight and customize specific dates.
- By default, the calendar mode is Gregorian. Enable Islamic mode by setting the CalendarMode property to CalendarType.Islamic. The selected value continues to be handled as a date/time value while the UI uses the Hijri calendar for display and navigation.
+ By default, the calendar mode is Gregorian. Enable Islamic mode by setting the CalendarMode property to CalendarType.Islamic. The selected value continues to be handled as a date/time value while the UI uses the Hijri calendar for display and navigation.
@@ -234,17 +234,17 @@
- The StrictMode property controls how typed input is validated against the configured Min and Max range.
+ The StrictMode property controls how typed input is validated against the configured Min and Max range.
When enabled, only valid date and time values within the specified range are accepted.
If the entered value is invalid, the component retains the previous valid value.
If the entered value is out of range, the component clamps the value to the nearest boundary (Min or Max).
- The following example demonstrates the DateTimePicker in StrictMode with a Min/Max range of 5/5/2019 2:00 AM to 5/25/2019 2:00 AM.
+ The following example demonstrates the DateTimePicker in StrictMode with a Min/Max range of @DateTime.Now.ToString("M/5/yyyy") 2:00 AM to @DateTime.Now.ToString("M/25/yyyy") 2:00 AM.
Only valid values within the range are accepted.
- If an out-of-range value such as 5/28/2019 is entered, the value is set to the Max value (5/25/2019 2:00 AM).
+ If an out-of-range value such as @DateTime.Now.ToString("M/28/yyyy") is entered, the value is set to the Max value (@DateTime.Now.ToString("M/25/yyyy") 2:00 AM).
If an invalid date is entered, the value remains at the previous valid value.
@@ -268,7 +268,7 @@
This sample demonstrates the week number and different week rules functionalities of the DateTimePicker component. Here, we have assigned FirstDay as the WeekRule for the DateTimePicker component.
- The DateTimePicker provides the WeekNumber and WeekRule properties to specify the rule for defining the first week of the year with options: FirstDay, FirstFullWeek, and FirstFourDayWeek.
+ The DateTimePicker provides the WeekNumber and WeekRule properties to specify the rule for defining the first week of the year with options: FirstDay, FirstFullWeek, and FirstFourDayWeek.
@@ -603,12 +603,12 @@ code {
@"
code{
- public DateTime StrictModeMinDate { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 05, 02, 00, 00);
+ public DateTime StrictModeMinDate { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 5, 02, 00, 00);
public DateTime StrictModeMaxDate { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 25, 02, 00, 00);
public DateTime? StrictModeDateValue { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 28, 02, 00, 00);
}
";
- public DateTime StrictModeMinDate { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 05, 02, 00, 00);
+ public DateTime StrictModeMinDate { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 5, 02, 00, 00);
public DateTime StrictModeMaxDate { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 25, 02, 00, 00);
public DateTime? StrictModeDateValue { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 28, 02, 00, 00);
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/TimePicker.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/TimePicker.razor
index ee8bae4..3117436 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/TimePicker.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Calendars/TimePicker.razor
@@ -10,13 +10,13 @@
Blazor Toolkit TimePicker Component
- The Blazor TimePicker component offers an intuitive interface for selecting time values with adjustable intervals and format options. It includes min/max restrictions, customizable display, templates, and accessibility support for efficient time entry across devices.
+ The Blazor TimePicker component offers an intuitive interface for selecting time values with adjustable intervals and format options. It includes min/max restrictions, customizable display, templates, and accessibility support for efficient time entry across devices.
-
+
@@ -25,20 +25,20 @@
Time Format
- The TimePicker provides an option to customize the display format in the component using the Format property.
+ The TimePicker provides an option to customize the display format in the component using the Format property.
@@ -48,15 +48,15 @@
Time Range
- TimePicker provides an option to select a time value within a specified range by using the Min and Max properties.
+ TimePicker provides an option to select a time value within a specified range by using the Min and Max properties.
The Min value should always be lesser than the Max value.
- The Value property depends on the Min/Max with respect to StrictMode property.
+ The Value property depends on the Min/Max with respect to StrictMode property.
-
+
@@ -65,7 +65,7 @@
Step Interval
- The TimePicker component supports the Step property, which sets the gap between consecutive time options in the list.
+ The TimePicker component supports the Step property, which sets the gap between consecutive time options in the list.
This makes time selection faster and more organized, helping users choose times in fixed intervals.
@@ -82,14 +82,14 @@
- The TimePicker component supports different label display modes through the FloatLabelType property.
+ The TimePicker component supports different label display modes through the FloatLabelType property.
This property controls how the label or placeholder text appears in relation to the input field.
The floating label behavior can be configured with the following options:
- Auto: The floating label appears above the input field when it is focused or has a value. This is the default state.
- Always: The floating label always remains above the input field.
- Never: The label never floats above the input field when the placeholder is available.
+ Auto : The floating label appears above the input field when it is focused or has a value. This is the default state.
+ Always : The floating label always remains above the input field.
+ Never : The label never floats above the input field when the placeholder is available.
@@ -98,15 +98,15 @@
Auto
-
+
Always
-
+
Never
-
+
@@ -119,11 +119,11 @@
The masking feature allows users to enter a time in the correct format, as specified by the Format property.
This helps to ensure that the time is entered correctly and can also make it easier for users to understand how to enter the time.
- The EnableMask property in the TimePicker component allows you to enable or disable the masking functionality.
+ The EnableMask property in the TimePicker component allows you to enable or disable the masking functionality.
When enabled, the input field will be displayed as masked with a specific time format pattern for entering the time.
- The TimePickerMaskPlaceholder directive allows you to set custom placeholder text for each segment of the time format in a TimePicker component.
+ The TimePickerMaskPlaceholder directive allows you to set custom placeholder text for each segment of the time format in a TimePicker component.
This can be used to provide additional context or instructions to the user about the expected format for the input.
To use the directive, include it in the component’s configuration along with the EnableMask property.
@@ -150,7 +150,7 @@
-
+
@@ -173,14 +173,14 @@
If you enter invalid time value like 9:00 tt, the value sets to the previous value.
- The following code demonstrates the DateTimePicker with StrictMode as true.
+ The following code demonstrates the TimePicker with StrictMode as true.
-
+
@@ -202,35 +202,35 @@
- Blur
+ OnBlur
Triggers when the input loses focus.
- ValueChange
+ ValueChange
Triggers when the TimePicker value is changed.
- OnClose
+ OnClose
Triggers when the TimePicker popup is closed.
- OnOpen
+ OnOpen
Triggers when the TimePicker popup is opened.
- Created
+ Created
Triggers when the TimePicker component is created.
- Destroyed
+ Destroyed
Triggers when the TimePicker component is destroyed.
- Focus
+ OnFocus
Triggers when the input element gets focus.
- OnItemRender
+ OnItemRender
Triggers while rendering each popup list item.
@@ -252,18 +252,18 @@
@code {
//Default
- private string DefaultCode => @" ";
+ private string DefaultCode => @" ";
//TimeFormat
private string TimeFormatCode =>
@"
@code{
@@ -274,7 +274,7 @@
//TimeRange
private string TimeRangeCode =>
-@"
+@"
@code{
public DateTime MinVal { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 15, 09, 00, 00);
@@ -297,15 +297,15 @@
private string FloatLabelCode =>
@"
Auto (default)
-
+
Always
-
+
Never
-
+
";
//Mask
@@ -319,12 +319,12 @@ code {
public DateTime? MaskTimeValue { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 11, 11, 30, 00);
//TimeOnly
- private string TimeOnlyCode => @" ";
- public TimeOnly Value { get; set; } = new TimeOnly(12, 00, 00);
+ private string TimeOnlyCode => @" ";
+ public TimeOnly? Value { get; set; } = new TimeOnly(12, 00, 00);
//StrictMode
private string StrictModeCode =>
-@"
+@"
code{
public DateTime StrictModeMinTime { get; set; } = new DateTime(DateTime.Now.Year, DateTime.Now.Month, 15, 08, 00, 00);
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Checkbox.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Checkbox.razor
index bd5cde6..67800cc 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Checkbox.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Checkbox.razor
@@ -36,8 +36,8 @@
Types
- Common CheckBox states include Checked , Unchecked , Disabled , and Indeterminate .
- Use Disabled to prevent interaction, and enable tri‑state using EnableTriState to support the Indeterminate state.
+ Common CheckBox states include Checked, Unchecked, Disabled, and Indeterminate.
+ Use Disabled to prevent interaction, and enable tri‑state using EnableTriState to support the Indeterminate state.
@@ -60,7 +60,7 @@
Binding Value
- Bind the checked state using Blazor’s bind-Checked for two‑way binding. When you need custom logic during updates,
+ Bind the checked state using Blazor's bind-Checked for two‑way binding. When you need custom logic during updates,
use the explicit pattern with Checked and CheckedChanged.
@@ -90,7 +90,7 @@
Label & Placement
- Provide context using the Label property and choose its position with LabelPosition (Before or After).
+ Provide context using the Label property and choose its position with LabelPosition (Before or After).
The positioning adapts to RTL when enabled.
@@ -247,7 +247,7 @@
Label="I accept the terms" />
- Submit
+ Submit
@if (formSubmitted)
{
@@ -266,8 +266,8 @@
The parent checkbox reflects group status:
- Checked (all), Unchecked (none), and Indeterminate (some). Clicking the parent only performs
- two states (check all / uncheck all); the Indeterminate state is shown programmatically based on child selections.
+ Checked (all), Unchecked (none), and Indeterminate (some). Clicking the parent only performs
+ two states (check all / uncheck all); the Indeterminate state is shown programmatically based on child selections.
@@ -521,7 +521,7 @@
Label=""I accept the terms"" />
formModel.Accept"" />
- Submit
+ Submit
@if (formSubmitted)
{
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/NumericTextbox.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/NumericTextbox.razor
index 5162ba7..b5df67d 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/NumericTextbox.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/NumericTextbox.razor
@@ -22,7 +22,7 @@
One-Way Binding
- Bind the value using the Value parameter (no two-way sync). Updating the backing field programmatically reflects in the UI.
+ Bind the value using the Value parameter (no two-way sync). Updating the backing field programmatically reflects in the UI.
@@ -43,7 +43,7 @@
Two-Way Binding
- Use bind-Value for two-way synchronization between the component and the bound field.
+ Use bind-Value for two-way synchronization between the component and the bound field.
@@ -65,7 +65,7 @@
Percentage Format
- Apply Format="P2" to display the value as a percentage when unfocused; underlying value remains numeric.
+ Apply Format with "P2" to display the value as a percentage when unfocused; underlying value remains numeric.
@@ -83,7 +83,7 @@
Currency Format
- Use Format="C2" to render a currency using the current culture’s currency symbol and separators.
+ Use Format with "C2" to render a currency using the current culture's currency symbol and separators.
@@ -153,7 +153,7 @@
Events
- Wire component events such as Created , Focus , Blur , ValueChange .
+ Wire component events such as Created , Focus , Blur , ValueChange .
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/RadioButton.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/RadioButton.razor
index ff2a8a7..692b68f 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/RadioButton.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/RadioButton.razor
@@ -43,8 +43,8 @@
Label Placement
- The Label property provides contextual text next to the Radio Button. Use the
- LabelPosition property to place the label either Before or After the radio.
+ The Label property provides contextual text next to the Radio Button. Use the
+ LabelPosition property to place the label either Before or After the radio.
Positioning automatically adapts when using RTL layouts.
diff --git a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Switch.razor b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Switch.razor
index 77f7c27..c121acb 100644
--- a/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Switch.razor
+++ b/samples/Blazor.Toolkit.Samples.Client/Pages/Components/Inputs/Switch.razor
@@ -22,7 +22,7 @@
Basic Usage
- The simplest way to use SfSwitch is through bind-Checked property for two‑way binding.
+ The simplest way to use SfSwitch is through bind-Checked property for two‑way binding.
@@ -40,7 +40,7 @@
Value Binding
- You can control the switch using either Checked or CheckedChanged events, depending on your binding style.
+ You can control the switch using either Checked or CheckedChanged events, depending on your binding style.
@@ -70,7 +70,7 @@
The Switch component supports both external labels and built‑in state labels.
External labels (using the label element) describe what the switch controls.
- Built‑in labels, configured using the OnLabel and OffLabel properties, display text inside the switch to indicate its ON or OFF state.
+ Built‑in labels, configured using the OnLabel and OffLabel properties, display text inside the switch to indicate its ON or OFF state.
@@ -93,7 +93,7 @@
States
- The switch can render in multiple states, including interactive and disabled modes. You can control availability using Disabled property
+ The switch can render in multiple states, including interactive and disabled modes. You can control availability using Disabled property
@@ -150,7 +150,7 @@
}