You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular ngx-charts:如何主动触发饼图Tooltip显示

问题描述

我正在创建一个自定义图例组件,其中每个数据条目都带有自己的Material进度条。当悬停在任意条目上时,我希望饼图显示对应数据条目的tooltip。

模板代码

<ngx-charts-pie-chart
    #pieChart
    ...
>
    <ng-template #tooltipTemplate let-model="model">
        <div style="padding: 5px;">
            <pre>{{ model.name }}</pre>
            <p style="font-size: 1rem;">{{ model.value | currency:'EUR':true }}</p>
        </div>
    </ng-template>
</ngx-charts-pie-chart>

<app-portfolio-preview-card-positions
    [portfolioHoldings]="portfolio.holdings"
    [portfolioTotal]="portfolio.total"
    (onPositionHovered)="positionHovered($event)"
></app-portfolio-preview-card-positions>

尝试的代码及问题

@ContentChild('tooltipTemplate') tooltipTemplate!: TemplateRef<any>;
@ViewChild('pieChart') pieChart!: PieChartComponent;
...
positionHovered(name: string) {
    // 此处希望设置饼图激活条目并显示对应tooltip
    this.pieChart.activeEntries = [{name: name}, ...this.pieChart.activeEntries];
    this.pieChart.activate.emit({ value: {name: name}, entries: this.pieChart.activeEntries });
    console.log(this.tooltipTemplate);
}

当前tooltipTemplate始终为undefined,请问我缺少了什么步骤才能主动调用tooltip?这是否可行?


解决方案

1. 为什么tooltipTemplate是undefined?

@ContentChild用于获取组件外部通过内容投影传入的模板,而你的tooltipTemplate是定义在ngx-charts-pie-chart组件内部的视图内容,不属于外部投影范畴,所以用@ContentChild无法获取到。应该直接通过饼图组件实例访问其内置的tooltip模板引用。

2. 正确触发饼图tooltip的实现步骤

ngx-charts的饼图组件内置了tooltip控制逻辑,无需手动获取外部模板,按以下方式修改代码即可:

@ViewChild('pieChart') pieChart!: PieChartComponent;
// 假设你的饼图数据源是这个变量
chartData: any[];

positionHovered(name: string) {
    // 1. 从数据源中匹配到完整的目标条目(tooltip需要完整的value等字段)
    const targetEntry = this.chartData.find(item => item.name === name);
    if (!targetEntry) return;

    // 2. 重置饼图的激活条目,避免多个条目同时激活
    this.pieChart.activeEntries = [targetEntry];
    // 触发激活事件,同步饼图的选中状态
    this.pieChart.activate.emit({ value: targetEntry, entries: this.pieChart.activeEntries });

    // 3. 手动触发tooltip显示
    const tooltipService = this.pieChart.tooltipService;
    const tooltipTemplate = this.pieChart.tooltipTemplate;
    if (tooltipService && tooltipTemplate) {
        // 获取对应扇区的中心位置,作为tooltip的显示坐标
        const targetSeries = this.pieChart.series.find(s => s.name === name);
        if (targetSeries) {
            const [x, y] = targetSeries.center;
            tooltipService.show(
                tooltipTemplate,
                targetEntry,
                { x, y },
                'right' // tooltip的显示方向,可根据需求调整
            );
        }
    }
}

3. 补充:鼠标离开时的清理逻辑

当鼠标离开自定义图例条目时,需要隐藏tooltip并重置激活状态,避免tooltip残留:

positionHoveredOut() {
    const tooltipService = this.pieChart.tooltipService;
    if (tooltipService) {
        tooltipService.hide();
    }
    this.pieChart.activeEntries = [];
    this.pieChart.deactivate.emit();
}

4. 版本兼容提示

如果你的ngx-charts版本中tooltipService或tooltipTemplate是私有属性,无法直接访问,可以改用@ViewChild获取tooltip组件实例:

import { TooltipComponent } from '@swimlane/ngx-charts';

@ViewChild(TooltipComponent) tooltip!: TooltipComponent;

// 在hover方法中调用
this.tooltip.show(/* 参数同上 */);

内容的提问来源于stack exchange,提问作者Manuel Brás

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.11 23:55:12