diff --git a/src/Helper.js b/src/Helper.js index dd87fe6..61b435d 100644 --- a/src/Helper.js +++ b/src/Helper.js @@ -331,16 +331,17 @@ class Helper { } /** - * Get state entities, filtered by area and domain. + * Get state entities, filtered by area, domain and optionally deviceClass. * * The result excludes hidden and disabled entities. * * @param {areaEntity} area Area entity. * @param {string} domain Domain of the entity-id. + * @param {string|null} deviceClass Device class attribute of the state. * * @return {stateObject[]} Array of state entities. */ - static getStateEntities(area, domain) { + static getStateEntities(area, domain, deviceClass = null) { if (!this.isInitialized()) { console.warn("Helper class should be initialized before calling this method!"); } @@ -355,7 +356,15 @@ class Helper { // Get states whose entity-id starts with the given string. const stateEntities = Object.values(this.#hassStates).filter( - state => state.entity_id.startsWith(`${domain}.`), + state => { + if (deviceClass + && state.attributes.device_class !== deviceClass + ) { + return false; + } + + return state.entity_id.startsWith(`${domain}.`) + }, ); for (const state of stateEntities) { diff --git a/src/cards/AreaCard.js b/src/cards/AreaCard.js index 16b4212..18e82c1 100644 --- a/src/cards/AreaCard.js +++ b/src/cards/AreaCard.js @@ -1,4 +1,5 @@ import {AbstractCard} from "./AbstractCard"; +import {Helper} from "../Helper"; /** * Area Card Class @@ -57,6 +58,68 @@ class AreaCard extends AbstractCard { this.options.primary = options.name; } } + + /** + * @inheritdoc + */ + getCard() { + let card = super.getCard(); + + if (!card.secondary) { + // Get or determine the relevant sensor entity IDs based on options or default behavior + const temperatureSensorId = this.options?.temperature || Helper.getStateEntities(this.entity, "sensor", "temperature")[0]?.entity_id; + const humiditySensorId = this.options?.humidity || Helper.getStateEntities(this.entity, "sensor", "humidity")[0]?.entity_id; + const illuminanceSensorId = this.options?.illuminance || Helper.getStateEntities(this.entity, "sensor", "illuminance")[0]?.entity_id; + + // Collect secondary pieces of information for the card, based on available sensors + let secondaries = []; + if (temperatureSensorId) { + secondaries.push(`🌡️{{ states('${temperatureSensorId}') | int }}°`); + } + if (humiditySensorId) { + secondaries.push(`💧{{ states('${humiditySensorId}') | int }}%`); + } + if (illuminanceSensorId) { + secondaries.push(`☀️{{ states('${illuminanceSensorId}')}}lx`); + } + + // Set the secondary information on the card as a combined string + card.secondary = secondaries.join(" "); + } + + if (!card.badge_icon) { + // Get or determine the relevant lock or binary sensor entity IDs + const lockId = this.options?.lock || Helper.getStateEntities(this.entity, "lock")[0]?.entity_id; + const windowBinarySensorId = this.options?.window || Helper.getStateEntities(this.entity, "binary_sensor", "window")[0]?.entity_id; + const doorBinarySensorId = this.options?.door || Helper.getStateEntities(this.entity, "binary_sensor", "door")[0]?.entity_id; + + // Construct badge conditions based on the existence and states of the entities + let badgeConditions = [] + if (lockId) { + badgeConditions.push({entity: lockId, state: 'unlocked', icon: 'mdi:lock-open'}) + } + if (windowBinarySensorId) { + badgeConditions.push({entity: windowBinarySensorId, state: 'on', icon: 'mdi:window-open-variant'}) + } + if (doorBinarySensorId) { + badgeConditions.push({entity: doorBinarySensorId, state: 'on', icon: 'mdi:door-open'}) + } + + // If there are badge conditions, construct a template for the badge icon based on conditions + if (badgeConditions.length) { + let badge = badgeConditions + .map(condition => `is_state('${condition.entity}', '${condition.state}') %}${condition.icon}{%`) + .join(' elif ') + badge = `{% if ${badge} endif %}` + + // Set badge properties on the card + card.badge_color = "red"; + card.badge_icon = badge; + } + } + + return card; + } } export {AreaCard};