mirror of
https://github.com/home-assistant/frontend.git
synced 2025-12-24 12:49:19 +00:00
Use entity naming in more cards and badges (#27541)
* Add support for button card, glance card and entities card * Add tests * Add support for attribute and button row * Add support to heading badge * Undo changes from rows * Add comment
This commit is contained in:
@@ -20,6 +20,7 @@ import "../chips/ha-chip-set";
|
|||||||
import "../chips/ha-input-chip";
|
import "../chips/ha-input-chip";
|
||||||
import "../ha-combo-box";
|
import "../ha-combo-box";
|
||||||
import type { HaComboBox } from "../ha-combo-box";
|
import type { HaComboBox } from "../ha-combo-box";
|
||||||
|
import "../ha-input-helper-text";
|
||||||
import "../ha-sortable";
|
import "../ha-sortable";
|
||||||
|
|
||||||
interface EntityNameOption {
|
interface EntityNameOption {
|
||||||
@@ -239,7 +240,6 @@ export class HaEntityNamePicker extends LitElement {
|
|||||||
.autofocus=${this.autofocus}
|
.autofocus=${this.autofocus}
|
||||||
.disabled=${this.disabled}
|
.disabled=${this.disabled}
|
||||||
.required=${this.required && !value.length}
|
.required=${this.required && !value.length}
|
||||||
.helper=${this.helper}
|
|
||||||
.items=${options}
|
.items=${options}
|
||||||
allow-custom-value
|
allow-custom-value
|
||||||
item-id-path="value"
|
item-id-path="value"
|
||||||
@@ -253,9 +253,20 @@ export class HaEntityNamePicker extends LitElement {
|
|||||||
</ha-combo-box>
|
</ha-combo-box>
|
||||||
</mwc-menu-surface>
|
</mwc-menu-surface>
|
||||||
</div>
|
</div>
|
||||||
|
${this._renderHelper()}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private _renderHelper() {
|
||||||
|
return this.helper
|
||||||
|
? html`
|
||||||
|
<ha-input-helper-text .disabled=${this.disabled}>
|
||||||
|
${this.helper}
|
||||||
|
</ha-input-helper-text>
|
||||||
|
`
|
||||||
|
: nothing;
|
||||||
|
}
|
||||||
|
|
||||||
private _onClosed(ev) {
|
private _onClosed(ev) {
|
||||||
ev.stopPropagation();
|
ev.stopPropagation();
|
||||||
this._opened = false;
|
this._opened = false;
|
||||||
@@ -510,6 +521,11 @@ export class HaEntityNamePicker extends LitElement {
|
|||||||
.sortable-drag {
|
.sortable-drag {
|
||||||
cursor: grabbing;
|
cursor: grabbing;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ha-input-helper-text {
|
||||||
|
display: block;
|
||||||
|
margin: var(--ha-space-2) 0 0;
|
||||||
|
}
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -179,7 +179,7 @@ export class HaGenericPicker extends LitElement {
|
|||||||
}
|
}
|
||||||
ha-input-helper-text {
|
ha-input-helper-text {
|
||||||
display: block;
|
display: block;
|
||||||
margin: 8px 0 0;
|
margin: var(--ha-space-2) 0 0;
|
||||||
}
|
}
|
||||||
`,
|
`,
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -9,13 +9,14 @@ import { LitElement, css, html, nothing } from "lit";
|
|||||||
import { customElement, state } from "lit/decorators";
|
import { customElement, state } from "lit/decorators";
|
||||||
import { ifDefined } from "lit/directives/if-defined";
|
import { ifDefined } from "lit/directives/if-defined";
|
||||||
import { styleMap } from "lit/directives/style-map";
|
import { styleMap } from "lit/directives/style-map";
|
||||||
|
import { computeCssColor } from "../../../common/color/compute-color";
|
||||||
import { DOMAINS_TOGGLE } from "../../../common/const";
|
import { DOMAINS_TOGGLE } from "../../../common/const";
|
||||||
import { transform } from "../../../common/decorators/transform";
|
import { transform } from "../../../common/decorators/transform";
|
||||||
import { applyThemesOnElement } from "../../../common/dom/apply_themes_on_element";
|
import { applyThemesOnElement } from "../../../common/dom/apply_themes_on_element";
|
||||||
import { fireEvent } from "../../../common/dom/fire_event";
|
import { fireEvent } from "../../../common/dom/fire_event";
|
||||||
import { computeDomain } from "../../../common/entity/compute_domain";
|
import { computeDomain } from "../../../common/entity/compute_domain";
|
||||||
import { computeStateDomain } from "../../../common/entity/compute_state_domain";
|
import { computeStateDomain } from "../../../common/entity/compute_state_domain";
|
||||||
import { computeStateName } from "../../../common/entity/compute_state_name";
|
import { stateActive } from "../../../common/entity/state_active";
|
||||||
import {
|
import {
|
||||||
stateColorBrightness,
|
stateColorBrightness,
|
||||||
stateColorCss,
|
stateColorCss,
|
||||||
@@ -40,6 +41,7 @@ import type { FrontendLocaleData } from "../../../data/translation";
|
|||||||
import type { Themes } from "../../../data/ws-themes";
|
import type { Themes } from "../../../data/ws-themes";
|
||||||
import type { HomeAssistant } from "../../../types";
|
import type { HomeAssistant } from "../../../types";
|
||||||
import { actionHandler } from "../common/directives/action-handler-directive";
|
import { actionHandler } from "../common/directives/action-handler-directive";
|
||||||
|
import { computeLovelaceEntityName } from "../common/entity/compute-lovelace-entity-name";
|
||||||
import { findEntities } from "../common/find-entities";
|
import { findEntities } from "../common/find-entities";
|
||||||
import { hasAction } from "../common/has-action";
|
import { hasAction } from "../common/has-action";
|
||||||
import { createEntityNotFoundWarning } from "../components/hui-warning";
|
import { createEntityNotFoundWarning } from "../components/hui-warning";
|
||||||
@@ -49,8 +51,6 @@ import type {
|
|||||||
LovelaceGridOptions,
|
LovelaceGridOptions,
|
||||||
} from "../types";
|
} from "../types";
|
||||||
import type { ButtonCardConfig } from "./types";
|
import type { ButtonCardConfig } from "./types";
|
||||||
import { computeCssColor } from "../../../common/color/compute-color";
|
|
||||||
import { stateActive } from "../../../common/entity/state_active";
|
|
||||||
|
|
||||||
export const getEntityDefaultButtonAction = (entityId?: string) =>
|
export const getEntityDefaultButtonAction = (entityId?: string) =>
|
||||||
entityId && DOMAINS_TOGGLE.has(computeDomain(entityId))
|
entityId && DOMAINS_TOGGLE.has(computeDomain(entityId))
|
||||||
@@ -183,9 +183,11 @@ export class HuiButtonCard extends LitElement implements LovelaceCard {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
const name = this._config.show_name
|
const name = computeLovelaceEntityName(
|
||||||
? this._config.name || (stateObj ? computeStateName(stateObj) : "")
|
this.hass,
|
||||||
: "";
|
stateObj,
|
||||||
|
this._config.name
|
||||||
|
);
|
||||||
|
|
||||||
return html`
|
return html`
|
||||||
<ha-card
|
<ha-card
|
||||||
@@ -195,8 +197,7 @@ export class HuiButtonCard extends LitElement implements LovelaceCard {
|
|||||||
hasDoubleClick: hasAction(this._config!.double_tap_action),
|
hasDoubleClick: hasAction(this._config!.double_tap_action),
|
||||||
})}
|
})}
|
||||||
role="button"
|
role="button"
|
||||||
aria-label=${this._config.name ||
|
aria-label=${name}
|
||||||
(stateObj ? computeStateName(stateObj) : "")}
|
|
||||||
tabindex=${ifDefined(
|
tabindex=${ifDefined(
|
||||||
hasAction(this._config.tap_action) ? "0" : undefined
|
hasAction(this._config.tap_action) ? "0" : undefined
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -272,7 +272,6 @@ export class HuiTileCard extends LitElement implements LovelaceCard {
|
|||||||
.stateObj=${stateObj}
|
.stateObj=${stateObj}
|
||||||
.hass=${this.hass}
|
.hass=${this.hass}
|
||||||
.content=${this._config.state_content}
|
.content=${this._config.state_content}
|
||||||
.name=${name}
|
|
||||||
>
|
>
|
||||||
</state-display>
|
</state-display>
|
||||||
`;
|
`;
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import {
|
|||||||
type EntityNameItem,
|
type EntityNameItem,
|
||||||
} from "../../../../common/entity/compute_entity_name_display";
|
} from "../../../../common/entity/compute_entity_name_display";
|
||||||
import type { HomeAssistant } from "../../../../types";
|
import type { HomeAssistant } from "../../../../types";
|
||||||
|
import { ensureArray } from "../../../../common/array/ensure-array";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Computes the display name for an entity in Lovelace (cards and badges).
|
* Computes the display name for an entity in Lovelace (cards and badges).
|
||||||
@@ -15,9 +16,24 @@ import type { HomeAssistant } from "../../../../types";
|
|||||||
*/
|
*/
|
||||||
export const computeLovelaceEntityName = (
|
export const computeLovelaceEntityName = (
|
||||||
hass: HomeAssistant,
|
hass: HomeAssistant,
|
||||||
stateObj: HassEntity,
|
stateObj: HassEntity | undefined,
|
||||||
nameConfig: string | EntityNameItem | EntityNameItem[] | undefined
|
nameConfig: string | EntityNameItem | EntityNameItem[] | undefined
|
||||||
): string =>
|
): string => {
|
||||||
typeof nameConfig === "string"
|
if (typeof nameConfig === "string") {
|
||||||
? nameConfig
|
return nameConfig;
|
||||||
: hass.formatEntityName(stateObj, nameConfig || DEFAULT_ENTITY_NAME);
|
}
|
||||||
|
const config = nameConfig || DEFAULT_ENTITY_NAME;
|
||||||
|
if (stateObj) {
|
||||||
|
return hass.formatEntityName(stateObj, config);
|
||||||
|
}
|
||||||
|
// If entity is not found, fall back to text parts in config
|
||||||
|
// This allows for static names even when the entity is missing
|
||||||
|
// e.g. for a card that doesn't require an entity
|
||||||
|
const textParts = ensureArray(config)
|
||||||
|
.filter((item) => item.type === "text")
|
||||||
|
.map((item) => ("text" in item ? item.text : ""));
|
||||||
|
if (textParts.length) {
|
||||||
|
return textParts.join(" ");
|
||||||
|
}
|
||||||
|
return "";
|
||||||
|
};
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ import { customElement, property, state } from "lit/decorators";
|
|||||||
import memoizeOne from "memoize-one";
|
import memoizeOne from "memoize-one";
|
||||||
import { assert, assign, boolean, object, optional, string } from "superstruct";
|
import { assert, assign, boolean, object, optional, string } from "superstruct";
|
||||||
import { fireEvent } from "../../../../common/dom/fire_event";
|
import { fireEvent } from "../../../../common/dom/fire_event";
|
||||||
|
import { DEFAULT_ENTITY_NAME } from "../../../../common/entity/compute_entity_name_display";
|
||||||
import "../../../../components/ha-form/ha-form";
|
import "../../../../components/ha-form/ha-form";
|
||||||
import type {
|
import type {
|
||||||
HaFormSchema,
|
HaFormSchema,
|
||||||
@@ -16,13 +17,14 @@ import type { ButtonCardConfig } from "../../cards/types";
|
|||||||
import type { LovelaceCardEditor } from "../../types";
|
import type { LovelaceCardEditor } from "../../types";
|
||||||
import { actionConfigStruct } from "../structs/action-struct";
|
import { actionConfigStruct } from "../structs/action-struct";
|
||||||
import { baseLovelaceCardConfig } from "../structs/base-card-struct";
|
import { baseLovelaceCardConfig } from "../structs/base-card-struct";
|
||||||
|
import { entityNameStruct } from "../structs/entity-name-struct";
|
||||||
import { configElementStyle } from "./config-elements-style";
|
import { configElementStyle } from "./config-elements-style";
|
||||||
|
|
||||||
const cardConfigStruct = assign(
|
const cardConfigStruct = assign(
|
||||||
baseLovelaceCardConfig,
|
baseLovelaceCardConfig,
|
||||||
object({
|
object({
|
||||||
entity: optional(string()),
|
entity: optional(string()),
|
||||||
name: optional(string()),
|
name: optional(entityNameStruct),
|
||||||
show_name: optional(boolean()),
|
show_name: optional(boolean()),
|
||||||
icon: optional(string()),
|
icon: optional(string()),
|
||||||
show_icon: optional(boolean()),
|
show_icon: optional(boolean()),
|
||||||
@@ -68,7 +70,13 @@ export class HuiButtonCardEditor
|
|||||||
(entityId: string | undefined) =>
|
(entityId: string | undefined) =>
|
||||||
[
|
[
|
||||||
{ name: "entity", selector: { entity: {} } },
|
{ name: "entity", selector: { entity: {} } },
|
||||||
{ name: "name", selector: { text: {} } },
|
{
|
||||||
|
name: "name",
|
||||||
|
selector: {
|
||||||
|
entity_name: { default_name: DEFAULT_ENTITY_NAME },
|
||||||
|
},
|
||||||
|
context: { entity: "entity" },
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "",
|
name: "",
|
||||||
type: "grid",
|
type: "grid",
|
||||||
|
|||||||
@@ -13,6 +13,7 @@ import {
|
|||||||
union,
|
union,
|
||||||
} from "superstruct";
|
} from "superstruct";
|
||||||
import { fireEvent } from "../../../../common/dom/fire_event";
|
import { fireEvent } from "../../../../common/dom/fire_event";
|
||||||
|
import { DEFAULT_ENTITY_NAME } from "../../../../common/entity/compute_entity_name_display";
|
||||||
import type { LocalizeFunc } from "../../../../common/translations/localize";
|
import type { LocalizeFunc } from "../../../../common/translations/localize";
|
||||||
import "../../../../components/ha-expansion-panel";
|
import "../../../../components/ha-expansion-panel";
|
||||||
import "../../../../components/ha-form/ha-form";
|
import "../../../../components/ha-form/ha-form";
|
||||||
@@ -27,6 +28,7 @@ import type { LovelaceGenericElementEditor } from "../../types";
|
|||||||
import "../conditions/ha-card-conditions-editor";
|
import "../conditions/ha-card-conditions-editor";
|
||||||
import { configElementStyle } from "../config-elements/config-elements-style";
|
import { configElementStyle } from "../config-elements/config-elements-style";
|
||||||
import { actionConfigStruct } from "../structs/action-struct";
|
import { actionConfigStruct } from "../structs/action-struct";
|
||||||
|
import { entityNameStruct } from "../structs/entity-name-struct";
|
||||||
|
|
||||||
export const DEFAULT_CONFIG: Partial<EntityHeadingBadgeConfig> = {
|
export const DEFAULT_CONFIG: Partial<EntityHeadingBadgeConfig> = {
|
||||||
type: "entity",
|
type: "entity",
|
||||||
@@ -37,7 +39,7 @@ export const DEFAULT_CONFIG: Partial<EntityHeadingBadgeConfig> = {
|
|||||||
const entityConfigStruct = object({
|
const entityConfigStruct = object({
|
||||||
type: optional(string()),
|
type: optional(string()),
|
||||||
entity: optional(string()),
|
entity: optional(string()),
|
||||||
name: optional(string()),
|
name: optional(entityNameStruct),
|
||||||
icon: optional(string()),
|
icon: optional(string()),
|
||||||
state_content: optional(union([string(), array(string())])),
|
state_content: optional(union([string(), array(string())])),
|
||||||
show_state: optional(boolean()),
|
show_state: optional(boolean()),
|
||||||
@@ -92,8 +94,11 @@ export class HuiHeadingEntityEditor
|
|||||||
{
|
{
|
||||||
name: "name",
|
name: "name",
|
||||||
selector: {
|
selector: {
|
||||||
text: {},
|
entity_name: {
|
||||||
|
default_name: DEFAULT_ENTITY_NAME,
|
||||||
|
},
|
||||||
},
|
},
|
||||||
|
context: { entity: "entity" },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "icon",
|
name: "icon",
|
||||||
|
|||||||
@@ -7,7 +7,6 @@ import memoizeOne from "memoize-one";
|
|||||||
import { computeCssColor } from "../../../common/color/compute-color";
|
import { computeCssColor } from "../../../common/color/compute-color";
|
||||||
import { hsv2rgb, rgb2hex, rgb2hsv } from "../../../common/color/convert-color";
|
import { hsv2rgb, rgb2hex, rgb2hsv } from "../../../common/color/convert-color";
|
||||||
import { computeDomain } from "../../../common/entity/compute_domain";
|
import { computeDomain } from "../../../common/entity/compute_domain";
|
||||||
import { computeStateName } from "../../../common/entity/compute_state_name";
|
|
||||||
import { stateActive } from "../../../common/entity/state_active";
|
import { stateActive } from "../../../common/entity/state_active";
|
||||||
import { stateColorCss } from "../../../common/entity/state_color";
|
import { stateColorCss } from "../../../common/entity/state_color";
|
||||||
import "../../../components/ha-heading-badge";
|
import "../../../components/ha-heading-badge";
|
||||||
@@ -16,6 +15,7 @@ import type { ActionHandlerEvent } from "../../../data/lovelace/action_handler";
|
|||||||
import "../../../state-display/state-display";
|
import "../../../state-display/state-display";
|
||||||
import type { HomeAssistant } from "../../../types";
|
import type { HomeAssistant } from "../../../types";
|
||||||
import { actionHandler } from "../common/directives/action-handler-directive";
|
import { actionHandler } from "../common/directives/action-handler-directive";
|
||||||
|
import { computeLovelaceEntityName } from "../common/entity/compute-lovelace-entity-name";
|
||||||
import { handleAction } from "../common/handle-action";
|
import { handleAction } from "../common/handle-action";
|
||||||
import { hasAction } from "../common/has-action";
|
import { hasAction } from "../common/has-action";
|
||||||
import { DEFAULT_CONFIG } from "../editor/heading-badge-editor/hui-entity-heading-badge-editor";
|
import { DEFAULT_CONFIG } from "../editor/heading-badge-editor/hui-entity-heading-badge-editor";
|
||||||
@@ -137,7 +137,11 @@ export class HuiEntityHeadingBadge
|
|||||||
"--icon-color": color,
|
"--icon-color": color,
|
||||||
};
|
};
|
||||||
|
|
||||||
const name = config.name || computeStateName(stateObj);
|
const name = computeLovelaceEntityName(
|
||||||
|
this.hass,
|
||||||
|
stateObj,
|
||||||
|
this._config.name
|
||||||
|
);
|
||||||
|
|
||||||
return html`
|
return html`
|
||||||
<ha-heading-badge
|
<ha-heading-badge
|
||||||
@@ -166,7 +170,7 @@ export class HuiEntityHeadingBadge
|
|||||||
.hass=${this.hass}
|
.hass=${this.hass}
|
||||||
.stateObj=${stateObj}
|
.stateObj=${stateObj}
|
||||||
.content=${config.state_content}
|
.content=${config.state_content}
|
||||||
.name=${config.name}
|
.name=${name}
|
||||||
dash-unavailable
|
dash-unavailable
|
||||||
></state-display>
|
></state-display>
|
||||||
`
|
`
|
||||||
|
|||||||
@@ -5,7 +5,6 @@ import { customElement, property } from "lit/decorators";
|
|||||||
import { join } from "lit/directives/join";
|
import { join } from "lit/directives/join";
|
||||||
import { ensureArray } from "../common/array/ensure-array";
|
import { ensureArray } from "../common/array/ensure-array";
|
||||||
import { computeStateDomain } from "../common/entity/compute_state_domain";
|
import { computeStateDomain } from "../common/entity/compute_state_domain";
|
||||||
import { computeStateName } from "../common/entity/compute_state_name";
|
|
||||||
import "../components/ha-relative-time";
|
import "../components/ha-relative-time";
|
||||||
import { isUnavailableState } from "../data/entity";
|
import { isUnavailableState } from "../data/entity";
|
||||||
import { SENSOR_DEVICE_CLASS_TIMESTAMP } from "../data/sensor";
|
import { SENSOR_DEVICE_CLASS_TIMESTAMP } from "../data/sensor";
|
||||||
@@ -100,8 +99,8 @@ class StateDisplay extends LitElement {
|
|||||||
|
|
||||||
return this.hass!.formatEntityState(stateObj);
|
return this.hass!.formatEntityState(stateObj);
|
||||||
}
|
}
|
||||||
if (content === "name") {
|
if (content === "name" && this.name) {
|
||||||
return html`${this.name || computeStateName(stateObj)}`;
|
return html`${this.name}`;
|
||||||
}
|
}
|
||||||
|
|
||||||
let relativeDateTime: string | Date | undefined;
|
let relativeDateTime: string | Date | undefined;
|
||||||
|
|||||||
@@ -77,4 +77,71 @@ describe("computeLovelaceEntityName", () => {
|
|||||||
expect(mockFormatEntityName).toHaveBeenCalledTimes(1);
|
expect(mockFormatEntityName).toHaveBeenCalledTimes(1);
|
||||||
expect(mockFormatEntityName).toHaveBeenCalledWith(stateObj, nameConfig);
|
expect(mockFormatEntityName).toHaveBeenCalledWith(stateObj, nameConfig);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe("when stateObj is undefined", () => {
|
||||||
|
it("returns empty string when nameConfig is undefined", () => {
|
||||||
|
const mockFormatEntityName = vi.fn();
|
||||||
|
const hass = createMockHass(mockFormatEntityName);
|
||||||
|
|
||||||
|
const result = computeLovelaceEntityName(hass, undefined, undefined);
|
||||||
|
|
||||||
|
expect(result).toBe("");
|
||||||
|
expect(mockFormatEntityName).not.toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
|
||||||
|
it("returns text from single text EntityNameItem", () => {
|
||||||
|
const mockFormatEntityName = vi.fn();
|
||||||
|
const hass = createMockHass(mockFormatEntityName);
|
||||||
|
const nameConfig = { type: "text" as const, text: "Custom Text" };
|
||||||
|
|
||||||
|
const result = computeLovelaceEntityName(hass, undefined, nameConfig);
|
||||||
|
|
||||||
|
expect(result).toBe("Custom Text");
|
||||||
|
expect(mockFormatEntityName).not.toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
|
||||||
|
it("returns joined text from multiple text EntityNameItems", () => {
|
||||||
|
const mockFormatEntityName = vi.fn();
|
||||||
|
const hass = createMockHass(mockFormatEntityName);
|
||||||
|
const nameConfig = [
|
||||||
|
{ type: "text" as const, text: "First" },
|
||||||
|
{ type: "text" as const, text: "Second" },
|
||||||
|
];
|
||||||
|
|
||||||
|
const result = computeLovelaceEntityName(hass, undefined, nameConfig);
|
||||||
|
|
||||||
|
expect(result).toBe("First Second");
|
||||||
|
expect(mockFormatEntityName).not.toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
|
||||||
|
it("returns only text items when mixed with non-text items", () => {
|
||||||
|
const mockFormatEntityName = vi.fn();
|
||||||
|
const hass = createMockHass(mockFormatEntityName);
|
||||||
|
const nameConfig = [
|
||||||
|
{ type: "text" as const, text: "Prefix" },
|
||||||
|
{ type: "device" as const },
|
||||||
|
{ type: "text" as const, text: "Suffix" },
|
||||||
|
{ type: "entity" as const },
|
||||||
|
];
|
||||||
|
|
||||||
|
const result = computeLovelaceEntityName(hass, undefined, nameConfig);
|
||||||
|
|
||||||
|
expect(result).toBe("Prefix Suffix");
|
||||||
|
expect(mockFormatEntityName).not.toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
|
||||||
|
it("returns empty string when no text items in config", () => {
|
||||||
|
const mockFormatEntityName = vi.fn();
|
||||||
|
const hass = createMockHass(mockFormatEntityName);
|
||||||
|
const nameConfig = [
|
||||||
|
{ type: "device" as const },
|
||||||
|
{ type: "entity" as const },
|
||||||
|
];
|
||||||
|
|
||||||
|
const result = computeLovelaceEntityName(hass, undefined, nameConfig);
|
||||||
|
|
||||||
|
expect(result).toBe("");
|
||||||
|
expect(mockFormatEntityName).not.toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user