Skip to content

fix: skip default select when interactions already registers element-select - #4696

Open
dyk1454683243-sudo wants to merge 2 commits into
VisActor:developfrom
dyk1454683243-sudo:cursor/fix-interactions-ismultiple-default-select-4563-e3ac
Open

dyk1454683243-sudo wants to merge 2 commits into
VisActor:developfrom
dyk1454683243-sudo:cursor/fix-interactions-ismultiple-default-select-4563-e3ac

Conversation

@dyk1454683243-sudo

@dyk1454683243-sudo dyk1454683243-sudo commented Sep 20, 2026 •

Copy link
Copy Markdown
Contributor

Fixes #4563

🤔 This is a ...

  • Bug fix
  • Test Case

🔗 Related issue link

Fixes #4563

💡 Background and solution

Specs that follow the official pie multi-select example:

interactions: [{ type: 'element-select', isMultiple: true }]

could not keep more than one sector selected.

Default select.enable: true still registered a single-select element-select trigger (pointertap, replace). The spec interactions entry registered a second one (click, accumulate). Those configs are not isEqual, so BaseChart._initInteractions kept both live. On click, default select applied selected first; the multi-select trigger then saw hasState and did nothing.

This change skips the default select trigger when spec.interactions already contains an element-select entry. Hover / dimension-hover defaults are unchanged.

  • Docs-shaped interactions multi-select works without select: false
  • Plain default select (no interactions) stays single-select
  • select: { mode: 'multiple' } without interactions still accumulates

📝 Changelog

Language Changelog
🇺🇸 English fix: skip default single-select when interactions already registers element-select, so isMultiple multi-select works
🇨🇳 Chinese 修复:当 interactions 已配置 element-select 时不再注册默认单选,使 isMultiple 多选生效

☑️ Self-Check before Merge

  • Doc is updated/provided or not needed
  • Demo is updated/provided or not needed
  • TypeScript definition is updated/provided or not needed
  • Changelog is provided or not needed

Verification

  • eslint --quiet on packages/vchart/src/series/base/base-series.ts and the new test: clean
  • prettier --check on the same files: clean
  • jest __tests__/unit/interaction/element-select.test.ts --runner=jest-runner --testEnvironment=node: 3 passed
  • Package jest-electron runner is the default; the node runner is enough for this non-render wiring/state regression.

…select

When spec.interactions includes element-select (including isMultiple: true),
do not also register the default single-select trigger so the two do not fight.

Co-authored-by: David <dyk1454683243-sudo@users.noreply.github.com>
Co-authored-by: David <dyk1454683243-sudo@users.noreply.github.com>
@dyk1454683243-sudo
dyk1454683243-sudo marked this pull request as ready for review September 20, 2026 02:33

@xile611 xile611 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

@dyk1454683243-sudo 已完成 review。这个改动确实修复了饼图 interactions: [{ type: 'element-select', isMultiple: true }] 与默认单选冲突的问题,但目前会关闭自定义交互作用范围以外的默认选中,建议修复这一回归后再合并。

验证基线 c4191139a340f18f0e32dcb353c51009d88a6205 与 PR 312350584a389c56dbfc6010f6cdceb8591509b0:

场景 基线 PR
饼图连续点击两个扇区(配置 selected 样式) 仅保留一个选中 正确多选
柱线组合图仅对 bar 配置 element-select,点击折线 point 正常选中 无法选中
折线图仅对 line 配置 element-select,点击 point 正常选中 无法选中

本地补充用例通过真实 VChart 创建图元,在 Node + canvas 环境显式配置 select: { trigger: 'pointertap' },通过已注册的事件处理器依次发送 pointertap / click;没有手动修改系列字段或替换图元。未做浏览器鼠标实测。PR 自带 3 个测试及修改文件的 ESLint、Prettier 均通过,但未覆盖限定 markNames 的场景。

请在解析实际匹配的图元后处理冲突,保留未被自定义交互覆盖的图元的默认选中;同时补充上述局部图元、跨系列场景的回归测试。具体位置见行内意见。

Comment on lines +960 to +963
if (interactions?.some(interaction => interaction.type === TRIGGER_TYPE_ENUM.ELEMENT_SELECT)) {
const defaultSelectIndex = res.findIndex(item => item.trigger.type === TRIGGER_TYPE_ENUM.ELEMENT_SELECT);
if (defaultSelectIndex >= 0) {
res.splice(defaultSelectIndex, 1);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[P2] 保留自定义交互作用范围外的默认选中

这里只要存在 element-select 就删除整个默认 select,忽略了 markNames / markIds 的作用范围。例如柱线组合图在图表级配置 interactions: [{ type: 'element-select', markNames: ['bar'], isMultiple: true }]:该配置会传给两个系列,折线系列虽然没有匹配的 bar 图元,也会先删除默认 select,随后又因匹配结果为空而不注册自定义交互,最终折线点完全无法选中。单个折线图配置 markNames: ['line'] 时,未被覆盖的 point 同样失去选中能力。上述两个场景均已验证基线通过、PR 失败。请先解析实际匹配的图元,仅处理重叠范围内的冲突,保留其他图元的默认选中,并补充回归测试。

@visactor-review-bot visactor-review-bot Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

已核对冻结 diff、默认与自定义 element-select 的注册及状态更新路径,新增发现 1 项独立的反选样式回归。既有作用范围缺陷仍待解决,参见 https://github.com/VisActor/VChart/pull/4696#discussion_r4056020786;本次不重复提交该问题。

验证:静态核验:默认 select 配置 reverseState='selected_reverse';本次改动移除该触发器;自定义 ElementSelect 默认选项未补 reverseState;Interaction.updateStates 因而绕开反选状态分支。依赖未安装,未运行自动化或视觉测试,不能视为测试通过。

限制:隔离环境未安装仓库依赖且无网络,未运行 Jest、浏览器交互或视觉回归;结论基于冻结源码的交互配置和状态更新调用链静态核对。;未对基线和 PR 进行可执行渲染对照;既有 review 所述局部图元与跨系列回归仅引用既有讨论,不作为本次新发现。

状态:completed

if (interactions?.some(interaction => interaction.type === TRIGGER_TYPE_ENUM.ELEMENT_SELECT)) {
const defaultSelectIndex = res.findIndex(item => item.trigger.type === TRIGGER_TYPE_ENUM.ELEMENT_SELECT);
if (defaultSelectIndex >= 0) {
res.splice(defaultSelectIndex, 1);

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

[P2] 替换默认选中时保留 selected_reverse 状态

当系列配置 state.selected_reverse,同时使用文档形式的 interactions: [{ type: 'element-select', isMultiple: true }](未显式填写 reverseState)时,删除默认 select 后,未选中的图元不再进入 selected_reverse,原本的淡化等样式消失。原因是 _defaultSelectConfig 为默认触发器设置了 reverseState: STATE_SELECTED_REVERSE,而自定义触发器直接使用原始 spec;ElementSelect.defaultOptions 仅补 state 和 trigger,Interaction.updateStates 收到空的 reverseState 时只执行选中分支。此前默认触发器会设置未选中图元的反选状态;且 IElementSelectSpec 的注释明确允许用 state.selected_reverse 配置非激活图元。建议在避免双触发器冲突的同时为未显式覆盖该字段的自定义 select 保留默认反选状态,并增加该样式的真实状态回归测试。此问题与现有讨论所述 markNames / markIds 导致图元无法选中的作用范围问题不同:这里即使自定义交互覆盖全部图元,反选视觉状态也会丢失。

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

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug] isMultiple is not working in the interactions configuration.

3 participants