Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to add new real-time data to lineChart ? #2773

Closed
Mohammed-Elias opened this issue Sep 6, 2017 · 10 comments
Closed

How to add new real-time data to lineChart ? #2773

Mohammed-Elias opened this issue Sep 6, 2017 · 10 comments

Comments

@Mohammed-Elias
Copy link

Mohammed-Elias commented Sep 6, 2017

Here my code to update the chart, but there's nothing happened :(

var dataSet = [ChartDataEntry(x: 0, y: 0.5)]
var lineData = LineChartData()
var line = LineChartDataSet()

override func viewDidLoad() {
      updateChart()
 }

func updateChart() {
 for index in 0..<count {                
     dataSet.append(ChartDataEntry(x: hour, y: price))
     line.values = dataSet
 }
        
        chartView.data?.notifyDataChanged()
        chartView.notifyDataSetChanged()
}
@thierryH91200
Copy link
Contributor

thierryH91200 commented Sep 6, 2017

here is an example if it can help you
you forgot the timer in your code and lots of other things

LineChartRealTimeViewController.zip

capture d ecran 2017-09-06 a 16 30 26

@Mohammed-Elias
Copy link
Author

@thierryH91200 Thanks man, but I think you misunderstand me, I already had a drawn chart, but in separate view I need to get the data with JSON parsing.

    var set1 = LineChartDataSet()
    set1 = (chartView.data?.dataSets[0] as? LineChartDataSet)!
    
    set1.values = yEntries
    chartView.data?.notifyDataChanged()
    chartView.notifyDataSetChanged()

after I wrote this snippet from your code, I didn't get the line chart.

this is my code after the parsing succeeded :

 func getCurreniesByTimeCompleted(prices: [CurrencyPrice?]?) {
    if let prices = prices {
        
        currenciesPrice = prices as! [CurrencyPrice]
        
        let dateFormatter = DateFormatter()
        dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SS"
        var localTimeZoneAbbreviation: String { return TimeZone.current.abbreviation() ?? "" }
        dateFormatter.timeZone = TimeZone(abbreviation: localTimeZoneAbbreviation)
        
        for index in 0..<currenciesPrice.count {
            let date = dateFormatter.date(from: currenciesPrice[index].timeStamp!)
            let hour = Calendar.current.component(.hour, from: date!)
            
            chartDataEntries.append(ChartDataEntry(x: Double(hour), y: currenciesPrice[index].price!))
            
            var set1 = LineChartDataSet()
            set1 = (chartView.data?.dataSets[0] as? LineChartDataSet)!
            
            set1.values = chartDataEntries
            chartView.data?.notifyDataChanged()
            chartView.notifyDataSetChanged()
        }
    }
} 

@thierryH91200
Copy link
Contributor

it should be better

func getCurreniesByTimeCompleted(prices: [CurrencyPrice?]?) {
    if let prices = prices {
        
        currenciesPrice = prices as! [CurrencyPrice]
        
        let dateFormatter = DateFormatter()
        dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss.SS"
        var localTimeZoneAbbreviation: String { return TimeZone.current.abbreviation() ?? "" }
        dateFormatter.timeZone = TimeZone(abbreviation: localTimeZoneAbbreviation)
        
        for index in 0..<currenciesPrice.count {
            let date = dateFormatter.date(from: currenciesPrice[index].timeStamp!)
            let hour = Calendar.current.component(.hour, from: date!)
            
            chartDataEntries.append(ChartDataEntry(x: Double(hour), y: currenciesPrice[index].price!))
        }
        var set1 = LineChartDataSet()
            set1 = (chartView.data?.dataSets[0] as? LineChartDataSet)!
            
            set1.values = chartDataEntries
            chartView.data?.notifyDataChanged()
            chartView.notifyDataSetChanged()
    }
} 

@Mohammed-Elias
Copy link
Author

Mohammed-Elias commented Sep 6, 2017

Didn't work, I think it would be from one of the attributes of the chartView.

var chartDataEntries = [ChartDataEntry]()
var lineData: LineChartData!
var lineDataSet: LineChartDataSet!

override func viewDidLoad() {

    let gradientColors = [ChartColorTemplates.colorFromString("#52FED542").cgColor,ChartColorTemplates.colorFromString("#52FFB300").cgColor]
    let gradient = CGGradient(colorsSpace: nil, colors: gradientColors as CFArray, locations: nil)
    
    lineDataSet = LineChartDataSet(values: chartDataEntries, label: "line")
    lineDataSet.colors = [chartColor]
    lineDataSet.lineWidth = 3
    lineDataSet.drawFilledEnabled = true
    lineDataSet.drawValuesEnabled = false
    lineDataSet.circleColors = [chartColor]
    lineDataSet.circleHoleColor = chartColor
    lineDataSet.circleRadius = 5
    lineDataSet.mode = .cubicBezier
    
    lineDataSet.fillAlpha = 1
    lineDataSet.fill = Fill(linearGradient: gradient!, angle: 90)
    lineDataSet.drawFilledEnabled = true
    
    lineData = LineChartData()
    lineData.addDataSet(lineDataSet)
    chartView.data = lineData
    
    lineDataSet.highlightColor = NSUIColor.clear
    
    chartView.setViewPortOffsets(left: 0, top: 0, right: 0, bottom: 0)
    
    chartView.chartDescription?.enabled = false
    chartView.doubleTapToZoomEnabled = false
    chartView.pinchZoomEnabled = false
    chartView.drawGridBackgroundEnabled = false
    
    chartView.legend.enabled = false
    chartView.rightAxis.enabled = false
    chartView.leftAxis.enabled = false
    
    chartView.xAxis.drawGridLinesEnabled = false
    chartView.xAxis.drawAxisLineEnabled = false
    chartView.xAxis.labelPosition = .bottomInside
    chartView.xAxis.labelTextColor = .white
    chartView.xAxis.avoidFirstLastClippingEnabled = true
    chartView.xAxis.setLabelCount(chartDataEntries.count, force: true)
    
    chartView.delegate = self

   // calling this method after I get success from JSON parsing
  //getCurreniesByTimeCompleted(prices: [CurrencyPrice?]?)
 }

Could you please take a look and tell if you see anything wrong ?
Forgive me if I waste you time :)

@thierryH91200
Copy link
Contributor

chartDataEntries is empty ??? =>
lineDataSet = LineChartDataSet(values: chartDataEntries, label: "line") ?????

put chartView.data = lineData to the end

var chartDataEntries = [ChartDataEntry]()
var lineData: LineChartData!
var lineDataSet: LineChartDataSet!

override func viewDidLoad() {

chartView.delegate = self

 chartView.setViewPortOffsets(left: 0, top: 0, right: 0, bottom: 0)
 chartView.chartDescription?.enabled = false
    chartView.doubleTapToZoomEnabled = false
    chartView.pinchZoomEnabled = false
    chartView.drawGridBackgroundEnabled = false
    
    chartView.legend.enabled = false
    chartView.rightAxis.enabled = false
    chartView.leftAxis.enabled = false
    
    chartView.xAxis.drawGridLinesEnabled = false
    chartView.xAxis.drawAxisLineEnabled = false
    chartView.xAxis.labelPosition = .bottomInside
    chartView.xAxis.labelTextColor = .white
    chartView.xAxis.avoidFirstLastClippingEnabled = true
    chartView.xAxis.setLabelCount(chartDataEntries.count, force: true)
    
    let gradientColors = [ChartColorTemplates.colorFromString("#52FED542").cgColor,ChartColorTemplates.colorFromString("#52FFB300").cgColor]
    let gradient = CGGradient(colorsSpace: nil, colors: gradientColors as CFArray, locations: nil)
    
    lineDataSet = LineChartDataSet(values: chartDataEntries, label: "line")
    lineDataSet.colors = [chartColor]
    lineDataSet.lineWidth = 3
    lineDataSet.drawFilledEnabled = true
    lineDataSet.drawValuesEnabled = false
    lineDataSet.circleColors = [chartColor]
    lineDataSet.circleHoleColor = chartColor
    lineDataSet.circleRadius = 5
    lineDataSet.mode = .cubicBezier
    
    lineDataSet.fillAlpha = 1
    lineDataSet.fill = Fill(linearGradient: gradient!, angle: 90)
    lineDataSet.drawFilledEnabled = true
 lineDataSet.highlightColor = NSUIColor.clear
    
    lineData = LineChartData()
    lineData.addDataSet(lineDataSet)
    chartView.data = lineData
 
   // calling this method after I get success from JSON parsing
  //getCurreniesByTimeCompleted(prices: [CurrencyPrice?]?)
 }

@Mohammed-Elias
Copy link
Author

Mohammed-Elias commented Sep 7, 2017

I put these at the end of viewDidLoad

   lineData = LineChartData()
   lineData.addDataSet(lineDataSet)
   chartView.data = lineData

and about your question here:
chartDataEntries is empty ??? =>
lineDataSet = LineChartDataSet(values: chartDataEntries, label: "line") ?????

I'll fill chartDataEntries ingetCurreniesByTimeCompleted with:
chartDataEntries.append(ChartDataEntry(x: Double(hour), y: currenciesPrice[index].price!))
then after I go through all the objects there I'll update the chartView with this:

   var set1 = LineChartDataSet()
   set1 = (chartView.data?.dataSets[0] as? LineChartDataSet)!
   set1.values = chartDataEntries
   chartView.data?.notifyDataChanged()
   chartView.notifyDataSetChanged()

The same, didn't draw anything, but I have a question here to where should I put set1 to make it the dataSet from chartView, to be more specific I have changed this lines:

   var set1 = LineChartDataSet()
   set1 = (chartView.data?.dataSets[0] as? LineChartDataSet)!
   set1.values = chartDataEntries
   chartView.data?.notifyDataChanged()
   chartView.notifyDataSetChanged()

with this lines

   lineDataSet.values = chartDataEntries
   chartView.data?.notifyDataChanged()
   chartView.notifyDataSetChanged()

but the same, nothing happened :(
after putting a breakpoint I'm very sure that chartDataEntries is full with 24 points.
Could you please explain it to me !

@thierryH91200
Copy link
Contributor

let gradientColors = [ChartColorTemplates.colorFromString("#52FED542").cgColor,ChartColorTemplates.colorFromString("#52FFB300").cgColor]
   let gradient = CGGradient(colorsSpace: nil, colors: gradientColors as CFArray, locations: nil)
   
   lineDataSet = LineChartDataSet(values: chartDataEntries, label: "line")  

<=== chartDataEntries is empty No data

lineDataSet.colors = [chartColor]
 lineDataSet.lineWidth = 3
 lineDataSet.drawFilledEnabled = true
 lineDataSet.drawValuesEnabled = false
 lineDataSet.circleColors = [chartColor]
 lineDataSet.circleHoleColor = chartColor
 lineDataSet.circleRadius = 5
 lineDataSet.mode = .cubicBezier

@Mohammed-Elias
Copy link
Author

Mohammed-Elias commented Sep 7, 2017

Thanks a lot, I appreciate everything you did write to help me, but the problem was from my JSON data: (x = the past 24 hours from this hour)

  [ChartDataEntry, x: 11.0, y 23.51,
   ChartDataEntry, x: 10.0, y 24.0,
   ChartDataEntry, x: 9.0, y 23.91,
   ChartDataEntry, x: 8.0, y 23.81,
   ChartDataEntry, x: 7.0, y 23.71,
   ChartDataEntry, x: 6.0, y 23.5,
   ChartDataEntry, x: 5.0, y 23.2,
   ChartDataEntry, x: 4.0, y 23.1,
   ChartDataEntry, x: 3.0, y 23.9,
   ChartDataEntry, x: 2.0, y 23.8,
   ChartDataEntry, x: 1.0, y 23.7,
   ChartDataEntry, x: 0.0, y 23.75,
   ChartDataEntry, x: 23.0, y 23.8,
   ChartDataEntry, x: 22.0, y 23.0,
   ChartDataEntry, x: 21.0, y 23.1,
   ChartDataEntry, x: 20.0, y 23.4,
   ChartDataEntry, x: 19.0, y 23.8,
   ChartDataEntry, x: 18.0, y 23.7,
   ChartDataEntry, x: 17.0, y 23.6,
   ChartDataEntry, x: 16.0, y 23.9,
   ChartDataEntry, x: 15.0, y 23.95,
   ChartDataEntry, x: 14.0, y 23.65,
   ChartDataEntry, x: 13.0, y 23.55,
   ChartDataEntry, x: 12.0, y 23.45]

as you notice the x property wasn't ordered ascending, this made the line chart go crazy.
but no the real question is how to draw this data without changing the order of the x.

@Mohammed-Elias
Copy link
Author

I have changed the date to integer then resort chartDataEntries array, then add to the dataSet of the chart.

@liuxuan30
Copy link
Member

this will be a good thread for people asking real time chart. Thanks @thierryH91200 !

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants