From d82bc4d3935ecc19a46c4fa928745f4ac932a737 Mon Sep 17 00:00:00 2001 From: Adam Borbas Date: Mon, 13 Jul 2026 21:52:49 +0200 Subject: [PATCH] Show area temperature and humidity to one decimal place MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Format the area climate summary with locale-aware one-fraction-digit precision instead of rounding to a whole number, so 23.6°C is shown instead of 24°C. Co-Authored-By: Claude Opus 4.8 (1M context) --- Hemera/Entities/AreaDisplayHelpers.swift | 10 ++++++++-- .../Entities/AreaDisplayHelpersTests.swift | 20 +++++++++++++++---- .../StateUpdatePropagationTests.swift | 4 ++-- 3 files changed, 26 insertions(+), 8 deletions(-) diff --git a/Hemera/Entities/AreaDisplayHelpers.swift b/Hemera/Entities/AreaDisplayHelpers.swift index 71fe1cc..824681b 100644 --- a/Hemera/Entities/AreaDisplayHelpers.swift +++ b/Hemera/Entities/AreaDisplayHelpers.swift @@ -24,9 +24,15 @@ enum AreaDisplayHelpers { let humidity = sensors.first { $0.deviceClass == "humidity" } let tempStr = temp.flatMap { Double($0.state) } - .map { "\(Int($0.rounded()))\(temp?.unitOfMeasurement ?? "°")" } + .map { (value: Double) -> String in + let number = value.formatted(.number.precision(.fractionLength(1))) + return number + (temp?.unitOfMeasurement ?? "°") + } let humStr = humidity.flatMap { Double($0.state) } - .map { "\(Int($0.rounded()))\(humidity?.unitOfMeasurement ?? "%")" } + .map { (value: Double) -> String in + let number = value.formatted(.number.precision(.fractionLength(1))) + return number + (humidity?.unitOfMeasurement ?? "%") + } return (tempStr, humStr) } diff --git a/HemeraTests/Entities/AreaDisplayHelpersTests.swift b/HemeraTests/Entities/AreaDisplayHelpersTests.swift index 421e0b9..adca69f 100644 --- a/HemeraTests/Entities/AreaDisplayHelpersTests.swift +++ b/HemeraTests/Entities/AreaDisplayHelpersTests.swift @@ -29,17 +29,29 @@ struct AreaDisplayHelpersTests { let (t, h) = AreaDisplayHelpers.climateSummary(from: [temp, humidity]) - #expect(t == "21°C") - #expect(h == "47%") + // Whole values still render with one decimal, using the current locale's separator. + #expect(t == 21.0.formatted(.number.precision(.fractionLength(1))) + "°C") + #expect(h == 47.0.formatted(.number.precision(.fractionLength(1))) + "%") } @Test - func climateSummary_roundsFractionalValues() { + func climateSummary_formatsFractionalValuesToOneDecimal() { let temp = SensorEntity(entityId: "sensor.temp", name: "T", state: "21.6", deviceClass: "temperature", unitOfMeasurement: "°C") let (t, _) = AreaDisplayHelpers.climateSummary(from: [temp]) - #expect(t == "22°C") + // Fractional value is preserved to one decimal, not rounded to a whole number. + #expect(t == 21.6.formatted(.number.precision(.fractionLength(1))) + "°C") + } + + @Test + func climateSummary_roundsToOneDecimal() { + let temp = SensorEntity(entityId: "sensor.temp", name: "T", state: "21.68", deviceClass: "temperature", unitOfMeasurement: "°C") + + let (t, _) = AreaDisplayHelpers.climateSummary(from: [temp]) + + // More than one decimal is rounded, not truncated. + #expect(t == 21.7.formatted(.number.precision(.fractionLength(1))) + "°C") } @Test diff --git a/HemeraTests/HomeAssistant/StateUpdatePropagationTests.swift b/HemeraTests/HomeAssistant/StateUpdatePropagationTests.swift index ea35588..67b3b45 100644 --- a/HemeraTests/HomeAssistant/StateUpdatePropagationTests.swift +++ b/HemeraTests/HomeAssistant/StateUpdatePropagationTests.swift @@ -122,7 +122,7 @@ struct StateUpdatePropagationTests { context.insert(sensor) let (tempBefore, _) = AreaDisplayHelpers.climateSummary(from: area.sensors) - #expect(tempBefore == "21°C") + #expect(tempBefore == 21.0.formatted(.number.precision(.fractionLength(1))) + "°C") let haEntity = try HAEntity( entityId: "sensor.temp", @@ -137,6 +137,6 @@ struct StateUpdatePropagationTests { EntityRegistry.shared.upsert(from: haEntity, in: context) let (tempAfter, _) = AreaDisplayHelpers.climateSummary(from: area.sensors) - #expect(tempAfter == "24°C") + #expect(tempAfter == 24.0.formatted(.number.precision(.fractionLength(1))) + "°C") } }