forked from DigiLive/mushroom-strategy
Add scene domain and associated tap-action (#164)
Scenes are added as a domain so they're available at the top navigation bar. The view doesn't have controller cards since switching multiple scenes at once makes no sense. --------- Co-authored-by: DigiLive <github@digilive.nl>
This commit is contained in:
@ -365,6 +365,17 @@ class Helper {
|
|||||||
return states;
|
return states;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the state object of a HASS entity.
|
||||||
|
*
|
||||||
|
* @param {EntityRegistryEntry} entity The entity for which to get the state.
|
||||||
|
* @returns {HassEntity | undefined} The state object of the entity, or undefined if not found.
|
||||||
|
* @static
|
||||||
|
*/
|
||||||
|
static getEntityState(entity: EntityRegistryEntry): HassEntity | undefined {
|
||||||
|
return this.#hassStates[entity.entity_id];
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Sanitize a classname.
|
* Sanitize a classname.
|
||||||
*
|
*
|
||||||
|
63
src/cards/SceneCard.ts
Normal file
63
src/cards/SceneCard.ts
Normal file
@ -0,0 +1,63 @@
|
|||||||
|
import {AbstractCard} from "./AbstractCard";
|
||||||
|
import {cards} from "../types/strategy/cards";
|
||||||
|
import {EntityRegistryEntry} from "../types/homeassistant/data/entity_registry";
|
||||||
|
import {generic} from "../types/strategy/generic";
|
||||||
|
import {EntityCardConfig} from "../types/lovelace-mushroom/cards/entity-card-config";
|
||||||
|
import {Helper} from "../Helper";
|
||||||
|
import isCallServiceActionConfig = generic.isCallServiceActionConfig;
|
||||||
|
import isCallServiceActionTarget = generic.isCallServiceActionTarget;
|
||||||
|
|
||||||
|
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||||
|
/**
|
||||||
|
* Scene Card Class
|
||||||
|
*
|
||||||
|
* Used to create a card for an entity of the scene domain.
|
||||||
|
*
|
||||||
|
* @class
|
||||||
|
* @extends AbstractCard
|
||||||
|
*/
|
||||||
|
class SceneCard extends AbstractCard {
|
||||||
|
/**
|
||||||
|
* Default configuration of the card.
|
||||||
|
*
|
||||||
|
* @type {EntityCardConfig}
|
||||||
|
* @private
|
||||||
|
*/
|
||||||
|
#defaultConfig: EntityCardConfig = {
|
||||||
|
type: "custom:mushroom-entity-card",
|
||||||
|
icon: "mdi:palette",
|
||||||
|
icon_color: "blue",
|
||||||
|
tap_action: {
|
||||||
|
action: "call-service",
|
||||||
|
service: "scene.turn_on",
|
||||||
|
target: {
|
||||||
|
entity_id: undefined,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class constructor.
|
||||||
|
*
|
||||||
|
* @param {EntityRegistryEntry} entity The hass entity to create a card for.
|
||||||
|
* @param {cards.EntityCardOptions} [options={}] Options for the card.
|
||||||
|
* @throws {Error} If the Helper module isn't initialized.
|
||||||
|
*/
|
||||||
|
constructor(entity: EntityRegistryEntry, options: cards.EntityCardOptions = {}) {
|
||||||
|
super(entity);
|
||||||
|
|
||||||
|
// Set the target for tap action.
|
||||||
|
if (
|
||||||
|
isCallServiceActionConfig(this.#defaultConfig.tap_action)
|
||||||
|
&& isCallServiceActionTarget(this.#defaultConfig.tap_action.target)
|
||||||
|
) {
|
||||||
|
this.#defaultConfig.tap_action.target.entity_id = entity.entity_id;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.#defaultConfig.icon = Helper.getEntityState(entity)?.attributes.icon ?? this.#defaultConfig.icon;
|
||||||
|
|
||||||
|
this.config = Object.assign(this.config, this.#defaultConfig, options);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export {SceneCard};
|
@ -37,6 +37,12 @@ export const getConfigurationDefaults = (localize: Function): StrategyDefaults =
|
|||||||
offService: "light.turn_off",
|
offService: "light.turn_off",
|
||||||
hidden: false,
|
hidden: false,
|
||||||
},
|
},
|
||||||
|
scene: {
|
||||||
|
title: localize("scene.scenes"),
|
||||||
|
showControls: false,
|
||||||
|
onService: "scene.turn_on",
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
fan: {
|
fan: {
|
||||||
title: localize("fan.fans"),
|
title: localize("fan.fans"),
|
||||||
showControls: true,
|
showControls: true,
|
||||||
@ -151,6 +157,10 @@ export const getConfigurationDefaults = (localize: Function): StrategyDefaults =
|
|||||||
order: 8,
|
order: 8,
|
||||||
hidden: false,
|
hidden: false,
|
||||||
},
|
},
|
||||||
|
scene: {
|
||||||
|
order: 9,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
@ -44,6 +44,9 @@
|
|||||||
"media_player": {
|
"media_player": {
|
||||||
"media_players": "Mediaplayers"
|
"media_players": "Mediaplayers"
|
||||||
},
|
},
|
||||||
|
"scene": {
|
||||||
|
"scenes": "Scenes"
|
||||||
|
},
|
||||||
"select": {
|
"select": {
|
||||||
"selects": "Selects"
|
"selects": "Selects"
|
||||||
},
|
},
|
||||||
|
@ -44,6 +44,9 @@
|
|||||||
"media_player": {
|
"media_player": {
|
||||||
"media_players": "Mediaspelers"
|
"media_players": "Mediaspelers"
|
||||||
},
|
},
|
||||||
|
"scene": {
|
||||||
|
"scenes": "Scenes"
|
||||||
|
},
|
||||||
"select": {
|
"select": {
|
||||||
"selects": "Statuslijsten"
|
"selects": "Statuslijsten"
|
||||||
},
|
},
|
||||||
|
@ -123,7 +123,7 @@ abstract class AbstractView {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Add a Controller Card for all the entities in the view.
|
// Add a Controller Card for all the entities in the view.
|
||||||
if (viewCards.length) {
|
if (this.viewControllerCard.cards.length && viewCards.length) {
|
||||||
viewCards.unshift(this.viewControllerCard);
|
viewCards.unshift(this.viewControllerCard);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
52
src/views/SceneView.ts
Normal file
52
src/views/SceneView.ts
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
import {Helper} from "../Helper";
|
||||||
|
import {AbstractView} from "./AbstractView";
|
||||||
|
import {views} from "../types/strategy/views";
|
||||||
|
|
||||||
|
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||||
|
/**
|
||||||
|
* Scene View Class.
|
||||||
|
*
|
||||||
|
* Used to create a view for entities of the scene domain.
|
||||||
|
*
|
||||||
|
* @class SceneView
|
||||||
|
* @extends AbstractView
|
||||||
|
*/
|
||||||
|
class SceneView extends AbstractView {
|
||||||
|
/**
|
||||||
|
* Domain of the view's entities.
|
||||||
|
*
|
||||||
|
* @type {string}
|
||||||
|
* @static
|
||||||
|
* @private
|
||||||
|
*/
|
||||||
|
static #domain: string = "scene";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Default configuration of the view.
|
||||||
|
*
|
||||||
|
* @type {views.ViewConfig}
|
||||||
|
* @private
|
||||||
|
*/
|
||||||
|
#defaultConfig: views.ViewConfig = {
|
||||||
|
title: Helper.customLocalize("scene.scenes"),
|
||||||
|
path: "scenes",
|
||||||
|
icon: "mdi:palette",
|
||||||
|
subview: false,
|
||||||
|
controllerCardOptions: {
|
||||||
|
showControls: false,
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class constructor.
|
||||||
|
*
|
||||||
|
* @param {views.ViewConfig} [options={}] Options for the view.
|
||||||
|
*/
|
||||||
|
constructor(options: views.ViewConfig = {}) {
|
||||||
|
super(SceneView.#domain);
|
||||||
|
|
||||||
|
this.config = Object.assign(this.config, this.#defaultConfig, options);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export {SceneView};
|
Reference in New Issue
Block a user