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

如何让Swift Charts的X轴区域响应chartXSelection点击?

实现SwiftUI Chart的X轴点击选择功能

问题描述

希望让SwiftUI的chartXSelection(value:)修饰符在用户点击X轴上的数值时也能触发选择,而不仅限于在图表绘图区域内点击拖动。

示例代码

private struct PlotPoint {
    let x: Double
    let y: Double
}

private struct PlotSeries: Identifiable {
    let id: Int
    let name: String
    let points: [PlotPoint]
}

private let data: [PlotSeries] = [
    PlotSeries(id: 0, name: "Series A", points: stride(from: 0.0, through: 1.0, by: 0.05).map { y in PlotPoint(x: y*y, y: y) }),
    PlotSeries(id: 1, name: "Series B", points: stride(from: 0.0, through: 1.0, by: 0.05).map { y in PlotPoint(x: y*y, y: y/2) })
]

struct AxisTap: View {
    @State private var selectedX: Double?
    var body: some View {
        VStack {
            Chart {
                if let selectedX {
                    BarMark(xStart: .value("x", selectedX), xEnd: .value("x", selectedX + 0.05))
                        .foregroundStyle(.yellow.opacity(0.5))
                }

                ForEach(data) { series in
                    let plot = LinePlot( series.points, x: .value("x", \.x), y: .value("y", \.y))
                    
                    plot
                        .symbol(by: .value("Series", series.name))
                        .foregroundStyle(by: .value("Series", series.name))
                }
            }
            .chartXAxis {
                AxisMarks() { value in
                    AxisGridLine()
                    AxisTick()
                    AxisValueLabel() {
                        if let axisValue = value.as(Double.self) {
                            VStack {
                                Text("|")
                                Text("v")
                                Text("\(axisValue.formatted())")
                            }
                        }
                    }
                }
            }
            .chartXSelection(value: $selectedX)
            .padding()
            Text("selectedX is: \(selectedX ?? 0.0)")
        }
    }
}

解决方案

默认情况下,chartXSelection仅监听图表的绘图区域手势,X轴的标签区域不在其响应范围内。要实现点击X轴数值触发选择,只需给AxisValueLabel的内容添加自定义点击手势,手动更新选中的X值即可:

修改chartXAxis中的AxisValueLabel部分:

AxisValueLabel() {
    if let axisValue = value.as(Double.self) {
        VStack {
            Text("|")
            Text("v")
            Text("\(axisValue.formatted())")
        }
        // 添加点击手势,手动设置选中的X值
        .onTapGesture {
            selectedX = axisValue
        }
    }
}

效果说明

  • 点击X轴上的任意数值标签,selectedX会立即更新为对应的值,下方文本会同步显示选中结果
  • 原有的图表区域拖动选择功能不受影响,两种交互方式可以共存

内容的提问来源于stack exchange,提问作者Curious Jorge

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.14 00:55:01