Compare commits

..

26 Commits

Author SHA1 Message Date
Zack Barett
d3765987c4 Merge branch 'dev' into Better-row-editor 2020-11-30 20:07:26 -06:00
Zack Arnett
259cb6a2d2 Review updates 2020-11-30 20:03:54 -06:00
HomeAssistant Azure
0e362b851b [ci skip] Translation update 2020-12-01 00:32:47 +00:00
Zack Arnett
68c3825c7b lint 2020-11-20 12:24:06 -06:00
Zack Arnett
2e3c3ded96 Update the rest of the editors 2020-11-20 12:19:08 -06:00
Zack Arnett
b6a93b439e more lint 2020-11-19 19:32:27 -06:00
Zack Arnett
ea4a5e4f1d lint 2020-11-19 19:24:27 -06:00
Zack Arnett
de71c348a5 Add More cards editors to config template 2020-11-19 19:20:31 -06:00
Zack Arnett
b27fe7e703 Clean up 2020-11-18 20:29:04 -06:00
Zack Arnett
06db9c4bee Show Code editor to only advanced 2020-11-18 20:16:53 -06:00
Zack Arnett
ae5018b501 lint 2020-11-18 18:13:56 -06:00
Zack Arnett
9ef3d02636 Fix header footer editor 2020-11-18 17:05:23 -06:00
Zack Arnett
9f2723deb8 fix enlarge 2020-11-18 17:02:02 -06:00
Zack Arnett
e9845e1009 Add row do something at least 2020-11-18 16:57:08 -06:00
Zack Arnett
40d8a76b4d Update Header footer 2020-11-17 22:23:41 -06:00
Zack Arnett
7a282ede59 Fix menu 2020-11-17 19:55:15 -06:00
Zack Arnett
48455c767f lint and wording 2020-11-17 17:22:01 -06:00
Zack Arnett
4385dd5c44 Convert entities card to advanced template 2020-11-17 17:17:30 -06:00
Zack Arnett
7733a5f831 Add handle back 2020-11-17 16:35:50 -06:00
Zack Arnett
b6c9676930 Lint 2020-11-17 16:18:21 -06:00
Zack Arnett
3692e36f12 use ha-settings-row 2020-11-17 16:13:15 -06:00
Zack Arnett
30e5fdb6e5 Advancded 2020-11-17 11:52:08 -06:00
Zack Arnett
99f4afec8d console.die 2020-11-15 16:25:30 -06:00
Zack Arnett
5ae6c05fe6 Update scrollbar on Dialog 2020-11-15 15:29:29 -06:00
Zack Arnett
effd5e4982 More changes 2020-11-15 14:50:00 -06:00
Zack Arnett
5592ea80a9 Make this place a little bit better 2020-11-14 20:46:14 -06:00
64 changed files with 2396 additions and 1976 deletions

View File

@@ -139,7 +139,7 @@ export class HaAreaDevicesPicker extends SubscribeMixin(LitElement) {
private _filteredDevices: DeviceRegistryEntry[] = [];
private _getAreasWithDevices = memoizeOne(
private _getDevices = memoizeOne(
(
devices: DeviceRegistryEntry[],
areas: AreaRegistryEntry[],
@@ -277,7 +277,7 @@ export class HaAreaDevicesPicker extends SubscribeMixin(LitElement) {
if (!this._devices || !this._areas || !this._entities) {
return html``;
}
const areas = this._getAreasWithDevices(
const areas = this._getDevices(
this._devices,
this._areas,
this._entities,

View File

@@ -126,17 +126,14 @@ export class HaDevicePicker extends SubscribeMixin(LitElement) {
}
const deviceEntityLookup: DeviceEntityLookup = {};
if (includeDomains || excludeDomains || includeDeviceClasses) {
for (const entity of entities) {
if (!entity.device_id) {
continue;
}
if (!(entity.device_id in deviceEntityLookup)) {
deviceEntityLookup[entity.device_id] = [];
}
deviceEntityLookup[entity.device_id].push(entity);
for (const entity of entities) {
if (!entity.device_id) {
continue;
}
if (!(entity.device_id in deviceEntityLookup)) {
deviceEntityLookup[entity.device_id] = [];
}
deviceEntityLookup[entity.device_id].push(entity);
}
const areaLookup: { [areaId: string]: AreaRegistryEntry } = {};

View File

@@ -95,7 +95,8 @@ export class HaEntityPicker extends LitElement {
@property() public entityFilter?: HaEntityPickerEntityFilterFunc;
@property({ type: Boolean }) public hideClearIcon = false;
@property({ type: Boolean, attribute: "hide-clear-icon" })
public hideClearIcon = false;
@property({ type: Boolean }) private _opened = false;

View File

@@ -29,17 +29,6 @@ import { SubscribeMixin } from "../mixins/subscribe-mixin";
import { PolymerChangedEvent } from "../polymer-types";
import { HomeAssistant } from "../types";
import memoizeOne from "memoize-one";
import {
DeviceEntityLookup,
DeviceRegistryEntry,
subscribeDeviceRegistry,
} from "../data/device_registry";
import {
EntityRegistryEntry,
subscribeEntityRegistry,
} from "../data/entity_registry";
import { computeDomain } from "../common/entity/compute_domain";
import type { HaDevicePickerDeviceFilterFunc } from "./device/ha-device-picker";
const rowRenderer = (
root: HTMLElement,
@@ -82,213 +71,39 @@ export class HaAreaPicker extends SubscribeMixin(LitElement) {
@property() public placeholder?: string;
@property() public _areas?: AreaRegistryEntry[];
@property({ type: Boolean, attribute: "no-add" })
public noAdd?: boolean;
/**
* Show only areas with entities from specific domains.
* @type {Array}
* @attr include-domains
*/
@property({ type: Array, attribute: "include-domains" })
public includeDomains?: string[];
/**
* Show no areas with entities of these domains.
* @type {Array}
* @attr exclude-domains
*/
@property({ type: Array, attribute: "exclude-domains" })
public excludeDomains?: string[];
/**
* Show only areas with entities of these device classes.
* @type {Array}
* @attr include-device-classes
*/
@property({ type: Array, attribute: "include-device-classes" })
public includeDeviceClasses?: string[];
@property() public deviceFilter?: HaDevicePickerDeviceFilterFunc;
@property() public entityFilter?: (entity: EntityRegistryEntry) => boolean;
@internalProperty() private _areas?: AreaRegistryEntry[];
@internalProperty() private _devices?: DeviceRegistryEntry[];
@internalProperty() private _entities?: EntityRegistryEntry[];
@internalProperty() private _opened?: boolean;
public hassSubscribe(): UnsubscribeFunc[] {
return [
subscribeAreaRegistry(this.hass.connection!, (areas) => {
this._areas = areas;
}),
subscribeDeviceRegistry(this.hass.connection!, (devices) => {
this._devices = devices;
}),
subscribeEntityRegistry(this.hass.connection!, (entities) => {
this._entities = entities;
this._areas = this.noAdd
? areas
: [
...areas,
{
area_id: "add_new",
name: this.hass.localize("ui.components.area-picker.add_new"),
},
];
}),
];
}
private _getAreas = memoizeOne(
(
areas: AreaRegistryEntry[],
devices: DeviceRegistryEntry[],
entities: EntityRegistryEntry[],
includeDomains: this["includeDomains"],
excludeDomains: this["excludeDomains"],
includeDeviceClasses: this["includeDeviceClasses"],
deviceFilter: this["deviceFilter"],
entityFilter: this["entityFilter"],
noAdd: this["noAdd"]
): AreaRegistryEntry[] => {
const deviceEntityLookup: DeviceEntityLookup = {};
let inputDevices: DeviceRegistryEntry[] | undefined;
let inputEntities: EntityRegistryEntry[] | undefined;
if (includeDomains || excludeDomains || includeDeviceClasses) {
for (const entity of entities) {
if (!entity.device_id) {
continue;
}
if (!(entity.device_id in deviceEntityLookup)) {
deviceEntityLookup[entity.device_id] = [];
}
deviceEntityLookup[entity.device_id].push(entity);
}
inputDevices = [...devices];
inputEntities = entities.filter((entity) => !entity.device_id);
} else if (deviceFilter) {
inputDevices = [...devices];
} else if (entityFilter) {
inputEntities = entities.filter((entity) => !entity.device_id);
}
if (includeDomains) {
inputDevices = inputDevices!.filter((device) => {
const devEntities = deviceEntityLookup[device.id];
if (!devEntities || !devEntities.length) {
return false;
}
return deviceEntityLookup[device.id].some((entity) =>
includeDomains.includes(computeDomain(entity.entity_id))
);
});
inputEntities = inputEntities!.filter((entity) =>
includeDomains.includes(computeDomain(entity.entity_id))
);
}
if (excludeDomains) {
inputDevices = inputDevices!.filter((device) => {
const devEntities = deviceEntityLookup[device.id];
if (!devEntities || !devEntities.length) {
return true;
}
return entities.every(
(entity) =>
!excludeDomains.includes(computeDomain(entity.entity_id))
);
});
inputEntities = inputEntities!.filter(
(entity) => !excludeDomains.includes(computeDomain(entity.entity_id))
);
}
if (includeDeviceClasses) {
inputDevices = inputDevices!.filter((device) => {
const devEntities = deviceEntityLookup[device.id];
if (!devEntities || !devEntities.length) {
return false;
}
return deviceEntityLookup[device.id].some((entity) => {
const stateObj = this.hass.states[entity.entity_id];
if (!stateObj) {
return false;
}
return (
stateObj.attributes.device_class &&
includeDeviceClasses.includes(stateObj.attributes.device_class)
);
});
});
inputEntities = inputEntities!.filter((entity) => {
const stateObj = this.hass.states[entity.entity_id];
return (
stateObj.attributes.device_class &&
includeDeviceClasses.includes(stateObj.attributes.device_class)
);
});
}
if (deviceFilter) {
inputDevices = inputDevices!.filter((device) => deviceFilter!(device));
}
if (entityFilter) {
entities = entities.filter((entity) => entityFilter!(entity));
}
let outputAreas = areas;
let areaIds: string[] | undefined;
if (inputDevices) {
areaIds = inputDevices
.filter((device) => device.area_id)
.map((device) => device.area_id!);
}
if (inputEntities) {
areaIds = (areaIds ?? []).concat(
inputEntities
.filter((entity) => entity.area_id)
.map((entity) => entity.area_id!)
);
}
if (areaIds) {
outputAreas = areas.filter((area) => areaIds!.includes(area.area_id));
}
return noAdd
? outputAreas
: [
...outputAreas,
{
area_id: "add_new",
name: this.hass.localize("ui.components.area-picker.add_new"),
},
];
}
);
protected render(): TemplateResult {
if (!this._devices || !this._areas || !this._entities) {
if (!this._areas) {
return html``;
}
const areas = this._getAreas(
this._areas,
this._devices,
this._entities,
this.includeDomains,
this.excludeDomains,
this.includeDeviceClasses,
this.deviceFilter,
this.entityFilter,
this.noAdd
);
return html`
<vaadin-combo-box-light
item-value-path="area_id"
item-id-path="area_id"
item-label-path="name"
.items=${areas}
.items=${this._areas}
.value=${this._value}
.renderer=${rowRenderer}
@opened-changed=${this._openedChanged}
@@ -323,7 +138,7 @@ export class HaAreaPicker extends SubscribeMixin(LitElement) {
</ha-icon-button>
`
: ""}
${areas.length > 0
${this._areas.length > 0
? html`
<ha-icon-button
aria-label=${this.hass.localize(

View File

@@ -23,6 +23,8 @@ export class HaButtonMenu extends LitElement {
@property({ type: Boolean }) public disabled = false;
@property({ type: Boolean }) public fixed = false;
@query("mwc-menu", true) private _menu?: Menu;
public get items() {
@@ -39,6 +41,7 @@ export class HaButtonMenu extends LitElement {
<slot name="trigger"></slot>
</div>
<mwc-menu
.fixed=${this.fixed}
.corner=${this.corner}
.multi=${this.multi}
.activatable=${this.activatable}

View File

@@ -11,7 +11,6 @@ import {
import { fireEvent } from "../common/dom/fire_event";
import type { ToggleButton } from "../types";
import "./ha-svg-icon";
import "@material/mwc-button/mwc-button";
@customElement("ha-button-toggle-group")
export class HaButtonToggleGroup extends LitElement {
@@ -22,22 +21,17 @@ export class HaButtonToggleGroup extends LitElement {
protected render(): TemplateResult {
return html`
<div>
${this.buttons.map((button) =>
button.iconPath
? html`<mwc-icon-button
.label=${button.label}
.value=${button.value}
?active=${this.active === button.value}
@click=${this._handleClick}
>
<ha-svg-icon .path=${button.iconPath}></ha-svg-icon>
</mwc-icon-button>`
: html`<mwc-button
.value=${button.value}
?active=${this.active === button.value}
@click=${this._handleClick}
>${button.label}</mwc-button
>`
${this.buttons.map(
(button) => html`
<mwc-icon-button
.label=${button.label}
.value=${button.value}
?active=${this.active === button.value}
@click=${this._handleClick}
>
<ha-svg-icon .path=${button.iconPath}></ha-svg-icon>
</mwc-icon-button>
`
)}
</div>
`;
@@ -55,15 +49,13 @@ export class HaButtonToggleGroup extends LitElement {
--mdc-icon-button-size: var(--button-toggle-size, 36px);
--mdc-icon-size: var(--button-toggle-icon-size, 20px);
}
mwc-icon-button,
mwc-button {
mwc-icon-button {
border: 1px solid var(--primary-color);
border-right-width: 0px;
position: relative;
cursor: pointer;
}
mwc-icon-button::before,
mwc-button::before {
mwc-icon-button::before {
top: 0;
left: 0;
width: 100%;
@@ -75,21 +67,17 @@ export class HaButtonToggleGroup extends LitElement {
content: "";
transition: opacity 15ms linear, background-color 15ms linear;
}
mwc-icon-button[active]::before,
mwc-button[active]::before {
mwc-icon-button[active]::before {
opacity: var(--mdc-icon-button-ripple-opacity, 0.12);
}
mwc-icon-button:first-child,
mwc-button:first-child {
mwc-icon-button:first-child {
border-radius: 4px 0 0 4px;
}
mwc-icon-button:last-child,
mwc-button:last-child {
mwc-icon-button:last-child {
border-radius: 0 4px 4px 0;
border-right-width: 1px;
}
mwc-icon-button:only-child,
mwc-button:only-child {
mwc-icon-button:only-child {
border-radius: 4px;
border-right-width: 1px;
}

View File

@@ -68,6 +68,12 @@ export class HaDialog extends MwcDialog {
top: var(--dialog-surface-top);
min-height: var(--mdc-dialog-min-height, auto);
}
:host([full]) .mdc-dialog .mdc-dialog__surface {
height: 100%;
width: 100%;
}
:host([flexContent]) .mdc-dialog .mdc-dialog__content {
display: flex;
flex-direction: column;
@@ -90,6 +96,23 @@ export class HaDialog extends MwcDialog {
margin-left: 40px;
margin-right: 0px;
}
.mdc-dialog__content::-webkit-scrollbar {
width: 0.4rem;
height: 0.4rem;
}
.mdc-dialog__content::-webkit-scrollbar-thumb {
-webkit-border-radius: 4px;
border-radius: 4px;
background: var(--scrollbar-thumb-color);
}
.mdc-dialog__content {
overflow-y: auto;
scrollbar-color: var(--scrollbar-thumb-color) transparent;
scrollbar-width: thin;
}
`,
];
}

View File

@@ -1,3 +1,4 @@
import { mdiChevronDown } from "@mdi/js";
import {
css,
CSSResult,
@@ -8,10 +9,9 @@ import {
query,
TemplateResult,
} from "lit-element";
import { classMap } from "lit-html/directives/class-map";
import { fireEvent } from "../common/dom/fire_event";
import "./ha-svg-icon";
import { mdiChevronDown } from "@mdi/js";
import { classMap } from "lit-html/directives/class-map";
@customElement("ha-expansion-panel")
class HaExpansionPanel extends LitElement {

View File

@@ -1,4 +1,4 @@
import { mdiHelpCircle } from "@mdi/js";
import { mdiHelpCircleOutline } from "@mdi/js";
import "@polymer/paper-tooltip/paper-tooltip";
import {
css,
@@ -18,7 +18,7 @@ export class HaHelpTooltip extends LitElement {
protected render(): TemplateResult {
return html`
<ha-svg-icon .path=${mdiHelpCircle}></ha-svg-icon>
<ha-svg-icon .path=${mdiHelpCircleOutline}></ha-svg-icon>
<paper-tooltip
offset="4"
.position=${this.position}

View File

@@ -1,16 +1,7 @@
import {
customElement,
html,
internalProperty,
LitElement,
property,
} from "lit-element";
import { customElement, html, LitElement, property } from "lit-element";
import { HomeAssistant } from "../../types";
import { AreaSelector } from "../../data/selector";
import "../ha-area-picker";
import { ConfigEntry, getConfigEntries } from "../../data/config_entries";
import { DeviceRegistryEntry } from "../../data/device_registry";
import { EntityRegistryEntry } from "../../data/entity_registry";
@customElement("ha-selector-area")
export class HaAreaSelector extends LitElement {
@@ -22,76 +13,14 @@ export class HaAreaSelector extends LitElement {
@property() public label?: string;
@internalProperty() public _configEntries?: ConfigEntry[];
protected updated(changedProperties) {
if (changedProperties.has("selector")) {
const oldSelector = changedProperties.get("selector");
if (
oldSelector !== this.selector &&
this.selector.area.device?.integration
) {
this._loadConfigEntries();
}
}
}
protected render() {
return html`<ha-area-picker
.hass=${this.hass}
.value=${this.value}
.label=${this.label}
no-add
.deviceFilter=${(device) => this._filterDevices(device)}
.entityFilter=${(entity) => this._filterEntities(entity)}
.includeDeviceClasses=${this.selector.area.entity?.device_class
? [this.selector.area.entity.device_class]
: undefined}
.includeDomains=${this.selector.area.entity?.domain
? [this.selector.area.entity.domain]
: undefined}
></ha-area-picker>`;
}
private _filterEntities(entity: EntityRegistryEntry): boolean {
if (this.selector.area.entity?.integration) {
if (entity.platform !== this.selector.area.entity.integration) {
return false;
}
}
return true;
}
private _filterDevices(device: DeviceRegistryEntry): boolean {
if (
this.selector.area.device?.manufacturer &&
device.manufacturer !== this.selector.area.device.manufacturer
) {
return false;
}
if (
this.selector.area.device?.model &&
device.model !== this.selector.area.device.model
) {
return false;
}
if (this.selector.area.device?.integration) {
if (
!this._configEntries?.some((entry) =>
device.config_entries.includes(entry.entry_id)
)
) {
return false;
}
}
return true;
}
private async _loadConfigEntries() {
this._configEntries = (await getConfigEntries(this.hass)).filter(
(entry) => entry.domain === this.selector.area.device?.integration
);
}
}
declare global {

View File

@@ -1,4 +1,4 @@
import "@polymer/paper-item/paper-item-body";
import "@material/mwc-list/mwc-list-item";
import {
css,
CSSResult,
@@ -18,18 +18,10 @@ export class HaSettingsRow extends LitElement {
protected render(): SVGTemplateResult {
return html`
<style>
paper-item-body {
padding-right: 16px;
}
</style>
<paper-item-body
?two-line=${!this.threeLine}
?three-line=${this.threeLine}
>
<mwc-list-item noninteractive ?twoline=${!this.threeLine}>
<slot name="heading"></slot>
<div secondary><slot name="description"></slot></div>
</paper-item-body>
<span slot="secondary"><slot name="description"></slot></span>
</mwc-list-item>
<slot></slot>
`;
}
@@ -42,6 +34,7 @@ export class HaSettingsRow extends LitElement {
align-content: normal;
align-self: auto;
align-items: center;
justify-content: space-between;
}
:host([narrow]) {
align-items: normal;
@@ -49,6 +42,9 @@ export class HaSettingsRow extends LitElement {
border-top: 1px solid var(--divider-color);
padding-bottom: 8px;
}
mwc-list-item {
--mdc-list-side-padding: 0;
}
::slotted(ha-switch) {
padding: 16px 0;
}

View File

@@ -19,26 +19,13 @@ export interface DeviceSelector {
integration?: string;
manufacturer?: string;
model?: string;
entity?: {
domain?: EntitySelector["entity"]["domain"];
device_class?: EntitySelector["entity"]["device_class"];
};
entity?: EntitySelector["entity"];
};
}
export interface AreaSelector {
area: {
entity?: {
integration?: EntitySelector["entity"]["integration"];
domain?: EntitySelector["entity"]["domain"];
device_class?: EntitySelector["entity"]["device_class"];
};
device?: {
integration?: DeviceSelector["device"]["integration"];
manufacturer?: DeviceSelector["device"]["manufacturer"];
model?: DeviceSelector["device"]["model"];
};
};
// eslint-disable-next-line @typescript-eslint/ban-types
area: {};
}
export interface NumberSelector {

View File

@@ -1,16 +1,16 @@
import { safeDump } from "js-yaml";
import {
css,
CSSResult,
customElement,
html,
LitElement,
internalProperty,
LitElement,
TemplateResult,
} from "lit-element";
import { HomeAssistant } from "../../../types";
import { LovelaceCard } from "../types";
import { ErrorCardConfig } from "./types";
import { safeDump } from "js-yaml";
@customElement("hui-error-card")
export class HuiErrorCard extends LitElement implements LovelaceCard {
@@ -49,6 +49,7 @@ export class HuiErrorCard extends LitElement implements LovelaceCard {
font-weight: 500;
user-select: text;
cursor: default;
overflow: hidden;
}
pre {
font-family: var(--code-font-family, monospace);

View File

@@ -179,6 +179,9 @@ export class HuiActionEditor extends LitElement {
.dropdown {
display: flex;
}
paper-dropdown-menu {
flex-grow: 1;
}
`;
}
}

View File

@@ -1,4 +1,4 @@
import { mdiDrag } from "@mdi/js";
import { mdiDragVerticalVariant } from "@mdi/js";
import {
css,
CSSResult,
@@ -68,7 +68,7 @@ export class HuiEntityEditor extends LitElement {
: this.entities!.map((entityConf, index) => {
return html`
<div class="entity" data-entity-id=${entityConf.entity}>
<ha-svg-icon .path=${mdiDrag}></ha-svg-icon>
<ha-svg-icon .path=${mdiDragVerticalVariant}></ha-svg-icon>
<ha-entity-picker
.hass=${this.hass}
.value=${entityConf.entity}
@@ -192,6 +192,7 @@ export class HuiEntityEditor extends LitElement {
.entity ha-svg-icon {
padding-right: 8px;
cursor: move;
color: var(--secondary-text-color);
}
.entity ha-entity-picker {
flex-grow: 1;

View File

@@ -26,11 +26,7 @@ export class HuiThemeSelectEditor extends LitElement {
return html`
<paper-dropdown-menu
.label=${this.label ||
`${this.hass!.localize(
"ui.panel.lovelace.editor.card.generic.theme"
)} (${this.hass!.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})`}
this.hass!.localize("ui.panel.lovelace.editor.card.generic.theme")}
dynamic-align
>
<paper-listbox

View File

@@ -1,5 +1,14 @@
import { mdiHelpCircle } from "@mdi/js";
import { RequestSelectedDetail } from "@material/mwc-list/mwc-list-item";
import {
mdiCheckboxBlankOutline,
mdiCheckBoxOutline,
mdiCodeBracesBox,
mdiDotsVertical,
mdiFormSelect,
mdiHelpCircleOutline,
} from "@mdi/js";
import deepFreeze from "deep-freeze";
import { UnsubscribeFunc } from "home-assistant-js-websocket";
import {
css,
CSSResultArray,
@@ -14,10 +23,16 @@ import {
} from "lit-element";
import type { HASSDomEvent } from "../../../../common/dom/fire_event";
import { fireEvent } from "../../../../common/dom/fire_event";
import { shouldHandleRequestSelectedEvent } from "../../../../common/mwc/handle-request-selected-event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/ha-circular-progress";
import "../../../../components/ha-dialog";
import "../../../../components/ha-header-bar";
import "../../../../components/ha-menu-button";
import {
CoreFrontendUserData,
getOptimisticFrontendUserDataCollection,
} from "../../../../data/frontend";
import type {
LovelaceCardConfig,
LovelaceViewConfig,
@@ -40,6 +55,7 @@ declare global {
// for fire event
interface HASSDomEvents {
"reload-lovelace": undefined;
"scroll-to-pos": { x: number; y: number };
}
// for add event listener
interface HTMLElementEventMap {
@@ -75,6 +91,12 @@ export class HuiDialogEditCard extends LitElement
@internalProperty() private _dirty = false;
@internalProperty() private _coreUserData?: CoreFrontendUserData | null;
@internalProperty() private _isAdvanced? = false;
private _unsubCoreData?: UnsubscribeFunc;
public async showDialog(params: EditCardDialogParams): Promise<void> {
this._params = params;
this._GUImode = true;
@@ -90,6 +112,13 @@ export class HuiDialogEditCard extends LitElement
if (params.cardConfig) {
this._dirty = true;
}
this._unsubCoreData = getOptimisticFrontendUserDataCollection(
this.hass.connection,
"core"
).subscribe((coreUserData) => {
this._coreUserData = coreUserData;
this._isAdvanced = coreUserData?.showAdvanced;
});
}
public closeDialog(): boolean {
@@ -102,6 +131,10 @@ export class HuiDialogEditCard extends LitElement
this._error = undefined;
this._documentationURL = undefined;
this._dirty = false;
if (this._unsubCoreData) {
this._unsubCoreData();
this._unsubCoreData = undefined;
}
fireEvent(this, "dialog-closed", { dialog: this.localName });
return true;
}
@@ -157,10 +190,11 @@ export class HuiDialogEditCard extends LitElement
<ha-dialog
open
scrimClickAction
full
.heading=${true}
@keydown=${this._ignoreKeydown}
@closed=${this._cancel}
@opened=${this._opened}
.heading=${true}
>
<div slot="heading">
<ha-header-bar>
@@ -177,11 +211,75 @@ export class HuiDialogEditCard extends LitElement
dir=${computeRTLDirection(this.hass)}
>
<mwc-icon-button>
<ha-svg-icon .path=${mdiHelpCircle}></ha-svg-icon>
<ha-svg-icon .path=${mdiHelpCircleOutline}></ha-svg-icon>
</mwc-icon-button>
</a>
`
: ""}
${this._cardConfig !== undefined
? html`
<ha-button-menu
fixed
corner="BOTTOM_START"
slot="actionItems"
@closed=${(ev) => ev.stopPropagation()}
>
<mwc-icon-button
slot="trigger"
.label=${this.hass!.localize(
"ui.panel.lovelace.editor.menu.open"
)}
.title=${this.hass!.localize(
"ui.panel.lovelace.editor.menu.open"
)}
>
<ha-svg-icon .path=${mdiDotsVertical}></ha-svg-icon>
</mwc-icon-button>
${this._coreUserData?.showAdvanced === true
? html`
<mwc-list-item
graphic="icon"
.label=${this.hass!.localize(
!this._cardEditorEl || this._GUImode
? "ui.panel.lovelace.editor.edit_card.show_code_editor"
: "ui.panel.lovelace.editor.edit_card.show_visual_editor"
)}
.disabled=${!this._guiModeAvailable}
@request-selected=${this._toggleMode}
>
<span
>${this.hass!.localize(
!this._cardEditorEl || this._GUImode
? "ui.panel.lovelace.editor.edit_card.show_code_editor"
: "ui.panel.lovelace.editor.edit_card.show_visual_editor"
)}</span
>
<ha-svg-icon
slot="graphic"
.path=${!this._cardEditorEl || this._GUImode
? mdiCodeBracesBox
: mdiFormSelect}
></ha-svg-icon>
</mwc-list-item>
`
: html`
<mwc-list-item
graphic="icon"
label="Show Advanced Options"
@request-selected=${this._toggleAdvanced}
>
<span>Show Advanced Options</span>
<ha-svg-icon
slot="graphic"
.path=${this._isAdvanced
? mdiCheckBoxOutline
: mdiCheckboxBlankOutline}
></ha-svg-icon>
</mwc-list-item>
`}
</ha-button-menu>
`
: ""}
</ha-header-bar>
</div>
<div class="content">
@@ -190,9 +288,11 @@ export class HuiDialogEditCard extends LitElement
.hass=${this.hass}
.lovelace=${this._params.lovelaceConfig}
.value=${this._cardConfig}
.isAdvanced=${this._isAdvanced}
@config-changed=${this._handleConfigChanged}
@GUImode-changed=${this._handleGUIModeChanged}
@editor-save=${this._save}
@scroll-to-pos=${this._scrollToPos}
></hui-card-element-editor>
</div>
<div class="element-preview">
@@ -211,22 +311,6 @@ export class HuiDialogEditCard extends LitElement
: ``}
</div>
</div>
${this._cardConfig !== undefined
? html`
<mwc-button
slot="secondaryAction"
@click=${this._toggleMode}
.disabled=${!this._guiModeAvailable}
class="gui-mode-button"
>
${this.hass!.localize(
!this._cardEditorEl || this._GUImode
? "ui.panel.lovelace.editor.edit_card.show_code_editor"
: "ui.panel.lovelace.editor.edit_card.show_visual_editor"
)}
</mwc-button>
`
: ""}
<div slot="primaryAction" @click=${this._save}>
<mwc-button @click=${this._cancel}>
${this.hass!.localize("ui.common.cancel")}
@@ -264,6 +348,13 @@ export class HuiDialogEditCard extends LitElement
ev.stopPropagation();
}
private _scrollToPos(ev: CustomEvent): void {
this.shadowRoot!.querySelector("ha-dialog")?.scrollToPos(
ev.detail.x,
ev.detail.y
);
}
private _handleConfigChanged(ev: HASSDomEvent<ConfigChangedEvent>) {
this._cardConfig = deepFreeze(ev.detail.config);
this._error = ev.detail.error;
@@ -277,10 +368,20 @@ export class HuiDialogEditCard extends LitElement
this._guiModeAvailable = ev.detail.guiModeAvailable;
}
private _toggleMode(): void {
private _toggleMode(ev: CustomEvent<RequestSelectedDetail>): void {
if (!shouldHandleRequestSelectedEvent(ev)) {
return;
}
this._cardEditorEl?.toggleMode();
}
private _toggleAdvanced(ev: CustomEvent<RequestSelectedDetail>): void {
if (!shouldHandleRequestSelectedEvent(ev)) {
return;
}
this._isAdvanced = !this._isAdvanced;
}
private _opened() {
this._cardEditorEl?.refreshYamlEditor();
}
@@ -358,37 +459,47 @@ export class HuiDialogEditCard extends LitElement
css`
:host {
--code-mirror-max-height: calc(100vh - 176px);
--dialog-content-padding: 0px 24px;
}
@media all and (max-width: 450px), all and (max-height: 500px) {
/* overrule the ha-style-dialog max-height on small screens */
ha-dialog {
--mdc-dialog-max-height: 100%;
height: 100%;
}
}
@media all and (min-width: 850px) {
ha-dialog {
--mdc-dialog-min-width: 845px;
--mdc-dialog-max-height: calc(100% - 72px);
}
}
ha-dialog {
--mdc-dialog-max-width: 845px;
--dialog-z-index: 5;
}
@media all and (min-width: 451px) and (min-height: 501px) {
ha-dialog {
--mdc-dialog-max-width: 90vw;
}
:host([large]) .content {
:host([large]) ha-dialog {
width: calc(90vw - 48px);
}
}
@media all and (min-width: 850px) {
ha-dialog {
--mdc-dialog-min-width: 845px;
}
}
@media (min-width: 1200px) {
ha-dialog {
--mdc-dialog-max-width: 1250px;
--dialog-surface-position: fixed;
}
}
ha-dialog {
--dialog-z-index: 5;
--mdc-dialog-max-height: 750px;
}
:host([large]) ha-dialog {
--mdc-dialog-max-width: calc(100% - 32px);
}
ha-header-bar {
--mdc-theme-on-primary: var(--primary-text-color);
--mdc-theme-primary: var(--mdc-theme-surface);
@@ -407,23 +518,17 @@ export class HuiDialogEditCard extends LitElement
flex-direction: column;
margin: 0 -10px;
}
.content hui-card-preview {
margin: 4px auto;
max-width: 390px;
}
.content .element-editor {
margin: 0 10px;
}
@media (min-width: 1200px) {
ha-dialog {
--mdc-dialog-max-width: calc(100% - 32px);
--mdc-dialog-min-width: 1000px;
--dialog-surface-position: fixed;
--dialog-surface-top: 40px;
--mdc-dialog-max-height: calc(100% - 72px);
}
.content {
flex-direction: row;
}
@@ -435,28 +540,34 @@ export class HuiDialogEditCard extends LitElement
}
.content hui-card-preview {
padding: 8px 10px;
margin: auto 0px;
margin: auto;
max-width: 500px;
}
}
.hidden {
display: none;
}
.element-editor {
margin-bottom: 8px;
}
.blur {
filter: blur(2px) grayscale(100%);
}
.element-preview {
position: relative;
}
.element-preview ha-circular-progress {
top: 50%;
left: 50%;
position: absolute;
z-index: 10;
}
hui-card-preview {
padding-top: 8px;
margin-bottom: 4px;
@@ -464,14 +575,13 @@ export class HuiDialogEditCard extends LitElement
width: 100%;
box-sizing: border-box;
}
.gui-mode-button {
margin-right: auto;
}
.header {
display: flex;
align-items: center;
justify-content: space-between;
}
.header_button {
color: inherit;
text-decoration: none;

View File

@@ -14,4 +14,13 @@ export const configElementStyle = css`
.suffix {
margin: 0 8px;
}
ha-settings-row {
padding: 0;
}
ha-expansion-panel {
padding-top: 8px;
}
ha-expansion-panel .title {
font-size: 16px;
}
`;

View File

@@ -19,6 +19,7 @@ import { HomeAssistant } from "../../../../types";
import { AlarmPanelCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -37,6 +38,8 @@ export class HuiAlarmPanelCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: AlarmPanelCardConfig;
public setConfig(config: AlarmPanelCardConfig): void {
@@ -68,62 +71,68 @@ export class HuiAlarmPanelCardEditor extends LitElement
const states = ["arm_home", "arm_away", "arm_night", "arm_custom_bypass"];
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._name}"
.configValue="${"name"}"
@value-changed="${this._valueChanged}"
></paper-input>
<span>Used States</span> ${this._states.map((state, index) => {
return html`
<div class="states">
<paper-item>${state}</paper-item>
<ha-icon
class="deleteState"
.value="${index}"
icon="hass:close"
@click=${this._stateRemoved}
></ha-icon>
</div>
`;
})}
<paper-dropdown-menu
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.alarm-panel.available_states"
)}"
@value-changed="${this._stateAdded}"
>
<paper-listbox slot="dropdown-content">
${states.map((state) => {
return html` <paper-item>${state}</paper-item> `;
})}
</paper-listbox>
</paper-dropdown-menu>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
allow-custom-entity
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
<span>Used States</span>
${this._states.map((state, index) => {
return html`
<div class="states">
<paper-item>${state}</paper-item>
<ha-icon
class="deleteState"
.value=${index}
icon="hass:close"
@click=${this._stateRemoved}
></ha-icon>
</div>
`;
})}
<paper-dropdown-menu
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.alarm-panel.available_states"
)}
@value-changed=${this._stateAdded}
>
<paper-listbox slot="dropdown-content">
${states.map((state) => {
return html`<paper-item>${state}</paper-item>`;
})}
</paper-listbox>
</paper-dropdown-menu>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -11,9 +11,9 @@ import {
import { assert, boolean, object, optional, string } from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import { stateIcon } from "../../../../common/entity/state_icon";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/ha-formfield";
import "../../../../components/ha-icon-input";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import { ActionConfig } from "../../../../data/lovelace";
import { HomeAssistant } from "../../../../types";
@@ -22,6 +22,7 @@ import "../../components/hui-action-editor";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { actionConfigStruct, EditorTarget } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -53,6 +54,8 @@ export class HuiButtonCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: ButtonCardConfig;
public setConfig(config: ButtonCardConfig): void {
@@ -107,117 +110,34 @@ export class HuiButtonCardEditor extends LitElement
return html``;
}
const dir = computeRTLDirection(this.hass!);
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
@value-changed=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
allow-custom-entity
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)}
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
@value-changed=${this._valueChanged}
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-icon-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._icon}
.placeholder=${this._icon ||
stateIcon(this.hass.states[this._entity])}
.configValue=${"icon"}
@value-changed=${this._valueChanged}
></ha-icon-input>
</div>
<div class="side-by-side">
<div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_name"
)}
.dir=${dir}
>
<ha-switch
.checked=${this._show_name !== false}
.configValue=${"show_name"}
@change=${this._change}
></ha-switch>
</ha-formfield>
</div>
<div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_state"
)}
.dir=${dir}
>
<ha-switch
.checked=${this._show_state !== false}
.configValue=${"show_state"}
@change=${this._change}
></ha-switch>
</ha-formfield>
</div>
<div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_icon"
)}
.dir=${dir}
>
<ha-switch
.checked=${this._show_icon !== false}
.configValue=${"show_icon"}
@change=${this._change}
></ha-switch>
</ha-formfield>
</div>
</div>
<div class="side-by-side">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon_height"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._icon_height}
.configValue=${"icon_height"}
@value-changed=${this._valueChanged}
type="number"
><div class="suffix" slot="suffix">px</div>
</paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
<div class="side-by-side">
<hui-action-editor
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.tap_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.hass=${this.hass}
.config=${this._tap_action}
.actions=${actions}
@@ -227,12 +147,40 @@ export class HuiButtonCardEditor extends LitElement
)}
@value-changed=${this._valueChanged}
></hui-action-editor>
</div>
<div slot="advanced" class="card-config">
<div class="side-by-side">
<ha-icon-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon"
)}
.value=${this._icon}
.placeholder=${this._icon ||
stateIcon(this.hass.states[this._entity])}
.configValue=${"icon"}
@value-changed=${this._valueChanged}
></ha-icon-input>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon_height"
)}
.value=${this._icon_height}
.configValue=${"icon_height"}
@value-changed=${this._valueChanged}
type="number"
><div class="suffix" slot="suffix">px</div>
</paper-input>
</div>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
<hui-action-editor
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.hass=${this.hass}
.config=${this._hold_action}
.actions=${actions}
@@ -242,8 +190,44 @@ export class HuiButtonCardEditor extends LitElement
)}
@value-changed=${this._valueChanged}
></hui-action-editor>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_state"
)}
</span>
<ha-switch
.checked=${this._show_state !== false}
.configValue=${"show_state"}
@change=${this._change}
></ha-switch>
</ha-settings-row>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_name"
)}
</span>
<ha-switch
.checked=${this._show_name !== false}
.configValue=${"show_name"}
@change=${this._change}
></ha-switch>
</ha-settings-row>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_icon"
)}
</span>
<ha-switch
.checked=${this._show_icon !== false}
.configValue=${"show_icon"}
@change=${this._change}
></ha-switch>
</ha-settings-row>
</div>
</div>
</hui-config-element-template>
`;
}

View File

@@ -1,5 +1,6 @@
import {
CSSResult,
css,
CSSResultArray,
customElement,
html,
internalProperty,
@@ -23,6 +24,7 @@ import type { CalendarCardConfig } from "../../cards/types";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import type { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import type { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -41,6 +43,8 @@ export class HuiCalendarCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@property({ attribute: false }) private _config?: CalendarCardConfig;
@internalProperty() private _configEntities?: string[];
@@ -69,14 +73,15 @@ export class HuiCalendarCardEditor extends LitElement
}
return html`
<div class="card-config">
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
@@ -105,28 +110,30 @@ export class HuiCalendarCardEditor extends LitElement
</paper-listbox>
</paper-dropdown-menu>
</div>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
<h3>
${`${this.hass.localize(
"ui.panel.lovelace.editor.card.calendar.calendar_entities"
)} (
${this.hass!.localize(
"ui.panel.lovelace.editor.card.config.required"
)})`}
</h3>
<ha-entities-picker
.hass=${this.hass!}
.value=${this._configEntities}
.includeDomains=${["calendar"]}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
<h3>
${this.hass.localize(
"ui.panel.lovelace.editor.card.calendar.calendar_entities"
) +
" (" +
this.hass!.localize("ui.panel.lovelace.editor.card.config.required") +
")"}
</h3>
<ha-entities-picker
.hass=${this.hass!}
.value=${this._configEntities}
.includeDomains=${["calendar"]}
@value-changed=${this._valueChanged}
>
</ha-entities-picker>
>
</ha-entities-picker>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}
@@ -175,8 +182,15 @@ export class HuiCalendarCardEditor extends LitElement
fireEvent(this, "config-changed", { config: this._config });
}
static get styles(): CSSResult {
return configElementStyle;
static get styles(): CSSResultArray {
return [
configElementStyle,
css`
paper-dropdown-menu {
width: 100%;
}
`,
];
}
}

View File

@@ -22,11 +22,11 @@ import {
union,
} from "superstruct";
import { fireEvent, HASSDomEvent } from "../../../../common/dom/fire_event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/entity/state-badge";
import "../../../../components/ha-card";
import "../../../../components/ha-formfield";
import "../../../../components/ha-icon";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import type { HomeAssistant } from "../../../../types";
import type { EntitiesCardConfig } from "../../cards/types";
@@ -35,6 +35,7 @@ import type { LovelaceRowConfig } from "../../entity-rows/types";
import { headerFooterConfigStructs } from "../../header-footer/types";
import type { LovelaceCardEditor } from "../../types";
import "../header-footer-editor/hui-header-footer-editor";
import "../hui-config-element-template";
import "../hui-entities-card-row-editor";
import "../hui-sub-element-editor";
import { processEditorEntities } from "../process-editor-entities";
@@ -62,6 +63,8 @@ export class HuiEntitiesCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: EntitiesCardConfig;
@internalProperty() private _configEntities?: LovelaceRowConfig[];
@@ -92,6 +95,7 @@ export class HuiEntitiesCardEditor extends LitElement
<hui-sub-element-editor
.hass=${this.hass}
.config=${this._subElementEditorConfig}
.isAdvancedUser=${this.isAdvanced}
@go-back=${this._goBack}
@config-changed=${this._handleSubElementChanged}
>
@@ -100,70 +104,80 @@ export class HuiEntitiesCardEditor extends LitElement
}
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
<div class="side-by-side">
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.entities.show_header_toggle"
)}
.dir=${computeRTLDirection(this.hass)}
>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-settings-row>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.entities.show_header_toggle"
)}
</span>
<span slot="description">
${this.hass.localize(
"ui.panel.lovelace.editor.card.entities.show_header_toggle_secondary"
)}
</span>
<ha-switch
.checked=${this._config!.show_header_toggle !== false}
.configValue=${"show_header_toggle"}
@change=${this._valueChanged}
></ha-switch>
</ha-formfield>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.state_color"
)}
.dir=${computeRTLDirection(this.hass)}
>
</ha-settings-row>
</div>
<hui-entities-card-row-editor
.hass=${this.hass}
.entities=${this._configEntities}
@entities-changed=${this._valueChanged}
@edit-detail-element=${this._editDetailElement}
></hui-entities-card-row-editor>
<div slot="advanced" class="card-config">
<hui-header-footer-editor
.hass=${this.hass}
.configValue=${"header"}
.config=${this._config.header}
@value-changed=${this._valueChanged}
@edit-detail-element=${this._editDetailElement}
></hui-header-footer-editor>
<hui-header-footer-editor
.hass=${this.hass}
.configValue=${"footer"}
.config=${this._config.footer}
@value-changed=${this._valueChanged}
@edit-detail-element=${this._editDetailElement}
></hui-header-footer-editor>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.state_color"
)}
</span>
<ha-switch
.checked=${this._config!.state_color}
.configValue=${"state_color"}
@change=${this._valueChanged}
></ha-switch>
</ha-formfield>
</ha-settings-row>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
<hui-header-footer-editor
.hass=${this.hass}
.configValue=${"header"}
.config=${this._config.header}
@value-changed=${this._valueChanged}
@edit-detail-element=${this._editDetailElement}
></hui-header-footer-editor>
<hui-header-footer-editor
.hass=${this.hass}
.configValue=${"footer"}
.config=${this._config.footer}
@value-changed=${this._valueChanged}
@edit-detail-element=${this._editDetailElement}
></hui-header-footer-editor>
</div>
<hui-entities-card-row-editor
.hass=${this.hass}
.entities=${this._configEntities}
@entities-changed=${this._valueChanged}
@edit-detail-element=${this._editDetailElement}
></hui-entities-card-row-editor>
</hui-config-element-template>
`;
}
@@ -188,20 +202,9 @@ export class HuiEntitiesCardEditor extends LitElement
return;
}
if (configValue === "row" || (ev.detail && ev.detail.entities)) {
if (ev.detail && ev.detail.entities) {
const newConfigEntities =
ev.detail.entities || this._configEntities!.concat();
if (configValue === "row") {
if (!value) {
newConfigEntities.splice(this._subElementEditorConfig!.index!, 1);
this._goBack();
} else {
newConfigEntities[this._subElementEditorConfig!.index!] = value;
}
this._subElementEditorConfig!.elementConfig = value;
}
this._config = { ...this._config!, entities: newConfigEntities };
this._configEntities = processEditorEntities(this._config!.entities);
} else if (configValue) {
@@ -221,18 +224,20 @@ export class HuiEntitiesCardEditor extends LitElement
private _handleSubElementChanged(ev: CustomEvent): void {
ev.stopPropagation();
if (!this._config || !this.hass) {
const configValue = this._subElementEditorConfig?.type;
if (!this._config || !this.hass || !configValue) {
return;
}
const configValue = this._subElementEditorConfig?.type;
const value = ev.detail.config;
let goBack = false;
if (configValue === "row") {
const newConfigEntities = this._configEntities!.concat();
if (!value) {
newConfigEntities.splice(this._subElementEditorConfig!.index!, 1);
this._goBack();
goBack = true;
} else {
newConfigEntities[this._subElementEditorConfig!.index!] = value;
}
@@ -240,9 +245,10 @@ export class HuiEntitiesCardEditor extends LitElement
this._config = { ...this._config!, entities: newConfigEntities };
this._configEntities = processEditorEntities(this._config!.entities);
} else if (configValue) {
if (value === "") {
if (!value || value === "") {
this._config = { ...this._config };
delete this._config[configValue!];
goBack = true;
} else {
this._config = {
...this._config,
@@ -251,16 +257,21 @@ export class HuiEntitiesCardEditor extends LitElement
}
}
this._subElementEditorConfig = {
...this._subElementEditorConfig!,
elementConfig: value,
};
if (goBack) {
this._goBack();
} else {
this._subElementEditorConfig = {
...this._subElementEditorConfig!,
elementConfig: value,
};
}
fireEvent(this, "config-changed", { config: this._config });
}
private _editDetailElement(ev: HASSDomEvent<EditSubElementEvent>): void {
this._subElementEditorConfig = ev.detail.subElementConfig;
fireEvent(this, "scroll-to-pos", { x: 0, y: 0 });
}
private _goBack(): void {

View File

@@ -20,6 +20,7 @@ import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { headerFooterConfigStructs } from "../../header-footer/types";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -39,6 +40,8 @@ export class HuiEntityCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: EntityCardConfig;
public setConfig(config: EntityCardConfig): void {
@@ -76,74 +79,67 @@ export class HuiEntityCardEditor extends LitElement
}
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)}
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<ha-entity-attribute-picker
.hass=${this.hass}
.entityId=${this._entity}
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.attribute"
)}
.value=${this._attribute}
.configValue=${"attribute"}
@value-changed=${this._valueChanged}
></ha-entity-attribute-picker>
<ha-icon-input
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.value=${this._icon}
.placeholder=${this._icon ||
stateIcon(this.hass.states[this._entity])}
.configValue=${"icon"}
@value-changed=${this._valueChanged}
></ha-icon-input>
</div>
<div class="side-by-side">
<ha-entity-attribute-picker
.hass=${this.hass}
.entityId=${this._entity}
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.attribute"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._attribute}
.configValue=${"attribute"}
@value-changed=${this._valueChanged}
></ha-entity-attribute-picker>
<paper-input
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.unit"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.value=${this._unit}
.configValue=${"unit"}
@value-changed=${this._valueChanged}
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -1,7 +1,6 @@
import "@polymer/paper-input/paper-input";
import {
css,
CSSResultArray,
CSSResult,
customElement,
html,
internalProperty,
@@ -11,14 +10,15 @@ import {
} from "lit-element";
import { assert, number, object, optional, string } from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/ha-formfield";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import { HomeAssistant } from "../../../../types";
import { GaugeCardConfig, SeverityConfig } from "../../cards/types";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -40,6 +40,8 @@ export class HuiGaugeCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: GaugeCardConfig;
public setConfig(config: GaugeCardConfig): void {
@@ -81,141 +83,131 @@ export class HuiGaugeCardEditor extends LitElement
}
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._name}"
.configValue=${"name"}
@value-changed="${this._valueChanged}"
></paper-input>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.unit"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._unit}"
.configValue=${"unit"}
@value-changed="${this._valueChanged}"
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.minimum"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._min}"
.configValue=${"min"}
@value-changed="${this._valueChanged}"
></paper-input>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.maximum"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._max}"
.configValue=${"max"}
@value-changed="${this._valueChanged}"
></paper-input>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.define"
)}
.dir=${computeRTLDirection(this.hass)}
>
<ha-switch
.checked="${this._config!.severity !== undefined}"
@change="${this._toggleSeverity}"
></ha-switch
></ha-formfield>
${this._config!.severity !== undefined
? html`
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.green"
)} (${this.hass.localize(
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
allow-custom-entity
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._severity ? this._severity.green : 0}"
.configValue=${"green"}
@value-changed="${this._severityChanged}"
></paper-input>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.yellow"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._severity ? this._severity.yellow : 0}"
.configValue=${"yellow"}
@value-changed="${this._severityChanged}"
></paper-input>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.red"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._severity ? this._severity.red : 0}"
.configValue=${"red"}
@value-changed="${this._severityChanged}"
></paper-input>
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
<div class="side-by-side">
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.minimum"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._min}
.configValue=${"min"}
@value-changed=${this._valueChanged}
></paper-input>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.maximum"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._max}
.configValue=${"max"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
`
: ""}
</div>
</div>
<div slot="advanced" class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.unit"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._unit}
.configValue=${"unit"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.define"
)}
</span>
<ha-switch
.checked=${this._config!.severity !== undefined}
@change=${this._toggleSeverity}
></ha-switch>
</ha-settings-row>
${this._config!.severity !== undefined
? html`
<div class="side-by-side">
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.green"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value=${this._severity ? this._severity.green : 0}
.configValue=${"green"}
@value-changed=${this._severityChanged}
></paper-input>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.yellow"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value=${this._severity ? this._severity.yellow : 0}
.configValue=${"yellow"}
@value-changed=${this._severityChanged}
></paper-input>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.gauge.severity.red"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value=${this._severity ? this._severity.red : 0}
.configValue=${"red"}
@value-changed=${this._severityChanged}
></paper-input>
</div>
`
: ""}
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}
static get styles(): CSSResultArray {
return [
configElementStyle,
css`
.severity {
display: none;
width: 100%;
padding-left: 16px;
flex-direction: row;
flex-wrap: wrap;
}
.severity > * {
flex: 1 0 30%;
padding-right: 4px;
}
ha-switch[checked] ~ .severity {
display: flex;
}
`,
];
static get styles(): CSSResult {
return configElementStyle;
}
private _toggleSeverity(ev: EntitiesEditorEvent): void {

View File

@@ -76,6 +76,7 @@ export class HuiGenericEntityRowEditor extends LitElement
return html`
<div class="card-config">
<ha-entity-picker
hide-clear-icon
allow-custom-entity
.hass=${this.hass}
.value=${this._config.entity}

View File

@@ -21,17 +21,18 @@ import {
union,
} from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/entity/state-badge";
import "../../../../components/ha-card";
import "../../../../components/ha-formfield";
import "../../../../components/ha-icon";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import { HomeAssistant } from "../../../../types";
import { ConfigEntity, GlanceCardConfig } from "../../cards/types";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { processEditorEntities } from "../process-editor-entities";
import {
EditorTarget,
@@ -57,6 +58,8 @@ export class HuiGlanceCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: GlanceCardConfig;
@internalProperty() private _configEntities?: ConfigEntity[];
@@ -100,103 +103,94 @@ export class HuiGlanceCardEditor extends LitElement
return html``;
}
const dir = computeRTLDirection(this.hass!);
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<hui-entity-editor
.hass=${this.hass}
.entities=${this._configEntities}
@entities-changed=${this._valueChanged}
></hui-entity-editor>
<div slot="advanced" class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.glance.columns"
)}
type="number"
.value=${this._columns}
.configValue=${"columns"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_name"
)}
</span>
<ha-switch
.checked=${this._config!.show_name !== false}
.configValue=${"show_name"}
@change=${this._valueChanged}
></ha-switch>
</ha-settings-row>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_icon"
)}
</span>
<ha-switch
.checked=${this._config!.show_icon !== false}
.configValue=${"show_icon"}
@change=${this._valueChanged}
>
</ha-switch>
</ha-settings-row>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_state"
)}
</span>
<ha-switch
.checked=${this._config!.show_state !== false}
.configValue=${"show_state"}
@change=${this._valueChanged}
>
</ha-switch>
</ha-settings-row>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.state_color"
)}
</span>
<ha-switch
.checked=${this._config!.state_color}
.configValue=${"state_color"}
@change=${this._valueChanged}
></ha-switch>
</ha-settings-row>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.glance.columns"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
type="number"
.value=${this._columns}
.configValue=${"columns"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div class="side-by-side">
<div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_name"
)}
.dir=${dir}
>
<ha-switch
.checked=${this._config!.show_name !== false}
.configValue=${"show_name"}
@change=${this._valueChanged}
></ha-switch>
</ha-formfield>
</div>
<div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_icon"
)}
.dir=${dir}
>
<ha-switch
.checked=${this._config!.show_icon !== false}
.configValue=${"show_icon"}
@change=${this._valueChanged}
>
</ha-switch>
</ha-formfield>
</div>
<div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_state"
)}
.dir=${dir}
>
<ha-switch
.checked=${this._config!.show_state !== false}
.configValue=${"show_state"}
@change=${this._valueChanged}
>
</ha-switch>
</ha-formfield>
</div>
</div>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.state_color"
)}
.dir=${computeRTLDirection(this.hass)}
>
<ha-switch
.checked=${this._config!.state_color}
.configValue=${"state_color"}
@change=${this._valueChanged}
></ha-switch>
</ha-formfield>
</div>
<hui-entity-editor
.hass=${this.hass}
.entities=${this._configEntities}
@entities-changed=${this._valueChanged}
></hui-entity-editor>
</hui-config-element-template>
`;
}

View File

@@ -24,6 +24,7 @@ import { EntityId } from "../../common/structs/is-entity-id";
import "../../components/hui-entity-editor";
import { EntityConfig } from "../../entity-rows/types";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { processEditorEntities } from "../process-editor-entities";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -49,6 +50,8 @@ export class HuiHistoryGraphCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: HistoryGraphCardConfig;
@internalProperty() private _configEntities?: EntityConfig[];
@@ -81,47 +84,48 @@ export class HuiHistoryGraphCardEditor extends LitElement
}
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._title}"
.configValue="${"title"}"
@value-changed="${this._valueChanged}"
></paper-input>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hours_to_show"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._hours_to_show}"
.configValue=${"hours_to_show"}
@value-changed="${this._valueChanged}"
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<div class="side-by-side">
<paper-input
type="number"
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hours_to_show"
)}
.value=${this._hours_to_show}
.configValue=${"hours_to_show"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<hui-entity-editor
.hass=${this.hass}
.entities=${this._configEntities}
@entities-changed=${this._valueChanged}
></hui-entity-editor>
</div>
<div slot="advanced" class="card-config">
<paper-input
type="number"
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.refresh_interval"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._refresh_interval}"
)}
.value=${this._refresh_interval}
.configValue=${"refresh_interval"}
@value-changed="${this._valueChanged}"
@value-changed=${this._valueChanged}
></paper-input>
</div>
<hui-entity-editor
.hass=${this.hass}
.entities="${this._configEntities}"
@entities-changed="${this._valueChanged}"
></hui-entity-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -15,6 +15,7 @@ import { HomeAssistant } from "../../../../types";
import { HumidifierCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -32,6 +33,8 @@ export class HuiHumidifierCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: HumidifierCardConfig;
public setConfig(config: HumidifierCardConfig): void {
@@ -57,37 +60,42 @@ export class HuiHumidifierCardEditor extends LitElement
}
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._name}"
.configValue="${"name"}"
@value-changed="${this._valueChanged}"
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -13,6 +13,7 @@ import { fireEvent } from "../../../../common/dom/fire_event";
import { HomeAssistant } from "../../../../types";
import { IframeCardConfig } from "../../cards/types";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -28,6 +29,8 @@ export class HuiIframeCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: IframeCardConfig;
public setConfig(config: IframeCardConfig): void {
@@ -53,40 +56,41 @@ export class HuiIframeCardEditor extends LitElement
}
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.url"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._url}"
.configValue="${"url"}"
@value-changed="${this._valueChanged}"
></paper-input>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
"ui.panel.lovelace.editor.card.generic.url"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._title}"
.configValue="${"title"}"
@value-changed="${this._valueChanged}"
.value=${this._url}
.configValue=${"url"}
@value-changed=${this._valueChanged}
></paper-input>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._aspect_ratio}"
.configValue="${"aspect_ratio"}"
@value-changed="${this._valueChanged}"
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
</div>
<div slot="advanced" class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)}
.value=${this._aspect_ratio}
.configValue=${"aspect_ratio"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
</hui-config-element-template>
`;
}

View File

@@ -19,6 +19,7 @@ import "../../components/hui-action-editor";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { actionConfigStruct, EditorTarget } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -39,6 +40,8 @@ export class HuiLightCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: LightCardConfig;
public setConfig(config: LightCardConfig): void {
@@ -85,78 +88,73 @@ export class HuiLightCardEditor extends LitElement
];
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@value-changed=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<div class="side-by-side">
<paper-input
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@value-changed=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<ha-icon-input
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.value=${this._icon}
.placeholder=${this._icon ||
stateIcon(this.hass.states[this._entity])}
.configValue=${"icon"}
@value-changed=${this._valueChanged}
></ha-icon-input>
<hui-action-editor
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)}
.hass=${this.hass}
.config=${this._hold_action}
.actions=${actions}
.configValue=${"hold_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-action-editor
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.double_tap_action"
)}
.hass=${this.hass}
.config=${this._double_tap_action}
.actions=${actions}
.configValue=${"double_tap_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
<hui-action-editor
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.hass=${this.hass}
.config=${this._hold_action}
.actions=${actions}
.configValue=${"hold_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-action-editor
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.double_tap_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.hass=${this.hass}
.config=${this._double_tap_action}
.actions=${actions}
.configValue=${"double_tap_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -17,6 +17,7 @@ import { LogbookCardConfig } from "../../cards/types";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -33,6 +34,8 @@ export class HuiLogbookCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: LogbookCardConfig;
@internalProperty() private _configEntities?: string[];
@@ -65,50 +68,51 @@ export class HuiLogbookCardEditor extends LitElement
}
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<paper-input
type="number"
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hours_to_show"
)}
.value=${this._hours_to_show}
.configValue=${"hours_to_show"}
@value-changed=${this._valueChanged}
></paper-input>
<h3>
${`${this.hass!.localize(
"ui.panel.lovelace.editor.card.generic.entities"
)} (${this.hass!.localize(
"ui.panel.lovelace.editor.card.config.required"
)})`}
</h3>
<ha-entities-picker
.hass=${this.hass}
.value=${this._configEntities}
@value-changed=${this._valueChanged}
>
</ha-entities-picker>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
<paper-input
type="number"
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hours_to_show"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._hours_to_show}
.configValue=${"hours_to_show"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<h3>
${`${this.hass!.localize(
"ui.panel.lovelace.editor.card.generic.entities"
)} (${this.hass!.localize(
"ui.panel.lovelace.editor.card.config.required"
)})`}
</h3>
<ha-entities-picker
.hass=${this.hass}
.value=${this._configEntities}
@value-changed=${this._valueChanged}
>
</ha-entities-picker>
</div>
</hui-config-element-template>
`;
}

View File

@@ -19,8 +19,8 @@ import {
string,
} from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/ha-formfield";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import { PolymerChangedEvent } from "../../../../polymer-types";
import { HomeAssistant } from "../../../../types";
@@ -29,6 +29,7 @@ import "../../components/hui-entity-editor";
import "../../components/hui-input-list-editor";
import { EntityConfig } from "../../entity-rows/types";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { processEditorEntities } from "../process-editor-entities";
import {
EditorTarget,
@@ -52,6 +53,8 @@ const cardConfigStruct = object({
export class HuiMapCardEditor extends LitElement implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: MapCardConfig;
@internalProperty() private _configEntities?: EntityConfig[];
@@ -94,87 +97,84 @@ export class HuiMapCardEditor extends LitElement implements LovelaceCardEditor {
}
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._title}"
.configValue="${"title"}"
@value-changed="${this._valueChanged}"
></paper-input>
<div class="side-by-side">
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._aspect_ratio}"
.configValue="${"aspect_ratio"}"
@value-changed="${this._valueChanged}"
></paper-input>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.map.default_zoom"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
type="number"
.value="${this._default_zoom}"
.configValue="${"default_zoom"}"
@value-changed="${this._valueChanged}"
></paper-input>
</div>
<div class="side-by-side">
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.map.dark_mode"
"ui.panel.lovelace.editor.card.generic.title"
)}
.dir=${computeRTLDirection(this.hass)}
>
<ha-switch
.checked="${this._dark_mode}"
.configValue="${"dark_mode"}"
@change="${this._valueChanged}"
></ha-switch
></ha-formfield>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.map.hours_to_show"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
type="number"
.value="${this._hours_to_show}"
.configValue="${"hours_to_show"}"
@value-changed="${this._valueChanged}"
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<hui-entity-editor
.hass=${this.hass}
.entities="${this._configEntities}"
@entities-changed="${this._entitiesValueChanged}"
></hui-entity-editor>
<h3>
${this.hass.localize(
"ui.panel.lovelace.editor.card.map.geo_location_sources"
)}
</h3>
<div class="geo_location_sources">
<hui-input-list-editor
inputLabel=${this.hass.localize(
"ui.panel.lovelace.editor.card.map.source"
<div class="side-by-side">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.map.default_zoom"
)}
type="number"
.value=${this._default_zoom}
.configValue=${"default_zoom"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.map.hours_to_show"
)}
type="number"
.value=${this._hours_to_show}
.configValue=${"hours_to_show"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.map.dark_mode"
)}
</span>
<ha-switch
.checked=${this._dark_mode}
.configValue=${"dark_mode"}
@change=${this._valueChanged}
></ha-switch>
</ha-settings-row>
<hui-entity-editor
.hass=${this.hass}
.value="${this._geo_location_sources}"
.configValue="${"geo_location_sources"}"
@value-changed="${this._valueChanged}"
></hui-input-list-editor>
.entities=${this._configEntities}
@entities-changed=${this._entitiesValueChanged}
></hui-entity-editor>
</div>
</div>
<div slot="advanced" class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)}
.value=${this._aspect_ratio}
.configValue=${"aspect_ratio"}
@value-changed=${this._valueChanged}
></paper-input>
<h3>
${this.hass.localize(
"ui.panel.lovelace.editor.card.map.geo_location_sources"
)}
</h3>
<div class="geo_location_sources">
<hui-input-list-editor
inputLabel=${this.hass.localize(
"ui.panel.lovelace.editor.card.map.source"
)}
.hass=${this.hass}
.value=${this._geo_location_sources}
.configValue=${"geo_location_sources"}
@value-changed=${this._valueChanged}
></hui-input-list-editor>
</div>
</div>
</hui-config-element-template>
`;
}

View File

@@ -15,6 +15,7 @@ import { HomeAssistant } from "../../../../types";
import { MarkdownCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -30,6 +31,8 @@ export class HuiMarkdownCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: MarkdownCardConfig;
public setConfig(config: MarkdownCardConfig): void {
@@ -55,38 +58,43 @@ export class HuiMarkdownCardEditor extends LitElement
}
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._title}"
.configValue="${"title"}"
@value-changed="${this._valueChanged}"
></paper-input>
<paper-textarea
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.markdown.content"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._content}"
.configValue="${"content"}"
@keydown=${this._ignoreKeydown}
@value-changed="${this._valueChanged}"
autocapitalize="none"
autocomplete="off"
spellcheck="false"
></paper-textarea>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<paper-textarea
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.markdown.content"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value=${this._content}
.configValue=${"content"}
@keydown=${this._ignoreKeydown}
@value-changed=${this._valueChanged}
autocapitalize="none"
autocomplete="off"
spellcheck="false"
></paper-textarea>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -1,18 +1,18 @@
import {
customElement,
html,
internalProperty,
LitElement,
property,
internalProperty,
TemplateResult,
} from "lit-element";
import { assert, object, optional, string } from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import "../../../../components/entity/ha-entity-picker";
import { HomeAssistant } from "../../../../types";
import { MediaControlCardConfig } from "../../cards/types";
import { LovelaceCardEditor } from "../../types";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { assert, object, string, optional } from "superstruct";
const cardConfigStruct = object({
type: string(),
@@ -45,17 +45,17 @@ export class HuiMediaControlCardEditor extends LitElement
return html`
<div class="card-config">
<ha-entity-picker
allow-custom-entity
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change="${this._valueChanged}"
allow-custom-entity
@change=${this._valueChanged}
></ha-entity-picker>
</div>
`;

View File

@@ -16,6 +16,7 @@ import { PictureCardConfig } from "../../cards/types";
import "../../components/hui-action-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { actionConfigStruct, EditorTarget } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -32,6 +33,8 @@ export class HuiPictureCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: PictureCardConfig;
public setConfig(config: PictureCardConfig): void {
@@ -63,50 +66,51 @@ export class HuiPictureCardEditor extends LitElement
const actions = ["navigate", "url", "call-service", "none"];
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.image"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.value="${this._image}"
.configValue="${"image"}"
@value-changed="${this._valueChanged}"
></paper-input>
<div class="side-by-side">
<hui-action-editor
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.tap_action"
"ui.panel.lovelace.editor.card.generic.image"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
"ui.panel.lovelace.editor.card.config.required"
)})"
.value=${this._image}
.configValue=${"image"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<hui-action-editor
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.tap_action"
)}
.hass=${this.hass}
.config="${this._tap_action}"
.actions="${actions}"
.configValue="${"tap_action"}"
@value-changed="${this._valueChanged}"
.config=${this._tap_action}
.actions=${actions}
.configValue=${"tap_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-action-editor
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.hass=${this.hass}
.config="${this._hold_action}"
.actions="${actions}"
.configValue="${"hold_action"}"
@value-changed="${this._valueChanged}"
.config=${this._hold_action}
.actions=${actions}
.configValue=${"hold_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</div>
</hui-config-element-template>
`;
}

View File

@@ -3,7 +3,8 @@ import "@polymer/paper-input/paper-input";
import "@polymer/paper-item/paper-item";
import "@polymer/paper-listbox/paper-listbox";
import {
CSSResult,
css,
CSSResultArray,
customElement,
html,
internalProperty,
@@ -13,8 +14,8 @@ import {
} from "lit-element";
import { assert, boolean, object, optional, string } from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/ha-formfield";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import { ActionConfig } from "../../../../data/lovelace";
import { HomeAssistant } from "../../../../types";
@@ -23,6 +24,7 @@ import "../../components/hui-action-editor";
import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { actionConfigStruct, EditorTarget } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -48,6 +50,8 @@ export class HuiPictureEntityCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: PictureEntityCardConfig;
public setConfig(config: PictureEntityCardConfig): void {
@@ -106,148 +110,137 @@ export class HuiPictureEntityCardEditor extends LitElement
const actions = ["more-info", "toggle", "navigate", "call-service", "none"];
const views = ["auto", "live"];
const dir = computeRTLDirection(this.hass!);
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
@value-changed="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._name}"
.configValue="${"name"}"
@value-changed="${this._valueChanged}"
></paper-input>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.image"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._image}"
.configValue="${"image"}"
@value-changed="${this._valueChanged}"
></paper-input>
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_image"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.hass=${this.hass}
.value="${this._camera_image}"
.configValue=${"camera_image"}
@value-changed="${this._valueChanged}"
.includeDomains=${includeDomains}
allow-custom-entity
></ha-entity-picker>
<div class="side-by-side">
<paper-dropdown-menu
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
allow-custom-entity
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_view"
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
"ui.panel.lovelace.editor.card.config.required"
)})"
.configValue="${"camera_view"}"
@value-changed="${this._valueChanged}"
>
<paper-listbox
slot="dropdown-content"
.selected="${views.indexOf(this._camera_view)}"
>
${views.map((view) => {
return html` <paper-item>${view}</paper-item> `;
})}
</paper-listbox>
</paper-dropdown-menu>
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
@value-changed=${this._valueChanged}
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._aspect_ratio}"
.configValue="${"aspect_ratio"}"
@value-changed="${this._valueChanged}"
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div class="side-by-side">
<div>
<ha-formfield
.label=${this.hass.localize(
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.image"
)}
.value=${this._image}
.configValue=${"image"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_name"
)}
.dir=${dir}
>
<ha-switch
.checked="${this._config!.show_name !== false}"
.configValue="${"show_name"}"
@change="${this._change}"
></ha-switch
></ha-formfield>
</div>
<div>
<ha-formfield
.label=${this.hass.localize(
</span>
<ha-switch
.checked=${this._config!.show_name !== false}
.configValue=${"show_name"}
@change=${this._change}
></ha-switch>
</ha-settings-row>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.show_state"
)}
.dir=${dir}
>
<ha-switch
.checked="${this._config!.show_state !== false}"
.configValue="${"show_state"}"
@change="${this._change}"
></ha-switch
></ha-formfield>
</div>
</div>
<div class="side-by-side">
</span>
<ha-switch
.checked=${this._config!.show_state !== false}
.configValue=${"show_state"}
@change=${this._change}
></ha-switch>
</ha-settings-row>
<hui-action-editor
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.tap_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.hass=${this.hass}
.config="${this._tap_action}"
.actions="${actions}"
.configValue="${"tap_action"}"
@value-changed="${this._valueChanged}"
.config=${this._tap_action}
.actions=${actions}
.configValue=${"tap_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<ha-expansion-panel>
<span class="title" slot="title">
${this.hass.localize(
`ui.panel.lovelace.editor.card.picture-entity.camera_options`
)}
</span>
<ha-entity-picker
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_image"
)}
.hass=${this.hass}
.value=${this._camera_image}
.configValue=${"camera_image"}
@value-changed=${this._valueChanged}
.includeDomains=${includeDomains}
allow-custom-entity
></ha-entity-picker>
<paper-dropdown-menu
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_view"
)}
.configValue=${"camera_view"}
@value-changed=${this._valueChanged}
>
<paper-listbox
slot="dropdown-content"
.selected=${views.indexOf(this._camera_view)}
>
${views.map((view) => {
return html`<paper-item>${view}</paper-item>`;
})}
</paper-listbox>
</paper-dropdown-menu>
</ha-expansion-panel>
</div>
<div slot="advanced" class="card-config">
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)}
.value=${this._aspect_ratio}
.configValue=${"aspect_ratio"}
@value-changed=${this._valueChanged}
></paper-input>
<hui-action-editor
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.hass=${this.hass}
.config="${this._hold_action}"
.actions="${actions}"
.configValue="${"hold_action"}"
@value-changed="${this._valueChanged}"
.config=${this._hold_action}
.actions=${actions}
.configValue=${"hold_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</div>
</hui-config-element-template>
`;
}
@@ -294,8 +287,15 @@ export class HuiPictureEntityCardEditor extends LitElement
fireEvent(this, "config-changed", { config: this._config });
}
static get styles(): CSSResult {
return configElementStyle;
static get styles(): CSSResultArray {
return [
configElementStyle,
css`
paper-dropdown-menu {
width: 100%;
}
`,
];
}
}

View File

@@ -3,7 +3,8 @@ import "@polymer/paper-input/paper-input";
import "@polymer/paper-item/paper-item";
import "@polymer/paper-listbox/paper-listbox";
import {
CSSResult,
css,
CSSResultArray,
customElement,
html,
internalProperty,
@@ -22,6 +23,7 @@ import "../../components/hui-entity-editor";
import "../../components/hui-theme-select-editor";
import { EntityConfig } from "../../entity-rows/types";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { processEditorEntities } from "../process-editor-entities";
import {
actionConfigStruct,
@@ -51,6 +53,8 @@ export class HuiPictureGlanceCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: PictureGlanceCardConfig;
@internalProperty() private _configEntities?: EntityConfig[];
@@ -112,120 +116,114 @@ export class HuiPictureGlanceCardEditor extends LitElement
const views = ["auto", "live"];
return html`
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._title}"
.configValue="${"title"}"
@value-changed="${this._valueChanged}"
></paper-input>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.image"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._image}"
.configValue="${"image"}"
@value-changed="${this._valueChanged}"
></paper-input>
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_image"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.hass=${this.hass}
.value="${this._camera_image}"
.configValue=${"camera_image"}
@value-changed="${this._valueChanged}"
allow-custom-entity
.includeDomains=${includeDomains}
></ha-entity-picker>
<div class="side-by-side">
<paper-dropdown-menu
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_view"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.configValue="${"camera_view"}"
@value-changed="${this._valueChanged}"
>
<paper-listbox
slot="dropdown-content"
.selected="${views.indexOf(this._camera_view)}"
>
${views.map((view) => {
return html` <paper-item>${view}</paper-item> `;
})}
</paper-listbox>
</paper-dropdown-menu>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._aspect_ratio}"
.configValue="${"aspect_ratio"}"
@value-changed="${this._valueChanged}"
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.image"
)}
.value=${this._image}
.configValue=${"image"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.picture-glance.state_entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
@value-changed="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<div class="side-by-side">
<hui-action-editor
.label="${this.hass.localize(
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.tap_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
)}
.hass=${this.hass}
.config="${this._tap_action}"
.actions="${actions}"
.configValue="${"tap_action"}"
@value-changed="${this._valueChanged}"
></hui-action-editor>
<hui-action-editor
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.hass=${this.hass}
.config="${this._hold_action}"
.actions="${actions}"
.configValue="${"hold_action"}"
@value-changed="${this._valueChanged}"
.config=${this._tap_action}
.actions=${actions}
.configValue=${"tap_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
</div>
<hui-entity-editor
.hass=${this.hass}
.entities="${this._configEntities}"
@entities-changed="${this._valueChanged}"
.entities=${this._configEntities}
@entities-changed=${this._valueChanged}
></hui-entity-editor>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<ha-expansion-panel>
<span class="title" slot="title">
${this.hass.localize(
`ui.panel.lovelace.editor.card.picture-entity.camera_options`
)}
</span>
<ha-entity-picker
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_image"
)}
.hass=${this.hass}
.value=${this._camera_image}
.configValue=${"camera_image"}
@value-changed=${this._valueChanged}
.includeDomains=${includeDomains}
allow-custom-entity
></ha-entity-picker>
<paper-dropdown-menu
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.camera_view"
)}
.configValue=${"camera_view"}
@value-changed=${this._valueChanged}
>
<paper-listbox
slot="dropdown-content"
.selected=${views.indexOf(this._camera_view)}
>
${views.map((view) => {
return html`<paper-item>${view}</paper-item>`;
})}
</paper-listbox>
</paper-dropdown-menu>
</ha-expansion-panel>
<div slot="advanced" class="card-config">
<ha-entity-picker
allow-custom-entity
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)}
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
@value-changed=${this._valueChanged}
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.aspect_ratio"
)}
.value=${this._aspect_ratio}
.configValue=${"aspect_ratio"}
@value-changed=${this._valueChanged}
></paper-input>
<hui-action-editor
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hold_action"
)}
.hass=${this.hass}
.config=${this._hold_action}
.actions=${actions}
.configValue=${"hold_action"}
@value-changed=${this._valueChanged}
></hui-action-editor>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}
@@ -258,8 +256,15 @@ export class HuiPictureGlanceCardEditor extends LitElement
fireEvent(this, "config-changed", { config: this._config });
}
static get styles(): CSSResult {
return configElementStyle;
static get styles(): CSSResultArray {
return [
configElementStyle,
css`
paper-dropdown-menu {
width: 100%;
}
`,
];
}
}

View File

@@ -16,6 +16,7 @@ import { HomeAssistant } from "../../../../types";
import { PlantStatusCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -33,6 +34,8 @@ export class HuiPlantStatusCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: PlantStatusCardConfig;
public setConfig(config: PlantStatusCardConfig): void {
@@ -58,37 +61,42 @@ export class HuiPlantStatusCardEditor extends LitElement
}
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._name}"
.configValue="${"name"}"
@value-changed="${this._valueChanged}"
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
allow-custom-entity
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -17,11 +17,13 @@ import { stateIcon } from "../../../../common/entity/state_icon";
import "../../../../components/entity/ha-entity-picker";
import "../../../../components/ha-formfield";
import "../../../../components/ha-icon-input";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import { HomeAssistant } from "../../../../types";
import { SensorCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -44,6 +46,8 @@ export class HuiSensorCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: SensorCardConfig;
public setConfig(config: SensorCardConfig): void {
@@ -91,105 +95,99 @@ export class HuiSensorCardEditor extends LitElement
const graphs = ["line", "none"];
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
<div class="side-by-side">
<ha-icon-input
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon"
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
<div class="side-by-side">
<paper-dropdown-menu
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.sensor.graph_type"
)}
.configValue=${"graph"}
@value-changed=${this._valueChanged}
>
<paper-listbox
slot="dropdown-content"
.selected=${graphs.indexOf(this._graph)}
>
${graphs.map((graph) => {
return html`<paper-item>${graph}</paper-item>`;
})}
</paper-listbox>
</paper-dropdown-menu>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hours_to_show"
)}
type="number"
.value=${this._hours_to_show}
.configValue=${"hours_to_show"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
</div>
<div slot="advanced" class="card-config">
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.sensor.show_more_detail"
)}
</span>
<ha-switch
.checked=${this._detail === 2}
.configValue=${"detail"}
@change=${this._change}
></ha-switch>
</ha-settings-row>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.unit"
)}
.value=${this._unit}
.configValue=${"unit"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-icon-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.icon"
)}
.value=${this._icon}
.placeholder=${this._icon ||
stateIcon(this.hass.states[this._entity])}
.configValue=${"icon"}
@value-changed=${this._valueChanged}
></ha-icon-input>
<paper-dropdown-menu
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.sensor.graph_type"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.configValue=${"graph"}
@value-changed=${this._valueChanged}
>
<paper-listbox
slot="dropdown-content"
.selected=${graphs.indexOf(this._graph)}
>
${graphs.map((graph) => {
return html`<paper-item>${graph}</paper-item>`;
})}
</paper-listbox>
</paper-dropdown-menu>
</div>
<div class="side-by-side">
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.unit"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._unit}
.configValue=${"unit"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-formfield
label=${this.hass.localize(
"ui.panel.lovelace.editor.card.sensor.show_more_detail"
)}
>
<ha-switch
.checked=${this._detail === 2}
.configValue=${"detail"}
@change=${this._change}
></ha-switch>
</ha-formfield>
</div>
<div class="side-by-side">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.hours_to_show"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
type="number"
.value=${this._hours_to_show}
.configValue=${"hours_to_show"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
</div>
</hui-config-element-template>
`;
}

View File

@@ -4,19 +4,20 @@ import {
CSSResult,
customElement,
html,
internalProperty,
LitElement,
property,
internalProperty,
TemplateResult,
} from "lit-element";
import { assert, object, optional, string } from "superstruct";
import { isComponentLoaded } from "../../../../common/config/is_component_loaded";
import { fireEvent } from "../../../../common/dom/fire_event";
import { HomeAssistant } from "../../../../types";
import { ShoppingListCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { string, assert, object, optional } from "superstruct";
const cardConfigStruct = object({
type: string(),
@@ -29,6 +30,8 @@ export class HuiShoppingListEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: ShoppingListCardConfig;
public setConfig(config: ShoppingListCardConfig): void {
@@ -50,33 +53,38 @@ export class HuiShoppingListEditor extends LitElement
}
return html`
<div class="card-config">
${!isComponentLoaded(this.hass, "shopping_list")
? html`
<div class="error">
${this.hass.localize(
"ui.panel.lovelace.editor.card.shopping-list.integration_not_loaded"
)}
</div>
`
: ""}
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._title}"
.configValue="${"title"}"
@value-changed="${this._valueChanged}"
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
${!isComponentLoaded(this.hass, "shopping_list")
? html`
<div class="error">
${this.hass.localize(
"ui.panel.lovelace.editor.card.shopping-list.integration_not_loaded"
)}
</div>
`
: ""}
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.title"
)}
.value=${this._title}
.configValue=${"title"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -15,6 +15,7 @@ import { HomeAssistant } from "../../../../types";
import { ThermostatCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -32,6 +33,8 @@ export class HuiThermostatCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: ThermostatCardConfig;
public setConfig(config: ThermostatCardConfig): void {
@@ -57,37 +60,42 @@ export class HuiThermostatCardEditor extends LitElement
}
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value="${this._entity}"
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change="${this._valueChanged}"
allow-custom-entity
></ha-entity-picker>
<paper-input
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value="${this._name}"
.configValue="${"name"}"
@value-changed="${this._valueChanged}"
></paper-input>
<hui-theme-select-editor
.hass=${this.hass}
.value="${this._theme}"
.configValue="${"theme"}"
@value-changed="${this._valueChanged}"
></hui-theme-select-editor>
</div>
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
</div>
<div slot="advanced" class="card-config">
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
.configValue=${"theme"}
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
</hui-config-element-template>
`;
}

View File

@@ -9,15 +9,16 @@ import {
} from "lit-element";
import { assert, boolean, object, optional, string } from "superstruct";
import { fireEvent } from "../../../../common/dom/fire_event";
import { computeRTLDirection } from "../../../../common/util/compute_rtl";
import "../../../../components/entity/ha-entity-attribute-picker";
import "../../../../components/entity/ha-entity-picker";
import "../../../../components/ha-formfield";
import "../../../../components/ha-settings-row";
import "../../../../components/ha-switch";
import "../../../../components/entity/ha-entity-attribute-picker";
import { HomeAssistant } from "../../../../types";
import { WeatherForecastCardConfig } from "../../cards/types";
import "../../components/hui-theme-select-editor";
import { LovelaceCardEditor } from "../../types";
import "../hui-config-element-template";
import { EditorTarget, EntitiesEditorEvent } from "../types";
import { configElementStyle } from "./config-elements-style";
@@ -37,6 +38,8 @@ export class HuiWeatherForecastCardEditor extends LitElement
implements LovelaceCardEditor {
@property({ attribute: false }) public hass?: HomeAssistant;
@property({ type: Boolean }) public isAdvanced?: boolean;
@internalProperty() private _config?: WeatherForecastCardConfig;
public setConfig(config: WeatherForecastCardConfig): void {
@@ -70,31 +73,56 @@ export class HuiWeatherForecastCardEditor extends LitElement
}
return html`
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<div class="side-by-side">
<paper-input
<hui-config-element-template
.hass=${this.hass}
.isAdvanced=${this.isAdvanced}
>
<div class="card-config">
<ha-entity-picker
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
"ui.panel.lovelace.editor.card.generic.entity"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
"ui.panel.lovelace.editor.card.config.required"
)})"
.hass=${this.hass}
.value=${this._entity}
.configValue=${"entity"}
.includeDomains=${includeDomains}
@change=${this._valueChanged}
allow-custom-entity
></ha-entity-picker>
<paper-input
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.name"
)}
.value=${this._name}
.configValue=${"name"}
@value-changed=${this._valueChanged}
></paper-input>
<ha-settings-row three-line>
<span slot="heading">
${this.hass.localize(
"ui.panel.lovelace.editor.card.weather-forecast.show_forecast"
)}
</span>
<ha-switch
.checked=${this._config!.show_forecast !== false}
.configValue=${"show_forecast"}
@change=${this._valueChanged}
></ha-switch>
</ha-settings-row>
</div>
<div slot="advanced" class="card-config">
<ha-entity-attribute-picker
.hass=${this.hass}
.entityId=${this._entity}
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.secondary_info_attribute"
)}
.value=${this._secondary_info_attribute}
.configValue=${"secondary_info_attribute"}
@value-changed=${this._valueChanged}
></ha-entity-attribute-picker>
<hui-theme-select-editor
.hass=${this.hass}
.value=${this._theme}
@@ -102,33 +130,7 @@ export class HuiWeatherForecastCardEditor extends LitElement
@value-changed=${this._valueChanged}
></hui-theme-select-editor>
</div>
<div class="side-by-side">
<ha-entity-attribute-picker
.hass=${this.hass}
.entityId=${this._entity}
.label="${this.hass.localize(
"ui.panel.lovelace.editor.card.generic.secondary_info_attribute"
)} (${this.hass.localize(
"ui.panel.lovelace.editor.card.config.optional"
)})"
.value=${this._secondary_info_attribute}
.configValue=${"secondary_info_attribute"}
@value-changed=${this._valueChanged}
></ha-entity-attribute-picker>
<ha-formfield
.label=${this.hass.localize(
"ui.panel.lovelace.editor.card.weather-forecast.show_forecast"
)}
.dir=${computeRTLDirection(this.hass)}
>
<ha-switch
.checked=${this._config!.show_forecast !== false}
.configValue=${"show_forecast"}
@change=${this._valueChanged}
></ha-switch
></ha-formfield>
</div>
</div>
</hui-config-element-template>
`;
}

View File

@@ -53,7 +53,7 @@ export class HuiCreateDialogHeaderFooter extends LitElement
`ui.panel.lovelace.editor.header-footer.choose_header_footer`,
"type",
this.hass!.localize(
`ui.panel.lovelace.editor.header-footer.${this._params.type}`
`ui.panel.lovelace.editor.header-footer.${this._params.type}.name`
)
)
)}

View File

@@ -1,5 +1,5 @@
import "@material/mwc-icon-button/mwc-icon-button";
import { mdiClose, mdiPencil, mdiPlus } from "@mdi/js";
import { mdiChevronRight } from "@mdi/js";
import "@polymer/paper-item/paper-item";
import "@polymer/paper-listbox/paper-listbox";
import {
@@ -31,56 +31,26 @@ export class HuiHeaderFooterEditor extends LitElement {
protected render(): TemplateResult {
return html`
<div>
<div @click=${this._click}>
<span>
${this.hass.localize(
`ui.panel.lovelace.editor.header-footer.${this.configValue}`
)}:
${!this.config?.type
? this.hass!.localize("ui.panel.lovelace.editor.common.none")
: this.hass!.localize(
`ui.panel.lovelace.editor.header-footer.types.${this.config?.type}.name`
)}
`ui.panel.lovelace.editor.header-footer.${this.configValue}.manage`
)}
</span>
</div>
<div>
${!this.config?.type
? html`
<mwc-icon-button
aria-label=${this.hass!.localize(
"ui.panel.lovelace.editor.common.add"
)}
class="add-icon"
@click=${this._add}
>
<ha-svg-icon .path=${mdiPlus}></ha-svg-icon>
</mwc-icon-button>
`
: html`
<mwc-icon-button
aria-label=${this.hass!.localize(
"ui.panel.lovelace.editor.common.clear"
)}
class="remove-icon"
@click=${this._delete}
>
<ha-svg-icon .path=${mdiClose}></ha-svg-icon>
</mwc-icon-button>
<mwc-icon-button
aria-label=${this.hass!.localize(
"ui.panel.lovelace.editor.common.edit"
)}
class="edit-icon"
@click=${this._edit}
>
<ha-svg-icon .path=${mdiPencil}></ha-svg-icon>
</mwc-icon-button>
`}
<ha-svg-icon .path=${mdiChevronRight}></ha-svg-icon>
</div>
`;
}
private _edit(): void {
private _click(): void {
if (!this.config?.type) {
showCreateHeaderFooterDialog(this, {
pickHeaderFooter: (config) => this._elementPicked(config),
type: this.configValue,
});
return;
}
fireEvent(this, "edit-detail-element", {
subElementConfig: {
elementConfig: this.config,
@@ -89,13 +59,6 @@ export class HuiHeaderFooterEditor extends LitElement {
});
}
private _add(): void {
showCreateHeaderFooterDialog(this, {
pickHeaderFooter: (config) => this._elementPicked(config),
type: this.configValue,
});
}
private _elementPicked(config: LovelaceHeaderFooterConfig): void {
fireEvent(this, "value-changed", { value: config });
fireEvent(this, "edit-detail-element", {
@@ -106,35 +69,20 @@ export class HuiHeaderFooterEditor extends LitElement {
});
}
private _delete(): void {
fireEvent(this, "value-changed", { value: "" });
}
static get styles(): CSSResult {
return css`
:host {
font-size: 16px;
display: flex;
flex-wrap: wrap;
justify-content: space-between;
align-items: center;
padding-bottom: 12px;
}
:host > div {
display: flex;
align-items: center;
justify-content: space-between;
padding-bottom: 12px;
min-height: 48px;
cursor: pointer;
}
mwc-icon-button,
.header-footer-icon {
--mdc-icon-button-size: 36px;
ha-svg-icon {
color: var(--secondary-text-color);
}
.header-footer-icon {
padding-right: 8px;
}
`;
}
}

View File

@@ -0,0 +1,46 @@
import {
CSSResult,
customElement,
html,
LitElement,
property,
TemplateResult,
} from "lit-element";
import "../../../components/ha-expansion-panel";
import { HomeAssistant } from "../../../types";
import { configElementStyle } from "./config-elements/config-elements-style";
@customElement("hui-config-element-template")
export class HuiConfigElementTemplate extends LitElement {
public hass!: HomeAssistant;
@property({ type: Boolean }) public isAdvanced? = false;
protected render(): TemplateResult {
return html`
<slot></slot>
${this.isAdvanced
? html`
<ha-expansion-panel>
<span class="title" slot="title">
${this.hass.localize(
`ui.panel.lovelace.editor.common.advanced_options`
)}
</span>
<slot name="advanced"></slot>
</ha-expansion-panel>
`
: ""}
`;
}
static get styles(): CSSResult {
return configElementStyle;
}
}
declare global {
interface HTMLElementTagNameMap {
"hui-config-element-template": HuiConfigElementTemplate;
}
}

View File

@@ -31,7 +31,11 @@ import { GUISupportError } from "./gui-support-error";
import { EditSubElementEvent, GUIModeChangedEvent } from "./types";
export interface ConfigChangedEvent {
config: LovelaceCardConfig | LovelaceRowConfig | LovelaceHeaderFooterConfig;
config:
| LovelaceCardConfig
| LovelaceRowConfig
| LovelaceHeaderFooterConfig
| undefined;
error?: string;
guiModeAvailable?: boolean;
}
@@ -55,6 +59,8 @@ export abstract class HuiElementEditor<T> extends LitElement {
@property({ attribute: false }) public lovelace?: LovelaceConfig;
@property({ attribute: false }) public isAdvanced?: boolean;
@internalProperty() private _yaml?: string;
@internalProperty() private _config?: T;
@@ -144,10 +150,14 @@ export abstract class HuiElementEditor<T> extends LitElement {
});
}
public toggleMode() {
public toggleMode(): void {
this.GUImode = !this.GUImode;
}
public remove(): void {
this._configElement?.remove();
}
public refreshYamlEditor(focus = false) {
if (this._configElement?.refreshYamlEditor) {
this._configElement.refreshYamlEditor(focus);
@@ -237,6 +247,9 @@ export abstract class HuiElementEditor<T> extends LitElement {
) {
this._configElement.lovelace = this.lovelace;
}
if (this._configElement && changedProperties.has("isAdvanced")) {
this._configElement.isAdvanced = this.isAdvanced;
}
}
private _handleUIConfigChanged(ev: UIConfigChangedEvent) {
@@ -283,6 +296,7 @@ export abstract class HuiElementEditor<T> extends LitElement {
}
configElement.hass = this.hass;
configElement.isAdvanced = this.isAdvanced;
if ("lovelace" in configElement) {
configElement.lovelace = this.lovelace;
}

View File

@@ -1,5 +1,6 @@
import "@material/mwc-button/mwc-button";
import "@material/mwc-icon-button";
import { mdiClose, mdiDrag, mdiPencil } from "@mdi/js";
import { mdiChevronRight, mdiDragVerticalVariant } from "@mdi/js";
import {
css,
CSSResult,
@@ -19,7 +20,7 @@ import Sortable, {
} from "sortablejs/modular/sortable.core.esm";
import { fireEvent } from "../../../common/dom/fire_event";
import "../../../components/entity/ha-entity-picker";
import type { HaEntityPicker } from "../../../components/entity/ha-entity-picker";
import "../../../components/ha-card";
import "../../../components/ha-svg-icon";
import { sortableStyles } from "../../../resources/ha-sortable-style";
import { HomeAssistant } from "../../../types";
@@ -63,78 +64,72 @@ export class HuiEntitiesCardRowEditor extends LitElement {
}
return html`
<h3>
${this.label ||
`${this.hass!.localize(
"ui.panel.lovelace.editor.card.generic.entities"
)} (${this.hass!.localize(
"ui.panel.lovelace.editor.card.config.required"
)})`}
</h3>
<div class="title">
<span>
${this.label ||
`${this.hass!.localize(
"ui.panel.lovelace.editor.card.generic.entities"
)}:`}
</span>
<mwc-button
.label=${this.hass!.localize(
"ui.panel.lovelace.editor.card.entities.add_row"
)}
@click=${this._addEntity}
></mwc-button>
</div>
<div class="entities">
${guard([this.entities, this._renderEmptySortable], () =>
this._renderEmptySortable
? ""
: this.entities!.map((entityConf, index) => {
const stateObj = this.hass!.states[
(entityConf as EntityConfig).entity
];
return html`
<div class="entity">
<ha-svg-icon class="handle" .path=${mdiDrag}></ha-svg-icon>
${entityConf.type
? html`
<div class="special-row">
<div>
<span>
${this.hass!.localize(
`ui.panel.lovelace.editor.card.entities.entity_row.${entityConf.type}`
)}
</span>
<span class="secondary"
>${this.hass!.localize(
"ui.panel.lovelace.editor.card.entities.edit_special_row"
)}</span
>
</div>
</div>
`
: html`
<ha-entity-picker
allow-custom-entity
hideClearIcon
.hass=${this.hass}
.value=${(entityConf as EntityConfig).entity}
.index=${index}
@value-changed=${this._valueChanged}
></ha-entity-picker>
`}
<mwc-icon-button
aria-label=${this.hass!.localize(
"ui.components.entity.entity-picker.clear"
)}
class="remove-icon"
.index=${index}
@click=${this._removeRow}
>
<ha-svg-icon .path=${mdiClose}></ha-svg-icon>
</mwc-icon-button>
<mwc-icon-button
aria-label=${this.hass!.localize(
"ui.components.entity.entity-picker.edit"
)}
<ha-card
outlined
class="entity"
.index=${index}
@click=${this._editRow}
>
<ha-svg-icon
class="handle"
.path=${mdiDragVerticalVariant}
></ha-svg-icon>
<div class="info">
<span class="primary">
${entityConf.type
? html`
${this.hass!.localize(
`ui.panel.lovelace.editor.card.entities.entity_row.${entityConf.type}`
)}
`
: html`
${(entityConf as EntityConfig).name ||
stateObj?.attributes.friendly_name ||
(entityConf as EntityConfig).entity}
`}
</span>
<span class="secondary">
${entityConf.type
? html`
${this.hass!.localize(
"ui.panel.lovelace.editor.card.entities.edit_special_row"
)}
`
: html`${(entityConf as EntityConfig).entity}`}
</span>
</div>
<ha-svg-icon
class="edit-icon"
.index=${index}
@click=${this._editRow}
>
<ha-svg-icon .path=${mdiPencil}></ha-svg-icon>
</mwc-icon-button>
</div>
.path=${mdiChevronRight}
></ha-svg-icon>
</ha-card>
`;
})
)}
</div>
<ha-entity-picker
.hass=${this.hass}
@value-changed=${this._addEntity}
></ha-entity-picker>
`;
}
@@ -189,16 +184,20 @@ export class HuiEntitiesCardRowEditor extends LitElement {
});
}
private async _addEntity(ev: CustomEvent): Promise<void> {
const value = ev.detail.value;
if (value === "") {
return;
}
private async _addEntity(): Promise<void> {
const newConfigEntities = this.entities!.concat({
entity: value as string,
entity: Object.keys(this.hass!.states)[0],
});
(ev.target as HaEntityPicker).value = "";
fireEvent(this, "entities-changed", { entities: newConfigEntities });
const index = newConfigEntities.length - 1;
fireEvent(this, "edit-detail-element", {
subElementConfig: {
index,
type: "row",
elementConfig: newConfigEntities[index],
},
});
}
private _rowMoved(ev: SortableEvent): void {
@@ -213,32 +212,6 @@ export class HuiEntitiesCardRowEditor extends LitElement {
fireEvent(this, "entities-changed", { entities: newEntities });
}
private _removeRow(ev: CustomEvent): void {
const index = (ev.currentTarget as any).index;
const newConfigEntities = this.entities!.concat();
newConfigEntities.splice(index, 1);
fireEvent(this, "entities-changed", { entities: newConfigEntities });
}
private _valueChanged(ev: CustomEvent): void {
const value = ev.detail.value;
const index = (ev.target as any).index;
const newConfigEntities = this.entities!.concat();
if (value === "") {
newConfigEntities.splice(index, 1);
} else {
newConfigEntities[index] = {
...newConfigEntities[index],
entity: value!,
};
}
fireEvent(this, "entities-changed", { entities: newConfigEntities });
}
private _editRow(ev: CustomEvent): void {
const index = (ev.currentTarget as any).index;
fireEvent(this, "edit-detail-element", {
@@ -254,43 +227,62 @@ export class HuiEntitiesCardRowEditor extends LitElement {
return [
sortableStyles,
css`
.entity {
.title {
font-size: 18px;
display: flex;
justify-content: space-between;
align-items: center;
}
.entity .handle {
padding-right: 8px;
cursor: move;
.entity {
display: flex;
align-items: center;
justify-content: space-between;
padding: 12px;
margin: 8px 0;
cursor: pointer;
}
.entity ha-entity-picker {
flex-grow: 1;
.handle {
min-width: 18px;
--mdc-icon-size: 18px;
padding-right: 8px;
cursor: move;
color: var(--secondary-text-color);
}
.special-row {
height: 60px;
font-size: 16px;
display: flex;
align-items: center;
justify-content: space-between;
flex-grow: 1;
}
.special-row div {
.info {
display: flex;
flex-direction: column;
overflow: hidden;
text-overflow: ellipsis;
overflow: hidden;
flex-grow: 1;
}
.remove-icon,
.edit-icon {
--mdc-icon-button-size: 36px;
min-width: 24px;
color: var(--secondary-text-color);
}
.primary {
text-overflow: ellipsis;
overflow: hidden;
}
.secondary {
font-size: 12px;
color: var(--secondary-text-color);
text-overflow: ellipsis;
overflow: hidden;
}
`,
];

View File

@@ -1,6 +1,14 @@
import "@material/mwc-button";
import "@material/mwc-icon-button";
import { mdiArrowLeft } from "@mdi/js";
import "@material/mwc-list/mwc-list-item";
import type { RequestSelectedDetail } from "@material/mwc-list/mwc-list-item";
import {
mdiArrowLeft,
mdiCodeBracesBox,
mdiDotsVertical,
mdiFormSelect,
mdiTrashCanOutline,
} from "@mdi/js";
import {
css,
CSSResult,
@@ -13,6 +21,8 @@ import {
TemplateResult,
} from "lit-element";
import { fireEvent, HASSDomEvent } from "../../../common/dom/fire_event";
import { shouldHandleRequestSelectedEvent } from "../../../common/mwc/handle-request-selected-event";
import "../../../components/ha-button-menu";
import "../../../components/ha-svg-icon";
import type { HomeAssistant } from "../../../types";
import type { LovelaceRowConfig } from "../entity-rows/types";
@@ -34,6 +44,8 @@ export class HuiSubElementEditor extends LitElement {
@property({ attribute: false }) public config!: SubElementEditorConfig;
@property({ type: Boolean }) public isAdvancedUser? = false;
@internalProperty() private _guiModeAvailable = true;
@internalProperty() private _guiMode = true;
@@ -55,17 +67,64 @@ export class HuiSubElementEditor extends LitElement {
)}</span
>
</div>
<mwc-button
<ha-button-menu
fixed
corner="BOTTOM_START"
slot="secondaryAction"
.disabled=${!this._guiModeAvailable}
@click=${this._toggleMode}
@closed=${(ev) => ev.stopPropagation()}
>
${this.hass.localize(
this._guiMode
? "ui.panel.lovelace.editor.edit_card.show_code_editor"
: "ui.panel.lovelace.editor.edit_card.show_visual_editor"
)}
</mwc-button>
<mwc-icon-button
slot="trigger"
.label=${this.hass!.localize("ui.panel.lovelace.editor.menu.open")}
.title=${this.hass!.localize("ui.panel.lovelace.editor.menu.open")}
>
<ha-svg-icon .path=${mdiDotsVertical}></ha-svg-icon>
</mwc-icon-button>
${this.isAdvancedUser
? html`
<mwc-list-item
graphic="icon"
.label=${this.hass!.localize(
this._guiMode
? "ui.panel.lovelace.editor.edit_card.show_code_editor"
: "ui.panel.lovelace.editor.edit_card.show_visual_editor"
)}
.disabled=${!this._guiModeAvailable}
@request-selected=${this._toggleMode}
>
<span
>${this.hass!.localize(
this._guiMode
? "ui.panel.lovelace.editor.edit_card.show_code_editor"
: "ui.panel.lovelace.editor.edit_card.show_visual_editor"
)}</span
>
<ha-svg-icon
slot="graphic"
.path=${this._guiMode ? mdiCodeBracesBox : mdiFormSelect}
></ha-svg-icon>
</mwc-list-item>
`
: ""}
<mwc-list-item
graphic="icon"
.label=${this.hass!.localize(
"ui.panel.lovelace.editor.common.delete"
)}
@request-selected=${this._remove}
>
<span
>${this.hass!.localize(
"ui.panel.lovelace.editor.common.delete"
)}</span
>
<ha-svg-icon
slot="graphic"
.path=${mdiTrashCanOutline}
></ha-svg-icon>
</mwc-list-item>
</ha-button-menu>
</div>
${this.config.type === "row"
? html`
@@ -95,10 +154,20 @@ export class HuiSubElementEditor extends LitElement {
fireEvent(this, "go-back");
}
private _toggleMode(): void {
private _toggleMode(ev: CustomEvent<RequestSelectedDetail>): void {
if (!shouldHandleRequestSelectedEvent(ev)) {
return;
}
this._editorElement?.toggleMode();
}
private _remove(ev: CustomEvent<RequestSelectedDetail>): void {
if (!shouldHandleRequestSelectedEvent(ev)) {
return;
}
fireEvent(this, "config-changed", { config: undefined });
}
private _handleGUIModeChanged(ev: HASSDomEvent<GUIModeChangedEvent>): void {
ev.stopPropagation();
this._guiMode = ev.detail.guiMode;

View File

@@ -85,6 +85,7 @@ export interface LovelaceRowEditor extends LovelaceGenericElementEditor {
export interface LovelaceGenericElementEditor extends HTMLElement {
hass?: HomeAssistant;
lovelace?: LovelaceConfig;
isAdvanced?: boolean;
setConfig(config: any): void;
refreshYamlEditor?: (focus: boolean) => void;
}

View File

@@ -2424,7 +2424,8 @@
"edit": "Edit",
"clear": "Clear",
"add": "Add",
"none": "None"
"delete": "Delete",
"advanced_options": "Advanced Options"
},
"raw_editor": {
"header": "Edit Configuration",
@@ -2564,12 +2565,14 @@
},
"entities": {
"name": "Entities",
"show_header_toggle": "Show Header Toggle?",
"show_header_toggle": "Show/Hide a toggle in the header to control all entities in the card",
"show_header_toggle_secondary": "Only visible when 2 or more entities can be toggled",
"toggle": "Toggle entities.",
"description": "The Entities card is the most common type of card. It groups items together into lists.",
"special_row": "special row",
"edit_special_row": "View the details of this row by clicking the edit button",
"entity_row_editor": "Entity Row Editor",
"add_row": "Add Row",
"secondary_info_values": {
"none": "No Secondary Info",
"entity-id": "Entity ID",
@@ -2667,9 +2670,9 @@
"minimum": "Minimum",
"name": "Name",
"refresh_interval": "Refresh Interval",
"show_icon": "Show Icon?",
"show_name": "Show Name?",
"show_state": "Show State?",
"show_icon": "Show/Hide the icon",
"show_name": "Show/Hide the name of the entity",
"show_state": "Show/Hide the state of the entity",
"tap_action": "Tap Action",
"title": "Title",
"theme": "Theme",
@@ -2679,12 +2682,12 @@
"state": "State",
"secondary_info_attribute": "Secondary Info Attribute",
"search": "Search",
"state_color": "Color icons based on state?"
"state_color": "Color the icons based on their current states"
},
"map": {
"name": "Map",
"geo_location_sources": "Geolocation Sources",
"dark_mode": "Dark Mode?",
"dark_mode": "Change the map colors to a dark theme",
"default_zoom": "Default Zoom",
"hours_to_show": "Hours to Show",
"source": "Source",
@@ -2709,7 +2712,8 @@
},
"picture-entity": {
"name": "Picture Entity",
"description": "The Picture Entity card displays an entity in the form of an image. Instead of images from URL, it can also show the picture of camera entities."
"description": "The Picture Entity card displays an entity in the form of an image. Instead of images from URL, it can also show the picture of camera entities.",
"camera_options": "Camera Options"
},
"picture-glance": {
"name": "Picture Glance",
@@ -2722,7 +2726,7 @@
},
"sensor": {
"name": "Sensor",
"show_more_detail": "Show more detail",
"show_more_detail": "Show/Hide more detail in the line graph",
"graph_type": "Graph Type",
"description": "The Sensor card gives you a quick overview of your sensors state with an optional graph to visualize change over time."
},
@@ -2742,7 +2746,7 @@
"weather-forecast": {
"name": "Weather Forecast",
"description": "The Weather Forecast card displays the weather. Very useful to include on interfaces that people display on the wall.",
"show_forecast": "Show Forecast"
"show_forecast": "Show/Hide the weather forecast at the bottom of the card"
}
},
"view": {
@@ -2761,8 +2765,14 @@
"by_card": "By Card"
},
"header-footer": {
"header": "Header",
"footer": "Footer",
"header": {
"name": "Header",
"manage": "Manage header configuration"
},
"footer": {
"name": "Footer",
"manage": "Manage footer configuration"
},
"choose_header_footer": "Choose a {type}",
"types": {
"graph": {

View File

@@ -1723,6 +1723,7 @@
},
"header": "Entity",
"headers": {
"area": "Oblast",
"entity_id": "ID entity",
"integration": "Integrace",
"name": "Název",
@@ -2450,6 +2451,16 @@
"value": "Hodnota"
},
"description": "Správa Zigbee Home Automation",
"device_pairing_card": {
"CONFIGURED": "Nastavení dokončeno",
"CONFIGURED_status_text": "Inicializuji",
"INITIALIZED": "Inicializace dokončena",
"INITIALIZED_status_text": "Zařízení je připraveno k použití",
"INTERVIEW_COMPLETE": "Dotazování dokončeno",
"INTERVIEW_COMPLETE_status_text": "Nastavuji",
"PAIRED": "Zařízení nalezeno",
"PAIRED_status_text": "Začínám dotazování"
},
"devices": {
"header": "Zigbee Home Automation - Zařízení"
},

View File

@@ -7,6 +7,7 @@
}
},
"groups": {
"owner": "Besitzer",
"system-admin": "Administratoren",
"system-read-only": "Nur-Lesen Benutzer",
"system-users": "Benutzer"
@@ -1740,6 +1741,7 @@
},
"header": "Entitäten",
"headers": {
"area": "Bereich",
"entity_id": "Entitäts-ID",
"integration": "Integration",
"name": "Name",
@@ -2404,14 +2406,18 @@
"system_generated_users_not_editable": "Systemgenerierte Benutzer können nicht aktualisiert werden.",
"system_generated_users_not_removable": "Vom System generierte Benutzer können nicht entfernt werden.",
"unnamed_user": "Unbenannter Benutzer",
"update_user": "Aktualisieren"
"update_user": "Aktualisieren",
"username": "Benutzername"
},
"picker": {
"add_user": "Benutzer hinzufügen",
"headers": {
"group": "Gruppe",
"is_active": "Aktiv",
"is_owner": "Besitzer",
"name": "Name",
"system": "System"
"system": "System",
"username": "Benutzername"
}
},
"users_privileges_note": "Benutzergruppen sind derzeit noch in Entwicklung. Der Benutzer wird nicht in der Lage sein, Änderungen an der Instanz über das UI vorzunehmen. Derzeit überprüfen wir noch alle API Endpunkte um sicherzustellen dass diese nur von Administratoren genutzt werden können."
@@ -2463,6 +2469,14 @@
"value": "Wert"
},
"description": "Zigbee Home Automation Netzwerkmanagement",
"device_pairing_card": {
"CONFIGURED": "Konfiguration abgeschlossen",
"CONFIGURED_status_text": "Initialisieren",
"INITIALIZED": "Initialisierung abgeschlossen",
"INITIALIZED_status_text": "Das Gerät ist einsatzbereit",
"INTERVIEW_COMPLETE_status_text": "Konfigurieren",
"PAIRED": "Gerät gefunden"
},
"devices": {
"header": "Zigbee Home Automation - Gerät"
},

View File

@@ -1744,6 +1744,7 @@
},
"header": "Entidades",
"headers": {
"area": "Área",
"entity_id": "ID de entidad",
"integration": "Integración",
"name": "Nombre",
@@ -2471,6 +2472,16 @@
"value": "Valor"
},
"description": "Administración de red de Domótica Zigbee",
"device_pairing_card": {
"CONFIGURED": "Configuración completada",
"CONFIGURED_status_text": "Inicializando",
"INITIALIZED": "Inicialización completada",
"INITIALIZED_status_text": "El dispositivo está listo para ser usado",
"INTERVIEW_COMPLETE": "Entrevista completada",
"INTERVIEW_COMPLETE_status_text": "Configurando",
"PAIRED": "Dispositivo encontrado",
"PAIRED_status_text": "Iniciando entrevista"
},
"devices": {
"header": "Domótica Zigbee - Dispositivo"
},

View File

@@ -1744,6 +1744,7 @@
},
"header": "Olemid",
"headers": {
"area": "Ala",
"entity_id": "Olemi ID",
"integration": "Sidumine",
"name": "Nimi",
@@ -2471,6 +2472,16 @@
"value": "Väärtus"
},
"description": "Zigbee Home Automation võrgu haldamine",
"device_pairing_card": {
"CONFIGURED": "Seadistamine on lõpetatud",
"CONFIGURED_status_text": "Lähtestan",
"INITIALIZED": "Lähtestamine on lõpetatud",
"INITIALIZED_status_text": "Seade on kasutamiseks valmis",
"INTERVIEW_COMPLETE": "Küsitlemine on lõpetatud",
"INTERVIEW_COMPLETE_status_text": "Seadistan",
"PAIRED": "Seade on leitud",
"PAIRED_status_text": "Alustan küsitlemist"
},
"devices": {
"header": "Zigbee Home Automation - Seade"
},

View File

@@ -1744,6 +1744,7 @@
},
"header": "Entità",
"headers": {
"area": "Area",
"entity_id": "ID entità",
"integration": "Integrazione",
"name": "Nome",
@@ -2471,6 +2472,16 @@
"value": "Valore"
},
"description": "Gestione rete Zigbee Home Automation",
"device_pairing_card": {
"CONFIGURED": "Configurazione completata",
"CONFIGURED_status_text": "Inizializzazione",
"INITIALIZED": "Inizializzazione completata",
"INITIALIZED_status_text": "Il dispositivo è pronto per l'uso",
"INTERVIEW_COMPLETE": "Interrogazione completata",
"INTERVIEW_COMPLETE_status_text": "Configurazione",
"PAIRED": "Dispositivo trovato",
"PAIRED_status_text": "Inizio interrogazione"
},
"devices": {
"header": "Zigbee Home Automation - Dispositivo"
},
@@ -2811,8 +2822,8 @@
"card": {
"alarm-panel": {
"available_states": "Stati disponibili",
"description": "La scheda del pannello di allarme consente di Attivare e Disattivare le tue integrazioni del pannello di controllo di allarme.",
"name": "Pannello di allarme"
"description": "La scheda del Pannello di Allarme consente di attivare e disattivare le tue integrazioni del pannello di controllo allarme.",
"name": "Pannello di Allarme"
},
"button": {
"default_action_help": "L'azione predefinita dipende dalle capacità dell'entità, verrà attivata o disattivata o verranno mostrate più informazioni.",
@@ -2876,7 +2887,7 @@
"toggle": "Attiva/disattiva entità."
},
"entity-filter": {
"description": "La scheda Filtro Entità consente di definire un elenco di entità che si desidera monitorare solo in un determinato stato.",
"description": "La scheda Filtro Entità consente di definire un elenco di entità che si desidera monitorare quando sono solamente in un determinato stato.",
"name": "Filtro Entità"
},
"entity": {
@@ -2884,10 +2895,10 @@
"name": "Entità"
},
"gauge": {
"description": "La scheda Indicatore è una scheda di base che consente di visualizzare visivamente i dati del sensore.",
"description": "La scheda Indicatore è una scheda di base che consente di visualizzare i dati di un sensore.",
"name": "Indicatore",
"severity": {
"define": "Definire la gravità?",
"define": "Definire l'intensità?",
"green": "Verde",
"red": "Rosso",
"yellow": "Giallo"
@@ -2899,15 +2910,15 @@
"camera_image": "Entità Fotocamera",
"camera_view": "Vista fotocamera",
"double_tap_action": "Azione doppio tocco",
"entities": "Entità",
"entity": "Entità",
"hold_action": "Azione di attesa",
"entities": "Molte Entità",
"entity": "Singola Entità",
"hold_action": "Azione tocco prolungato",
"hours_to_show": "Ore da mostrare",
"icon": "Icona",
"icon_height": "Altezza icona",
"image": "Percorso immagine",
"manual": "Manuale",
"manual_description": "Devi aggiungere una scheda personalizzata o semplicemente si vuole scrivere manualmente il file in yaml?",
"manual_description": "Devi aggiungere una scheda personalizzata o vuoi semplicemente scrivere manualmente il file in yaml?",
"maximum": "Massimo",
"minimum": "Minimo",
"name": "Nome",
@@ -2920,7 +2931,7 @@
"show_state": "Mostrare lo stato?",
"state": "Stato",
"state_color": "Colorare le icone in base allo stato?",
"tap_action": "Tocca Azione",
"tap_action": "Azione tocco",
"theme": "Tema",
"title": "Titolo",
"unit": "Unità",
@@ -2937,27 +2948,27 @@
},
"history-graph": {
"description": "La scheda Grafico Storico consente di visualizzare un grafico per ciascuna delle entità elencate.",
"name": "Grafico cronologico"
"name": "Grafico Storico"
},
"horizontal-stack": {
"description": "La scheda Pila Orizzontale consente di raggruppare insieme più schede, in modo che siano sempre l'una accanto all'altra nello spazio di una colonna.",
"name": "Pila orizzontale"
},
"humidifier": {
"description": "La scheda Umidificatore fornisce il controllo della tua entità umidificatore, consentendo di modificare l'umidità e la modalità dell'entità.",
"description": "La scheda Umidificatore fornisce il controllo della tua entità umidificatore. Ti consente di modificare l'umidità e la modalità di funzionamento dell'entità.",
"name": "Umidificatore"
},
"iframe": {
"description": "La scheda Pagina Web consente di incorporare la pagina Web preferita direttamente in Home Assistant.",
"name": "Pagina web"
"description": "La scheda Pagina Web consente di incorporare la tua pagina web preferita direttamente in Home Assistant.",
"name": "Pagina Web"
},
"light": {
"description": "La scheda Luce consente di modificare la luminosità della luce.",
"name": "Luce"
},
"logbook": {
"description": "La scheda del Diario di bordo mostra un elenco di eventi per le entità.",
"name": "Diario di bordo"
"description": "La scheda Registro mostra un elenco di eventi per le entità.",
"name": "Registro"
},
"map": {
"dark_mode": "Modalità scura?",
@@ -2970,7 +2981,7 @@
},
"markdown": {
"content": "Contenuto",
"description": "La scheda Ribassi viene utilizzata per presentare i ribassi.",
"description": "La scheda Markdown viene utilizzata per eseguire il rendering di testo scritto in linguaggio Markdown per una gradevole formattazione della visualizzazione.",
"name": "Markdown"
},
"media-control": {
@@ -2987,7 +2998,7 @@
},
"picture-glance": {
"description": "La scheda Occhiata Immagine mostra un'immagine e gli stati dell'entità corrispondenti come una icona. Le entità sul lato destro consentono azioni di commutazione, altre mostrano più informazioni di dialogo.",
"name": "Vista immagine",
"name": "Sguardo d'Immagine",
"state_entity": "Stato Entità"
},
"picture": {
@@ -2996,7 +3007,7 @@
},
"plant-status": {
"description": "La scheda dello Stato della Pianta è per tutti gli adorabili botanici là fuori.",
"name": "Stato pianta"
"name": "Stato della Pianta"
},
"sensor": {
"description": "La scheda Sensore offre una rapida panoramica dello stato dei sensori con un grafico opzionale per visualizzare il cambiamento nel tempo.",
@@ -3006,7 +3017,7 @@
"show_more_detail": "Mostra ulteriori dettagli"
},
"shopping-list": {
"description": "La scheda della Lista della Spesa consente di aggiungere, modificare, selezionare e cancellare gli articoli dalla lista della spesa.",
"description": "La scheda Lista della Spesa consente di aggiungere, modificare, selezionare e cancellare gli articoli dalla tua lista della spesa.",
"integration_not_loaded": "Questa carta richiede l'integrazione \"shopping_list\" per essere configurata.",
"name": "Lista della spesa"
},
@@ -3055,7 +3066,7 @@
"options": "Altre opzioni",
"pick_card": "Quale scheda vorresti aggiungere?",
"pick_card_view_title": "Quale scheda vorresti aggiungere alla tua vista {name}?",
"search_cards": "Schede di ricerca",
"search_cards": "Cerca schede",
"show_code_editor": "Mostra Editor di Codice",
"show_visual_editor": "Mostra Editor Visivo",
"toggle_editor": "Attiva / disattiva l'editor",

View File

@@ -7,6 +7,7 @@
}
},
"groups": {
"owner": "소유자",
"system-admin": "관리자",
"system-read-only": "읽기 전용 사용자",
"system-users": "사용자"
@@ -332,13 +333,13 @@
"zwave": {
"default": {
"dead": "응답없음",
"initializing": "초기화중",
"initializing": "초기화 중",
"ready": "준비",
"sleeping": "절전모드"
},
"query_stage": {
"dead": "응답없음 ({query_stage})",
"initializing": "초기화중 ({query_stage})"
"initializing": "초기화 중 ({query_stage})"
}
}
},
@@ -747,6 +748,7 @@
"edit": "구성요소 편집",
"history": "기록 내용",
"last_changed": "최근 변경 됨",
"last_updated": "최근 업데이트 됨",
"person": {
"create_zone": "현재 위치로 지역 만들기"
},
@@ -807,6 +809,7 @@
"navigation": {
"areas": "영역",
"automation": "자동화",
"blueprint": "블루프린트",
"core": "일반",
"customize": "사용자화",
"devices": "기기",
@@ -972,6 +975,13 @@
"automation": {
"caption": "자동화",
"description": "자동화를 관리합니다",
"dialog_new": {
"start_empty": "빈 자동화로 시작하기",
"thingtalk": {
"create": "만들기",
"input_label": "이 자동화로 무엇을 하시겠습니까?"
}
},
"editor": {
"actions": {
"add": "동작 추가",
@@ -1052,6 +1062,14 @@
"unsupported_action": "UI 미지원 동작: {action}"
},
"alias": "이름",
"blueprint": {
"blueprint_to_use": "사용할 블루프린트",
"header": "블루프린트",
"inputs": "입력",
"manage_blueprints": "블루프린트 관리",
"no_blueprints": "블루프린트가 존재하지 않습니다",
"no_inputs": "이 블루프린트에는 입력이 없습니다."
},
"conditions": {
"add": "조건 추가",
"delete": "삭제",
@@ -1268,6 +1286,39 @@
"show_info_automation": "자동화에 대한 정보 표시"
}
},
"blueprint": {
"add": {
"error_no_url": "블루프린트의 URL 을 입력해주세요.",
"file_name": "로컬 블루프린트 파일 이름",
"header": "새로운 블루프린트 추가",
"import_btn": "블루프린트 가져오기",
"import_header": "\"{name}\" (유형: {domain}) 가져오기",
"import_introduction": "Github 및 커뮤니티 포럼에서 다른 사용자의 블루프린트를 가져올 수 있습니다. 블루프린트의 URL 을 하단의 입력란에 입력해주세요.",
"importing": "블루프린트를 가져오는 중 ...",
"raw_blueprint": "블루프린트 내용",
"save_btn": "블루프린트 저장하기",
"saving": "블루프린트 저장 중 ...",
"unsupported_blueprint": "이 블루프린트는 지원되지 않습니다.",
"url": "블루프린트의 URL"
},
"caption": "블루프린트",
"description": "블루프린트를 관리합니다",
"overview": {
"add_blueprint": "블루프린트 가져오기",
"confirm_delete_header": "이 블루프린트를 삭제하시겠습니까?",
"confirm_delete_text": "이 블루프린트를 삭제하시겠습니까?",
"delete_blueprint": "블루프린트 삭제",
"header": "블루프린트 편집기",
"headers": {
"domain": "도메인",
"file_name": "파일 이름",
"name": "이름"
},
"introduction": "블루프린트 편집기를 사용하면 블루프린트를 만들고 편집할 수 있습니다.",
"learn_more": "블루프린트에 대해 더 알아보기",
"use_blueprint": "자동화 만들기"
}
},
"cloud": {
"account": {
"alexa": {
@@ -1572,6 +1623,7 @@
},
"header": "구성요소",
"headers": {
"area": "영역",
"entity_id": "구성요소 ID",
"integration": "통합 구성요소",
"name": "이름",
@@ -2174,18 +2226,23 @@
"system_generated_users_not_editable": "시스템 자동 생성 사용자는 업데이트할 수 없습니다.",
"system_generated_users_not_removable": "시스템 자동 생성 사용자는 제거할 수 없습니다.",
"unnamed_user": "이름이 없는 사용자",
"update_user": "업데이트"
"update_user": "업데이트",
"username": "사용자 이름"
},
"picker": {
"headers": {
"group": "그룹",
"is_active": "활성화",
"is_owner": "소유자",
"name": "이름",
"system": "시스템"
"system": "시스템",
"username": "사용자 이름"
}
},
"users_privileges_note": "사용자 그룹 기능은 현재 작업 중이며, 사용자는 UI 를 통해 인스턴스를 관리할 수 없습니다. 모든 사용자 관리 API 엔드포인트가 관리자에 대한 액세스를 올바르게 제한하는지를 확인하는 중입니다."
},
"zha": {
"add_device": "기기 추가",
"add_device_page": {
"discovered_text": "기기가 발견되면 여기에 표시됩니다.",
"discovery_text": "발견된 기기가 여기에 표시됩니다. 기기의 설명서를 참고하여 기기를 페어링 모드로 설정해주세요.",
@@ -2231,6 +2288,16 @@
"value": "값"
},
"description": "Zigbee Home Automation 네트워크를 관리합니다",
"device_pairing_card": {
"CONFIGURED": "구성이 완료되었습니다",
"CONFIGURED_status_text": "초기화 중",
"INITIALIZED": "초기화가 완료되었습니다",
"INITIALIZED_status_text": "기기를 사용할 준비가 되었습니다",
"INTERVIEW_COMPLETE": "인터뷰가 완료되었습니다",
"INTERVIEW_COMPLETE_status_text": "구성 중",
"PAIRED": "기기가 발견되었습니다",
"PAIRED_status_text": "인터뷰 시작 중"
},
"devices": {
"header": "Zigbee Home Automation - 기기"
},
@@ -2246,6 +2313,7 @@
"unbind_button_label": "그룹 바인딩 해제"
},
"groups": {
"add_group": "그룹 추가",
"add_members": "구성 기기 추가",
"adding_members": "구성 기기 추가",
"caption": "그룹",
@@ -2288,7 +2356,11 @@
"hint_wakeup": "Xiaomi 센서와 같은 일부 기기는 상호 작용하는 동안 기기의 절전 모드 해제가 가능한 약 5초 동안 누를 수 있는 절전 해제 버튼이 있습니다.",
"introduction": "단일 기기에 영향을 주는 ZHA 명령을 실행합니다. 사용 가능한 명령 목록을 보려면 기기를 선택해주세요."
},
"title": "Zigbee Home Automation"
"title": "Zigbee Home Automation",
"visualization": {
"caption": "시각화",
"header": "네트워크 시각화"
}
},
"zone": {
"add_zone": "지역 추가",
@@ -2457,6 +2529,8 @@
"filter_attributes": "속성 필터",
"filter_entities": "구성요소 필터",
"filter_states": "상태 필터",
"last_changed": "최근 변경 됨",
"last_updated": "최근 업데이트 됨",
"more_info": "정보 더보기",
"no_entities": "구성요소가 없습니다",
"set_state": "상태 설정",
@@ -2706,7 +2780,8 @@
},
"picture-glance": {
"description": "그림 한눈에 보기 카드는 이미지와 해당 구성요소의 상태가 아이콘으로 표시됩니다. 오른쪽의 구성요소는 토글 작업을 허용하고 다른 구성요소는 추가 정보 대화상자를 표시합니다.",
"name": "그림 한눈에 보기"
"name": "그림 한눈에 보기",
"state_entity": "상태 구성요소"
},
"picture": {
"description": "그림 카드를 사용하면 인터페이스의 다양한 경로를 탐색하거나 서비스를 호출하는 데 사용할 이미지를 설정할 수 있습니다.",

View File

@@ -7,6 +7,7 @@
}
},
"groups": {
"owner": "Besëtzer",
"system-admin": "Administrateuren",
"system-read-only": "Benotzer mat nëmmen Lies Rechter",
"system-users": "Benotzer"
@@ -547,6 +548,11 @@
"clear": "Läschen",
"show_areas": "Beräicher uweisen"
},
"blueprint-picker": {
"add_user": "Benotzer erstellen",
"remove_user": "Benotzer läschen",
"select_blueprint": "Plang auswielen"
},
"data-table": {
"no-data": "Keng Donnée",
"search": "Sichen"
@@ -716,6 +722,7 @@
"enabled_cause": "Desaktivéiert duerch {cause}.",
"enabled_description": "Deaktivéiert Entitéiten ginn net am Home Assistant bäigesat.",
"enabled_label": "Entitéit aktivéieren",
"enabled_restart_confirm": "Start Home Assistant nei fir dës Entitéiten z'aktivéieren",
"entity_id": "ID vun der Entitéit",
"icon": "Ikon",
"icon_error": "Ikonen sollten am format 'prefix:numm' sinn, Beispill: 'mdi:home'",
@@ -788,6 +795,11 @@
},
"more_info_control": {
"controls": "Kontrollen",
"cover": {
"close_cover": "Paart zoumaachen",
"open_cover": "Paart opmaachen",
"open_tilt_cover": "Paart op Kipp stelle"
},
"details": "Detailler",
"dismiss": "Dialog ofbriechen",
"edit": "Entitéit änneren",
@@ -851,6 +863,29 @@
},
"quick-bar": {
"commands": {
"navigation": {
"areas": "Beräicher",
"automation": "Automatisme",
"blueprint": "Pläng",
"core": "Generell",
"customize": "Personaliséierungen",
"devices": "Apparate",
"entities": "Entitéite",
"helpers": "Helfer",
"info": "Info",
"integrations": "Integratioune",
"logs": "Logs",
"lovelace": "Lovelace Tableau de Bord",
"navigate_to": "Navigéieren zu {panel}",
"navigate_to_config": "Navigéieren zu {panel} Konfiguratioun",
"person": "Persoune",
"scene": "Zeene",
"script": "Skripte",
"server_control": "Server Kontrolle",
"tags": "Tags",
"users": "Benotzer",
"zone": "Zone"
},
"reload": {
"automation": "Automatisme frësch lueden",
"command_line": "Kommando Zeilen Entitéite frësch lueden",
@@ -993,6 +1028,20 @@
"automation": {
"caption": "Automatismen",
"description": "Automatismen verwalten",
"dialog_new": {
"blueprint": {
"use_blueprint": "Plang benotzen"
},
"header": "Nei Automatisme erstellen",
"how": "Wéi wëlls du deng nei Automatisme erstellen?",
"start_empty": "Mat enger eideler Automatisme ufänken",
"thingtalk": {
"create": "Erstellen",
"header": "Beschréif den Automatisme deen soll erstallt ginn",
"input_label": "Wat soll dësen Automatisme maachen?",
"intro": "A mir probéieren et fir dech z'erstellen. Zum Beispill: Schalt Luuchten aus wann ech fort ginn."
}
},
"editor": {
"actions": {
"add": "Aktioun dobäisetzen",
@@ -1073,6 +1122,14 @@
"unsupported_action": "Keng UI Ënnerstëtzung fir Aktioun: {action}"
},
"alias": "Numm",
"blueprint": {
"blueprint_to_use": "Plang fir ze benotzen",
"header": "Plang",
"inputs": "Agab",
"manage_blueprints": "Pläng verwalten",
"no_blueprints": "Du hues kee Plang",
"no_inputs": "Dëse Plang huet keng Agab."
},
"conditions": {
"add": "Konditioun dobäisetzen",
"delete": "Läschen",
@@ -1315,6 +1372,39 @@
}
}
},
"blueprint": {
"add": {
"error_no_url": "Gëff d'URL vum Plang un.",
"file_name": "Lokal Plang Datei Numm",
"header": "Neie Plang erstellen",
"import_btn": "Plang importéieren",
"import_header": "Import \"{name}\" (typ: {domain})",
"import_introduction": "Du kanns Pl¨ng vun aaner Github Benotzer an Community Forumer importéieren. Gëff d'URL vum Plang an.",
"importing": "Plang gëtt importéiert...",
"raw_blueprint": "Plang Inhalt",
"save_btn": "Plang späicheren",
"saving": "Plang gëtt gespäichert...",
"unsupported_blueprint": "Dëse Plang gëtt net ënnerstëtzt",
"url": "URL vum Plang"
},
"caption": "Pläng",
"description": "Pläng verwalten",
"overview": {
"add_blueprint": "Plang importéieren",
"confirm_delete_header": "Dëse Plang läschen?",
"confirm_delete_text": "Sécher fir dëse Plang ze läsche?",
"delete_blueprint": "Plang läschen",
"header": "Plang Editeur",
"headers": {
"domain": "Domain",
"file_name": "Datei Numm",
"name": "Numm"
},
"introduction": "De Plang Editeur erlabt et Pläng z'erstellen an ze veränneren.",
"learn_more": "Méi iwwert Plèang léieren",
"use_blueprint": "Automatisme erstellen"
}
},
"cloud": {
"account": {
"alexa": {
@@ -1628,6 +1718,7 @@
},
"header": "Entitéiten",
"headers": {
"area": "Beräich",
"entity_id": "ID vun der Entitéit",
"integration": "Integratioun",
"name": "Numm",
@@ -1689,6 +1780,8 @@
"info": {
"built_using": "Erstallt mat",
"caption": "Info",
"copy_github": "Fir Github",
"copy_raw": "Rengen Text",
"custom_uis": "Personaliséierte Benotzer Interface:",
"description": "Informatioune zu denger Home Assistant Installation uweisen",
"developed_by": "Entwéckelt vun enger ganzer Rei fantastesche Leit.",
@@ -2152,6 +2245,8 @@
},
"picker": {
"add_script": "Neie Skript erstellen",
"duplicate": "Duplizéieren",
"duplicate_script": "Skript duplizéieren",
"edit_script": "Skript änneren",
"header": "Skript Editeur",
"headers": {
@@ -2283,18 +2378,24 @@
"system_generated_users_not_editable": "Net méiglech System generéiert Benotzer z'aktualiséieren.",
"system_generated_users_not_removable": "Ka keng System generéiert Benotzer läschen.",
"unnamed_user": "Benotzer ouni Numm",
"update_user": "Aktualiséieren"
"update_user": "Aktualiséieren",
"username": "Benotzernumm"
},
"picker": {
"add_user": "Benotzer erstellen",
"headers": {
"group": "Grupp",
"is_active": "Aktiv",
"is_owner": "Besëtzer",
"name": "Numm",
"system": "System"
"system": "System",
"username": "Benotzernumm"
}
},
"users_privileges_note": "Benotzer Gruppp ass nach \"Work in progress\". De Benotzer kann d'Instanz net via UI verwalten. MIr sin mat engem Audit am gaang vun all Management API Endpunkt fir sécher ze stellen dass déi den accès richteg op Administrateuren limitéieren."
},
"zha": {
"add_device": "Apparat dobäisetzen",
"add_device_page": {
"discovered_text": "Apparater tauchen hei op soubaal se entdeckt sinn.",
"discovery_text": "Entdeckten Apparater tauchen op dëser Platz op. Suivéiert d'Instruktiounen fir är Apparater an aktivéiert den Kupplung's Mod.",
@@ -2340,6 +2441,16 @@
"value": "Wäert"
},
"description": "Gestioun vum Zigbee Home Automation Reseau",
"device_pairing_card": {
"CONFIGURED": "Konfiguratioun fäerdeg",
"CONFIGURED_status_text": "Initialiséiert",
"INITIALIZED": "Initialiséierung fäerdeg",
"INITIALIZED_status_text": "Den Apparat ass prett fir ze benotzen",
"INTERVIEW_COMPLETE": "Interview fäerdeg",
"INTERVIEW_COMPLETE_status_text": "Konfiguréiert",
"PAIRED": "Apparat fonnt",
"PAIRED_status_text": "Interview fänkt un"
},
"devices": {
"header": "Zigbee Haus Automatismen - Apparat"
},
@@ -2355,6 +2466,7 @@
"unbind_button_label": "Grupp opléisen"
},
"groups": {
"add_group": "Grupp dobäisetzen",
"add_members": "Membere bäisetzen",
"adding_members": "Membere gi bäigesat",
"caption": "Gruppe",
@@ -2397,7 +2509,11 @@
"hint_wakeup": "Verschidden Apparater wéi Xiaomi Sensoren hunn ee klenge Knäppchen deen een an Intervalle vu ~5s drécke ka fir dass den Apparat un bléift wärend der Interaktioun.",
"introduction": "ZHA Kommandoe ausféieren déi nëmmen een Apparat betreffen. Wielt een Apparat aus fir seng Lëscht vun verfügbare Kommandoe ze gesinn."
},
"title": "Zigbee Haus Automatismen"
"title": "Zigbee Haus Automatismen",
"visualization": {
"caption": "Visualisatioun",
"header": "Visualisatioun vum Netzwierk"
}
},
"zone": {
"add_zone": "Zon dobäisetzen",
@@ -2566,6 +2682,8 @@
"filter_attributes": "Attributer filteren",
"filter_entities": "Entitéite filteren",
"filter_states": "Zoustänn filteren",
"last_changed": "Läscht Ännerung",
"last_updated": "Läscht Aktualiséierung",
"more_info": "Méi Info",
"no_entities": "Keng Entitéiten",
"set_state": "Zoustand setzen",
@@ -2817,6 +2935,9 @@
"description": "Luucht Kaart erlaabt et d'Hellegkeet vun de Luuchten ze veränneren.",
"name": "Luucht"
},
"logbook": {
"name": "Logbuch"
},
"map": {
"dark_mode": "Däischteren Modus",
"default_zoom": "Standard Zoom",
@@ -2939,6 +3060,7 @@
},
"header": "UI änneren",
"header-footer": {
"choose_header_footer": "{typ} auswielen",
"footer": "Fousszeilen",
"header": "Entête",
"types": {
@@ -2947,6 +3069,9 @@
},
"graph": {
"name": "Graph"
},
"picture": {
"name": "Bild"
}
}
},

View File

@@ -7,6 +7,7 @@
}
},
"groups": {
"owner": "Eier",
"system-admin": "Administratorer",
"system-read-only": "Brukere med lesetilgang",
"system-users": "Brukere"
@@ -1743,6 +1744,7 @@
},
"header": "Entiteter",
"headers": {
"area": "Område",
"entity_id": "Entitets-ID",
"integration": "Integrasjon",
"name": "Navn",
@@ -2399,7 +2401,7 @@
"delete_user": "Slett bruker",
"group": "Gruppe",
"id": "Id",
"name": "Navn",
"name": "Visningsnavn",
"new_password": "Nytt passord",
"owner": "Eier",
"password_changed": "Passordet ble endret",
@@ -2407,14 +2409,18 @@
"system_generated_users_not_editable": "Kan ikke oppdatere systemopprettede brukere.",
"system_generated_users_not_removable": "Kan ikke fjerne systemopprettede brukere.",
"unnamed_user": "Bruker uten navn",
"update_user": "Oppdater"
"update_user": "Oppdater",
"username": "Brukernavn"
},
"picker": {
"add_user": "Legg til bruker",
"headers": {
"group": "Gruppe",
"name": "Navn",
"system": ""
"is_active": "Aktiv",
"is_owner": "Eier",
"name": "Visningsnavn",
"system": "System generert",
"username": "Brukernavn"
}
},
"users_privileges_note": "Brukergruppefunksjonen er et pågående arbeid. Brukeren vil ikke kunne administrere forekomsten via brukergrensesnittet. Vi overvåker fortsatt alle administrasjons-API-endepunkter for å sikre at de begrenser tilgangen til administratorer på riktig måte."
@@ -2466,6 +2472,16 @@
"value": "Verdi"
},
"description": "ZigBee Hjemmeautomasjon nettverksadministrasjon",
"device_pairing_card": {
"CONFIGURED": "Konfigurasjonen er fullført",
"CONFIGURED_status_text": "Initialiserer",
"INITIALIZED": "Initialiseringen er fullført",
"INITIALIZED_status_text": "Enheten er klar til bruk",
"INTERVIEW_COMPLETE": "Intervju fullført",
"INTERVIEW_COMPLETE_status_text": "Konfigurerer",
"PAIRED": "Enhet funnet",
"PAIRED_status_text": "Starter intervju"
},
"devices": {
"header": "ZigBee Hjemmeautomasjon - Enhet"
},

View File

@@ -7,6 +7,7 @@
}
},
"groups": {
"owner": "Eigenaar",
"system-admin": "Beheerders",
"system-read-only": "Alleen-lezen gebruikers",
"system-users": "Gebruikers"
@@ -1400,7 +1401,7 @@
"error_no_url": "Voer de URL van de blauwdruk in.",
"header": "Voeg een nieuwe blauwdruk toe",
"import_btn": "Blauwdruk importeren",
"import_header": "Importeer {name} ( {domain} )",
"import_header": "Importeer \"{name}\" (type: {domain})",
"import_introduction": "U kunt blauwdrukken van andere gebruikers importeren vanuit Github en de communityforums. Voer de URL van de blauwdruk hieronder in.",
"importing": "Blauwdruk importeren ...",
"save_btn": "Bewaar blauwdruk",
@@ -1410,14 +1411,18 @@
"caption": "Blauwdrukken",
"description": "Beheer blauwdrukken",
"overview": {
"add_blueprint": "Blauwdruk importeren",
"confirm_delete_header": "Deze blauwdruk verwijderen?",
"confirm_delete_text": "Weet je zeker dat je deze blauwdruk wilt verwijderen?",
"header": "Blauwdrukeditor",
"headers": {
"domain": "Domein",
"file_name": "Bestandsnaam",
"name": "Naam"
},
"introduction": "Met de blauwdrukeditor kunt je blauwdrukken maken en bewerken.",
"learn_more": "Meer informatie over blauwdrukken"
"learn_more": "Meer informatie over blauwdrukken",
"use_blueprint": "Automatisering maken"
}
},
"cloud": {
@@ -1734,6 +1739,7 @@
},
"header": "Entiteiten",
"headers": {
"area": "Gebied",
"entity_id": "Entiteits-ID",
"integration": "Integratie",
"name": "Naam",
@@ -1864,11 +1870,11 @@
"delete": "Verwijder",
"delete_button": "Verwijder {integration}.",
"delete_confirm": "Weet je zeker dat je deze integratie wilt verwijderen?",
"device_unavailable": "apparaat niet beschikbaar",
"device_unavailable": "Apparaat niet beschikbaar",
"devices": "{count} {count, plural,\n one {apparaat}\n other {apparaten}\n}",
"documentation": "Documentatie",
"entities": "{count} {count, plural,\n one {entiteit}\n other {entiteiten}\n}",
"entity_unavailable": "entiteit niet beschikbaar",
"entity_unavailable": "Entiteit niet beschikbaar",
"firmware": "Firmware: {version}",
"hub": "Verbonden via",
"manuf": "door {manufacturer}",
@@ -2390,7 +2396,7 @@
"delete_user": "Verwijder gebruiker",
"group": "Groep",
"id": "ID",
"name": "Naam",
"name": "Weergavenaam",
"new_password": "Nieuw wachtwoord",
"owner": "Eigenaar",
"password_changed": "Het wachtwoord is gewijzigd!",
@@ -2398,19 +2404,24 @@
"system_generated_users_not_editable": "Kan door het systeem gegenereerde gebruikers niet bijwerken.",
"system_generated_users_not_removable": "Kan door het systeem gegenereerde gebruikers niet verwijderen.",
"unnamed_user": "Naamloze gebruiker",
"update_user": "Bijwerken"
"update_user": "Bijwerken",
"username": "Gebruikersnaam"
},
"picker": {
"add_user": "Gebruiker toevoegen",
"headers": {
"group": "Groep",
"name": "Naam",
"system": "Systeem"
"is_active": "Actief",
"is_owner": "Eigenaar",
"name": "Weergavenaam",
"system": "Systeem gegenereerd",
"username": "Gebruikersnaam"
}
},
"users_privileges_note": "Gebruikersgroepen zijn nog in ontwikkeling. De gebruiker kan de instantie niet beheren via de interface. We controleren nog steeds alle beheer API eindpunten om ervoor te zorgen dat ze de toegang tot beheerders correct beperken."
},
"zha": {
"add_device": "Apparaat toevoegen",
"add_device_page": {
"discovered_text": "Apparaten zullen hier verschijnen zodra ze zijn ontdekt.",
"discovery_text": "Gevonden apparaten worden hier weergegeven. Volg de instructies voor je apparaat of apparaten en plaats het apparaat of de apparaten in de koppelingsmodus.",
@@ -2456,6 +2467,14 @@
"value": "Waarde"
},
"description": "Zigbee Home Automation netwerkbeheer",
"device_pairing_card": {
"CONFIGURED": "Configuratie voltooid",
"CONFIGURED_status_text": "Initialiseren",
"INITIALIZED": "Initialisatie voltooid",
"INITIALIZED_status_text": "Het apparaat is klaar voor gebruik",
"INTERVIEW_COMPLETE_status_text": "Configureren",
"PAIRED": "Apparaat gevonden"
},
"devices": {
"header": "Zigbee Home Automation - Apparaat"
},
@@ -2471,6 +2490,7 @@
"unbind_button_label": "Ontkoppel groep"
},
"groups": {
"add_group": "Groep toevoegen",
"add_members": "Leden toevoegen",
"adding_members": "Leden toevoegen",
"caption": "Groepen",
@@ -2967,7 +2987,8 @@
},
"picture-glance": {
"description": "De Picture Glance-kaart toont een afbeelding en de bijbehorende entiteitstoestanden als een pictogram. De entiteiten aan de rechterkant staan schakelacties toe, andere tonen het dialoogvenster met meer informatie.",
"name": "Afbeelding oogopslag"
"name": "Afbeelding oogopslag",
"state_entity": "Status entiteit"
},
"picture": {
"description": "Met de Picture-kaart kunt u een afbeelding instellen voor navigatie naar verschillende paden in uw interface of om een service te activeren.",
@@ -3178,7 +3199,7 @@
"attribute_not_found": "Kenmerk {attribute} niet beschikbaar in: {entity}",
"entity_non_numeric": "Entiteit is niet-numeriek: {entity}",
"entity_not_found": "Entiteit niet beschikbaar: {entity}",
"entity_unavailable": "{entity} is momenteel niet beschikbaar",
"entity_unavailable": "Entiteit is momenteel niet beschikbaar: {entity}",
"starting": "Home Assistant is aan het opstarten, wellicht is nog niet alles beschikbaar"
}
},

View File

@@ -1744,6 +1744,7 @@
},
"header": "Rejestr encji",
"headers": {
"area": "Obszar",
"entity_id": "Identyfikator encji",
"integration": "Integracja",
"name": "Nazwa",
@@ -2471,6 +2472,16 @@
"value": "Wartość"
},
"description": "Zarządzanie siecią Zigbee Home Automation",
"device_pairing_card": {
"CONFIGURED": "Konfigurowanie zakończona",
"CONFIGURED_status_text": "Inicjalizacja",
"INITIALIZED": "Inicjalizacja zakończona",
"INITIALIZED_status_text": "Urządzenie jest gotowe do użycia",
"INTERVIEW_COMPLETE": "Odpytywanie zakończone",
"INTERVIEW_COMPLETE_status_text": "Konfigurowanie",
"PAIRED": "Znaleziono urządzenie",
"PAIRED_status_text": "Rozpoczęcie odpytywania"
},
"devices": {
"header": "Zigbee Home Automation - urządzenie"
},

View File

@@ -7,6 +7,7 @@
}
},
"groups": {
"owner": "Proprietário",
"system-admin": "Administradores",
"system-read-only": "Utilizadores só com permissões de leitura",
"system-users": "Utilizadores"
@@ -547,6 +548,11 @@
"clear": "Limpar",
"show_areas": "Mostrar áreas"
},
"blueprint-picker": {
"add_user": "Adicionar um utilizador",
"remove_user": "Remover utilizador",
"select_blueprint": "Escolhe um projeto"
},
"data-table": {
"no-data": "Dados do evento",
"search": "Procurar"
@@ -732,15 +738,15 @@
"enabled_label": "Ativar entidade",
"enabled_restart_confirm": "Reinicie o Home Assistant para ativar as entidades",
"entity_id": "Identificação da entidade",
"icon": "Substituição do ícone",
"icon": "Ícone",
"icon_error": "Os ícones devem estar no formato 'prefixo:nome do ícone', por exemplo 'mdi:home'.",
"name": "Substituição do nome",
"name": "Nome",
"note": "Nota: isto pode ainda não funcionar com todas as integrações.",
"unavailable": "Esta entidade não está atualmente disponível.",
"update": "Atualizar"
},
"faq": "Documentação",
"no_unique_id": "Esta entidade não tem uma identificação única, portanto suas configurações não podem ser geridas a partir da UI. Para mais informações, ver {faq_link}.",
"no_unique_id": "Esta entidade (\"{entity_id}\") não tem uma identificação única, portanto suas configurações não podem ser geridas a partir da UI. Para mais informações, ver {faq_link}.",
"related": "Relacionadas",
"settings": "Definições"
},
@@ -872,6 +878,7 @@
"navigation": {
"areas": "Áreas",
"automation": "Automação",
"blueprint": "Projecto",
"core": "Geral",
"customize": "Personalização",
"devices": "Dispositivos",
@@ -1041,6 +1048,20 @@
"automation": {
"caption": "Automação",
"description": "Gerir Automações",
"dialog_new": {
"blueprint": {
"use_blueprint": "Utilize o projeto"
},
"header": "Criar uma automatização",
"how": "Como quer criar uma automatização?",
"start_empty": "Começar com uma automatização vazia",
"thingtalk": {
"create": "Criar",
"header": "Descreva a automatização que pretende criar",
"input_label": "O que deve fazer esta automatização?",
"intro": "E nós vamos tentar criar por ti. Por exemplo: Desliga as luzes quando eu sair."
}
},
"editor": {
"actions": {
"add": "Adicionar ação",
@@ -1121,6 +1142,14 @@
"unsupported_action": "Ação não suportada: {action}"
},
"alias": "Nome",
"blueprint": {
"blueprint_to_use": "Projeto a usar",
"header": "Projeto",
"inputs": "Entrada",
"manage_blueprints": "Gerir projetos",
"no_blueprints": "Tu nao tens nenhum projeto",
"no_inputs": "Este projeto não tem nenhuma entrada"
},
"conditions": {
"add": "Acrescentar condição",
"delete": "Apagar",
@@ -1206,7 +1235,7 @@
"edit_ui": "Editar com IU",
"edit_yaml": "Editar como YAML",
"enable_disable": "Habilitar/desabilitar automação",
"introduction": "Crie automações para dar vida à sua casa",
"introduction": "Utilize automações para dar vida à sua casa",
"load_error_not_editable": "Apenas as automações em automations.yaml são editáveis.",
"load_error_unknown": "Erro ao carregar a automação ({err_no}).",
"max": {
@@ -1358,6 +1387,39 @@
}
}
},
"blueprint": {
"add": {
"error_no_url": "Por favor introduza o URL do projeto",
"file_name": "Nome do ficheiro do projeto local",
"header": "Adicionar novo projeto",
"import_btn": "Importar projeto",
"import_header": "Importar \"{name}\" (tipo: {domain})",
"import_introduction": "Você pode importar projetos de outros utilizadores pelo Github e pelo fórum da comunidade. introduza o URL do projeto abaixo",
"importing": "A importar projeto...",
"raw_blueprint": "Conteúdo do projeto",
"save_btn": "Projeto guardado",
"saving": "A guardar projecto...",
"unsupported_blueprint": "Projeto não suportado",
"url": "URL do projeto"
},
"caption": "Projeto",
"description": "Gerir projeto",
"overview": {
"add_blueprint": "Importar projeto",
"confirm_delete_header": "Apagar projeto",
"confirm_delete_text": "Tem a certeza que pretende apagar este projeto?",
"delete_blueprint": "Excluir projeto",
"header": "Editor de projetos",
"headers": {
"domain": "Domínio",
"file_name": "Nome do ficheiro",
"name": "Nome"
},
"introduction": "Este editor de projetos permite criar e editar projetos.",
"learn_more": "Aprenda mais sobre projetos",
"use_blueprint": "Criar automação"
}
},
"cloud": {
"account": {
"alexa": {
@@ -1670,6 +1732,7 @@
},
"header": "Entidades",
"headers": {
"area": "Área",
"entity_id": "ID da Entidade",
"integration": "Integração",
"name": "Nome",
@@ -1682,7 +1745,7 @@
"confirm_partly_text": "Você pode remover apenas {removable} das {selected} entidades selecionadas. As entidades só podem ser removidas quando a integração deixar de suportá-las. Por vezes é necessário reiniciar o Home Assistant antes de poder remover as entidades de uma integração removida. Tem a certeza de que deseja remover as entidades removíveis?",
"confirm_partly_title": "Apenas {number} {number, plural,\n uma {selected entity} pode ser removida \n outras {selected entities} podem ser removidas \n}.",
"confirm_text": "Deve remover da configuração do Lovelace e das automações se contêm estas entidades",
"confirm_title": "Deseja remover {number} entidades?"
"confirm_title": "Deseja remover {number} {number, plural,\n one {entidade}\n other {entidades}\n}?"
},
"search": "Procurar entidades",
"selected": "Selecionou {number}",
@@ -1732,6 +1795,7 @@
"built_using": "Construído com",
"caption": "Informação",
"copy_github": "Para GitHub",
"copy_raw": "Texto simples",
"custom_uis": "IUs personalizados:",
"description": "Ver informações sobre a instalação do Home Assistant",
"developed_by": "Desenvolvido por um punhado de pessoas incríveis.",
@@ -2126,7 +2190,7 @@
"without_device": "Entidades sem dispositivo"
},
"icon": "Ícone",
"introduction": "Crie cenários para dar vida à sua casa.",
"introduction": "Utilize cenários para dar vida à sua casa.",
"load_error_not_editable": "Apenas cenários em scenes.yaml são editáveis.",
"load_error_unknown": "Erro ao carregar cena ({err_no}).",
"name": "Nome",
@@ -2309,7 +2373,7 @@
"delete_user": "Apagar utilizador",
"group": "Grupo",
"id": "ID",
"name": "Nome",
"name": "Nome em Exibição",
"new_password": "Nova senha",
"owner": "Proprietário",
"password_changed": "A senha foi alterada com sucesso",
@@ -2317,19 +2381,24 @@
"system_generated_users_not_editable": "Não foi possível atualizar os utilizadores gerados pelo sistema.",
"system_generated_users_not_removable": "Não é possível remover utilizadores gerados pelo sistema.",
"unnamed_user": "Utilizador sem nome",
"update_user": "Atualizar"
"update_user": "Atualizar",
"username": "Nome de Utilizador"
},
"picker": {
"add_user": "Adicionar Utilizador",
"headers": {
"group": "Grupo",
"name": "Nome",
"system": "Sistema"
"is_active": "Ativo",
"is_owner": "Proprietário",
"name": "Nome em Exibição",
"system": "Gerado pelo sistema",
"username": "Nome de Utilizador"
}
},
"users_privileges_note": "O grupo de utilizadores é um trabalho em progresso. O utilizador não poderá administrar a instância por meio da interface de utilizador. Ainda estamos a auditar todos os endpoints da API de gestão para garantir que eles limitam corretamente o acesso aos administradores."
},
"zha": {
"add_device": "Adicionar Dispositivo",
"add_device_page": {
"discovered_text": "Os dispositivos aparecem aqui uma vez descobertos.",
"discovery_text": "Os dispositivos descobertos aparecerão aqui. Siga as instruções para o(s) seu(s) dispositivo(s) e coloque o(s) dispositivo(s) em modo de emparelhamento.",
@@ -2375,6 +2444,16 @@
"value": "Valor"
},
"description": "Gestão de rede Zigbee Home Automation",
"device_pairing_card": {
"CONFIGURED": "Configuração Completa",
"CONFIGURED_status_text": "A inicializar",
"INITIALIZED": "Inicialização completa",
"INITIALIZED_status_text": "O dispositivo está pronto para uso",
"INTERVIEW_COMPLETE": "Entrevista Completa",
"INTERVIEW_COMPLETE_status_text": "Configurando",
"PAIRED": "Dispositivo encontrado",
"PAIRED_status_text": "A iniciar entrevista"
},
"devices": {
"header": "Zigbee Home Automation - Dispositivo"
},
@@ -2390,6 +2469,7 @@
"unbind_button_label": "Desvincular grupo"
},
"groups": {
"add_group": "Adicionar grupo",
"add_members": "Adicionar membros",
"adding_members": "A Adicionar membros",
"caption": "Grupos",
@@ -2432,7 +2512,11 @@
"hint_wakeup": "Alguns dispositivos, como os sensores Xiaomi, têm um botão de ativação que você pode pressionar em intervalos de ~ 5 segundos para manter os dispositivos acordados enquanto você interage com eles.",
"introduction": "Execute comandos ZHA que afetem um único dispositivo. Escolha um dispositivo para ver uma lista de comandos disponíveis."
},
"title": "Automação residencial zigbee"
"title": "Automação residencial zigbee",
"visualization": {
"caption": "Visualização",
"header": "Visualização de rede"
}
},
"zone": {
"add_zone": "Adicionar zona",
@@ -2622,6 +2706,7 @@
"reset": "Redefinir para modelo de demonstração",
"result_type": "Tipo de resultado",
"template_extensions": "Extensões de templates do Home Assistant",
"time": "Este modelo atualiza ao início de cada minuto",
"title": "Template",
"unknown_error_template": "Erro desconhecido ao processar o template"
}
@@ -2688,7 +2773,7 @@
}
},
"changed_toast": {
"message": "A configuração do Lovelace foi atualizada para este painel, gostaria de atualizar?",
"message": "A configuração do Lovelace foi atualizada para este painel, gostaria de atualizar para verificar as alterações?",
"refresh": "Atualizar"
},
"editor": {
@@ -2852,6 +2937,10 @@
"description": "O cartão Luz permite alterar o brilho da luz.",
"name": "Luz"
},
"logbook": {
"description": "O cartão dos registos mostra a lista de eventos para as entidades",
"name": "Registos"
},
"map": {
"dark_mode": "Modo escuro?",
"default_zoom": "Zoom padrão",
@@ -2880,7 +2969,8 @@
},
"picture-glance": {
"description": "O cartão Vista de imagem mostra uma imagem e os estados das entidades correspondentes como um ícone. As entidades do lado direito permitem alternar ações, outras mostram a opção mais informações.",
"name": "Vista sobre imagem"
"name": "Vista sobre imagem",
"state_entity": "Estado da entidade"
},
"picture": {
"description": "O cartão de imagem permite definir uma imagem a ser usada para navegação em vários pontos na sua interface ou para chamar um serviço.",

View File

@@ -1687,6 +1687,7 @@
},
"header": "Объекты",
"headers": {
"area": "Помещение",
"entity_id": "ID объекта",
"integration": "Интеграция",
"name": "Название",
@@ -2414,6 +2415,16 @@
"value": "Значение"
},
"description": "Управление сетью Zigbee Home Automation",
"device_pairing_card": {
"CONFIGURED": "Настройка завершена",
"CONFIGURED_status_text": "Инициализация",
"INITIALIZED": "Инициализация завершена",
"INITIALIZED_status_text": "Устройство готово к использованию",
"INTERVIEW_COMPLETE": "Опрос завершен",
"INTERVIEW_COMPLETE_status_text": "Настройка",
"PAIRED": "Найдено устройство",
"PAIRED_status_text": "Опрос начат"
},
"devices": {
"header": "Zigbee Home Automation - Устройство"
},

View File

@@ -2876,6 +2876,9 @@
"dropdown_label": "Панель",
"header": "Панель"
},
"enable_shortcuts": {
"header": "Гарячі клавіші"
},
"force_narrow": {
"description": "Це дозволить приховати бічну панель за замовчуванням, як і для мобільних пристроїв.",
"header": "Завжди приховувати бічну панель"

View File

@@ -1744,6 +1744,7 @@
},
"header": "實體",
"headers": {
"area": "分區",
"entity_id": "實體 ID",
"integration": "整合",
"name": "名稱",
@@ -2471,6 +2472,16 @@
"value": "數值"
},
"description": "Zigbee 家庭自動化網路管理",
"device_pairing_card": {
"CONFIGURED": "設定完成",
"CONFIGURED_status_text": "初始化中",
"INITIALIZED": "初始化完成",
"INITIALIZED_status_text": "設備已準備就緒",
"INTERVIEW_COMPLETE": "探訪完成",
"INTERVIEW_COMPLETE_status_text": "設定中",
"PAIRED": "找到設備",
"PAIRED_status_text": "開始探訪"
},
"devices": {
"header": "Zigbee 家庭自動化 - 設備"
},