forked from DigiLive/mushroom-strategy
Add localization
Fixed dashboard strings are replaced with a string in the language as defined by the user. Currently, languages `en` and `nl` are supported. If the user-defined language isn't supported, the language will fall back to english. Untranslated strings will fall back to the translation keyword. Resolves #166
This commit is contained in:
@ -1,10 +1,11 @@
|
|||||||
import {configurationDefaults} from "./configurationDefaults";
|
import {getConfigurationDefaults} from "./configurationDefaults";
|
||||||
import {HassEntities, HassEntity} from "home-assistant-js-websocket";
|
import {HassEntities, HassEntity} from "home-assistant-js-websocket";
|
||||||
import deepmerge from "deepmerge";
|
import deepmerge from "deepmerge";
|
||||||
import {EntityRegistryEntry} from "./types/homeassistant/data/entity_registry";
|
import {EntityRegistryEntry} from "./types/homeassistant/data/entity_registry";
|
||||||
import {DeviceRegistryEntry} from "./types/homeassistant/data/device_registry";
|
import {DeviceRegistryEntry} from "./types/homeassistant/data/device_registry";
|
||||||
import {AreaRegistryEntry} from "./types/homeassistant/data/area_registry";
|
import {AreaRegistryEntry} from "./types/homeassistant/data/area_registry";
|
||||||
import {generic} from "./types/strategy/generic";
|
import {generic} from "./types/strategy/generic";
|
||||||
|
import setupCustomLocalize from "./localize";
|
||||||
import StrategyArea = generic.StrategyArea;
|
import StrategyArea = generic.StrategyArea;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -68,6 +69,7 @@ class Helper {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
static #debug: boolean;
|
static #debug: boolean;
|
||||||
|
static customLocalize: Function;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class constructor.
|
* Class constructor.
|
||||||
@ -140,8 +142,12 @@ class Helper {
|
|||||||
*/
|
*/
|
||||||
static async initialize(info: generic.DashBoardInfo): Promise<void> {
|
static async initialize(info: generic.DashBoardInfo): Promise<void> {
|
||||||
// Initialize properties.
|
// Initialize properties.
|
||||||
this.#hassStates = info.hass.states;
|
this.customLocalize = setupCustomLocalize(info.hass);
|
||||||
|
|
||||||
|
const configurationDefaults = getConfigurationDefaults(this.customLocalize)
|
||||||
this.#strategyOptions = deepmerge(configurationDefaults, info.config?.strategy?.options ?? {});
|
this.#strategyOptions = deepmerge(configurationDefaults, info.config?.strategy?.options ?? {});
|
||||||
|
|
||||||
|
this.#hassStates = info.hass.states;
|
||||||
this.#debug = this.#strategyOptions.debug;
|
this.#debug = this.#strategyOptions.debug;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
@ -4,151 +4,153 @@ import StrategyDefaults = generic.StrategyDefaults;
|
|||||||
/**
|
/**
|
||||||
* Default configuration for the mushroom strategy.
|
* Default configuration for the mushroom strategy.
|
||||||
*/
|
*/
|
||||||
export const configurationDefaults: StrategyDefaults = {
|
export const getConfigurationDefaults = (localize: Function): StrategyDefaults => {
|
||||||
areas: {
|
return {
|
||||||
undisclosed: {
|
areas: {
|
||||||
area_id: "undisclosed",
|
undisclosed: {
|
||||||
floor_id: null,
|
area_id: "undisclosed",
|
||||||
name: "Undisclosed",
|
floor_id: null,
|
||||||
picture: null,
|
name: "Undisclosed",
|
||||||
icon: "mdi:floor-plan",
|
picture: null,
|
||||||
labels: [],
|
icon: "mdi:floor-plan",
|
||||||
aliases: [],
|
labels: [],
|
||||||
hidden: false,
|
aliases: [],
|
||||||
|
hidden: false,
|
||||||
|
}
|
||||||
|
},
|
||||||
|
debug: false,
|
||||||
|
domains: {
|
||||||
|
_: {
|
||||||
|
hide_config_entities: false,
|
||||||
|
},
|
||||||
|
default: {
|
||||||
|
title: localize("generic.miscellaneous"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
light: {
|
||||||
|
title: localize("light.lights"),
|
||||||
|
showControls: true,
|
||||||
|
iconOn: "mdi:lightbulb",
|
||||||
|
iconOff: "mdi:lightbulb-off",
|
||||||
|
onService: "light.turn_on",
|
||||||
|
offService: "light.turn_off",
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
fan: {
|
||||||
|
title: localize("fan.fans"),
|
||||||
|
showControls: true,
|
||||||
|
iconOn: "mdi:fan",
|
||||||
|
iconOff: "mdi:fan-off",
|
||||||
|
onService: "fan.turn_on",
|
||||||
|
offService: "fan.turn_off",
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
cover: {
|
||||||
|
title: localize("cover.covers"),
|
||||||
|
showControls: true,
|
||||||
|
iconOn: "mdi:arrow-up",
|
||||||
|
iconOff: "mdi:arrow-down",
|
||||||
|
onService: "cover.open_cover",
|
||||||
|
offService: "cover.close_cover",
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
switch: {
|
||||||
|
title: localize("switch.switches"),
|
||||||
|
showControls: true,
|
||||||
|
iconOn: "mdi:power-plug",
|
||||||
|
iconOff: "mdi:power-plug-off",
|
||||||
|
onService: "switch.turn_on",
|
||||||
|
offService: "switch.turn_off",
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
camera: {
|
||||||
|
title: localize("camera.cameras"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
lock: {
|
||||||
|
title: localize("lock.locks"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
climate: {
|
||||||
|
title: localize("climate.climates"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
media_player: {
|
||||||
|
title: localize("media_player.media_players"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
sensor: {
|
||||||
|
title: localize("sensor.sensors"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
binary_sensor: {
|
||||||
|
title: `${localize("sensor.binary")} ` + localize("sensor.sensors"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
number: {
|
||||||
|
title: localize("generic.numbers"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
vacuum: {
|
||||||
|
title: localize("vacuum.vacuums"),
|
||||||
|
showControls: true,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
select: {
|
||||||
|
title: localize("select.selects"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
input_select: {
|
||||||
|
title: localize("input_select.input_selects"),
|
||||||
|
showControls: false,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
home_view: {
|
||||||
|
hidden: [],
|
||||||
|
},
|
||||||
|
views: {
|
||||||
|
home: {
|
||||||
|
order: 1,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
light: {
|
||||||
|
order: 2,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
fan: {
|
||||||
|
order: 3,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
cover: {
|
||||||
|
order: 4,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
switch: {
|
||||||
|
order: 5,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
climate: {
|
||||||
|
order: 6,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
camera: {
|
||||||
|
order: 7,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
vacuum: {
|
||||||
|
order: 8,
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
}
|
}
|
||||||
},
|
};
|
||||||
debug: false,
|
|
||||||
domains: {
|
|
||||||
_: {
|
|
||||||
hide_config_entities: false,
|
|
||||||
},
|
|
||||||
default: {
|
|
||||||
title: "Miscellaneous",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
light: {
|
|
||||||
title: "Lights",
|
|
||||||
showControls: true,
|
|
||||||
iconOn: "mdi:lightbulb",
|
|
||||||
iconOff: "mdi:lightbulb-off",
|
|
||||||
onService: "light.turn_on",
|
|
||||||
offService: "light.turn_off",
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
fan: {
|
|
||||||
title: "Fans",
|
|
||||||
showControls: true,
|
|
||||||
iconOn: "mdi:fan",
|
|
||||||
iconOff: "mdi:fan-off",
|
|
||||||
onService: "fan.turn_on",
|
|
||||||
offService: "fan.turn_off",
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
cover: {
|
|
||||||
title: "Covers",
|
|
||||||
showControls: true,
|
|
||||||
iconOn: "mdi:arrow-up",
|
|
||||||
iconOff: "mdi:arrow-down",
|
|
||||||
onService: "cover.open_cover",
|
|
||||||
offService: "cover.close_cover",
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
switch: {
|
|
||||||
title: "Switches",
|
|
||||||
showControls: true,
|
|
||||||
iconOn: "mdi:power-plug",
|
|
||||||
iconOff: "mdi:power-plug-off",
|
|
||||||
onService: "switch.turn_on",
|
|
||||||
offService: "switch.turn_off",
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
camera: {
|
|
||||||
title: "Cameras",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
lock: {
|
|
||||||
title: "Locks",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
climate: {
|
|
||||||
title: "Climates",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
media_player: {
|
|
||||||
title: "Media Players",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
sensor: {
|
|
||||||
title: "Sensors",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
binary_sensor: {
|
|
||||||
title: "Binary Sensors",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
number: {
|
|
||||||
title: "Numbers",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
vacuum: {
|
|
||||||
title: "Vacuums",
|
|
||||||
showControls: true,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
select: {
|
|
||||||
title: "Selects",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
input_select: {
|
|
||||||
title: "Input Selects",
|
|
||||||
showControls: false,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
home_view: {
|
|
||||||
hidden: [],
|
|
||||||
},
|
|
||||||
views: {
|
|
||||||
home: {
|
|
||||||
order: 1,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
light: {
|
|
||||||
order: 2,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
fan: {
|
|
||||||
order: 3,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
cover: {
|
|
||||||
order: 4,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
switch: {
|
|
||||||
order: 5,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
climate: {
|
|
||||||
order: 6,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
camera: {
|
|
||||||
order: 7,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
vacuum: {
|
|
||||||
order: 8,
|
|
||||||
hidden: false,
|
|
||||||
},
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
56
src/localize.ts
Normal file
56
src/localize.ts
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
import {HomeAssistant} from "./types/homeassistant/types";
|
||||||
|
import * as en from "./translations/en.json";
|
||||||
|
import * as nl from "./translations/nl.json";
|
||||||
|
|
||||||
|
/* Registry of currently supported languages */
|
||||||
|
const languages: Record<string, unknown> = {
|
||||||
|
en,
|
||||||
|
nl,
|
||||||
|
};
|
||||||
|
|
||||||
|
/* The fallback language if the user-defined language isn't defined */
|
||||||
|
const DEFAULT_LANG = "en";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a string by keyword and language.
|
||||||
|
*
|
||||||
|
* @param {string} key The keyword to look for in object notation (E.g. generic.home).
|
||||||
|
* @param {string} lang The language to get the string from (E.g. en).
|
||||||
|
*
|
||||||
|
* @return {string | undefined} The requested string or undefined if the keyword doesn't exist/on error.
|
||||||
|
*/
|
||||||
|
function getTranslatedString(key: string, lang: string): string | undefined {
|
||||||
|
try {
|
||||||
|
return key
|
||||||
|
.split(".")
|
||||||
|
.reduce(
|
||||||
|
(o, i) => (o as Record<string, unknown>)[i],
|
||||||
|
languages[lang]
|
||||||
|
) as string;
|
||||||
|
} catch (_) {
|
||||||
|
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set up the localization.
|
||||||
|
*
|
||||||
|
* It reads the user-defined language with a fall-back to english and returns a function to get strings from
|
||||||
|
* language-files by keyword.
|
||||||
|
*
|
||||||
|
* If the keyword is undefined, or on error, the keyword itself is returned.
|
||||||
|
*
|
||||||
|
* @param {HomeAssistant} hass The Home Assistant object.
|
||||||
|
* @return {(key: string) => string} The function to call for translating strings.
|
||||||
|
*/
|
||||||
|
export default function setupCustomLocalize(hass?: HomeAssistant): (key: string) => string {
|
||||||
|
return function (key: string) {
|
||||||
|
const lang = hass?.locale.language ?? DEFAULT_LANG;
|
||||||
|
|
||||||
|
let translated = getTranslatedString(key, lang);
|
||||||
|
if (!translated) translated = getTranslatedString(key, DEFAULT_LANG);
|
||||||
|
|
||||||
|
return translated ?? key;
|
||||||
|
};
|
||||||
|
}
|
61
src/translations/en.json
Normal file
61
src/translations/en.json
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
{
|
||||||
|
"camera": {
|
||||||
|
"all_cameras": "All Cameras",
|
||||||
|
"cameras": "Cameras"
|
||||||
|
},
|
||||||
|
"climate": {
|
||||||
|
"all_climates": "All Climates",
|
||||||
|
"climates": "Climates"
|
||||||
|
},
|
||||||
|
"covers": {
|
||||||
|
"all_covers": "All Covers",
|
||||||
|
"covers": "Covers"
|
||||||
|
},
|
||||||
|
"fan": {
|
||||||
|
"all_fans": "All Fans",
|
||||||
|
"fans": "Fans"
|
||||||
|
},
|
||||||
|
"generic": {
|
||||||
|
"all": "All",
|
||||||
|
"areas": "Areas",
|
||||||
|
"busy": "Busy",
|
||||||
|
"good_afternoon": "Good afternoon",
|
||||||
|
"good_evening": "Good evening",
|
||||||
|
"good_morning": "Good morning",
|
||||||
|
"hello": "Hello",
|
||||||
|
"home": "Home",
|
||||||
|
"miscellaneous": "Miscellaneous",
|
||||||
|
"numbers": "Numbers",
|
||||||
|
"off": "Off",
|
||||||
|
"on": "On",
|
||||||
|
"open": "Open"
|
||||||
|
},
|
||||||
|
"input_select": {
|
||||||
|
"input_selects": "Input Selects"
|
||||||
|
},
|
||||||
|
"light": {
|
||||||
|
"all_lights": "All Lights",
|
||||||
|
"lights": "Lights"
|
||||||
|
},
|
||||||
|
"lock": {
|
||||||
|
"locks": "Locks"
|
||||||
|
},
|
||||||
|
"media_player": {
|
||||||
|
"media_players": "Mediaplayers"
|
||||||
|
},
|
||||||
|
"select": {
|
||||||
|
"selects": "Selects"
|
||||||
|
},
|
||||||
|
"sensor": {
|
||||||
|
"binary": "Binary",
|
||||||
|
"sensors": "Sensors"
|
||||||
|
},
|
||||||
|
"switch": {
|
||||||
|
"all_switches": "All Switches",
|
||||||
|
"switches": "Switches"
|
||||||
|
},
|
||||||
|
"vacuum": {
|
||||||
|
"all_vacuums": "All Vacuums",
|
||||||
|
"vacuums": "Vacuums"
|
||||||
|
}
|
||||||
|
}
|
61
src/translations/nl.json
Normal file
61
src/translations/nl.json
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
{
|
||||||
|
"camera": {
|
||||||
|
"all_cameras": "Alle Cameras",
|
||||||
|
"cameras": "Cameras"
|
||||||
|
},
|
||||||
|
"climate": {
|
||||||
|
"all_climates": "Alle Klimaatregelingen",
|
||||||
|
"climates": "Klimaatregelingen"
|
||||||
|
},
|
||||||
|
"covers": {
|
||||||
|
"all_covers": "Alle Bedekkingen",
|
||||||
|
"covers": "Bedekkingen"
|
||||||
|
},
|
||||||
|
"fan": {
|
||||||
|
"all_fans": "Alle Ventilatoren",
|
||||||
|
"fans": "Ventilatoren"
|
||||||
|
},
|
||||||
|
"generic": {
|
||||||
|
"all": "Alle",
|
||||||
|
"areas": "Ruimtes",
|
||||||
|
"busy": "Bezig",
|
||||||
|
"good_afternoon": "Goede middag",
|
||||||
|
"good_evening": "Goede avond",
|
||||||
|
"good_morning": "Goede morgen",
|
||||||
|
"hello": "Hallo",
|
||||||
|
"home": "Start",
|
||||||
|
"miscellaneous": "Overige",
|
||||||
|
"numbers": "Nummers",
|
||||||
|
"off": "Uit",
|
||||||
|
"on": "Aan",
|
||||||
|
"open": "Open"
|
||||||
|
},
|
||||||
|
"input_select": {
|
||||||
|
"input_selects": "Lijsten"
|
||||||
|
},
|
||||||
|
"light": {
|
||||||
|
"all_lights": "Alle Lampen",
|
||||||
|
"lights": "Lampen"
|
||||||
|
},
|
||||||
|
"lock": {
|
||||||
|
"locks": "Sloten"
|
||||||
|
},
|
||||||
|
"media_player": {
|
||||||
|
"media_players": "Mediaspelers"
|
||||||
|
},
|
||||||
|
"select": {
|
||||||
|
"selects": "Statuslijsten"
|
||||||
|
},
|
||||||
|
"sensor": {
|
||||||
|
"binary": "Binaire",
|
||||||
|
"sensors": "Sensoren"
|
||||||
|
},
|
||||||
|
"switch": {
|
||||||
|
"all_switches": "Alle Schakelaars",
|
||||||
|
"switches": "Schakelaars"
|
||||||
|
},
|
||||||
|
"vacuum": {
|
||||||
|
"all_vacuums": "Alle Afzuiging",
|
||||||
|
"vacuums": "Afzuiging"
|
||||||
|
}
|
||||||
|
}
|
@ -30,7 +30,7 @@ class CameraView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Cameras",
|
title: Helper.customLocalize("camera.cameras"),
|
||||||
path: "cameras",
|
path: "cameras",
|
||||||
icon: "mdi:cctv",
|
icon: "mdi:cctv",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -46,8 +46,10 @@ class CameraView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Cameras",
|
title: Helper.customLocalize("camera.all_cameras"),
|
||||||
subtitle: Helper.getCountTemplate(CameraView.#domain, "ne", "off") + " cameras on",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(CameraView.#domain, "ne", "off")} ${Helper.customLocalize("camera.cameras")} `
|
||||||
|
+ Helper.customLocalize("generic.busy"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -30,7 +30,7 @@ class ClimateView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Climates",
|
title: Helper.customLocalize("climate.climates"),
|
||||||
path: "climates",
|
path: "climates",
|
||||||
icon: "mdi:thermostat",
|
icon: "mdi:thermostat",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -46,8 +46,10 @@ class ClimateView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Climates",
|
title: Helper.customLocalize("climate.all_climates"),
|
||||||
subtitle: Helper.getCountTemplate(ClimateView.#domain, "ne", "off") + " climates on",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(ClimateView.#domain, "ne", "off")} ${Helper.customLocalize("climate.climates")} `
|
||||||
|
+ Helper.customLocalize("generic.busy"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -30,7 +30,7 @@ class CoverView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Covers",
|
title: Helper.customLocalize("cover.covers"),
|
||||||
path: "covers",
|
path: "covers",
|
||||||
icon: "mdi:window-open",
|
icon: "mdi:window-open",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -49,8 +49,10 @@ class CoverView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Covers",
|
title: Helper.customLocalize("cover.all_covers"),
|
||||||
subtitle: Helper.getCountTemplate(CoverView.#domain, "eq", "open") + " covers open",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(CoverView.#domain, "eq", "open")} ${Helper.customLocalize("cover.covers")} `
|
||||||
|
+ Helper.customLocalize("generic.open"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -30,7 +30,7 @@ class FanView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Fans",
|
title: Helper.customLocalize("fan.fans"),
|
||||||
path: "fans",
|
path: "fans",
|
||||||
icon: "mdi:fan",
|
icon: "mdi:fan",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -49,8 +49,10 @@ class FanView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Fans",
|
title: Helper.customLocalize("fan.all_fans"),
|
||||||
subtitle: Helper.getCountTemplate(FanView.#domain, "eq", "on") + " fans on",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(FanView.#domain, "eq", "on")} ${Helper.customLocalize("fan.fans")} `
|
||||||
|
+ Helper.customLocalize("generic.on"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -27,7 +27,7 @@ class HomeView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Home",
|
title: Helper.customLocalize("generic.home"),
|
||||||
icon: "mdi:home-assistant",
|
icon: "mdi:home-assistant",
|
||||||
path: "home",
|
path: "home",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -77,24 +77,28 @@ class HomeView extends AbstractView {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!Helper.strategyOptions.home_view.hidden.includes("greeting")) {
|
if (!Helper.strategyOptions.home_view.hidden.includes("greeting")) {
|
||||||
homeViewCards.push({
|
const greeting =
|
||||||
type: "custom:mushroom-template-card",
|
homeViewCards.push({
|
||||||
primary: "{% set time = now().hour %} {% if (time >= 18) %} Good Evening, {{user}}! {% elif (time >= 12) %} Good Afternoon, {{user}}! {% elif (time >= 5) %} Good Morning, {{user}}! {% else %} Hello, {{user}}! {% endif %}",
|
type: "custom:mushroom-template-card",
|
||||||
icon: "mdi:hand-wave",
|
primary:
|
||||||
icon_color: "orange",
|
`{% set time = now().hour %} {% if (time >= 18) %} ${Helper.customLocalize("generic.good_evening")},{{user}}!
|
||||||
tap_action: {
|
{% elif (time >= 12) %} ${Helper.customLocalize("generic.good_afternoon")}, {{user}}!
|
||||||
action: "none",
|
{% elif (time >= 5) %} ${Helper.customLocalize("generic.good_morning")}, {{user}}!
|
||||||
} as ActionConfig,
|
{% else %} ${Helper.customLocalize("generic.hello")}, {{user}}! {% endif %}`,
|
||||||
double_tap_action: {
|
icon: "mdi:hand-wave",
|
||||||
action: "none",
|
icon_color: "orange",
|
||||||
} as ActionConfig,
|
tap_action: {
|
||||||
hold_action: {
|
action: "none",
|
||||||
action: "none",
|
} as ActionConfig,
|
||||||
} as ActionConfig,
|
double_tap_action: {
|
||||||
} as TemplateCardConfig);
|
action: "none",
|
||||||
|
} as ActionConfig,
|
||||||
|
hold_action: {
|
||||||
|
action: "none",
|
||||||
|
} as ActionConfig,
|
||||||
|
} as TemplateCardConfig);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Add quick access cards.
|
// Add quick access cards.
|
||||||
if (options.quick_access_cards) {
|
if (options.quick_access_cards) {
|
||||||
homeViewCards.push(...options.quick_access_cards);
|
homeViewCards.push(...options.quick_access_cards);
|
||||||
@ -225,7 +229,7 @@ class HomeView extends AbstractView {
|
|||||||
if (!Helper.strategyOptions.home_view.hidden.includes("areasTitle")) {
|
if (!Helper.strategyOptions.home_view.hidden.includes("areasTitle")) {
|
||||||
groupedCards.push({
|
groupedCards.push({
|
||||||
type: "custom:mushroom-title-card",
|
type: "custom:mushroom-title-card",
|
||||||
title: "Areas",
|
title: Helper.customLocalize("generic.areas"),
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -30,7 +30,7 @@ class LightView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Lights",
|
title: Helper.customLocalize("light.lights"),
|
||||||
path: "lights",
|
path: "lights",
|
||||||
icon: "mdi:lightbulb-group",
|
icon: "mdi:lightbulb-group",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -49,8 +49,10 @@ class LightView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Lights",
|
title: Helper.customLocalize("light.all_lights"),
|
||||||
subtitle: Helper.getCountTemplate(LightView.#domain, "eq", "on") + " lights on",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(LightView.#domain, "eq", "on")} ${Helper.customLocalize("light.lights")} `
|
||||||
|
+ Helper.customLocalize("generic.on"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -30,7 +30,7 @@ class SwitchView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Switches",
|
title: Helper.customLocalize("switch.switches"),
|
||||||
path: "switches",
|
path: "switches",
|
||||||
icon: "mdi:dip-switch",
|
icon: "mdi:dip-switch",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -49,8 +49,10 @@ class SwitchView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Switches",
|
title: Helper.customLocalize("switch.all_switches"),
|
||||||
subtitle: Helper.getCountTemplate(SwitchView.#domain, "eq", "on") + " switches on",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(SwitchView.#domain, "eq", "on")} ${Helper.customLocalize("switch.switches")} `
|
||||||
|
+ Helper.customLocalize("generic.on"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -30,7 +30,7 @@ class VacuumView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#defaultConfig: views.ViewConfig = {
|
#defaultConfig: views.ViewConfig = {
|
||||||
title: "Vacuums",
|
title: Helper.customLocalize("vacuum.vacuums"),
|
||||||
path: "vacuums",
|
path: "vacuums",
|
||||||
icon: "mdi:robot-vacuum",
|
icon: "mdi:robot-vacuum",
|
||||||
subview: false,
|
subview: false,
|
||||||
@ -49,8 +49,10 @@ class VacuumView extends AbstractView {
|
|||||||
* @private
|
* @private
|
||||||
*/
|
*/
|
||||||
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
#viewControllerCardConfig: cards.ControllerCardOptions = {
|
||||||
title: "All Vacuums",
|
title: Helper.customLocalize("vacuum.all_vacuums"),
|
||||||
subtitle: Helper.getCountTemplate(VacuumView.#domain, "ne", "off") + " vacuums on",
|
subtitle:
|
||||||
|
`${Helper.getCountTemplate(VacuumView.#domain, "ne", "off")} ${Helper.customLocalize("vacuum.vacuums")} `
|
||||||
|
+ Helper.customLocalize("generic.busy"),
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -29,7 +29,9 @@
|
|||||||
"strictNullChecks": true,
|
"strictNullChecks": true,
|
||||||
|
|
||||||
/* Completeness */
|
/* Completeness */
|
||||||
"skipLibCheck": true
|
"skipLibCheck": true,
|
||||||
|
|
||||||
|
"resolveJsonModule": true,
|
||||||
},
|
},
|
||||||
"ts-node": {
|
"ts-node": {
|
||||||
"compilerOptions": {
|
"compilerOptions": {
|
||||||
|
Reference in New Issue
Block a user