Search code examples
iosswiftswiftuichartsswiftui-charts

SwiftUI Charts: Adding Label To Bar Chart Bar


I am working in SwiftUI with the new Charts framework introduced in WWDC22 for iOS 16.

I want the value of each bar to be displayed inside the bar, but I don't see anyway in the Charts framework to do this. The best I can do is use a ZStack and try layering text on top of the chart, which works, but doesn't keep the text centered in the bar as the data changes.

Anyone discovered a way to do this natively in SwiftUI Charts?


Solution

  • The bars can be annotated by using an overlay position and a center alignment using this code:

    .annotation(position: .overlay, alignment: .center) { 
      // your Text or other overlay here
    }
    

    An example chart with the annotations.

    enter image description here

    The complete code that was used to create the chart is provided below for reference.

    Chart code:

    struct BarChart4: View {
        var body: some View {
            VStack(alignment: .center)  {
                Text("Basic Bar Chart")
                    .font(.callout)
                    .foregroundStyle(.secondary)
                
                Chart (BarData4.data) { shape in
                    BarMark (
                        x: .value("Shape", shape.type),
                        y: .value("Count", shape.count)
                    )
                    .annotation(position: .overlay, alignment: .center) {
                        Text("\(shape.count, format: .number.precision(.fractionLength(0)))")
                            .foregroundColor(.white)
                    }
                }
            }
        }
    }
    

    Sample Data:

    struct BarData4 {
        static let data: [ShapeModel] = [
            .init(type: "Square",    count: 12),
            .init(type: "Heart",     count: 10),
            .init(type: "Rectangle", count: 21),
            .init(type: "Star",      count: 15),
            .init(type: "Circle",    count: 8),
            .init(type: "Triangle",  count: 6)
        ]
    }
    

    And the Data Model:

    struct ShapeModel: Identifiable {
        var type: String
        var count: Double
        var id = UUID()
    }