0

I'm trying to plot temperature data on a LineMark chart. My array of chartDATETIME values are formatted to the timezone at the coordinates that the user selects. I know those values are correct because I've printed them.

For some reason, when I plot the temperature and date time values on a LineMark, the chart changes my datetimes to my local timezone. I can't figure out how to stop the chart from doing this.

Chart(viewModel.weatherArray, id: \.chartDATETIME) {
    LineMark(
        x: .value("Date", $0.chartDATETIME, unit: .hour),
        y: .value("Temp", $0.chartTMP)
    )
    .lineStyle(StrokeStyle(lineWidth: lineWidth))
    .foregroundStyle(chartColor.gradient)
    .interpolationMethod(interpolationMethod.mode)  
}
Cheolhyun
  • 169
  • 1
  • 7
SkimoBen
  • 19
  • 3
  • is `chartDATETIME` a `Date`? If so, note a `Date` is "A specific point in time, **independent of any calendar or time zone.**" see: https://developer.apple.com/documentation/foundation/date It is when you use the formating that you get a `String` with the selected timezone. The `Date` itself has no timezone, think of it as all `UTC`. So use an appropriate DateFormatter for localized representations. – workingdog support Ukraine Mar 15 '23 at 23:30
  • @workingdogsupportUkraine Thanks for the pointer, it is in fact a Date, because LineMarks require a date for the xAxis I believe. Do you happen to know if there's a different Date format that supports time zones? – SkimoBen Mar 16 '23 at 02:21
  • If your data is a `Date` (read from an API for example), then you cannot recover the timezone from it, because it does not have it. If you read the date as a `String`, then you have a chance to get to the timezone, **if it is included**. AFAIK, Apple does not give you the timezone from a `DateFormatter`. So you have to cook it yourself. Extract it from the string, eg: `dateString.suffix(7)` from ISO8601Date string and use it in the DateFormatter timeZone. – workingdog support Ukraine Mar 16 '23 at 03:46
  • What API are you using? API like `openweathermap` provide fields like `timezone` and `timezoneOffset`. With `WeatherKit` you have lat,lon coordinates, from which you will have to obtain the timezone, unless there is also a field somewhere in the response about the timezone. – workingdog support Ukraine Mar 16 '23 at 04:38
  • Thanks! My API does have a UTC offset. I ended up using that to offset the the labels on the x axis and in my lolipop head (It's an interactive chart). The concept seemed a bit weird to me, having the actual Date values in UTC, but just displaying them in the right timezone. Oh well, it works! – SkimoBen Mar 16 '23 at 21:29

1 Answers1

-1

As the comments note, the Swift Date type is basically bound to UTC. LineMark charts also require a Date type, because they automatically convert the Date values into your local timezone for the chart labels.

The workaround is to change the labels on the chart using the .chartXAxis modifier.

var body: some View {
    chartTempVar
        .chartXAxis {
            AxisMarks(format: Date.FormatStyle(
                date: .omitted,
                time: .shortened,
                timeZone: TimeZone(secondsFromGMT: chartUTCOffest)!))
        }
}
SkimoBen
  • 19
  • 3