Search code examples
swiftuiswift5ios-charts

How to set String value as x of ChartDataEntry.init in Charts?


I'm currently developing an application using SwiftUI.

I'm trying to use a Charts(Charts) in my SwiftUI project.

I want to show some String value as x-axis, but when I call ChartDataEntry.init there is an error because the type String data can't be accepted.

So I tried to solve it referring to this article Trying to enter Date/String in ChartDataEntry

But then I can't call this DateAxisValueFormatter() and still solve this problem...

How could I solve it in the case of the code below?


Here is the code:

import SwiftUI
import Charts

struct LineChartSwiftUI: UIViewRepresentable {
    let lineChart = LineChartView()

    func makeUIView(context: UIViewRepresentableContext<LineChartSwiftUI>) -> LineChartView {
        setUpChart()
        return lineChart
    }

    func updateUIView(_ uiView: LineChartView, context: UIViewRepresentableContext<LineChartSwiftUI>) {

    }

    func setUpChart() {
        lineChart.noDataText = "No Data Available"
        let dataSets = [getLineChartDataSet()]
        let data = LineChartData(dataSets: dataSets)
        data.setValueFont(.systemFont(ofSize: 7, weight: .light))
        lineChart.data = data
        
    }

    func getChartDataPoints(sessions: [String], accuracy: [Double]) -> [ChartDataEntry] {
        var dataPoints: [ChartDataEntry] = []
        
        for count in (0..<sessions.count) {
            dataPoints.append(ChartDataEntry.init(x: Double(sessions[count]), y: accuracy[count])) // I have an error here

        }
        return dataPoints
    }

    func getLineChartDataSet() -> LineChartDataSet {
        let dataPoints = getChartDataPoints(sessions: ["1,Dec","5,Dec","10,Dec","15,Dec","20,Dec"], accuracy: [20.0, 40.0, 60.0, 80.0, 100.0])
        
        let set = LineChartDataSet(entries: dataPoints, label: "DataSet")
        set.lineWidth = 2.5
        set.circleRadius = 4
        set.circleHoleRadius = 2
        let color = ChartColorTemplates.vordiplom()[0]
        set.setColor(color)
        set.setCircleColor(color)
        return set
    }
}

Xcode: Version 12.0.1

charts: v3.6.0


Solution

  • You can implement delegate method like this

    extension LineChartSwiftUI: IAxisValueFormatter {
    
        func stringForValue(_ value: Double, axis: AxisBase?) -> String {
            if axis is XAxis {
                // do something you need for X axis
                return valueTransformedToString
            }
        }
    
    }
    

    And set value formatter as axis to self as delegated, like this:

    lineChart.xAxis.valueFormatter = self
    

    In delegated method you just need to implement values transforming to your format.