import Foundation import SFSafeSymbols struct TemperatureSensor { let address: [UInt8] let value: TemperatureValue let date: Date var optionalValue: Double? { value.optionalValue } var hexAddress: String { String(format: "%02X %02X %02X %02X %02X %02X %02X %02X", address[0], address[1], address[2], address[3], address[4], address[5], address[6], address[7]) } var temperatureIcon: SFSymbol { TemperatureSensor.temperatureIcon(optionalValue) } var temperatureText: String { value.text } var updateText: String { date.timePassedText } static func temperatureIcon(_ temp: Double?) -> SFSymbol { guard let temp else { return .thermometerMediumSlash } guard temp > 0 else { return .thermometerSnowflake } guard temp > 15 else { return .thermometerLow } guard temp > 25 else { return .thermometerMedium } return .thermometerHigh } } extension TemperatureSensor { init?(address: [UInt8], valueByte: UInt8, secondsAgo: UInt16) { guard address.contains(where: { $0 != 0 }) else { // Empty address return nil } self.address = address self.value = .init(byte: valueByte) self.date = Date().addingTimeInterval(-TimeInterval(secondsAgo)) } } extension Date { var timePassedText: String { let secs = Int(-timeIntervalSinceNow.rounded()) guard secs > 1 else { return "Now" } guard secs >= 60 else { return "\(secs) seconds ago" } let minutes = secs / 60 guard minutes > 1 else { return "1 minute ago" } guard minutes >= 60 else { return "\(minutes) minutes ago" } let hours = minutes / 60 guard hours > 1 else { return "1 hour ago" } guard hours >= 60 else { return "\(hours) hours ago" } let days = hours / 24 guard days > 1 else { return "1 day ago" } return "\(days) days ago" } }