feat(Dropdown): add ItemsTemplate parameter#7046
Conversation
Reviewer's GuideImplements an ItemsTemplate parameter in the Dropdown component to allow fully customizable item rendering through a new DropdownItem component; updates the rendering logic and styling, extends unit tests to cover the new behavior, and adds a demo in the sample pages with an accompanying click handler. Sequence diagram for Dropdown with ItemsTemplate and DropdownItem clicksequenceDiagram
actor User
participant Dropdown
participant DropdownItem
participant ToastService
User->>Dropdown: Clicks dropdown button
Dropdown->>DropdownItem: Renders custom items via ItemsTemplate
User->>DropdownItem: Clicks item
DropdownItem->>DropdownItem: Checks IsDisabled
DropdownItem->>DropdownItem: Calls OnClickItem()
DropdownItem->>ToastService: Executes OnClick callback
ToastService-->>User: Shows notification
Class diagram for new DropdownItem component and updated DropdownclassDiagram
class DropdownItem {
+string? Text
+string? Icon
+bool Disabled
+Func<bool>? OnDisabledCallback
+Func<Task>? OnClick
+RenderFragment? ChildContent
-string? ItemIconString
-string? ItemClassString
-bool IsDisabled
-Task OnClickItem()
}
class Dropdown {
+RenderFragment? ItemsTemplate
-List<ComponentBase> _items
}
Dropdown "1" o-- "*" DropdownItem : uses via ItemsTemplate
File-Level Changes
Assessment against linked issues
Possibly linked issues
Tips and commandsInteracting with Sourcery
Customizing Your ExperienceAccess your dashboard to:
Getting Help
|
There was a problem hiding this comment.
Hey there - I've reviewed your changes and they look great!
Prompt for AI Agents
Please address the comments from this code review:
## Individual Comments
### Comment 1
<location> `src/BootstrapBlazor/Components/Dropdown/DropdownItem.razor.cs:57` </location>
<code_context>
+ .AddClass("disabled", IsDisabled)
+ .Build();
+
+ private bool IsDisabled => OnDisabledCallback?.Invoke() ?? Disabled;
+
+ private async Task OnClickItem()
</code_context>
<issue_to_address>
**issue (bug_risk):** OnDisabledCallback may throw if it throws an exception.
Wrap OnDisabledCallback.Invoke() in a try/catch to prevent exceptions from disrupting dropdown rendering.
</issue_to_address>
### Comment 2
<location> `src/BootstrapBlazor/Components/Dropdown/DropdownItem.razor:11-15` </location>
<code_context>
+{
+ <DynamicElement class="@ItemClassString"
+ TriggerClick="!IsDisabled" OnClick="OnClickItem">
+ <i class="@ItemIconString"></i>
+ <span>@Text</span>
+ </DynamicElement>
</code_context>
<issue_to_address>
**suggestion:** Rendering an empty <i> element if Icon is not set.
Consider rendering the <i> element only when Icon is provided to prevent unnecessary empty elements in the DOM.
```suggestion
<DynamicElement class="@ItemClassString"
TriggerClick="!IsDisabled" OnClick="OnClickItem">
@if (!string.IsNullOrEmpty(ItemIconString))
{
<i class="@ItemIconString"></i>
}
<span>@Text</span>
</DynamicElement>
```
</issue_to_address>
### Comment 3
<location> `test/UnitTest/Components/DropdownTest.cs:325-332` </location>
<code_context>
+ cut.Contains("fa-solid fa-icon3");
+ cut.Contains("dropdown-item-test3");
+
+ cut.DoesNotContain("fa-solid fa-icon4");
+ cut.DoesNotContain("dropdown-item-test4");
+ cut.Contains("dropdown-item-childcontent");
+
+ cut.Contains("dropdown-item disabled");
</code_context>
<issue_to_address>
**suggestion (testing):** Suggestion to add explicit assertions for disabled item click behavior.
Add an assertion to confirm that clicking a disabled DropdownItem does not trigger its OnClick handler or change the 'clicked' state.
```suggestion
cut.Contains("dropdown-item disabled");
Assert.False(clicked);
// Find the disabled dropdown item and try to click it
var disabledItem = cut.Find(".dropdown-item.disabled");
await cut.InvokeAsync(() => disabledItem.Click());
// Assert that clicking the disabled item does not change the clicked state
Assert.False(clicked);
var item = cut.Find(".dropdown-item:not(.disabled)");
await cut.InvokeAsync(() => item.Click());
Assert.True(clicked);
}
```
</issue_to_address>Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #7046 +/- ##
=========================================
Coverage 100.00% 100.00%
=========================================
Files 743 745 +2
Lines 32480 32515 +35
Branches 4500 4506 +6
=========================================
+ Hits 32480 32515 +35
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
Link issues
fixes #7045
Summary By Copilot
Regression?
Risk
Verification
Packaging changes reviewed?
☑️ Self Check before Merge
Summary by Sourcery
Add ItemsTemplate support to the Dropdown component by introducing a new DropdownItem component for customizable items, update styling and sample page, and extend tests for the new functionality
New Features:
Enhancements:
Documentation:
Tests: