mirror of
https://github.com/DigiLive/mushroom-strategy.git
synced 2025-08-09 14:24:26 +02:00
Refactor chips to badges
This commit is contained in:
@@ -116,7 +116,7 @@ class Registry {
|
||||
const { ConfigurationDefaults } = await import('./configurationDefaults');
|
||||
|
||||
try {
|
||||
Registry._strategyOptions = deepmerge(ConfigurationDefaults, info.config?.strategy?.options ?? {});
|
||||
Registry._strategyOptions = deepmerge(ConfigurationDefaults, info.config.strategy.options ?? {});
|
||||
} catch (e) {
|
||||
logMessage(lvlFatal, 'Error importing strategy options!', e);
|
||||
}
|
||||
@@ -189,7 +189,6 @@ class Registry {
|
||||
Registry.strategyOptions.areas.undisclosed.type = 'default';
|
||||
|
||||
// Remove hidden areas if configured as so and sort them by name.
|
||||
|
||||
Registry._areas = new RegistryFilter(Registry.areas).isNotHidden().orderBy(['order', 'name'], 'asc').toList();
|
||||
}
|
||||
|
||||
@@ -200,7 +199,7 @@ class Registry {
|
||||
Registry.strategyOptions.views = Object.fromEntries(
|
||||
entries.sort(([_, a], [__, b]) => {
|
||||
return (a.order ?? Infinity) - (b.order ?? Infinity) || (a.title ?? '').localeCompare(b.title ?? '');
|
||||
}),
|
||||
})
|
||||
) as Record<SupportedViews, StrategyViewConfig>;
|
||||
};
|
||||
|
||||
@@ -216,7 +215,7 @@ class Registry {
|
||||
}
|
||||
|
||||
return 0; // Maintain the original order when none or only one item is sortable.
|
||||
}),
|
||||
})
|
||||
) as { [K in SupportedDomains]: K extends '_' ? AllDomainsConfig : SingleDomainConfig };
|
||||
};
|
||||
|
||||
@@ -256,7 +255,7 @@ class Registry {
|
||||
.whereDomain(domain)
|
||||
.where((entity) => !entity.entity_id.endsWith('_stateful_scene') && entity.platform !== 'group')
|
||||
.toList()
|
||||
.map((entity) => `states['${entity.entity_id}']`),
|
||||
.map((entity) => `states['${entity.entity_id}']`)
|
||||
);
|
||||
|
||||
// noinspection SpellCheckingInspection
|
||||
@@ -273,15 +272,15 @@ class Registry {
|
||||
/**
|
||||
* Get the names of the specified type which aren't set to hidden in the strategy options.
|
||||
*
|
||||
* @param {string} type The type of options to filter ("domain", "view", "chip").
|
||||
* @param {string} type The type of options to filter ("domain", "view", "badge").
|
||||
*
|
||||
* @returns {string[]} For domains and views: names of items that aren't hidden.
|
||||
* For chips: names of items that are explicitly set to true.
|
||||
* For badges: names of items that are explicitly set to true.
|
||||
*/
|
||||
static getExposedNames(type: 'domain' | 'view' | 'chip'): string[] {
|
||||
// TODO: Align chip with other types.
|
||||
if (type === 'chip') {
|
||||
return Object.entries(Registry.strategyOptions.chips)
|
||||
static getExposedNames(type: 'domain' | 'view' | 'badge'): string[] {
|
||||
// TODO: Align badge with other types.
|
||||
if (type === 'badge') {
|
||||
return Object.entries(Registry.strategyOptions.badges)
|
||||
.filter(([_, value]) => value === true)
|
||||
.map(([key]) => key.split('_')[0]);
|
||||
}
|
||||
|
@@ -1,25 +1,24 @@
|
||||
import { Registry } from '../Registry';
|
||||
import { LovelaceChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import { logMessage, lvlFatal } from '../utilities/debug';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
abstract class AbstractChip {
|
||||
abstract class AbstractBadge {
|
||||
/**
|
||||
* Abstract Chip class.
|
||||
* Abstract Badge class.
|
||||
*
|
||||
* To create a chip configuration, this class should be extended by a child class.
|
||||
* Child classes should override the default configuration so the chip correctly reflects the entity.
|
||||
* To create a badge configuration, this class should be extended by a child class.
|
||||
* Child classes should override the default configuration so the badge correctly reflects the entity.
|
||||
*
|
||||
* @remarks
|
||||
* Before using this class, the Registry module must be initialized by calling {@link Registry.initialize}.
|
||||
*/
|
||||
|
||||
/**
|
||||
* Configuration of the chip.
|
||||
* Configuration of the badge.
|
||||
*
|
||||
* Child classes should override this property to reflect their own card type and options.
|
||||
* Child classes should override this property to reflect their own badge type and options.
|
||||
*/
|
||||
protected configuration: LovelaceChipConfig = {
|
||||
// TODO: Check if this is correct vs custom:mushroom-template-badge. Also in child classes.
|
||||
protected configuration: LovelaceBadgeConfig = {
|
||||
type: 'template',
|
||||
};
|
||||
|
||||
@@ -31,18 +30,18 @@ abstract class AbstractChip {
|
||||
*/
|
||||
protected constructor() {
|
||||
if (!Registry.initialized) {
|
||||
logMessage(lvlFatal, 'Registry not initialized!');
|
||||
logMessage(lvlFatal, 'Registry is not initialized!');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a chip configuration.
|
||||
* Get a badge configuration.
|
||||
*
|
||||
* The configuration should be set by any of the child classes so the chip correctly reflects an entity.
|
||||
* The configuration should be set by any of the child classes so the badge correctly reflects an entity.
|
||||
*/
|
||||
getChipConfiguration(): LovelaceChipConfig {
|
||||
getConfiguration(): LovelaceBadgeConfig {
|
||||
return this.configuration;
|
||||
}
|
||||
}
|
||||
|
||||
export default AbstractChip;
|
||||
export default AbstractBadge;
|
51
src/badges/ClimateBadge.ts
Normal file
51
src/badges/ClimateBadge.ts
Normal file
@@ -0,0 +1,51 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import AbstractBadge from './AbstractBadge';
|
||||
import { Registry } from '../Registry';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* Climate Badge class.
|
||||
*
|
||||
* Used to create a badge configuration to indicate how many climates are operating.
|
||||
*/
|
||||
class ClimateBadge extends AbstractBadge {
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {LovelaceBadgeConfig} [customConfiguration] Custom badge configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: LovelaceBadgeConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...ClimateBadge.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the badge. */
|
||||
static getDefaultConfig(): LovelaceBadgeConfig {
|
||||
return {
|
||||
type: 'custom:mushroom-template-badge',
|
||||
icon: 'mdi:thermostat',
|
||||
color: 'orange',
|
||||
content: Registry.getCountTemplate('climate', 'ne', 'off'),
|
||||
/* `
|
||||
🔄${Registry.getCountTemplate('climate', 'eq', 'auto')}
|
||||
↕️❄️${Registry.getCountTemplate('climate', 'eq', 'heat_cool')}
|
||||
🔥${Registry.getCountTemplate('climate', 'eq', 'heat')}
|
||||
❄️${Registry.getCountTemplate('climate', 'eq', 'cool')}
|
||||
💧${Registry.getCountTemplate('climate', 'eq', 'dry')}
|
||||
💨${Registry.getCountTemplate('climate', 'eq', 'fan_only')}
|
||||
⭕${Registry.getCountTemplate('climate', 'eq', 'off')}
|
||||
`,*/
|
||||
tap_action: {
|
||||
action: 'none',
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'climates',
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export default ClimateBadge;
|
42
src/badges/CoverBadge.ts
Normal file
42
src/badges/CoverBadge.ts
Normal file
@@ -0,0 +1,42 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import AbstractBadge from './AbstractBadge';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* Cover Badge class.
|
||||
*
|
||||
* Used to create a badge configuration to indicate how many covers aren't closed.
|
||||
*/
|
||||
class CoverBadge extends AbstractBadge {
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {LovelaceBadgeConfig} [customConfiguration] Custom badge configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: LovelaceBadgeConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...CoverBadge.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the badge. */
|
||||
static getDefaultConfig(): LovelaceBadgeConfig {
|
||||
return {
|
||||
type: 'custom:mushroom-template-badge',
|
||||
icon: 'mdi:window-open',
|
||||
color: 'cyan',
|
||||
content: Registry.getCountTemplate('cover', 'search', '(open|opening|closing)'),
|
||||
tap_action: {
|
||||
action: 'none',
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'covers',
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export default CoverBadge;
|
49
src/badges/FanBadge.ts
Normal file
49
src/badges/FanBadge.ts
Normal file
@@ -0,0 +1,49 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import RegistryFilter from '../utilities/RegistryFilter';
|
||||
import AbstractBadge from './AbstractBadge';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* Fan Badge class.
|
||||
*
|
||||
* Used to create a badge to indicate how many fans are on and to switch them all off.
|
||||
*/
|
||||
class FanBadge extends AbstractBadge {
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {LovelaceBadgeConfig} [customConfiguration] Custom badge configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: LovelaceBadgeConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...FanBadge.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the badge. */
|
||||
static getDefaultConfig(): LovelaceBadgeConfig {
|
||||
return {
|
||||
type: 'custom:mushroom-template-badge',
|
||||
icon: 'mdi:fan',
|
||||
color: 'green',
|
||||
content: Registry.getCountTemplate('fan', 'eq', 'on'),
|
||||
tap_action: {
|
||||
action: 'perform-action',
|
||||
perform_action: 'fan.turn_off',
|
||||
target: {
|
||||
entity_id: new RegistryFilter(Registry.entities)
|
||||
.whereDomain('fan')
|
||||
.getValuesByProperty('entity_id') as string[],
|
||||
},
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'fans',
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export default FanBadge;
|
49
src/badges/LightBadge.ts
Normal file
49
src/badges/LightBadge.ts
Normal file
@@ -0,0 +1,49 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import RegistryFilter from '../utilities/RegistryFilter';
|
||||
import AbstractBadge from './AbstractBadge';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* Light Badge class.
|
||||
*
|
||||
* Used to create a badge configuration to indicate how many lights are on and to switch them all off.
|
||||
*/
|
||||
class LightBadge extends AbstractBadge {
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {LovelaceBadgeConfig} [customConfiguration] Custom badge configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: LovelaceBadgeConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...LightBadge.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the badge. */
|
||||
static getDefaultConfig(): LovelaceBadgeConfig {
|
||||
return {
|
||||
type: 'custom:mushroom-template-badge',
|
||||
icon: 'mdi:lightbulb-group',
|
||||
color: 'amber',
|
||||
content: Registry.getCountTemplate('light', 'eq', 'on'),
|
||||
tap_action: {
|
||||
action: 'perform-action',
|
||||
perform_action: 'light.turn_off',
|
||||
target: {
|
||||
entity_id: new RegistryFilter(Registry.entities)
|
||||
.whereDomain('light')
|
||||
.getValuesByProperty('entity_id') as string[],
|
||||
},
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'lights',
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export default LightBadge;
|
49
src/badges/SwitchBadge.ts
Normal file
49
src/badges/SwitchBadge.ts
Normal file
@@ -0,0 +1,49 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import RegistryFilter from '../utilities/RegistryFilter';
|
||||
import AbstractBadge from './AbstractBadge';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* Switch Badge class.
|
||||
*
|
||||
* Used to create a badge configuration to indicate how many switches are on and to switch them all off.
|
||||
*/
|
||||
class SwitchBadge extends AbstractBadge {
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {LovelaceBadgeConfig} [customConfiguration] Custom badge configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: LovelaceBadgeConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...SwitchBadge.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the badge. */
|
||||
static getDefaultConfig(): LovelaceBadgeConfig {
|
||||
return {
|
||||
type: 'custom:mushroom-template-badge',
|
||||
icon: 'mdi:dip-switch',
|
||||
color: 'blue',
|
||||
content: Registry.getCountTemplate('switch', 'eq', 'on'),
|
||||
tap_action: {
|
||||
action: 'perform-action',
|
||||
perform_action: 'switch.turn_off',
|
||||
target: {
|
||||
entity_id: new RegistryFilter(Registry.entities)
|
||||
.whereDomain('switch')
|
||||
.getValuesByProperty('entity_id') as string[],
|
||||
},
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'switches',
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export default SwitchBadge;
|
35
src/badges/WeatherBadge.ts
Normal file
35
src/badges/WeatherBadge.ts
Normal file
@@ -0,0 +1,35 @@
|
||||
// noinspection JSUnusedGlobalSymbols False positive.
|
||||
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
import { EntityBadgeConfig } from '../types/homeassistant/panels/lovelace/badges/types';
|
||||
import AbstractBadge from './AbstractBadge';
|
||||
|
||||
/**
|
||||
* Weather Badge class.
|
||||
*
|
||||
* Used to create a badge configuration to indicate the current weather.
|
||||
*/
|
||||
class WeatherBadge extends AbstractBadge {
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {string} entityId Id of a weather entity.
|
||||
* @param {LovelaceBadgeConfig} [customConfiguration] Custom badge configuration.
|
||||
*/
|
||||
constructor(entityId: string, customConfiguration?: LovelaceBadgeConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...WeatherBadge.getDefaultConfig(entityId), ...customConfiguration };
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the badge. */
|
||||
static getDefaultConfig(entityId: string): EntityBadgeConfig {
|
||||
return {
|
||||
type: 'entity',
|
||||
entity: entityId,
|
||||
state_content: ['state', 'temperature'],
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
export default WeatherBadge;
|
@@ -37,7 +37,7 @@ abstract class AbstractCard {
|
||||
*/
|
||||
protected constructor(entity: RegistryEntry) {
|
||||
if (!Registry.initialized) {
|
||||
logMessage(lvlFatal, 'Registry not initialized!');
|
||||
logMessage(lvlFatal, 'Registry is not initialized!');
|
||||
}
|
||||
|
||||
this.entity = entity;
|
||||
|
@@ -1,42 +0,0 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import { TemplateChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import AbstractChip from './AbstractChip';
|
||||
|
||||
/**
|
||||
* Climate Chip class.
|
||||
*
|
||||
* Used to create a chip configuration to indicate how many climates are operating.
|
||||
*/
|
||||
class ClimateChip extends AbstractChip {
|
||||
/** Returns the default configuration object for the chip. */
|
||||
static getDefaultConfig(): TemplateChipConfig {
|
||||
return {
|
||||
type: 'template',
|
||||
icon: 'mdi:thermostat',
|
||||
icon_color: 'orange',
|
||||
content: Registry.getCountTemplate('climate', 'ne', 'off'),
|
||||
tap_action: {
|
||||
action: 'none',
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'climates',
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {TemplateChipConfig} [customConfiguration] Custom chip configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: TemplateChipConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...ClimateChip.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
}
|
||||
|
||||
export default ClimateChip;
|
@@ -1,42 +0,0 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import { TemplateChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import AbstractChip from './AbstractChip';
|
||||
|
||||
/**
|
||||
* Cover Chip class.
|
||||
*
|
||||
* Used to create a chip configuration to indicate how many covers aren't closed.
|
||||
*/
|
||||
class CoverChip extends AbstractChip {
|
||||
/** Returns the default configuration object for the chip. */
|
||||
static getDefaultConfig(): TemplateChipConfig {
|
||||
return {
|
||||
type: 'template',
|
||||
icon: 'mdi:window-open',
|
||||
icon_color: 'cyan',
|
||||
content: Registry.getCountTemplate('cover', 'search', '(open|opening|closing)'),
|
||||
tap_action: {
|
||||
action: 'none',
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'covers',
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {TemplateChipConfig} [customConfiguration] Custom chip configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: TemplateChipConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...CoverChip.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
}
|
||||
|
||||
export default CoverChip;
|
@@ -1,49 +0,0 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import { TemplateChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import AbstractChip from './AbstractChip';
|
||||
import RegistryFilter from '../utilities/RegistryFilter';
|
||||
|
||||
/**
|
||||
* Fan Chip class.
|
||||
*
|
||||
* Used to create a chip to indicate how many fans are on and to switch them all off.
|
||||
*/
|
||||
class FanChip extends AbstractChip {
|
||||
/** Returns the default configuration object for the chip. */
|
||||
static getDefaultConfig(): TemplateChipConfig {
|
||||
return {
|
||||
type: 'template',
|
||||
icon: 'mdi:fan',
|
||||
icon_color: 'green',
|
||||
content: Registry.getCountTemplate('fan', 'eq', 'on'),
|
||||
tap_action: {
|
||||
action: 'perform-action',
|
||||
perform_action: 'fan.turn_off',
|
||||
target: {
|
||||
entity_id: new RegistryFilter(Registry.entities)
|
||||
.whereDomain('fan')
|
||||
.getValuesByProperty('entity_id') as string[],
|
||||
},
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'fans',
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {TemplateChipConfig} [customConfiguration] Custom chip configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: TemplateChipConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...FanChip.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
}
|
||||
|
||||
export default FanChip;
|
@@ -1,49 +0,0 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import { TemplateChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import AbstractChip from './AbstractChip';
|
||||
import RegistryFilter from '../utilities/RegistryFilter';
|
||||
|
||||
/**
|
||||
* Light Chip class.
|
||||
*
|
||||
* Used to create a chip configuration to indicate how many lights are on and to switch them all off.
|
||||
*/
|
||||
class LightChip extends AbstractChip {
|
||||
/** Returns the default configuration object for the chip. */
|
||||
static getDefaultConfig(): TemplateChipConfig {
|
||||
return {
|
||||
type: 'template',
|
||||
icon: 'mdi:lightbulb-group',
|
||||
icon_color: 'amber',
|
||||
content: Registry.getCountTemplate('light', 'eq', 'on'),
|
||||
tap_action: {
|
||||
action: 'perform-action',
|
||||
perform_action: 'light.turn_off',
|
||||
target: {
|
||||
entity_id: new RegistryFilter(Registry.entities)
|
||||
.whereDomain('light')
|
||||
.getValuesByProperty('entity_id') as string[],
|
||||
},
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'lights',
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {TemplateChipConfig} [customConfiguration] Custom chip configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: TemplateChipConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...LightChip.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
}
|
||||
|
||||
export default LightChip;
|
@@ -1,49 +0,0 @@
|
||||
// noinspection JSUnusedGlobalSymbols Class is dynamically imported.
|
||||
|
||||
import { Registry } from '../Registry';
|
||||
import { TemplateChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import AbstractChip from './AbstractChip';
|
||||
import RegistryFilter from '../utilities/RegistryFilter';
|
||||
|
||||
/**
|
||||
* Switch Chip class.
|
||||
*
|
||||
* Used to create a chip configuration to indicate how many switches are on and to switch them all off.
|
||||
*/
|
||||
class SwitchChip extends AbstractChip {
|
||||
/** Returns the default configuration object for the chip. */
|
||||
static getDefaultConfig(): TemplateChipConfig {
|
||||
return {
|
||||
type: 'template',
|
||||
icon: 'mdi:dip-switch',
|
||||
icon_color: 'blue',
|
||||
content: Registry.getCountTemplate('switch', 'eq', 'on'),
|
||||
tap_action: {
|
||||
action: 'perform-action',
|
||||
perform_action: 'switch.turn_off',
|
||||
target: {
|
||||
entity_id: new RegistryFilter(Registry.entities)
|
||||
.whereDomain('switch')
|
||||
.getValuesByProperty('entity_id') as string[],
|
||||
},
|
||||
},
|
||||
hold_action: {
|
||||
action: 'navigate',
|
||||
navigation_path: 'switches',
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {TemplateChipConfig} [customConfiguration] Custom chip configuration.
|
||||
*/
|
||||
constructor(customConfiguration?: TemplateChipConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...SwitchChip.getDefaultConfig(), ...customConfiguration };
|
||||
}
|
||||
}
|
||||
|
||||
export default SwitchChip;
|
@@ -1,35 +0,0 @@
|
||||
// noinspection JSUnusedGlobalSymbols False positive.
|
||||
|
||||
import { WeatherChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import AbstractChip from './AbstractChip';
|
||||
|
||||
/**
|
||||
* Weather Chip class.
|
||||
*
|
||||
* Used to create a chip configuration to indicate the current weather.
|
||||
*/
|
||||
class WeatherChip extends AbstractChip {
|
||||
/** Returns the default configuration object for the chip. */
|
||||
static getDefaultConfig(entityId: string): WeatherChipConfig {
|
||||
return {
|
||||
type: 'weather',
|
||||
entity: entityId,
|
||||
show_temperature: true,
|
||||
show_conditions: true,
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Class Constructor.
|
||||
*
|
||||
* @param {string} entityId Id of a weather entity.
|
||||
* @param {WeatherChipConfig} [customConfiguration] Custom chip configuration.
|
||||
*/
|
||||
constructor(entityId: string, customConfiguration?: WeatherChipConfig) {
|
||||
super();
|
||||
|
||||
this.configuration = { ...this.configuration, ...WeatherChip.getDefaultConfig(entityId), ...customConfiguration };
|
||||
}
|
||||
}
|
||||
|
||||
export default WeatherChip;
|
@@ -27,15 +27,15 @@ export const ConfigurationDefaults: StrategyDefaults = {
|
||||
},
|
||||
},
|
||||
card_options: {},
|
||||
chips: {
|
||||
// TODO: Make chips sortable.
|
||||
badges: {
|
||||
// TODO: Make badges sortable.
|
||||
weather_entity: 'auto',
|
||||
light_count: true,
|
||||
fan_count: true,
|
||||
cover_count: true,
|
||||
switch_count: true,
|
||||
climate_count: true,
|
||||
extra_chips: [],
|
||||
extra_badges: [],
|
||||
},
|
||||
debug: false,
|
||||
domains: {
|
||||
|
22
src/types/homeassistant/panels/lovelace/badges/types.ts
Normal file
22
src/types/homeassistant/panels/lovelace/badges/types.ts
Normal file
@@ -0,0 +1,22 @@
|
||||
import type { ActionConfig } from '../../../data/lovelace/config/action';
|
||||
import type { LovelaceBadgeConfig } from '../../../data/lovelace/config/badge';
|
||||
|
||||
export interface EntityBadgeConfig extends LovelaceBadgeConfig {
|
||||
type: 'entity';
|
||||
entity?: string;
|
||||
name?: string;
|
||||
icon?: string;
|
||||
color?: string;
|
||||
show_name?: boolean;
|
||||
show_state?: boolean;
|
||||
show_icon?: boolean;
|
||||
show_entity_picture?: boolean;
|
||||
state_content?: string | string[];
|
||||
tap_action?: ActionConfig;
|
||||
hold_action?: ActionConfig;
|
||||
double_tap_action?: ActionConfig;
|
||||
/**
|
||||
* @deprecated use `show_state`, `show_name`, `icon_type`
|
||||
*/
|
||||
display_type?: string;
|
||||
}
|
@@ -1,15 +1,15 @@
|
||||
import { LovelaceCardConfig } from '../../homeassistant/data/lovelace/config/card';
|
||||
import { LovelaceChipConfig } from '../utils/lovelace/chip/types';
|
||||
import { MushroomChipConfig } from '../utils/lovelace/chip/types';
|
||||
|
||||
/**
|
||||
* Chips Card Configuration
|
||||
*
|
||||
* @property {LovelaceChipConfig[]} chips - Array of chips to display.
|
||||
* @property {MushroomChipConfig[]} chips - Array of chips to display.
|
||||
* @property {string} [alignment] - Chips alignment (start, end, center, justify). Defaults to 'start'.
|
||||
*
|
||||
* @see https://github.com/piitaya/lovelace-mushroom/blob/main/docs/cards/chips.md
|
||||
*/
|
||||
export interface ChipsCardConfig extends LovelaceCardConfig {
|
||||
chips: LovelaceChipConfig[];
|
||||
chips: MushroomChipConfig[];
|
||||
alignment?: string;
|
||||
}
|
||||
|
@@ -146,12 +146,12 @@ export type TemplateChipConfig = {
|
||||
* Conditional Chip Config
|
||||
*
|
||||
* @property {"conditional"} type - Type of the chip.
|
||||
* @property {LovelaceChipConfig} [chip] - A chip configuration.
|
||||
* @property {MushroomChipConfig} [chip] - A chip configuration.
|
||||
* @property {[]} conditions - Conditions for the chip.
|
||||
*/
|
||||
export type ConditionalChipConfig = {
|
||||
type: 'conditional';
|
||||
chip?: LovelaceChipConfig;
|
||||
chip?: MushroomChipConfig;
|
||||
conditions: any[];
|
||||
};
|
||||
|
||||
@@ -189,8 +189,8 @@ export type SpacerChipConfig = {
|
||||
type: 'spacer';
|
||||
};
|
||||
|
||||
/** Lovelace Chip Config */
|
||||
export type LovelaceChipConfig =
|
||||
/** Mushroom Chip Config */
|
||||
export type MushroomChipConfig =
|
||||
| ActionChipConfig
|
||||
| AlarmControlPanelChipConfig
|
||||
| BackChipConfig
|
||||
|
@@ -5,9 +5,9 @@ import { LovelaceCardConfig } from '../homeassistant/data/lovelace/config/card';
|
||||
import { LovelaceConfig } from '../homeassistant/data/lovelace/config/types';
|
||||
import { LovelaceViewConfig, LovelaceViewRawConfig } from '../homeassistant/data/lovelace/config/view';
|
||||
import { HomeAssistant } from '../homeassistant/types';
|
||||
import { LovelaceChipConfig } from '../lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import { StrategyHeaderCardConfig } from './strategy-cards';
|
||||
import { AreaRegistryEntry } from '../homeassistant/data/area_registry';
|
||||
import { LovelaceBadgeConfig } from '../homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* List of supported domains.
|
||||
@@ -60,11 +60,11 @@ const SUPPORTED_VIEWS = [
|
||||
] as const;
|
||||
|
||||
/**
|
||||
* List of supported chips.
|
||||
* List of supported badges.
|
||||
*
|
||||
* This constant array defines the chips that are supported by the strategy.
|
||||
* This constant array defines the badges that are supported by the strategy.
|
||||
*/
|
||||
const SUPPORTED_CHIPS = ['light', 'fan', 'cover', 'switch', 'climate', 'weather'] as const;
|
||||
const SUPPORTED_BADGES = ['light', 'fan', 'cover', 'switch', 'climate', 'weather'] as const;
|
||||
|
||||
/**
|
||||
* List of home view sections.
|
||||
@@ -72,11 +72,11 @@ const SUPPORTED_CHIPS = ['light', 'fan', 'cover', 'switch', 'climate', 'weather'
|
||||
* This constant array defines the sections that are present in the home view.
|
||||
*/
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const HOME_VIEW_SECTIONS = ['areas', 'areasTitle', 'chips', 'greeting', 'persons'] as const;
|
||||
const HOME_VIEW_SECTIONS = ['areas', 'areasTitle', 'badges', 'greeting', 'persons'] as const;
|
||||
|
||||
export type SupportedDomains = (typeof SUPPORTED_DOMAINS)[number];
|
||||
export type SupportedViews = (typeof SUPPORTED_VIEWS)[number];
|
||||
export type SupportedChips = (typeof SUPPORTED_CHIPS)[number];
|
||||
export type SupportedBadges = (typeof SUPPORTED_BADGES)[number];
|
||||
export type HomeViewSections = (typeof HOME_VIEW_SECTIONS)[number];
|
||||
|
||||
/**
|
||||
@@ -205,7 +205,7 @@ export interface SingleDomainConfig extends Partial<StrategyHeaderCardConfig> {
|
||||
*
|
||||
* @property {Object.<string, StrategyArea>} areas - The configuration of areas.
|
||||
* @property {Object.<string, CustomCardConfig>} card_options - Card options for entities.
|
||||
* @property {ChipConfiguration} chips - The configuration of chips in the Home view.
|
||||
* @property {BadgeConfiguration} badges - The configuration of badges in the Home view.
|
||||
* @property {boolean} debug - If True, the strategy outputs more verbose debug information in the console.
|
||||
* @property {Object.<string, AllDomainsConfig | SingleDomainConfig>} domains - List of domains.
|
||||
* @property {LovelaceCardConfig[]} extra_cards - List of cards to show below room cards.
|
||||
@@ -218,7 +218,7 @@ export interface SingleDomainConfig extends Partial<StrategyHeaderCardConfig> {
|
||||
export interface StrategyConfig {
|
||||
areas: { [S: string]: StrategyArea };
|
||||
card_options: { [S: string]: CustomCardConfig };
|
||||
chips: ChipConfiguration;
|
||||
badges: BadgeConfiguration;
|
||||
debug: boolean;
|
||||
domains: { [K in SupportedDomains]: K extends '_' ? AllDomainsConfig : SingleDomainConfig };
|
||||
extra_cards: LovelaceCardConfig[];
|
||||
@@ -267,21 +267,21 @@ export interface AllAreasConfig {
|
||||
}
|
||||
|
||||
/**
|
||||
* A list of chips to show in the Home view.
|
||||
* A list of badges to show in the Home view.
|
||||
*
|
||||
* @property {boolean} climate_count - Chip to display the number of climates which are not off.
|
||||
* @property {boolean} cover_count - Chip to display the number of unclosed covers.
|
||||
* @property {LovelaceChipConfig[] | []} extra_chips - List of extra chips.
|
||||
* @property {boolean} fan_count - Chip to display the number of fans on.
|
||||
* @property {boolean} light_count - Chip to display the number of lights on.
|
||||
* @property {boolean} switch_count - Chip to display the number of switches on.
|
||||
* @property {'auto' | `weather.${string}`} weather_entity - Entity id for the weather chip to use.
|
||||
* @property {boolean} climate_count - Badge to display the number of climates which are not off.
|
||||
* @property {boolean} cover_count - Badge to display the number of unclosed covers.
|
||||
* @property {LovelaceBadgeConfig[] | []} extra_badges - List of extra badges.
|
||||
* @property {boolean} fan_count - Badge to display the number of fans on.
|
||||
* @property {boolean} light_count - Badge to display the number of lights on.
|
||||
* @property {boolean} switch_count - Badge to display the number of switches on.
|
||||
* @property {'auto' | `weather.${string}`} weather_entity - Entity id for the weather badges to use.
|
||||
* Accepts `weather.` ids or `auto` only.
|
||||
*/
|
||||
export interface ChipConfiguration {
|
||||
export interface BadgeConfiguration {
|
||||
climate_count: boolean;
|
||||
cover_count: boolean;
|
||||
extra_chips: LovelaceChipConfig[] | [];
|
||||
extra_badges: LovelaceBadgeConfig[] | [];
|
||||
fan_count: boolean;
|
||||
light_count: boolean;
|
||||
switch_count: boolean;
|
||||
@@ -361,11 +361,11 @@ export function isSupportedDomain(id: string): id is SupportedDomains {
|
||||
}
|
||||
|
||||
/**
|
||||
* Type guard to check if the strategy supports a given chip identifier.
|
||||
* Type guard to check if the strategy supports a given badge identifier.
|
||||
*
|
||||
* @param {string} id - The chip identifier to check (e.g., "light", "climate", "weather").
|
||||
* @returns {boolean} - True if the identifier represents a supported chip type.
|
||||
* @param {string} id - The badge identifier to check (e.g., "light", "climate", "weather").
|
||||
* @returns {boolean} - True if the identifier represents a supported badge type.
|
||||
*/
|
||||
export function isSupportedChip(id: string): id is SupportedChips {
|
||||
return isInSupportedList(id, SUPPORTED_CHIPS);
|
||||
export function isSupportedBadge(id: string): id is SupportedBadges {
|
||||
return isInSupportedList(id, SUPPORTED_BADGES);
|
||||
}
|
||||
|
117
src/utilities/NoticeManager.ts
Normal file
117
src/utilities/NoticeManager.ts
Normal file
@@ -0,0 +1,117 @@
|
||||
import { HomeAssistant } from '../types/homeassistant/types';
|
||||
|
||||
interface NoticeOptions {
|
||||
title?: string;
|
||||
storageKey?: string;
|
||||
version?: string;
|
||||
notificationId?: string;
|
||||
}
|
||||
|
||||
interface StoredNotice {
|
||||
shown: boolean;
|
||||
timestamp: string;
|
||||
version: string;
|
||||
}
|
||||
|
||||
export class NoticeManager {
|
||||
private static readonly DEFAULT_NAMESPACE = 'mushroom_strategy_notice';
|
||||
private static readonly DEFAULT_TITLE = 'Deprecation Notice';
|
||||
|
||||
constructor(
|
||||
private readonly hass: HomeAssistant,
|
||||
private readonly options: { namespace?: string } = {}
|
||||
) {}
|
||||
|
||||
/**
|
||||
* Shows a deprecation notice if it hasn't been shown before.
|
||||
*/
|
||||
public async showDeprecationNotice(id: string, message: string, options: NoticeOptions = {}): Promise<void> {
|
||||
const storageKey = this.getStorageKey(id, options.storageKey);
|
||||
const notificationId = options.notificationId || `mushroom_strategy_${id}`;
|
||||
const title = options.title || NoticeManager.DEFAULT_TITLE;
|
||||
|
||||
try {
|
||||
// Check if notice was already shown
|
||||
if (this.hasBeenShownSync(storageKey)) {
|
||||
return; // Notice was already shown
|
||||
}
|
||||
|
||||
// Show persistent notification
|
||||
await this.hass.callService('persistent_notification', 'create', {
|
||||
title: title,
|
||||
message: message,
|
||||
notification_id: notificationId,
|
||||
});
|
||||
|
||||
// Mark as shown
|
||||
this.markAsShownSync(storageKey, options.version || '1.0.0');
|
||||
} catch (error) {
|
||||
console.error(`[NoticeManager] Failed to show deprecation notice '${id}':`, error);
|
||||
// Fallback to console if service call fails
|
||||
console.warn(`[${title}] ${message}`);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Clears a previously shown notice.
|
||||
*/
|
||||
public async clearNotice(id: string, customKey?: string, notificationId?: string): Promise<void> {
|
||||
const storageKey = this.getStorageKey(id, customKey);
|
||||
try {
|
||||
// Clear from storage
|
||||
localStorage.removeItem(storageKey);
|
||||
|
||||
// Clear the notification if notificationId is provided
|
||||
if (notificationId) {
|
||||
await this.hass.callService('persistent_notification', 'dismiss', {
|
||||
notification_id: notificationId,
|
||||
});
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(`[NoticeManager] Failed to clear notice '${id}':`, error);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if a notice has been shown before.
|
||||
*/
|
||||
public hasBeenShown(id: string, customKey?: string): boolean {
|
||||
const storageKey = this.getStorageKey(id, customKey);
|
||||
return this.hasBeenShownSync(storageKey);
|
||||
}
|
||||
|
||||
private hasBeenShownSync(storageKey: string): boolean {
|
||||
try {
|
||||
const stored = localStorage.getItem(storageKey);
|
||||
if (!stored) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const notice = JSON.parse(stored) as StoredNotice;
|
||||
return notice.shown;
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
private getStorageKey(id: string, customKey?: string): string {
|
||||
if (customKey) {
|
||||
return customKey;
|
||||
}
|
||||
const namespace = this.options.namespace || NoticeManager.DEFAULT_NAMESPACE;
|
||||
return `${namespace}_${id}`;
|
||||
}
|
||||
|
||||
private markAsShownSync(storageKey: string, version: string): void {
|
||||
const notice: StoredNotice = {
|
||||
shown: true,
|
||||
timestamp: new Date().toISOString(),
|
||||
version,
|
||||
};
|
||||
try {
|
||||
localStorage.setItem(storageKey, JSON.stringify(notice));
|
||||
} catch (error) {
|
||||
console.error('[NoticeManager] Failed to save notice state:', error);
|
||||
}
|
||||
}
|
||||
}
|
@@ -4,11 +4,9 @@ import { Registry } from '../Registry';
|
||||
import { ActionConfig } from '../types/homeassistant/data/lovelace/config/action';
|
||||
import { LovelaceCardConfig } from '../types/homeassistant/data/lovelace/config/card';
|
||||
import { AreaCardConfig, StackCardConfig } from '../types/homeassistant/panels/lovelace/cards/types';
|
||||
import { ChipsCardConfig } from '../types/lovelace-mushroom/cards/chips-card';
|
||||
import { PersonCardConfig } from '../types/lovelace-mushroom/cards/person-card-config';
|
||||
import { TemplateCardConfig } from '../types/lovelace-mushroom/cards/template-card-config';
|
||||
import { LovelaceChipConfig } from '../types/lovelace-mushroom/utils/lovelace/chip/types';
|
||||
import { isSupportedChip } from '../types/strategy/strategy-generics';
|
||||
import { isSupportedBadge } from '../types/strategy/strategy-generics';
|
||||
import { ViewConfig } from '../types/strategy/strategy-views';
|
||||
import { sanitizeClassName } from '../utilities/auxiliaries';
|
||||
import { logMessage, lvlError, lvlInfo } from '../utilities/debug';
|
||||
@@ -16,6 +14,8 @@ import { localize } from '../utilities/localize';
|
||||
import AbstractView from './AbstractView';
|
||||
import registryFilter from '../utilities/RegistryFilter';
|
||||
import { stackHorizontal } from '../utilities/cardStacking';
|
||||
import { LovelaceViewConfig } from '../types/homeassistant/data/lovelace/config/view';
|
||||
import { LovelaceBadgeConfig } from '../types/homeassistant/data/lovelace/config/badge';
|
||||
|
||||
/**
|
||||
* Home View Class.
|
||||
@@ -38,8 +38,15 @@ class HomeView extends AbstractView {
|
||||
}
|
||||
|
||||
/** Returns the default configuration object for the view. */
|
||||
// TODO: Move type and max_columns to the abstract class.
|
||||
static getDefaultConfig(): ViewConfig {
|
||||
return {
|
||||
//type: 'sections',
|
||||
//max_columns: 4,
|
||||
header: {
|
||||
badges_position: 'top',
|
||||
layout: 'center',
|
||||
},
|
||||
title: localize('generic.home'),
|
||||
icon: 'mdi:home-assistant',
|
||||
path: 'home',
|
||||
@@ -47,6 +54,19 @@ class HomeView extends AbstractView {
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a view configuration.
|
||||
*
|
||||
* The configuration includes the card configurations which are created by createCardConfigurations().
|
||||
*/
|
||||
async getView(): Promise<LovelaceViewConfig> {
|
||||
return {
|
||||
...this.baseConfiguration,
|
||||
badges: await this.createBadgeSection(),
|
||||
cards: await this.createCardConfigurations(),
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Create the configuration of the cards to include in the view.
|
||||
*
|
||||
@@ -55,24 +75,16 @@ class HomeView extends AbstractView {
|
||||
async createCardConfigurations(): Promise<LovelaceCardConfig[]> {
|
||||
const homeViewCards: LovelaceCardConfig[] = [];
|
||||
|
||||
let chipsSection, personsSection, areasSection;
|
||||
let personsSection, areasSection;
|
||||
|
||||
try {
|
||||
[chipsSection, personsSection, areasSection] = await Promise.all([
|
||||
this.createChipsSection(),
|
||||
this.createPersonsSection(),
|
||||
this.createAreasSection(),
|
||||
]);
|
||||
[personsSection, areasSection] = await Promise.all([this.createPersonsSection(), this.createAreasSection()]);
|
||||
} catch (e) {
|
||||
logMessage(lvlError, 'Error importing created sections!', e);
|
||||
|
||||
return homeViewCards;
|
||||
}
|
||||
|
||||
if (chipsSection) {
|
||||
homeViewCards.push(chipsSection);
|
||||
}
|
||||
|
||||
if (personsSection) {
|
||||
homeViewCards.push(personsSection);
|
||||
}
|
||||
@@ -125,71 +137,67 @@ class HomeView extends AbstractView {
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a chip section to include in the view
|
||||
* Create a badge section to include in the view.
|
||||
*
|
||||
* If the section is marked as hidden in the strategy option, then the section is not created.
|
||||
*/
|
||||
private async createChipsSection(): Promise<ChipsCardConfig | undefined> {
|
||||
if (Registry.strategyOptions.home_view.hidden.includes('chips')) {
|
||||
private async createBadgeSection(): Promise<LovelaceBadgeConfig[] | undefined> {
|
||||
if (Registry.strategyOptions.home_view.hidden.includes('badges')) {
|
||||
// The section is hidden.
|
||||
return;
|
||||
}
|
||||
|
||||
const chipConfigurations: LovelaceChipConfig[] = [];
|
||||
const exposedChips = Registry.getExposedNames('chip');
|
||||
const configurations: LovelaceBadgeConfig[] = [];
|
||||
const exposedBadges = Registry.getExposedNames('badge');
|
||||
|
||||
let Chip;
|
||||
let Badge;
|
||||
|
||||
// Weather chip.
|
||||
// FIXME: It's not possible to hide the weather chip in the configuration.
|
||||
// Weather badge.
|
||||
// FIXME: It's not possible to hide the weather badge in the configuration.
|
||||
const weatherEntityId =
|
||||
Registry.strategyOptions.chips.weather_entity === 'auto'
|
||||
Registry.strategyOptions.badges.weather_entity === 'auto'
|
||||
? Registry.entities.find((entity) => entity.entity_id.startsWith('weather.'))?.entity_id
|
||||
: Registry.strategyOptions.chips.weather_entity;
|
||||
: Registry.strategyOptions.badges.weather_entity;
|
||||
|
||||
if (weatherEntityId) {
|
||||
try {
|
||||
Chip = (await import('../chips/WeatherChip')).default;
|
||||
const weatherChip = new Chip(weatherEntityId);
|
||||
Badge = (await import('../badges/WeatherBadge')).default;
|
||||
const weatherBadge = new Badge(weatherEntityId);
|
||||
|
||||
chipConfigurations.push(weatherChip.getChipConfiguration());
|
||||
configurations.push(weatherBadge.getConfiguration());
|
||||
} catch (e) {
|
||||
logMessage(lvlError, 'Error importing chip weather!', e);
|
||||
logMessage(lvlError, 'Error importing badge weather!', e);
|
||||
}
|
||||
} else {
|
||||
logMessage(lvlInfo, 'Weather chip has no entities available.');
|
||||
logMessage(lvlInfo, 'Weather badge has no entities available.');
|
||||
}
|
||||
|
||||
// Numeric chips.
|
||||
for (const chipName of exposedChips) {
|
||||
if (!isSupportedChip(chipName) || !new registryFilter(Registry.entities).whereDomain(chipName).count()) {
|
||||
logMessage(lvlInfo, `Chip for domain ${chipName} is unsupported or has no entities available.`);
|
||||
// Numeric badges.
|
||||
for (const badgeName of exposedBadges) {
|
||||
if (!isSupportedBadge(badgeName) || !new registryFilter(Registry.entities).whereDomain(badgeName).count()) {
|
||||
logMessage(lvlInfo, `Badge for domain ${badgeName} is unsupported or has no entities available.`);
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
const moduleName = sanitizeClassName(chipName + 'Chip');
|
||||
const moduleName = sanitizeClassName(badgeName + 'Badge');
|
||||
|
||||
try {
|
||||
Chip = (await import(`../chips/${moduleName}`)).default;
|
||||
const currentChip = new Chip();
|
||||
Badge = (await import(`../badges/${moduleName}`)).default;
|
||||
const currentBadge = new Badge();
|
||||
|
||||
chipConfigurations.push(currentChip.getChipConfiguration());
|
||||
configurations.push(currentBadge.getConfiguration());
|
||||
} catch (e) {
|
||||
logMessage(lvlError, `Error importing chip ${chipName}!`, e);
|
||||
logMessage(lvlError, `Error importing badge ${badgeName}!`, e);
|
||||
}
|
||||
}
|
||||
|
||||
// Add extra chips.
|
||||
if (Registry.strategyOptions.chips?.extra_chips) {
|
||||
chipConfigurations.push(...Registry.strategyOptions.chips.extra_chips);
|
||||
// Add extra badges.
|
||||
if (Registry.strategyOptions.badges?.extra_badges) {
|
||||
configurations.push(...Registry.strategyOptions.badges.extra_badges);
|
||||
}
|
||||
|
||||
return {
|
||||
type: 'custom:mushroom-chips-card',
|
||||
alignment: 'center',
|
||||
chips: chipConfigurations,
|
||||
};
|
||||
return configurations;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -210,15 +218,14 @@ class HomeView extends AbstractView {
|
||||
cardConfigurations.push(
|
||||
...Registry.entities
|
||||
.filter((entity) => entity.entity_id.startsWith('person.'))
|
||||
.map((person) => new PersonCard(person).getCard()),
|
||||
.map((person) => new PersonCard(person).getCard())
|
||||
);
|
||||
|
||||
return {
|
||||
type: 'vertical-stack',
|
||||
cards: stackHorizontal(
|
||||
cardConfigurations,
|
||||
Registry.strategyOptions.home_view.stack_count['persons'] ??
|
||||
Registry.strategyOptions.home_view.stack_count['_'],
|
||||
Registry.strategyOptions.home_view.stack_count['persons'] ?? Registry.strategyOptions.home_view.stack_count['_']
|
||||
),
|
||||
};
|
||||
}
|
||||
@@ -258,7 +265,7 @@ class HomeView extends AbstractView {
|
||||
new AreaCard(area, {
|
||||
...Registry.strategyOptions.areas['_'],
|
||||
...Registry.strategyOptions.areas[area.area_id],
|
||||
}).getCard(),
|
||||
}).getCard()
|
||||
);
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user