Skip to content

Conversation

@ArgoZhang
Copy link
Member

@ArgoZhang ArgoZhang commented Feb 13, 2026

Link issues

fixes #7664

Summary By Copilot

Regression?

  • Yes
  • No

Risk

  • High
  • Medium
  • Low

Verification

  • Manual (required)
  • Automated

Packaging changes reviewed?

  • Yes
  • No
  • N/A

☑️ Self Check before Merge

⚠️ Please check all items below before review. ⚠️

  • Doc is updated/provided or not needed
  • Demo is updated/provided or not needed
  • Merge the latest code from the main branch

Summary by Sourcery

Add support for resetting and re-rendering the table column list UI when its display mode changes, and update the sample to demonstrate the new behavior.

New Features:

  • Introduce a resetColumnList client-side method and wire it from the Table component to reset the column list dropdown/popover when configuration changes.
  • Add new Table parameters and sample controls to toggle column list visibility mode and controls at runtime.

Enhancements:

  • Make the Table JavaScript init flow async and ensure reset logic runs accordingly.
  • Adjust dropdown/popover styling via a new CSS class so column list popovers share consistent sizing with standard dropdowns.
  • Clean up minor JavaScript code style issues in table and base popover modules.

Documentation:

  • Extend localized sample text to describe the new column list popover toolbar dropdown option.

Copilot AI review requested due to automatic review settings February 13, 2026 00:53
@bb-auto bb-auto bot added the enhancement New feature or request label Feb 13, 2026
@bb-auto bb-auto bot added this to the v10.3.0 milestone Feb 13, 2026
@sourcery-ai
Copy link
Contributor

sourcery-ai bot commented Feb 13, 2026

Reviewer's Guide

Adds client- and server-side support for resetting the Table column list popover/dropdown mode at runtime, including a new JavaScript entry point, state tracking in the Table component, styling for popover dropdown menus, and sample/demo wiring with localization updates.

Sequence diagram for resetting Table column list popover/dropdown mode at runtime

sequenceDiagram
    actor User
    participant TablesColumnList as TablesColumnList
    participant Table as TableComponent
    participant JSInterop
    participant TableJs as TableJsModule
    participant BsDropdown as BootstrapDropdown
    participant PopoverModule as PopoverModule

    User->>TablesColumnList: Toggle IsPopoverToolbarDropdownButton switch
    activate TablesColumnList
    TablesColumnList-->>TablesColumnList: Update _isPopoverToolbarDropdownButton
    TablesColumnList-->>Table: Re-render with IsPopoverToolbarDropdownButton
    deactivate TablesColumnList

    Table->>Table: OnAfterRenderAsync(firstRender)
    alt First render
        Table-->>Table: _lastIsPopoverToolbarDropdownButtonValue = IsPopoverToolbarDropdownButton
        Table->>JSInterop: InvokeVoidAsync("init", Id)
        JSInterop->>TableJs: init(id, invoke, options)
        TableJs->>TableJs: reset(id)
    else Subsequent render
        Table-->>Table: Compare _lastIsPopoverPopoverToolbarDropdownButtonValue
        alt Mode changed
            Table-->>Table: _lastIsPopoverToolbarDropdownButtonValue = IsPopoverToolbarDropdownButton
            Table->>JSInterop: InvokeVoidAsync("resetColumnList", Id)
            JSInterop->>TableJs: resetColumnList(id)
            activate TableJs
            TableJs-->>TableJs: const table = Data.get(id)
            TableJs-->>TableJs: Find toolbar.dropdown-column
            TableJs->>BsDropdown: getInstance(button)
            alt Dropdown instance exists
                BsDropdown-->>TableJs: instance
                TableJs->>BsDropdown: dispose()
            end
            TableJs-->>TableJs: Find existing popover for dropdown
            alt Popover exists
                TableJs->>PopoverModule: dispose(p)
                TableJs-->>TableJs: Remove p from table.popovers
            end
            TableJs-->>TableJs: If button data-bs-toggle is bb.dropdown
            TableJs->>PopoverModule: init(dropdown, isDisabled)
            PopoverModule-->>TableJs: popoverInstance
            TableJs-->>TableJs: Push popoverInstance to table.popovers
            deactivate TableJs
        else Mode unchanged
            Table-->>Table: No JS interop call
        end
    end
Loading

Updated class diagram for Table component and TablesColumnList sample

classDiagram
    class TableComponent {
        +bool ShowColumnListControls
        +bool IsPopoverToolbarDropdownButton
        -bool _lastIsPopoverToolbarDropdownButtonValue
        -string DropdownListClassString
        +Task OnAfterRenderAsync(bool firstRender)
        +Task ProcessFirstRender()
        +Task InvokeVoidAsync(string identifier, string id)
    }

    class TablesColumnList {
        -TableComponent TableColumnVisible
        -bool _isPopoverToolbarDropdownButton
        -bool _showColumnListControls
        +Task OnInitializedAsync()
        +Task OnQueryAsync()
        +Task ResetVisibleColumns()
    }

    class TableJsModule {
        +async init(string id, object invoke, object options)
        +async reset(string id)
        +void saveColumnList(string tableName, object columns)
        +void resetColumnList(string id)
    }

    class PopoverModule {
        +object init(object element, object options)
        +void dispose(object popover)
    }

    TablesColumnList --> TableComponent : configures
    TableComponent --> TableJsModule : uses_JSInterop
    TableJsModule --> PopoverModule : manages_popovers
Loading

File-Level Changes

Change Details Files
Make table JS initialization async and ensure reset logic completes before returning.
  • Change Table.razor.js init function to be async
  • Await the reset(id) call during initialization so initial column list state and event wiring complete before init returns
  • Minor formatting cleanup around reset implementation
src/BootstrapBlazor/Components/Table/Table.razor.js
Introduce resetColumnList JS API to reinitialize the column list dropdown/popover and its popover instance.
  • Add resetColumnList(id) export that looks up the table in Data, finds the toolbar .dropdown-column element, and resets its dropdown and Popover instances
  • Dispose existing bootstrap.Dropdown instance and its Popover, update table.popovers list, and conditionally re-init a new Popover for bb.dropdown buttons
src/BootstrapBlazor/Components/Table/Table.razor.js
Track and react to changes of IsPopoverToolbarDropdownButton on the Table component to call the JS resetColumnList hook.
  • Add IsPopoverToolbarDropdownButton-dependent CSS class dropdown-menu-popover to DropdownListClassString
  • Introduce backing field _lastIsPopoverToolbarDropdownButtonValue to detect runtime changes
  • Initialize the backing field on first render and, on subsequent renders, when the flag changes, invoke the JS resetColumnList(Id) helper from OnAfterRenderAsync
src/BootstrapBlazor/Components/Table/Table.razor.cs
Adjust Table SCSS to support popover-styled column list dropdown menus with shared max-height behavior.
  • Define .dropdown-menu-popover with --bb-table-columnlist-max-height sourced from --bb-dropdown-max-height
  • Share the column list max-height styles between .table-toolbar .dropdown-column .dropdown-menu and .dropdown-menu-popover
src/BootstrapBlazor/Components/Table/Table.razor.scss
Update the Table column list sample to demo the new IsPopoverToolbarDropdownButton and ShowColumnListControls toggles.
  • Add UI controls (two switches) for IsPopoverToolbarDropdownButton and ShowColumnListControls along with a new localized description line
  • Wire these switches to backing fields _isPopoverToolbarDropdownButton and _showColumnListControls in the sample code-behind
  • Change the Table usage to bind ShowColumnList, ShowColumnListControls, and IsPopoverToolbarDropdownButton properties instead of hard-coded values and simplify other props accordingly
src/BootstrapBlazor.Server/Components/Samples/Table/TablesColumnList.razor
src/BootstrapBlazor.Server/Components/Samples/Table/TablesColumnList.razor.cs
Minor JS cleanup in base-popover and locale file updates for new sample text.
  • Remove an unnecessary BOM character and superfluous semicolon in base-popover.js
  • Update en-US.json and zh-CN.json localization files to include text for the new IsPopoverToolbarDropdownButton description (exact entries to be checked in diff)
src/BootstrapBlazor/wwwroot/modules/base-popover.js
src/BootstrapBlazor.Server/Locales/en-US.json
src/BootstrapBlazor.Server/Locales/zh-CN.json

Assessment against linked issues

Issue Objective Addressed Explanation
#7664 Add support in the Table component for a ResetColumnList method that can reset/reinitialize the column list UI behavior.
#7664 Update Table samples/docs to demonstrate and configure the new ResetColumnList-related behavior.

Possibly linked issues


Tips and commands

Interacting with Sourcery

  • Trigger a new review: Comment @sourcery-ai review on the pull request.
  • Continue discussions: Reply directly to Sourcery's review comments.
  • Generate a GitHub issue from a review comment: Ask Sourcery to create an
    issue from a review comment by replying to it. You can also reply to a
    review comment with @sourcery-ai issue to create an issue from it.
  • Generate a pull request title: Write @sourcery-ai anywhere in the pull
    request title to generate a title at any time. You can also comment
    @sourcery-ai title on the pull request to (re-)generate the title at any time.
  • Generate a pull request summary: Write @sourcery-ai summary anywhere in
    the pull request body to generate a PR summary at any time exactly where you
    want it. You can also comment @sourcery-ai summary on the pull request to
    (re-)generate the summary at any time.
  • Generate reviewer's guide: Comment @sourcery-ai guide on the pull
    request to (re-)generate the reviewer's guide at any time.
  • Resolve all Sourcery comments: Comment @sourcery-ai resolve on the
    pull request to resolve all Sourcery comments. Useful if you've already
    addressed all the comments and don't want to see them anymore.
  • Dismiss all Sourcery reviews: Comment @sourcery-ai dismiss on the pull
    request to dismiss all existing Sourcery reviews. Especially useful if you
    want to start fresh with a new review - don't forget to comment
    @sourcery-ai review to trigger a new review!

Customizing Your Experience

Access your dashboard to:

  • Enable or disable review features such as the Sourcery-generated pull request
    summary, the reviewer's guide, and others.
  • Change the review language.
  • Add, remove or edit custom review instructions.
  • Adjust other review settings.

Getting Help

Copy link
Contributor

@sourcery-ai sourcery-ai bot left a comment

Choose a reason for hiding this comment

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

Hey - I've found 1 issue, and left some high level feedback:

  • In resetColumnList (Table.razor.js), button is not null-checked before button.getAttribute('data-bs-toggle') is called, which can throw if the .dropdown-toggle element is missing; consider returning early or guarding that usage when button is falsy.
  • In TablesColumnList.razor, the ShowColumnListControls="_showColumnListControls" attribute is treated as a string literal rather than a C# expression; update it to ShowColumnListControls="@_showColumnListControls" so the property is correctly bound.
Prompt for AI Agents
Please address the comments from this code review:

## Overall Comments
- In `resetColumnList` (Table.razor.js), `button` is not null-checked before `button.getAttribute('data-bs-toggle')` is called, which can throw if the `.dropdown-toggle` element is missing; consider returning early or guarding that usage when `button` is falsy.
- In `TablesColumnList.razor`, the `ShowColumnListControls="_showColumnListControls"` attribute is treated as a string literal rather than a C# expression; update it to `ShowColumnListControls="@_showColumnListControls"` so the property is correctly bound.

## Individual Comments

### Comment 1
<location> `src/BootstrapBlazor/Components/Table/Table.razor.js:1004` </location>
<code_context>
     })
 }

+export function resetColumnList(id) {
+    const table = Data.get(id);
+    if (table) {
</code_context>

<issue_to_address>
**issue (complexity):** Consider simplifying resetColumnList by using early returns for null checks and extracting the dropdown/popover reset logic into a small helper function.

You can keep the new behavior while reducing nesting and making the control flow more linear by:

1. Guarding early for missing `table`, `toolbar`, `dropdown`, or `button`.
2. Extracting the dropdown/popover reset logic into a tiny helper so it’s not inlined inside the exported function.

For example:

```js
function resetDropdownPopover(table, dropdown, button) {
  const dropdownToggle = bootstrap.Dropdown.getInstance(button);
  if (dropdownToggle) {
    dropdownToggle.dispose();
  }

  const existingPopover = table.popovers.find(p => p.el === dropdown);
  if (existingPopover) {
    table.popovers = table.popovers.filter(p => p !== existingPopover);
    Popover.dispose(existingPopover);
  }

  if (button.getAttribute('data-bs-toggle') === 'bb.dropdown') {
    table.popovers.push(Popover.init(dropdown, {
      isDisabled: () => false
    }));
  }
}

export function resetColumnList(id) {
  const table = Data.get(id);
  if (!table || !table.toolbar) return;

  const dropdown = table.toolbar.querySelector('.dropdown-column');
  if (!dropdown) return;

  const button = dropdown.querySelector('.dropdown-toggle');
  if (!button) return;

  resetDropdownPopover(table, dropdown, button);
}
```

This keeps all current behavior (dispose/re-init dropdown and popover, update `table.popovers`) but:

- Flattens the control flow with early returns.
- Encapsulates the dropdown/popover reset pattern in one helper, so it’s easier to reuse wherever the column dropdown is initially set up.
- Avoids assuming `button` always exists, preventing a possible runtime error.
</issue_to_address>

Sourcery is free for open source - if you like our reviews please consider sharing them ✨
Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.

@codecov
Copy link

codecov bot commented Feb 13, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 100.00%. Comparing base (d49a9e8) to head (f2b9427).
⚠️ Report is 2 commits behind head on main.

Additional details and impacted files
@@            Coverage Diff            @@
##              main     #7665   +/-   ##
=========================================
  Coverage   100.00%   100.00%           
=========================================
  Files          749       749           
  Lines        33183     33196   +13     
  Branches      4604      4605    +1     
=========================================
+ Hits         33183     33196   +13     
Flag Coverage Δ
BB 100.00% <100.00%> (?)

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR implements a resetColumnList method for the Table component to support dynamically switching between dropdown and popover display modes for the column list toolbar button. The implementation detects when the IsPopoverToolbarDropdownButton property changes and properly reinitializes the dropdown/popover component on the client side.

Changes:

  • Added client-side resetColumnList JavaScript function to properly dispose and reinitialize the column list dropdown/popover
  • Implemented change detection in C# to track IsPopoverToolbarDropdownButton property changes and trigger the reset
  • Added CSS styling for popover mode and updated localization resources for the new feature

Reviewed changes

Copilot reviewed 8 out of 8 changed files in this pull request and generated 3 comments.

Show a summary per file
File Description
src/BootstrapBlazor/wwwroot/modules/base-popover.js Removed unnecessary semicolon and restored UTF-8 BOM encoding
src/BootstrapBlazor/Components/Table/Table.razor.scss Added CSS variable and styling for dropdown-menu-popover mode
src/BootstrapBlazor/Components/Table/Table.razor.js Made init and reset async, added new resetColumnList export function, minor code cleanup
src/BootstrapBlazor/Components/Table/Table.razor.cs Added change tracking for IsPopoverToolbarDropdownButton and logic to call resetColumnList when it changes
src/BootstrapBlazor.Server/Locales/zh-CN.json Added Chinese description for the new feature
src/BootstrapBlazor.Server/Locales/en-US.json Added English description for the new feature
src/BootstrapBlazor.Server/Components/Samples/Table/TablesColumnList.razor.cs Added state variables for demo controls
src/BootstrapBlazor.Server/Components/Samples/Table/TablesColumnList.razor Updated demo to showcase the new feature with toggle controls

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

@ArgoZhang ArgoZhang merged commit cd23901 into main Feb 13, 2026
4 checks passed
@ArgoZhang ArgoZhang deleted the dev-table-column-list branch February 13, 2026 01:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat(Table): support ResetColumnList method

1 participant