Merge pull request #5436 from home-assistant/dev

20200403.0
This commit is contained in:
Bram Kragten 2020-04-03 18:04:07 +02:00 committed by GitHub
commit a438439ce0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
77 changed files with 753 additions and 307 deletions

View File

@ -2,7 +2,7 @@ from setuptools import setup, find_packages
setup( setup(
name="home-assistant-frontend", name="home-assistant-frontend",
version="20200401.0", version="20200403.0",
description="The Home Assistant frontend", description="The Home Assistant frontend",
url="https://github.com/home-assistant/home-assistant-polymer", url="https://github.com/home-assistant/home-assistant-polymer",
author="The Home Assistant Authors", author="The Home Assistant Authors",

View File

@ -27,7 +27,7 @@ class SearchInput extends LitElement {
protected render(): TemplateResult { protected render(): TemplateResult {
return html` return html`
<style> <style>
.no-underline { .no-underline:not(.focused) {
--paper-input-container-underline: { --paper-input-container-underline: {
display: none; display: none;
height: 0; height: 0;

View File

@ -86,6 +86,7 @@ export class HaDataTable extends LitElement {
@property({ type: Object }) public columns: DataTableColumnContainer = {}; @property({ type: Object }) public columns: DataTableColumnContainer = {};
@property({ type: Array }) public data: DataTableRowData[] = []; @property({ type: Array }) public data: DataTableRowData[] = [];
@property({ type: Boolean }) public selectable = false; @property({ type: Boolean }) public selectable = false;
@property({ type: Boolean }) public hasFab = false;
@property({ type: Boolean, attribute: "auto-height" }) @property({ type: Boolean, attribute: "auto-height" })
public autoHeight = false; public autoHeight = false;
@property({ type: String }) public id = "id"; @property({ type: String }) public id = "id";
@ -98,6 +99,7 @@ export class HaDataTable extends LitElement {
@property({ type: Array }) private _filteredData: DataTableRowData[] = []; @property({ type: Array }) private _filteredData: DataTableRowData[] = [];
@query("slot[name='header']") private _header!: HTMLSlotElement; @query("slot[name='header']") private _header!: HTMLSlotElement;
@query(".mdc-data-table__table") private _table!: HTMLDivElement; @query(".mdc-data-table__table") private _table!: HTMLDivElement;
private _checkableRowsCount?: number; private _checkableRowsCount?: number;
private _checkedRows: string[] = []; private _checkedRows: string[] = [];
private _sortColumns: { private _sortColumns: {
@ -281,75 +283,84 @@ export class HaDataTable extends LitElement {
: html` : html`
<div class="mdc-data-table__content scroller"> <div class="mdc-data-table__content scroller">
${scroll({ ${scroll({
items: this._filteredData, items: !this.hasFab
renderItem: (row: DataTableRowData) => html` ? this._filteredData
<div : [...this._filteredData, ...[{ empty: true }]],
.rowId="${row[this.id]}" renderItem: (row: DataTableRowData) => {
@click=${this._handleRowClick} if (row.empty) {
class="mdc-data-table__row ${classMap({ return html`
"mdc-data-table__row--selected": this._checkedRows.includes( <div class="mdc-data-table__row"></div>
String(row[this.id]) `;
), }
})}" return html`
aria-selected=${ifDefined( <div
this._checkedRows.includes(String(row[this.id])) .rowId="${row[this.id]}"
? true @click=${this._handleRowClick}
: undefined class="mdc-data-table__row ${classMap({
)} "mdc-data-table__row--selected": this._checkedRows.includes(
.selectable=${row.selectable !== false} String(row[this.id])
> ),
${this.selectable })}"
? html` aria-selected=${ifDefined(
<div this._checkedRows.includes(String(row[this.id]))
class="mdc-data-table__cell mdc-data-table__cell--checkbox" ? true
> : undefined
<ha-checkbox )}
class="mdc-data-table__row-checkbox" .selectable=${row.selectable !== false}
@change=${this._handleRowCheckboxClick} >
.disabled=${row.selectable === false} ${this.selectable
.checked=${this._checkedRows.includes( ? html`
String(row[this.id]) <div
)} class="mdc-data-table__cell mdc-data-table__cell--checkbox"
> >
</ha-checkbox> <ha-checkbox
class="mdc-data-table__row-checkbox"
@change=${this._handleRowCheckboxClick}
.disabled=${row.selectable === false}
.checked=${this._checkedRows.includes(
String(row[this.id])
)}
>
</ha-checkbox>
</div>
`
: ""}
${Object.entries(this.columns).map((columnEntry) => {
const [key, column] = columnEntry;
return html`
<div
class="mdc-data-table__cell ${classMap({
"mdc-data-table__cell--numeric": Boolean(
column.type === "numeric"
),
"mdc-data-table__cell--icon": Boolean(
column.type === "icon"
),
"mdc-data-table__cell--icon-button": Boolean(
column.type === "icon-button"
),
grows: Boolean(column.grows),
})}"
style=${column.width
? styleMap({
[column.grows
? "minWidth"
: "width"]: column.width,
maxWidth: column.maxWidth
? column.maxWidth
: "",
})
: ""}
>
${column.template
? column.template(row[key], row)
: row[key]}
</div> </div>
` `;
: ""} })}
${Object.entries(this.columns).map((columnEntry) => { </div>
const [key, column] = columnEntry; `;
return html` },
<div
class="mdc-data-table__cell ${classMap({
"mdc-data-table__cell--numeric": Boolean(
column.type === "numeric"
),
"mdc-data-table__cell--icon": Boolean(
column.type === "icon"
),
"mdc-data-table__cell--icon-button": Boolean(
column.type === "icon-button"
),
grows: Boolean(column.grows),
})}"
style=${column.width
? styleMap({
[column.grows
? "minWidth"
: "width"]: column.width,
maxWidth: column.maxWidth
? column.maxWidth
: "",
})
: ""}
>
${column.template
? column.template(row[key], row)
: row[key]}
</div>
`;
})}
</div>
`,
})} })}
</div> </div>
`} `}

View File

@ -40,6 +40,11 @@ export class HaTabsSubpageDataTable extends LitElement {
* @type {Boolean} * @type {Boolean}
*/ */
@property({ type: Boolean }) public selectable = false; @property({ type: Boolean }) public selectable = false;
/**
* Do we need to add padding for a fab.
* @type {Boolean}
*/
@property({ type: Boolean }) public hasFab = false;
/** /**
* Field with a unique id per entry in data. * Field with a unique id per entry in data.
* @type {String} * @type {String}
@ -95,6 +100,8 @@ export class HaTabsSubpageDataTable extends LitElement {
<slot name="header"> <slot name="header">
<div class="search-toolbar"> <div class="search-toolbar">
<search-input <search-input
.filter=${this.filter}
class="header"
no-label-float no-label-float
no-underline no-underline
@value-changed=${this._handleSearchChange} @value-changed=${this._handleSearchChange}
@ -109,6 +116,7 @@ export class HaTabsSubpageDataTable extends LitElement {
.data=${this.data} .data=${this.data}
.filter=${this.filter} .filter=${this.filter}
.selectable=${this.selectable} .selectable=${this.selectable}
.hasFab=${this.hasFab}
.id=${this.id} .id=${this.id}
.noDataText=${this.noDataText} .noDataText=${this.noDataText}
> >
@ -119,6 +127,7 @@ export class HaTabsSubpageDataTable extends LitElement {
<slot name="header"> <slot name="header">
<div class="table-header"> <div class="table-header">
<search-input <search-input
.filter=${this.filter}
no-label-float no-label-float
no-underline no-underline
@value-changed=${this._handleSearchChange} @value-changed=${this._handleSearchChange}
@ -153,13 +162,16 @@ export class HaTabsSubpageDataTable extends LitElement {
border-bottom: 1px solid rgba(var(--rgb-primary-text-color), 0.12); border-bottom: 1px solid rgba(var(--rgb-primary-text-color), 0.12);
} }
.search-toolbar { .search-toolbar {
margin-left: -24px;
color: var(--secondary-text-color); color: var(--secondary-text-color);
} }
search-input { search-input {
position: relative; position: relative;
top: 2px; top: 2px;
} }
search-input.header {
left: -8px;
top: -7px;
}
`; `;
} }
} }

View File

@ -45,7 +45,8 @@ class HassTabsSubpage extends LitElement {
activeTab: PageNavigation | undefined, activeTab: PageNavigation | undefined,
showAdvanced: boolean | undefined, showAdvanced: boolean | undefined,
_components, _components,
_language _language,
_narrow
) => { ) => {
const shownTabs = tabs.filter( const shownTabs = tabs.filter(
(page) => (page) =>
@ -101,7 +102,8 @@ class HassTabsSubpage extends LitElement {
this._activeTab, this._activeTab,
this.hass.userData?.showAdvanced, this.hass.userData?.showAdvanced,
this.hass.config.components, this.hass.config.components,
this.hass.language this.hass.language,
this.narrow
); );
return html` return html`
@ -113,7 +115,7 @@ class HassTabsSubpage extends LitElement {
></ha-paper-icon-button-arrow-prev> ></ha-paper-icon-button-arrow-prev>
${this.narrow ${this.narrow
? html` ? html`
<div main-title><slot name="header"></slot></div> <div class="main-title"><slot name="header"></slot></div>
` `
: ""} : ""}
${tabs.length > 1 || !this.narrow ${tabs.length > 1 || !this.narrow
@ -190,10 +192,8 @@ class HassTabsSubpage extends LitElement {
} }
#tabbar:not(.bottom-bar) { #tabbar:not(.bottom-bar) {
margin: auto; flex: 1;
left: 50%; justify-content: center;
position: absolute;
transform: translate(-50%, 0);
} }
.tab { .tab {
@ -228,14 +228,17 @@ class HassTabsSubpage extends LitElement {
ha-menu-button, ha-menu-button,
ha-paper-icon-button-arrow-prev, ha-paper-icon-button-arrow-prev,
::slotted([slot="toolbar-icon"]) { ::slotted([slot="toolbar-icon"]) {
flex-shrink: 0;
pointer-events: auto; pointer-events: auto;
color: var(--sidebar-icon-color); color: var(--sidebar-icon-color);
} }
[main-title] { .main-title {
margin: 0 0 0 24px; flex: 1;
overflow: hidden;
text-overflow: ellipsis;
max-height: 40px;
line-height: 20px; line-height: 20px;
flex-grow: 1;
} }
.content { .content {
@ -247,11 +250,6 @@ class HassTabsSubpage extends LitElement {
-webkit-overflow-scrolling: touch; -webkit-overflow-scrolling: touch;
} }
#toolbar-icon {
position: absolute;
right: 16px;
}
:host([narrow]) .content { :host([narrow]) .content {
height: calc(100% - 128px); height: calc(100% - 128px);
} }

View File

@ -82,9 +82,10 @@ class NotificationManager extends LitElement {
static get styles(): CSSResult { static get styles(): CSSResult {
return css` return css`
:host { ha-toast {
display: flex; display: flex;
align-items: center; align-items: center;
justify-content: space-between;
} }
mwc-button { mwc-button {
color: var(--primary-color); color: var(--primary-color);

View File

@ -108,6 +108,7 @@ export class HaConfigAreasDashboard extends LitElement {
"ui.panel.config.areas.picker.no_areas" "ui.panel.config.areas.picker.no_areas"
)} )}
id="area_id" id="area_id"
hasFab
> >
<paper-icon-button <paper-icon-button
slot="toolbar-icon" slot="toolbar-icon"

View File

@ -160,6 +160,7 @@ class HaAutomationPicker extends LitElement {
.noDataText=${this.hass.localize( .noDataText=${this.hass.localize(
"ui.panel.config.automation.picker.no_automations" "ui.panel.config.automation.picker.no_automations"
)} )}
hasFab
> >
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<ha-fab <ha-fab

View File

@ -108,7 +108,7 @@ export class HaConfigEntities extends SubscribeMixin(LitElement) {
type: "icon", type: "icon",
sortable: true, sortable: true,
filterable: true, filterable: true,
width: "55px", width: "68px",
template: (_status, entity: any) => template: (_status, entity: any) =>
entity.unavailable || entity.disabled_by || entity.readonly entity.unavailable || entity.disabled_by || entity.readonly
? html` ? html`
@ -169,7 +169,7 @@ export class HaConfigEntities extends SubscribeMixin(LitElement) {
), ),
sortable: true, sortable: true,
filterable: true, filterable: true,
width: "20%", width: "25%",
}; };
columns.platform = { columns.platform = {
title: this.hass.localize( title: this.hass.localize(

View File

@ -152,8 +152,6 @@ class HaPanelConfig extends HassRouterPage {
protected routerOptions: RouterOptions = { protected routerOptions: RouterOptions = {
defaultPage: "dashboard", defaultPage: "dashboard",
cacheAll: true,
preloadAll: true,
routes: { routes: {
areas: { areas: {
tag: "ha-config-areas", tag: "ha-config-areas",

View File

@ -148,6 +148,7 @@ export class HaConfigHelpers extends LitElement {
.columns=${this._columns(this.narrow, this.hass.language)} .columns=${this._columns(this.narrow, this.hass.language)}
.data=${this._getItems(this._stateItems)} .data=${this._getItems(this._stateItems)}
@row-click=${this._openEditDialog} @row-click=${this._openEditDialog}
hasFab
> >
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<ha-fab <ha-fab

View File

@ -104,7 +104,7 @@ export class HaConfigLovelaceDashboards extends LitElement {
), ),
sortable: true, sortable: true,
filterable: true, filterable: true,
width: "15%", width: "20%",
template: (mode) => template: (mode) =>
html` html`
${this.hass.localize( ${this.hass.localize(
@ -143,7 +143,7 @@ export class HaConfigLovelaceDashboards extends LitElement {
"ui.panel.config.lovelace.dashboards.picker.headers.sidebar" "ui.panel.config.lovelace.dashboards.picker.headers.sidebar"
), ),
type: "icon", type: "icon",
width: "100px", width: "121px",
template: (sidebar) => template: (sidebar) =>
sidebar sidebar
? html` ? html`
@ -229,6 +229,7 @@ export class HaConfigLovelaceDashboards extends LitElement {
.data=${this._getItems(this._dashboards)} .data=${this._getItems(this._dashboards)}
@row-click=${this._editDashboard} @row-click=${this._editDashboard}
id="url_path" id="url_path"
hasFab
> >
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<ha-fab <ha-fab

View File

@ -97,6 +97,7 @@ export class HaConfigLovelaceRescources extends LitElement {
"ui.panel.config.lovelace.resources.picker.no_resources" "ui.panel.config.lovelace.resources.picker.no_resources"
)} )}
@row-click=${this._editResource} @row-click=${this._editResource}
hasFab
> >
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<ha-fab <ha-fab

View File

@ -131,6 +131,7 @@ class HaSceneDashboard extends LitElement {
.noDataText=${this.hass.localize( .noDataText=${this.hass.localize(
"ui.panel.config.scene.picker.no_scenes" "ui.panel.config.scene.picker.no_scenes"
)} )}
hasFab
> >
<paper-icon-button <paper-icon-button
slot="toolbar-icon" slot="toolbar-icon"

View File

@ -126,6 +126,7 @@ class HaScriptPicker extends LitElement {
.noDataText=${this.hass.localize( .noDataText=${this.hass.localize(
"ui.panel.config.script.picker.no_scripts" "ui.panel.config.script.picker.no_scripts"
)} )}
hasFab
> >
<paper-icon-button <paper-icon-button
slot="toolbar-icon" slot="toolbar-icon"

View File

@ -94,6 +94,7 @@ export class HaConfigUsers extends LitElement {
.columns=${this._columns(this.hass.language)} .columns=${this._columns(this.hass.language)}
.data=${this._users} .data=${this._users}
@row-click=${this._editUser} @row-click=${this._editUser}
hasFab
> >
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<ha-fab <ha-fab

View File

@ -19,7 +19,7 @@ import {
addGroup, addGroup,
ZHAGroup, ZHAGroup,
} from "../../../data/zha"; } from "../../../data/zha";
import { ZHADevicesDataTable } from "./zha-devices-data-table"; import "./zha-devices-data-table";
import { SelectionChangedEvent } from "../../../components/data-table/ha-data-table"; import { SelectionChangedEvent } from "../../../components/data-table/ha-data-table";
import { navigate } from "../../../common/navigate"; import { navigate } from "../../../common/navigate";
import { PolymerChangedEvent } from "../../../polymer-types"; import { PolymerChangedEvent } from "../../../polymer-types";
@ -27,6 +27,8 @@ import "@polymer/paper-spinner/paper-spinner";
import "@material/mwc-button"; import "@material/mwc-button";
import { PaperInputElement } from "@polymer/paper-input/paper-input"; import { PaperInputElement } from "@polymer/paper-input/paper-input";
import { HASSDomEvent } from "../../../common/dom/fire_event"; import { HASSDomEvent } from "../../../common/dom/fire_event";
// tslint:disable-next-line: no-duplicate-imports
import { ZHADevicesDataTable } from "./zha-devices-data-table";
@customElement("zha-add-group-page") @customElement("zha-add-group-page")
export class ZHAAddGroupPage extends LitElement { export class ZHAAddGroupPage extends LitElement {

View File

@ -13,8 +13,6 @@ class ZHAConfigDashboardRouter extends HassRouterPage {
protected routerOptions: RouterOptions = { protected routerOptions: RouterOptions = {
defaultPage: "dashboard", defaultPage: "dashboard",
cacheAll: true,
preloadAll: true,
showLoading: true, showLoading: true,
routes: { routes: {
dashboard: { dashboard: {

View File

@ -27,13 +27,15 @@ import {
Cluster, Cluster,
fetchClustersForZhaNode, fetchClustersForZhaNode,
} from "../../../data/zha"; } from "../../../data/zha";
import { ZHAClustersDataTable } from "./zha-clusters-data-table"; import "./zha-clusters-data-table";
import { haStyle } from "../../../resources/styles"; import { haStyle } from "../../../resources/styles";
import { HomeAssistant } from "../../../types"; import { HomeAssistant } from "../../../types";
import { ItemSelectedEvent } from "./types"; import { ItemSelectedEvent } from "./types";
import "@polymer/paper-item/paper-item"; import "@polymer/paper-item/paper-item";
import { SelectionChangedEvent } from "../../../components/data-table/ha-data-table"; import { SelectionChangedEvent } from "../../../components/data-table/ha-data-table";
import { HASSDomEvent } from "../../../common/dom/fire_event"; import { HASSDomEvent } from "../../../common/dom/fire_event";
// tslint:disable-next-line: no-duplicate-imports
import { ZHAClustersDataTable } from "./zha-clusters-data-table";
@customElement("zha-group-binding-control") @customElement("zha-group-binding-control")
export class ZHAGroupBindingControl extends LitElement { export class ZHAGroupBindingControl extends LitElement {
@ -48,7 +50,7 @@ export class ZHAGroupBindingControl extends LitElement {
@property() private _clusters: Cluster[] = []; @property() private _clusters: Cluster[] = [];
private _groupToBind?: ZHAGroup; private _groupToBind?: ZHAGroup;
private _clustersToBind?: Cluster[]; private _clustersToBind?: Cluster[];
@query("zha-devices-data-table") @query("zha-clusters-data-table")
private _zhaClustersDataTable!: ZHAClustersDataTable; private _zhaClustersDataTable!: ZHAClustersDataTable;
protected updated(changedProperties: PropertyValues): void { protected updated(changedProperties: PropertyValues): void {

View File

@ -5,6 +5,7 @@ import { createCardElement } from "../create-element/create-card-element";
import { LovelaceCard, LovelaceCardEditor } from "../types"; import { LovelaceCard, LovelaceCardEditor } from "../types";
import { computeCardSize } from "../common/compute-card-size"; import { computeCardSize } from "../common/compute-card-size";
import { ConditionalCardConfig } from "./types"; import { ConditionalCardConfig } from "./types";
import { LovelaceCardConfig } from "../../../data/lovelace";
@customElement("hui-conditional-card") @customElement("hui-conditional-card")
class HuiConditionalCard extends HuiConditionalBase implements LovelaceCard { class HuiConditionalCard extends HuiConditionalBase implements LovelaceCard {
@ -19,7 +20,8 @@ class HuiConditionalCard extends HuiConditionalBase implements LovelaceCard {
return { return {
type: "conditional", type: "conditional",
conditions: [], conditions: [],
card: { type: "" }, // @ts-ignore
card: {},
}; };
} }
@ -30,17 +32,35 @@ class HuiConditionalCard extends HuiConditionalBase implements LovelaceCard {
throw new Error("No card configured."); throw new Error("No card configured.");
} }
if (this._element && this._element.parentElement) { this._element = this._createCardElement(config.card);
this.removeChild(this._element);
}
this._element = createCardElement(config.card) as LovelaceCard;
this.appendChild(this._element);
} }
public getCardSize(): number { public getCardSize(): number {
return computeCardSize(this._element as LovelaceCard); return computeCardSize(this._element as LovelaceCard);
} }
private _createCardElement(cardConfig: LovelaceCardConfig) {
const element = createCardElement(cardConfig) as LovelaceCard;
if (this.hass) {
element.hass = this.hass;
}
element.addEventListener(
"ll-rebuild",
(ev) => {
ev.stopPropagation();
this._rebuildCard(cardConfig);
},
{ once: true }
);
return element;
}
private _rebuildCard(config: LovelaceCardConfig): void {
this._element = this._createCardElement(config);
if (this.lastChild) {
this.replaceChild(this._element, this.lastChild);
}
}
} }
declare global { declare global {

View File

@ -187,6 +187,9 @@ class HuiEntitiesCard extends LitElement implements LovelaceCard {
return css` return css`
ha-card { ha-card {
height: 100%; height: 100%;
display: flex;
flex-direction: column;
justify-content: space-between;
} }
.card-header { .card-header {
display: flex; display: flex;
@ -199,6 +202,10 @@ class HuiEntitiesCard extends LitElement implements LovelaceCard {
text-overflow: ellipsis; text-overflow: ellipsis;
} }
#states {
flex: 1;
}
#states > * { #states > * {
margin: 8px 0; margin: 8px 0;
} }

View File

@ -189,6 +189,12 @@ export class HuiEntityCard extends LitElement implements LovelaceCard {
static get styles(): CSSResult { static get styles(): CSSResult {
return css` return css`
ha-card {
height: 100%;
display: flex;
flex-direction: column;
justify-content: space-between;
}
ha-card > div { ha-card > div {
cursor: pointer; cursor: pointer;
} }

View File

@ -9,6 +9,7 @@ import { evaluateFilter } from "../common/evaluate-filter";
class EntityFilterCard extends HTMLElement implements LovelaceCard { class EntityFilterCard extends HTMLElement implements LovelaceCard {
public isPanel?: boolean; public isPanel?: boolean;
private _editMode = false;
private _element?: LovelaceCard; private _element?: LovelaceCard;
private _config?: EntityFilterCardConfig; private _config?: EntityFilterCardConfig;
private _configEntities?: EntityFilterEntityConfig[]; private _configEntities?: EntityFilterEntityConfig[];
@ -51,6 +52,14 @@ class EntityFilterCard extends HTMLElement implements LovelaceCard {
} }
} }
set editMode(editMode: boolean) {
this._editMode = editMode;
if (!this._element) {
return;
}
this._element.editMode = editMode;
}
set hass(hass: HomeAssistant) { set hass(hass: HomeAssistant) {
if (!hass || !this._config) { if (!hass || !this._config) {
return; return;
@ -114,6 +123,7 @@ class EntityFilterCard extends HTMLElement implements LovelaceCard {
} }
element.isPanel = this.isPanel; element.isPanel = this.isPanel;
element.editMode = this._editMode;
element.hass = hass; element.hass = hass;
} }

View File

@ -125,16 +125,17 @@ export class HuiLightCard extends LitElement implements LovelaceCard {
<div class="content"> <div class="content">
<div id="controls"> <div id="controls">
<div id="slider"> <div id="slider">
${supportsFeature(stateObj, SUPPORT_BRIGHTNESS) <round-slider
? html` min="0"
<round-slider .value=${brightness}
min="0" @value-changing=${this._dragEvent}
.value=${brightness} @value-changed=${this._setBrightness}
@value-changing=${this._dragEvent} style=${styleMap({
@value-changed=${this._setBrightness} visibility: supportsFeature(stateObj, SUPPORT_BRIGHTNESS)
></round-slider> ? "visible"
` : "hidden",
: ""} })}
></round-slider>
<paper-icon-button <paper-icon-button
class="light-button ${classMap({ class="light-button ${classMap({
"slider-center": supportsFeature( "slider-center": supportsFeature(
@ -322,6 +323,13 @@ export class HuiLightCard extends LitElement implements LovelaceCard {
color: var(--paper-item-icon-color, #44739e); color: var(--paper-item-icon-color, #44739e);
width: 60%; width: 60%;
height: auto; height: auto;
position: absolute;
max-width: calc(100% - 40px);
box-sizing: border-box;
border-radius: 100%;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
} }
.light-button.state-on { .light-button.state-on {
@ -332,16 +340,6 @@ export class HuiLightCard extends LitElement implements LovelaceCard {
color: var(--state-icon-unavailable-color); color: var(--state-icon-unavailable-color);
} }
.slider-center {
position: absolute;
max-width: calc(100% - 40px);
box-sizing: border-box;
border-radius: 100%;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
#info { #info {
text-align: center; text-align: center;
margin-top: -56px; margin-top: -56px;

View File

@ -79,6 +79,7 @@ class HuiMapCard extends LitElement implements LovelaceCard {
@property() @property()
private _history?: HassEntity[][]; private _history?: HassEntity[][];
private _date?: Date; private _date?: Date;
private _loaded = false;
@property() @property()
private _config?: MapCardConfig; private _config?: MapCardConfig;
@ -282,6 +283,10 @@ class HuiMapCard extends LitElement implements LovelaceCard {
} }
private async loadMap(): Promise<void> { private async loadMap(): Promise<void> {
if (this._loaded) {
return;
}
this._loaded = true;
[this._leafletMap, this.Leaflet] = await setupLeafletMap( [this._leafletMap, this.Leaflet] = await setupLeafletMap(
this._mapEl, this._mapEl,
this._config !== undefined ? this._config.dark_mode === true : false this._config !== undefined ? this._config.dark_mode === true : false

View File

@ -27,6 +27,7 @@ import {
import { ShoppingListCardConfig, SensorCardConfig } from "./types"; import { ShoppingListCardConfig, SensorCardConfig } from "./types";
import { applyThemesOnElement } from "../../../common/dom/apply_themes_on_element"; import { applyThemesOnElement } from "../../../common/dom/apply_themes_on_element";
import { actionHandler } from "../common/directives/action-handler-directive"; import { actionHandler } from "../common/directives/action-handler-directive";
import { classMap } from "lit-html/directives/class-map";
@customElement("hui-shopping-list-card") @customElement("hui-shopping-list-card")
class HuiShoppingListCard extends LitElement implements LovelaceCard { class HuiShoppingListCard extends LitElement implements LovelaceCard {
@ -108,7 +109,12 @@ class HuiShoppingListCard extends LitElement implements LovelaceCard {
} }
return html` return html`
<ha-card .header="${this._config.title}"> <ha-card
.header=${this._config.title}
class=${classMap({
"has-header": "title" in this._config,
})}
>
<div class="addRow"> <div class="addRow">
<ha-icon <ha-icon
class="addButton" class="addButton"
@ -209,6 +215,15 @@ class HuiShoppingListCard extends LitElement implements LovelaceCard {
static get styles(): CSSResult { static get styles(): CSSResult {
return css` return css`
ha-card {
padding-bottom: 16px;
padding-top: 16px;
}
.has-header {
padding-top: 0;
}
.editRow, .editRow,
.addRow { .addRow {
display: flex; display: flex;

View File

@ -5,6 +5,7 @@ import {
CSSResult, CSSResult,
css, css,
property, property,
PropertyValues,
} from "lit-element"; } from "lit-element";
import { createCardElement } from "../create-element/create-card-element"; import { createCardElement } from "../create-element/create-card-element";
@ -25,21 +26,10 @@ export abstract class HuiStackCard extends LitElement implements LovelaceCard {
return { cards: [] }; return { cards: [] };
} }
@property() public hass?: HomeAssistant;
@property() public editMode?: boolean;
@property() protected _cards?: LovelaceCard[]; @property() protected _cards?: LovelaceCard[];
@property() private _config?: StackCardConfig; @property() private _config?: StackCardConfig;
private _hass?: HomeAssistant;
set hass(hass: HomeAssistant) {
this._hass = hass;
if (!this._cards) {
return;
}
for (const element of this._cards) {
element.hass = this._hass;
}
}
public getCardSize(): number { public getCardSize(): number {
return 1; return 1;
@ -56,6 +46,21 @@ export abstract class HuiStackCard extends LitElement implements LovelaceCard {
}); });
} }
protected updated(changedProps: PropertyValues) {
super.updated(changedProps);
if (
!this._cards ||
(!changedProps.has("hass") && !changedProps.has("editMode"))
) {
return;
}
for (const element of this._cards) {
element.hass = this.hass;
element.editMode = this.editMode;
}
}
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this._config || !this._cards) { if (!this._config || !this._cards) {
return html``; return html``;
@ -87,8 +92,8 @@ export abstract class HuiStackCard extends LitElement implements LovelaceCard {
private _createCardElement(cardConfig: LovelaceCardConfig) { private _createCardElement(cardConfig: LovelaceCardConfig) {
const element = createCardElement(cardConfig) as LovelaceCard; const element = createCardElement(cardConfig) as LovelaceCard;
if (this._hass) { if (this.hass) {
element.hass = this._hass; element.hass = this.hass;
} }
element.addEventListener( element.addEventListener(
"ll-rebuild", "ll-rebuild",

View File

@ -239,24 +239,26 @@ export class HuiThermostatCard extends LitElement implements LovelaceCard {
tabindex="0" tabindex="0"
></paper-icon-button> ></paper-icon-button>
<div id="controls"> <div class="content">
<div id="slider"> <div id="controls">
${slider} <div id="slider">
<div id="slider-center"> ${slider}
<div id="temperature"> <div id="slider-center">
${currentTemperature} ${setValues} <div id="temperature">
${currentTemperature} ${setValues}
</div>
</div> </div>
</div> </div>
</div> </div>
</div> <div id="info">
<div id="info"> <div id="modes">
<div id="modes"> ${(stateObj.attributes.hvac_modes || [])
${(stateObj.attributes.hvac_modes || []) .concat()
.concat() .sort(compareClimateHvacModes)
.sort(compareClimateHvacModes) .map((modeItem) => this._renderIcon(modeItem, mode))}
.map((modeItem) => this._renderIcon(modeItem, mode))} </div>
${name}
</div> </div>
${name}
</div> </div>
</ha-card> </ha-card>
`; `;
@ -423,6 +425,7 @@ export class HuiThermostatCard extends LitElement implements LovelaceCard {
} }
ha-card { ha-card {
height: 100%;
position: relative; position: relative;
overflow: hidden; overflow: hidden;
--name-font-size: 1.2rem; --name-font-size: 1.2rem;
@ -481,6 +484,13 @@ export class HuiThermostatCard extends LitElement implements LovelaceCard {
z-index: 25; z-index: 25;
} }
.content {
height: 100%;
display: flex;
flex-direction: column;
justify-content: center;
}
#controls { #controls {
display: flex; display: flex;
justify-content: center; justify-content: center;

View File

@ -36,7 +36,7 @@ export class HuiCardOptions extends LitElement {
<ha-card> <ha-card>
<div class="options"> <div class="options">
<div class="primary-actions"> <div class="primary-actions">
<mwc-button @click="${this._editCard}" <mwc-button @click=${this._editCard}
>${this.hass!.localize( >${this.hass!.localize(
"ui.panel.lovelace.editor.edit_card.edit" "ui.panel.lovelace.editor.edit_card.edit"
)}</mwc-button )}</mwc-button
@ -47,17 +47,17 @@ export class HuiCardOptions extends LitElement {
title="Move card down" title="Move card down"
class="move-arrow" class="move-arrow"
icon="hass:arrow-down" icon="hass:arrow-down"
@click="${this._cardDown}" @click=${this._cardDown}
?disabled="${this.lovelace!.config.views[this.path![0]].cards! ?disabled=${this.lovelace!.config.views[this.path![0]].cards!
.length === .length ===
this.path![1] + 1}" this.path![1] + 1}
></paper-icon-button> ></paper-icon-button>
<paper-icon-button <paper-icon-button
title="Move card up" title="Move card up"
class="move-arrow" class="move-arrow"
icon="hass:arrow-up" icon="hass:arrow-up"
@click="${this._cardUp}" @click=${this._cardUp}
?disabled="${this.path![1] === 0}" ?disabled=${this.path![1] === 0}
></paper-icon-button> ></paper-icon-button>
<paper-menu-button <paper-menu-button
horizontal-align="right" horizontal-align="right"
@ -73,7 +73,7 @@ export class HuiCardOptions extends LitElement {
)} )}
></paper-icon-button> ></paper-icon-button>
<paper-listbox slot="dropdown-content"> <paper-listbox slot="dropdown-content">
<paper-item @tap="${this._moveCard}"> <paper-item @tap=${this._moveCard}>
${this.hass!.localize( ${this.hass!.localize(
"ui.panel.lovelace.editor.edit_card.move" "ui.panel.lovelace.editor.edit_card.move"
)}</paper-item )}</paper-item
@ -83,7 +83,7 @@ export class HuiCardOptions extends LitElement {
"ui.panel.lovelace.editor.edit_card.duplicate" "ui.panel.lovelace.editor.edit_card.duplicate"
)}</paper-item )}</paper-item
> >
<paper-item .class="delete-item" @tap="${this._deleteCard}"> <paper-item class="delete-item" @tap=${this._deleteCard}>
${this.hass!.localize( ${this.hass!.localize(
"ui.panel.lovelace.editor.edit_card.delete" "ui.panel.lovelace.editor.edit_card.delete"
)}</paper-item )}</paper-item
@ -99,6 +99,7 @@ export class HuiCardOptions extends LitElement {
static get styles(): CSSResult { static get styles(): CSSResult {
return css` return css`
:host(:hover) { :host(:hover) {
overflow: hidden;
outline: 2px solid var(--primary-color); outline: 2px solid var(--primary-color);
} }
@ -140,6 +141,10 @@ export class HuiCardOptions extends LitElement {
padding: 0; padding: 0;
} }
paper-listbox {
padding: 0;
}
paper-item.header { paper-item.header {
color: var(--primary-text-color); color: var(--primary-text-color);
text-transform: uppercase; text-transform: uppercase;
@ -149,6 +154,7 @@ export class HuiCardOptions extends LitElement {
paper-item { paper-item {
cursor: pointer; cursor: pointer;
white-space: nowrap;
} }
paper-item.delete-item { paper-item.delete-item {

View File

@ -12,6 +12,7 @@ import { ConditionalCardConfig } from "../cards/types";
@customElement("hui-conditional-base") @customElement("hui-conditional-base")
export class HuiConditionalBase extends UpdatingElement { export class HuiConditionalBase extends UpdatingElement {
@property() public hass?: HomeAssistant; @property() public hass?: HomeAssistant;
@property() public editMode?: boolean;
@property() protected _config?: ConditionalCardConfig | ConditionalRowConfig; @property() protected _config?: ConditionalCardConfig | ConditionalRowConfig;
protected _element?: LovelaceCard | LovelaceRow; protected _element?: LovelaceCard | LovelaceRow;
@ -30,8 +31,11 @@ export class HuiConditionalBase extends UpdatingElement {
throw new Error("Conditions are invalid."); throw new Error("Conditions are invalid.");
} }
if (this.lastChild) {
this.removeChild(this.lastChild);
}
this._config = config; this._config = config;
this.style.display = "none";
} }
protected update(): void { protected update(): void {
@ -39,13 +43,19 @@ export class HuiConditionalBase extends UpdatingElement {
return; return;
} }
const visible = checkConditionsMet(this._config.conditions, this.hass); this._element.editMode = this.editMode;
const visible =
this.editMode || checkConditionsMet(this._config.conditions, this.hass);
this.style.setProperty("display", visible ? "" : "none");
if (visible) { if (visible) {
this._element.hass = this.hass; this._element.hass = this.hass;
if (!this._element.parentElement) {
this.appendChild(this._element);
}
} }
this.style.setProperty("display", visible ? "" : "none");
} }
} }

View File

@ -25,15 +25,18 @@ import { EntityConfig } from "../../entity-rows/types";
import { getCardElementClass } from "../../create-element/create-card-element"; import { getCardElementClass } from "../../create-element/create-card-element";
import { GUIModeChangedEvent } from "../types"; import { GUIModeChangedEvent } from "../types";
export interface ConfigChangedEvent {
config: LovelaceCardConfig;
error?: string;
guiModeAvailable?: boolean;
}
declare global { declare global {
interface HASSDomEvents { interface HASSDomEvents {
"entities-changed": { "entities-changed": {
entities: EntityConfig[]; entities: EntityConfig[];
}; };
"config-changed": { "config-changed": ConfigChangedEvent;
config: LovelaceCardConfig;
error?: string;
};
"GUImode-changed": GUIModeChangedEvent; "GUImode-changed": GUIModeChangedEvent;
} }
} }
@ -75,6 +78,7 @@ export class HuiCardEditor extends LitElement {
fireEvent(this, "config-changed", { fireEvent(this, "config-changed", {
config: this.value!, config: this.value!,
error: this._error, error: this._error,
guiModeAvailable: !(this.hasWarning || this.hasError),
}); });
} }
@ -101,7 +105,10 @@ export class HuiCardEditor extends LitElement {
public set GUImode(guiMode: boolean) { public set GUImode(guiMode: boolean) {
this._GUImode = guiMode; this._GUImode = guiMode;
fireEvent(this as HTMLElement, "GUImode-changed", { guiMode }); fireEvent(this as HTMLElement, "GUImode-changed", {
guiMode,
guiModeAvailable: !(this.hasWarning || this.hasError),
});
} }
private get _yamlEditor(): HaCodeEditor { private get _yamlEditor(): HaCodeEditor {
@ -174,6 +181,13 @@ export class HuiCardEditor extends LitElement {
} }
fireEvent(this as HTMLElement, "iron-resize"); fireEvent(this as HTMLElement, "iron-resize");
} }
if (this._configElement && changedProperties.has("hass")) {
this._configElement.hass = this.hass;
}
if (this._configElement && changedProperties.has("lovelace")) {
this._configElement.lovelace = this.lovelace;
}
} }
private _refreshYamlEditor(focus = false) { private _refreshYamlEditor(focus = false) {
@ -232,6 +246,13 @@ export class HuiCardEditor extends LitElement {
this._configElement = configElement; this._configElement = configElement;
this._configElType = cardType; this._configElType = cardType;
// Perform final setup
this._configElement.hass = this.hass;
this._configElement.lovelace = this.lovelace;
this._configElement.addEventListener("config-changed", (ev) =>
this._handleUIConfigChanged(ev as UIConfigChangedEvent)
);
} }
// Setup GUI editor and check that it can handle the current config // Setup GUI editor and check that it can handle the current config
@ -240,16 +261,6 @@ export class HuiCardEditor extends LitElement {
} catch (err) { } catch (err) {
throw Error(`WARNING: ${err.message}`); throw Error(`WARNING: ${err.message}`);
} }
// Perform final setup
this._configElement!.hass = this.hass;
this._configElement!.lovelace = this.lovelace;
this._configElement!.addEventListener("config-changed", (ev) =>
this._handleUIConfigChanged(ev as UIConfigChangedEvent)
);
this.GUImode = true;
return;
} catch (err) { } catch (err) {
if (err.message.startsWith("WARNING:")) { if (err.message.startsWith("WARNING:")) {
this._warning = err.message.substr(8); this._warning = err.message.substr(8);

View File

@ -200,6 +200,7 @@ export class HuiCardPicker extends LitElement {
background: var(--primary-background-color, #fafafa); background: var(--primary-background-color, #fafafa);
cursor: pointer; cursor: pointer;
box-sizing: border-box; box-sizing: border-box;
position: relative;
} }
.card-header { .card-header {
@ -242,6 +243,13 @@ export class HuiCardPicker extends LitElement {
align-items: center; align-items: center;
justify-content: center; justify-content: center;
} }
.overlay {
position: absolute;
width: 100%;
height: 100%;
z-index: 1;
}
`, `,
]; ];
} }
@ -297,7 +305,12 @@ export class HuiCardPicker extends LitElement {
} }
return html` return html`
<div class="card" @click="${this._cardPicked}" .config="${cardConfig}"> <div class="card">
<div
class="overlay"
@click=${this._cardPicked}
.config=${cardConfig}
></div>
<div <div
class="preview ${classMap({ class="preview ${classMap({
description: !element || element.tagName === "HUI-ERROR-CARD", description: !element || element.tagName === "HUI-ERROR-CARD",

View File

@ -19,7 +19,7 @@ import {
} from "../../../../data/lovelace"; } from "../../../../data/lovelace";
import "./hui-card-editor"; import "./hui-card-editor";
// tslint:disable-next-line // tslint:disable-next-line
import { HuiCardEditor } from "./hui-card-editor"; import { HuiCardEditor, ConfigChangedEvent } from "./hui-card-editor";
import "./hui-card-preview"; import "./hui-card-preview";
import "./hui-card-picker"; import "./hui-card-picker";
import { EditCardDialogParams } from "./show-edit-card-dialog"; import { EditCardDialogParams } from "./show-edit-card-dialog";
@ -52,12 +52,15 @@ export class HuiDialogEditCard extends LitElement {
@property() private _saving: boolean = false; @property() private _saving: boolean = false;
@property() private _error?: string; @property() private _error?: string;
@property() private _guiModeAvailable? = true;
@query("hui-card-editor") private _cardEditorEl?: HuiCardEditor; @query("hui-card-editor") private _cardEditorEl?: HuiCardEditor;
@property() private _GUImode?: boolean; @property() private _GUImode = true;
public async showDialog(params: EditCardDialogParams): Promise<void> { public async showDialog(params: EditCardDialogParams): Promise<void> {
this._params = params; this._params = params;
this._GUImode = true;
this._guiModeAvailable = true;
const [view, card] = params.path; const [view, card] = params.path;
this._viewConfig = params.lovelaceConfig.views[view]; this._viewConfig = params.lovelaceConfig.views[view];
this._cardConfig = this._cardConfig =
@ -139,8 +142,7 @@ export class HuiDialogEditCard extends LitElement {
? html` ? html`
<mwc-button <mwc-button
@click=${this._toggleMode} @click=${this._toggleMode}
?disabled=${this._cardEditorEl?.hasWarning || .disabled=${!this._guiModeAvailable}
this._cardEditorEl?.hasError}
class="gui-mode-button" class="gui-mode-button"
> >
${this.hass!.localize( ${this.hass!.localize(
@ -288,9 +290,10 @@ export class HuiDialogEditCard extends LitElement {
this._error = ev.detail.error; this._error = ev.detail.error;
} }
private _handleConfigChanged(ev) { private _handleConfigChanged(ev: HASSDomEvent<ConfigChangedEvent>) {
this._cardConfig = deepFreeze(ev.detail.config); this._cardConfig = deepFreeze(ev.detail.config);
this._error = ev.detail.error; this._error = ev.detail.error;
this._guiModeAvailable = ev.detail.guiModeAvailable;
} }
private _handleKeyUp(ev: KeyboardEvent) { private _handleKeyUp(ev: KeyboardEvent) {
@ -302,6 +305,7 @@ export class HuiDialogEditCard extends LitElement {
private _handleGUIModeChanged(ev: HASSDomEvent<GUIModeChangedEvent>): void { private _handleGUIModeChanged(ev: HASSDomEvent<GUIModeChangedEvent>): void {
ev.stopPropagation(); ev.stopPropagation();
this._GUImode = ev.detail.guiMode; this._GUImode = ev.detail.guiMode;
this._guiModeAvailable = ev.detail.guiModeAvailable;
} }
private _toggleMode(): void { private _toggleMode(): void {

View File

@ -60,7 +60,7 @@ export class HuiAlarmPanelCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -88,7 +88,7 @@ export class HuiButtonCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -6,18 +6,24 @@ import {
property, property,
CSSResult, CSSResult,
css, css,
query,
} from "lit-element"; } from "lit-element";
import "@polymer/paper-tabs"; import "@polymer/paper-tabs";
import { struct } from "../../common/structs/struct"; import { struct } from "../../common/structs/struct";
import { HomeAssistant } from "../../../../types"; import { HomeAssistant } from "../../../../types";
import { LovelaceCardEditor } from "../../types"; import { LovelaceCardEditor } from "../../types";
import { StackCardConfig } from "../../cards/types"; import { ConditionalCardConfig } from "../../cards/types";
import { fireEvent } from "../../../../common/dom/fire_event"; import { fireEvent, HASSDomEvent } from "../../../../common/dom/fire_event";
import { LovelaceConfig } from "../../../../data/lovelace"; import { LovelaceConfig } from "../../../../data/lovelace";
import "../../../../components/entity/ha-entity-picker"; import "../../../../components/entity/ha-entity-picker";
import "../../../../components/ha-switch"; import "../../../../components/ha-switch";
import {
HuiCardEditor,
ConfigChangedEvent,
} from "../card-editor/hui-card-editor";
import { GUIModeChangedEvent } from "../types";
const conditionStruct = struct({ const conditionStruct = struct({
entity: "string", entity: "string",
@ -35,10 +41,13 @@ export class HuiConditionalCardEditor extends LitElement
implements LovelaceCardEditor { implements LovelaceCardEditor {
@property() public hass?: HomeAssistant; @property() public hass?: HomeAssistant;
@property() public lovelace?: LovelaceConfig; @property() public lovelace?: LovelaceConfig;
@property() private _config?: StackCardConfig; @property() private _config?: ConditionalCardConfig;
@property() private _GUImode = true;
@property() private _guiModeAvailable? = true;
@property() private _cardTab: boolean = false; @property() private _cardTab: boolean = false;
@query("hui-card-editor") private _cardEditorEl?: HuiCardEditor;
public setConfig(config: StackCardConfig): void { public setConfig(config: ConditionalCardConfig): void {
this._config = cardConfigStruct(config); this._config = cardConfigStruct(config);
} }
@ -66,9 +75,20 @@ export class HuiConditionalCardEditor extends LitElement
${this._cardTab ${this._cardTab
? html` ? html`
<div class="card"> <div class="card">
${this._config.card.type ${this._config.card.type !== undefined
? html` ? html`
<div class="card-options"> <div class="card-options">
<mwc-button
@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>
<mwc-button @click=${this._handleReplaceCard} <mwc-button @click=${this._handleReplaceCard}
>${this.hass!.localize( >${this.hass!.localize(
"ui.panel.lovelace.editor.card.conditional.change_type" "ui.panel.lovelace.editor.card.conditional.change_type"
@ -80,13 +100,14 @@ export class HuiConditionalCardEditor extends LitElement
.value=${this._config.card} .value=${this._config.card}
.lovelace=${this.lovelace} .lovelace=${this.lovelace}
@config-changed=${this._handleCardChanged} @config-changed=${this._handleCardChanged}
@GUImode-changed=${this._handleGUIModeChanged}
></hui-card-editor> ></hui-card-editor>
` `
: html` : html`
<hui-card-picker <hui-card-picker
.hass=${this.hass} .hass=${this.hass}
.lovelace=${this.lovelace} .lovelace=${this.lovelace}
@config-changed=${this._handleCardChanged} @config-changed=${this._handleCardPicked}
></hui-card-picker> ></hui-card-picker>
`} `}
</div> </div>
@ -162,18 +183,49 @@ export class HuiConditionalCardEditor extends LitElement
this._cardTab = parseInt((ev.target! as any).selected!, 10) === 1; this._cardTab = parseInt((ev.target! as any).selected!, 10) === 1;
} }
private _handleCardChanged(ev: CustomEvent): void { private _toggleMode(): void {
this._cardEditorEl?.toggleMode();
}
private _setMode(value: boolean): void {
this._GUImode = value;
if (this._cardEditorEl) {
this._cardEditorEl!.GUImode = value;
}
}
private _handleGUIModeChanged(ev: HASSDomEvent<GUIModeChangedEvent>): void {
ev.stopPropagation();
this._GUImode = ev.detail.guiMode;
this._guiModeAvailable = ev.detail.guiModeAvailable;
}
private _handleCardPicked(ev: CustomEvent): void {
ev.stopPropagation();
if (!this._config) {
return;
}
this._setMode(true);
this._guiModeAvailable = true;
this._config.card = ev.detail.config;
fireEvent(this, "config-changed", { config: this._config });
}
private _handleCardChanged(ev: HASSDomEvent<ConfigChangedEvent>): void {
ev.stopPropagation(); ev.stopPropagation();
if (!this._config) { if (!this._config) {
return; return;
} }
this._config.card = ev.detail.config; this._config.card = ev.detail.config;
this._guiModeAvailable = ev.detail.guiModeAvailable;
fireEvent(this, "config-changed", { config: this._config }); fireEvent(this, "config-changed", { config: this._config });
} }
private _handleReplaceCard(): void { private _handleReplaceCard(): void {
if (!this._config) { if (!this._config) {
return; return;
} }
// @ts-ignore
this._config.card = {}; this._config.card = {};
fireEvent(this, "config-changed", { config: this._config }); fireEvent(this, "config-changed", { config: this._config });
} }
@ -267,6 +319,9 @@ export class HuiConditionalCardEditor extends LitElement
justify-content: flex-end; justify-content: flex-end;
width: 100%; width: 100%;
} }
.gui-mode-button {
margin-right: auto;
}
`; `;
} }
} }

View File

@ -67,7 +67,7 @@ export class HuiEntitiesCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -69,7 +69,7 @@ export class HuiEntityCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -73,7 +73,7 @@ export class HuiGaugeCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -80,7 +80,7 @@ export class HuiGlanceCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -67,7 +67,7 @@ export class HuiHistoryGraphCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -47,7 +47,7 @@ export class HuiIframeCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -72,7 +72,7 @@ export class HuiLightCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -79,7 +79,7 @@ export class HuiMapCardEditor extends LitElement implements LovelaceCardEditor {
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -50,7 +50,7 @@ export class HuiMarkdownCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -37,7 +37,7 @@ export class HuiMediaControlCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -60,7 +60,7 @@ export class HuiPictureCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -100,7 +100,7 @@ export class HuiPictureEntityCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -111,7 +111,7 @@ export class HuiPictureGlanceCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -51,7 +51,7 @@ export class HuiPlantStatusCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -78,7 +78,7 @@ export class HuiSensorCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -46,7 +46,7 @@ export class HuiShoppingListEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -16,7 +16,10 @@ import { LovelaceCardEditor } from "../../types";
import { StackCardConfig } from "../../cards/types"; import { StackCardConfig } from "../../cards/types";
import { fireEvent, HASSDomEvent } from "../../../../common/dom/fire_event"; import { fireEvent, HASSDomEvent } from "../../../../common/dom/fire_event";
import { LovelaceConfig } from "../../../../data/lovelace"; import { LovelaceConfig } from "../../../../data/lovelace";
import { HuiCardEditor } from "../card-editor/hui-card-editor"; import {
HuiCardEditor,
ConfigChangedEvent,
} from "../card-editor/hui-card-editor";
import { GUIModeChangedEvent } from "../types"; import { GUIModeChangedEvent } from "../types";
const cardConfigStruct = struct({ const cardConfigStruct = struct({
@ -32,7 +35,8 @@ export class HuiStackCardEditor extends LitElement
@property() public lovelace?: LovelaceConfig; @property() public lovelace?: LovelaceConfig;
@property() private _config?: StackCardConfig; @property() private _config?: StackCardConfig;
@property() private _selectedCard: number = 0; @property() private _selectedCard: number = 0;
@property() private _GUImode?: boolean; @property() private _GUImode = true;
@property() private _guiModeAvailable? = true;
@query("hui-card-editor") private _cardEditorEl?: HuiCardEditor; @query("hui-card-editor") private _cardEditorEl?: HuiCardEditor;
public setConfig(config: StackCardConfig): void { public setConfig(config: StackCardConfig): void {
@ -52,7 +56,7 @@ export class HuiStackCardEditor extends LitElement
<paper-tabs <paper-tabs
.selected=${selected} .selected=${selected}
scrollable scrollable
@iron-select=${this._handleSelectedCard} @iron-activate=${this._handleSelectedCard}
> >
${this._config.cards.map((_card, i) => { ${this._config.cards.map((_card, i) => {
return html` return html`
@ -65,7 +69,7 @@ export class HuiStackCardEditor extends LitElement
<paper-tabs <paper-tabs
id="add-card" id="add-card"
.selected=${selected === numcards ? "0" : undefined} .selected=${selected === numcards ? "0" : undefined}
@iron-select=${this._handleSelectedCard} @iron-activate=${this._handleSelectedCard}
> >
<paper-tab> <paper-tab>
<ha-icon icon="hass:plus"></ha-icon> <ha-icon icon="hass:plus"></ha-icon>
@ -80,8 +84,7 @@ export class HuiStackCardEditor extends LitElement
<div id="card-options"> <div id="card-options">
<mwc-button <mwc-button
@click=${this._toggleMode} @click=${this._toggleMode}
?disabled=${this._cardEditorEl?.hasWarning || .disabled=${!this._guiModeAvailable}
this._cardEditorEl?.hasError}
class="gui-mode-button" class="gui-mode-button"
> >
${this.hass!.localize( ${this.hass!.localize(
@ -94,7 +97,7 @@ export class HuiStackCardEditor extends LitElement
id="move-before" id="move-before"
title="Move card before" title="Move card before"
icon="hass:arrow-left" icon="hass:arrow-left"
?disabled=${selected === 0} .disabled=${selected === 0}
@click=${this._handleMove} @click=${this._handleMove}
></paper-icon-button> ></paper-icon-button>
@ -102,7 +105,7 @@ export class HuiStackCardEditor extends LitElement
id="move-after" id="move-after"
title="Move card after" title="Move card after"
icon="hass:arrow-right" icon="hass:arrow-right"
?disabled=${selected === numcards - 1} .disabled=${selected === numcards - 1}
@click=${this._handleMove} @click=${this._handleMove}
></paper-icon-button> ></paper-icon-button>
@ -134,18 +137,22 @@ export class HuiStackCardEditor extends LitElement
} }
private _handleSelectedCard(ev) { private _handleSelectedCard(ev) {
this._selectedCard = if (ev.target.id === "add-card") {
ev.target.id === "add-card" this._selectedCard = this._config!.cards.length;
? this._config!.cards.length return;
: parseInt(ev.target.selected, 10); }
this._setMode(true);
this._guiModeAvailable = true;
this._selectedCard = parseInt(ev.detail.selected, 10);
} }
private _handleConfigChanged(ev) { private _handleConfigChanged(ev: HASSDomEvent<ConfigChangedEvent>) {
ev.stopPropagation(); ev.stopPropagation();
if (!this._config) { if (!this._config) {
return; return;
} }
this._config.cards[this._selectedCard] = ev.detail.config; this._config.cards[this._selectedCard] = ev.detail.config;
this._guiModeAvailable = ev.detail.guiModeAvailable;
fireEvent(this, "config-changed", { config: this._config }); fireEvent(this, "config-changed", { config: this._config });
} }
@ -183,12 +190,20 @@ export class HuiStackCardEditor extends LitElement
private _handleGUIModeChanged(ev: HASSDomEvent<GUIModeChangedEvent>): void { private _handleGUIModeChanged(ev: HASSDomEvent<GUIModeChangedEvent>): void {
ev.stopPropagation(); ev.stopPropagation();
this._GUImode = ev.detail.guiMode; this._GUImode = ev.detail.guiMode;
this._guiModeAvailable = ev.detail.guiModeAvailable;
} }
private _toggleMode(): void { private _toggleMode(): void {
this._cardEditorEl?.toggleMode(); this._cardEditorEl?.toggleMode();
} }
private _setMode(value: boolean): void {
this._GUImode = value;
if (this._cardEditorEl) {
this._cardEditorEl!.GUImode = value;
}
}
static get styles(): CSSResult { static get styles(): CSSResult {
return css` return css`
.toolbar { .toolbar {

View File

@ -50,7 +50,7 @@ export class HuiThermostatCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -49,7 +49,7 @@ export class HuiWeatherForecastCardEditor extends LitElement
} }
protected render(): TemplateResult { protected render(): TemplateResult {
if (!this.hass) { if (!this.hass || !this._config) {
return html``; return html``;
} }

View File

@ -119,6 +119,40 @@ export const deleteCard = (
}; };
}; };
export const insertCard = (
config: LovelaceConfig,
path: [number, number],
cardConfig: LovelaceCardConfig
) => {
const [viewIndex, cardIndex] = path;
const views: LovelaceViewConfig[] = [];
config.views.forEach((viewConf, index) => {
if (index !== viewIndex) {
views.push(config.views[index]);
return;
}
const cards = viewConf.cards
? [
...viewConf.cards.slice(0, cardIndex),
cardConfig,
...viewConf.cards.slice(cardIndex),
]
: [cardConfig];
views.push({
...viewConf,
cards,
});
});
return {
...config,
views,
};
};
export const swapCard = ( export const swapCard = (
config: LovelaceConfig, config: LovelaceConfig,
path1: [number, number], path1: [number, number],

View File

@ -1,5 +1,5 @@
import { Lovelace } from "../types"; import { Lovelace } from "../types";
import { deleteCard } from "./config-util"; import { deleteCard, insertCard } from "./config-util";
import { showAlertDialog } from "../../../dialogs/generic/show-dialog-box"; import { showAlertDialog } from "../../../dialogs/generic/show-dialog-box";
import { HomeAssistant } from "../../../types"; import { HomeAssistant } from "../../../types";
import { showDeleteCardDialog } from "./card-editor/show-delete-card-dialog"; import { showDeleteCardDialog } from "./card-editor/show-delete-card-dialog";
@ -16,8 +16,12 @@ export async function confDeleteCard(
cardConfig, cardConfig,
deleteCard: async () => { deleteCard: async () => {
try { try {
await lovelace.saveConfig(deleteCard(lovelace.config, path)); const newLovelace = deleteCard(lovelace.config, path);
showDeleteSuccessToast(element, hass!); await lovelace.saveConfig(newLovelace);
const action = async () => {
await lovelace.saveConfig(insertCard(newLovelace, path, cardConfig));
};
showDeleteSuccessToast(element, hass!, action);
} catch (err) { } catch (err) {
showAlertDialog(element, { showAlertDialog(element, {
text: `Deleting failed: ${err.message}`, text: `Deleting failed: ${err.message}`,

View File

@ -16,6 +16,7 @@ export interface YamlChangedEvent extends Event {
export interface GUIModeChangedEvent { export interface GUIModeChangedEvent {
guiMode: boolean; guiMode: boolean;
guiModeAvailable: boolean;
} }
export interface ViewEditEvent extends Event { export interface ViewEditEvent extends Event {

View File

@ -391,7 +391,7 @@ export class HuiEditView extends LitElement {
.preview-badges { .preview-badges {
display: flex; display: flex;
justify-content: center; justify-content: center;
margin: 8px 16px; margin: 12px 16px;
flex-wrap: wrap; flex-wrap: wrap;
} }
`, `,

View File

@ -84,6 +84,18 @@ class HuiMediaPlayerEntityRow extends LitElement implements LovelaceRow {
const stateObj = this.hass.states[this._config.entity]; const stateObj = this.hass.states[this._config.entity];
if (!stateObj) {
return html`
<hui-warning
>${this.hass.localize(
"ui.panel.lovelace.warning.entity_not_found",
"entity",
this._config.entity
)}</hui-warning
>
`;
}
const buttons = html` const buttons = html`
${!this._narrow && supportsFeature(stateObj, SUPPORT_PREVIOUS_TRACK) ${!this._narrow && supportsFeature(stateObj, SUPPORT_PREVIOUS_TRACK)
? html` ? html`
@ -112,18 +124,6 @@ class HuiMediaPlayerEntityRow extends LitElement implements LovelaceRow {
: ""} : ""}
`; `;
if (!stateObj) {
return html`
<hui-warning
>${this.hass.localize(
"ui.panel.lovelace.warning.entity_not_found",
"entity",
this._config.entity
)}</hui-warning
>
`;
}
return html` return html`
<hui-generic-entity-row <hui-generic-entity-row
.hass=${this.hass} .hass=${this.hass}

View File

@ -69,6 +69,7 @@ export type LovelaceRowConfig =
export interface LovelaceRow extends HTMLElement { export interface LovelaceRow extends HTMLElement {
hass?: HomeAssistant; hass?: HomeAssistant;
editMode?: boolean;
setConfig(config: LovelaceRowConfig); setConfig(config: LovelaceRowConfig);
} }

View File

@ -13,12 +13,7 @@ class HuiConditionalRow extends HuiConditionalBase implements LovelaceRow {
throw new Error("No row configured."); throw new Error("No row configured.");
} }
if (this._element && this._element.parentElement) {
this.removeChild(this._element);
}
this._element = createRowElement(config.row) as LovelaceRow; this._element = createRowElement(config.row) as LovelaceRow;
this.appendChild(this._element);
} }
} }

View File

@ -524,6 +524,7 @@
"cancel": "Cancel", "cancel": "Cancel",
"delete": "Delete", "delete": "Delete",
"close": "Close", "close": "Close",
"undo": "Undo",
"save": "Save", "save": "Save",
"yes": "Yes", "yes": "Yes",
"no": "No", "no": "No",

View File

@ -1,7 +1,19 @@
import { showToast } from "./toast"; import { showToast } from "./toast";
import { HomeAssistant } from "../types"; import { HomeAssistant } from "../types";
import { ShowToastParams } from "../managers/notification-manager";
export const showDeleteSuccessToast = (el: HTMLElement, hass: HomeAssistant) => export const showDeleteSuccessToast = (
showToast(el, { el: HTMLElement,
hass: HomeAssistant,
action?: () => void
) => {
const toastParams: ShowToastParams = {
message: hass!.localize("ui.common.successfully_deleted"), message: hass!.localize("ui.common.successfully_deleted"),
}); };
if (action) {
toastParams.action = { action, text: hass!.localize("ui.common.undo") };
}
showToast(el, toastParams);
};

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Pressió atmosfèrica", "air_pressure": "Pressió atmosfèrica",
"humidity": "Humitat", "humidity": "Humitat",
"precipitation": "Precipitació",
"temperature": "Temperatura", "temperature": "Temperatura",
"visibility": "Visibilitat", "visibility": "Visibilitat",
"wind_speed": "Velocitat del vent" "wind_speed": "Velocitat del vent"
@ -2174,6 +2175,7 @@
"attribute": "Atribut", "attribute": "Atribut",
"camera_image": "Entitat de càmera", "camera_image": "Entitat de càmera",
"camera_view": "Visualització de càmera", "camera_view": "Visualització de càmera",
"double_tap_action": "Acció en tocar dues vegades",
"entities": "Entitats", "entities": "Entitats",
"entity": "Entitat", "entity": "Entitat",
"hold_action": "Acció en mantenir", "hold_action": "Acció en mantenir",
@ -2224,6 +2226,7 @@
"default_zoom": "Zoom predeterminat", "default_zoom": "Zoom predeterminat",
"description": "La targeta mapa et permet mostrar diferents entitats sobre un mapa.", "description": "La targeta mapa et permet mostrar diferents entitats sobre un mapa.",
"geo_location_sources": "Fonts de geolocalització", "geo_location_sources": "Fonts de geolocalització",
"hours_to_show": "Hores a mostrar",
"name": "Mapa", "name": "Mapa",
"source": "Font" "source": "Font"
}, },
@ -2280,6 +2283,10 @@
"name": "Previsió meteorològica" "name": "Previsió meteorològica"
} }
}, },
"cardpicker": {
"custom_card": "Personalitzada",
"no_description": "No hi ha cap descripció disponible."
},
"edit_card": { "edit_card": {
"add": "Afegir targeta", "add": "Afegir targeta",
"delete": "Elimina", "delete": "Elimina",

View File

@ -40,7 +40,7 @@
"lovelace": "Lovelace", "lovelace": "Lovelace",
"mailbox": "Postkasse", "mailbox": "Postkasse",
"media_player": "Medieafspiller", "media_player": "Medieafspiller",
"notify": "Meddelelser", "notify": "Notifikationer",
"person": "Person", "person": "Person",
"plant": "Plante", "plant": "Plante",
"proximity": "Nærhed", "proximity": "Nærhed",
@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Lufttryk", "air_pressure": "Lufttryk",
"humidity": "Luftfugtighed", "humidity": "Luftfugtighed",
"precipitation": "Nedbør",
"temperature": "Temperatur", "temperature": "Temperatur",
"visibility": "Sigtbarhed", "visibility": "Sigtbarhed",
"wind_speed": "Vindhastighed" "wind_speed": "Vindhastighed"
@ -531,7 +532,9 @@
"wnw": "VNV", "wnw": "VNV",
"wsw": "VSV" "wsw": "VSV"
}, },
"forecast": "Vejrudsigt" "forecast": "Vejrudsigt",
"high": "Maks.",
"low": "Min."
} }
}, },
"common": { "common": {
@ -687,7 +690,7 @@
"not_editable_text": "Denne entitet kan ikke ændres fra brugerfladen, fordi det er defineret i configuration.yaml.", "not_editable_text": "Denne entitet kan ikke ændres fra brugerfladen, fordi det er defineret i configuration.yaml.",
"platform_not_loaded": "{platform}-integrationen er ikke indlæst. Tilføj den til din konfiguration. Enten ved at tilføje 'default_config:' eller '{platform}:'.", "platform_not_loaded": "{platform}-integrationen er ikke indlæst. Tilføj den til din konfiguration. Enten ved at tilføje 'default_config:' eller '{platform}:'.",
"required_error_msg": "Dette felt er påkrævet", "required_error_msg": "Dette felt er påkrævet",
"yaml_not_editable": "Indstillingerne for denne entitet kan ikke redigeres fra brugerfladen. Det er kun entiteter, der er konfigureret fra brugergrænsefladen, der kan konfigureres herfra." "yaml_not_editable": "Indstillingerne for denne entitet kan ikke redigeres fra brugerfladen. Det er kun entiteter, der er konfigureret fra brugerfladen, der kan konfigureres herfra."
}, },
"more_info_control": { "more_info_control": {
"dismiss": "Afvis dialog", "dismiss": "Afvis dialog",
@ -792,8 +795,8 @@
"notification_drawer": { "notification_drawer": {
"click_to_configure": "Klik på knappen for at konfigurere {entity}", "click_to_configure": "Klik på knappen for at konfigurere {entity}",
"close": "Luk", "close": "Luk",
"empty": "Ingen meddelelser", "empty": "Ingen notifikationer",
"title": "Meddelelser" "title": "Notifikationer"
}, },
"notification_toast": { "notification_toast": {
"connection_lost": "Forbindelse afbrudt. Opretter forbindelse igen...", "connection_lost": "Forbindelse afbrudt. Opretter forbindelse igen...",
@ -1488,7 +1491,7 @@
}, },
"configure": "Konfigurer", "configure": "Konfigurer",
"configured": "Konfigureret", "configured": "Konfigureret",
"description": "Administrer tilsluttede enheder og tjenester", "description": "Administrer og opsæt integrationer",
"details": "Integrationsdetaljer", "details": "Integrationsdetaljer",
"discovered": "Fundet", "discovered": "Fundet",
"home_assistant_website": "Home Assistants hjemmeside", "home_assistant_website": "Home Assistants hjemmeside",
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "Aktivér bruger", "activate_user": "Aktivér bruger",
"active": "Aktiv", "active": "Aktiv",
"admin": "Administrator",
"caption": "Vis bruger", "caption": "Vis bruger",
"change_password": "Skift adgangskode", "change_password": "Skift adgangskode",
"confirm_user_deletion": "Er du sikker på, at du vil slette {name}?", "confirm_user_deletion": "Er du sikker på, at du vil slette {name}?",
@ -1744,6 +1748,7 @@
"owner": "Ejer", "owner": "Ejer",
"rename_user": "Omdøb bruger", "rename_user": "Omdøb bruger",
"system_generated": "Systemgenereret", "system_generated": "Systemgenereret",
"system_generated_users_not_editable": "Systemoprettede brugere kan ikke opdateres.",
"system_generated_users_not_removable": "Kan ikke fjerne systemgenererede brugere.", "system_generated_users_not_removable": "Kan ikke fjerne systemgenererede brugere.",
"unnamed_user": "Unavngiven bruger", "unnamed_user": "Unavngiven bruger",
"update_user": "Opdater", "update_user": "Opdater",
@ -2175,6 +2180,7 @@
"attribute": "Egenskab", "attribute": "Egenskab",
"camera_image": "Kameraentitet", "camera_image": "Kameraentitet",
"camera_view": "Kameravisning", "camera_view": "Kameravisning",
"double_tap_action": "Handling ved dobbelttryk",
"entities": "Entiteter", "entities": "Entiteter",
"entity": "Entitet", "entity": "Entitet",
"hold_action": "Handling ved hold", "hold_action": "Handling ved hold",
@ -2225,6 +2231,7 @@
"default_zoom": "Standard-zoom", "default_zoom": "Standard-zoom",
"description": "Kort-kortet giver dig mulighed for at vise entiteter på et kort.", "description": "Kort-kortet giver dig mulighed for at vise entiteter på et kort.",
"geo_location_sources": "Lokalitetskilder", "geo_location_sources": "Lokalitetskilder",
"hours_to_show": "Vis i antal timer",
"name": "Kort", "name": "Kort",
"source": "Kilde" "source": "Kilde"
}, },
@ -2281,6 +2288,10 @@
"name": "Vejrudsigt" "name": "Vejrudsigt"
} }
}, },
"cardpicker": {
"custom_card": "Brugerdefineret",
"no_description": "Ingen beskrivelse tilgængelig."
},
"edit_card": { "edit_card": {
"add": "Tilføj kort", "add": "Tilføj kort",
"delete": "Slet kort", "delete": "Slet kort",
@ -2642,12 +2653,12 @@
"header": "Multifaktor-godkendelsesmoduler" "header": "Multifaktor-godkendelsesmoduler"
}, },
"push_notifications": { "push_notifications": {
"description": "Send meddelelser til denne enhed.", "description": "Send notifikationer til denne enhed.",
"error_load_platform": "Konfigurer notify.html5", "error_load_platform": "Konfigurer notify.html5",
"error_use_https": "Kræver SSL aktiveret til brugerflade.", "error_use_https": "Kræver SSL aktiveret til brugerflade.",
"header": "Push-meddelelser", "header": "Push-notifikationer",
"link_promo": "Lær mere", "link_promo": "Lær mere",
"push_notifications": "Push-meddelelser" "push_notifications": "Push-notifikationer"
}, },
"refresh_tokens": { "refresh_tokens": {
"confirm_delete": "Er du sikker på, at du vil slette opdateringsstoken til {name}?", "confirm_delete": "Er du sikker på, at du vil slette opdateringsstoken til {name}?",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Luftdruck", "air_pressure": "Luftdruck",
"humidity": "Luftfeuchtigkeit", "humidity": "Luftfeuchtigkeit",
"precipitation": "Niederschlag",
"temperature": "Temperatur", "temperature": "Temperatur",
"visibility": "Sichtweite", "visibility": "Sichtweite",
"wind_speed": "Windgeschwindigkeit" "wind_speed": "Windgeschwindigkeit"
@ -531,7 +532,9 @@
"wnw": "WNW", "wnw": "WNW",
"wsw": "WSW" "wsw": "WSW"
}, },
"forecast": "Prognose" "forecast": "Prognose",
"high": "Hoch",
"low": "Niedrig"
} }
}, },
"common": { "common": {
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "Benutzer aktivieren", "activate_user": "Benutzer aktivieren",
"active": "Aktiv", "active": "Aktiv",
"admin": "Administrator",
"caption": "Benutzer anzeigen", "caption": "Benutzer anzeigen",
"change_password": "Passwort ändern", "change_password": "Passwort ändern",
"confirm_user_deletion": "Möchten Sie {name} wirklich löschen?", "confirm_user_deletion": "Möchten Sie {name} wirklich löschen?",
@ -1744,6 +1748,7 @@
"owner": "Besitzer", "owner": "Besitzer",
"rename_user": "Benutzer umbenennen", "rename_user": "Benutzer umbenennen",
"system_generated": "System generiert", "system_generated": "System generiert",
"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.", "system_generated_users_not_removable": "Vom System generierte Benutzer können nicht entfernt werden.",
"unnamed_user": "Unbenannter Benutzer", "unnamed_user": "Unbenannter Benutzer",
"update_user": "Aktualisieren", "update_user": "Aktualisieren",
@ -2175,6 +2180,7 @@
"attribute": "Attribut", "attribute": "Attribut",
"camera_image": "Kamera-Entität", "camera_image": "Kamera-Entität",
"camera_view": "Kameraansicht", "camera_view": "Kameraansicht",
"double_tap_action": "Doppeltipp-Aktion",
"entities": "Ungenutzte Elemente", "entities": "Ungenutzte Elemente",
"entity": "Entität", "entity": "Entität",
"hold_action": "Halte-Aktion", "hold_action": "Halte-Aktion",
@ -2225,6 +2231,7 @@
"default_zoom": "Standard-Zoom", "default_zoom": "Standard-Zoom",
"description": "Mit der Map-Karte kannst du Objekte auf einer Karte anzeigen lassen.", "description": "Mit der Map-Karte kannst du Objekte auf einer Karte anzeigen lassen.",
"geo_location_sources": "Geolocation-Quellen", "geo_location_sources": "Geolocation-Quellen",
"hours_to_show": "Zu zeigende Stunden",
"name": "Karte", "name": "Karte",
"source": "Quelle" "source": "Quelle"
}, },
@ -2281,6 +2288,10 @@
"name": "Wettervorhersage" "name": "Wettervorhersage"
} }
}, },
"cardpicker": {
"custom_card": "Benutzerdefiniert",
"no_description": "Keine Beschreibung verfügbar."
},
"edit_card": { "edit_card": {
"add": "Karte hinzufügen", "add": "Karte hinzufügen",
"delete": "Löschen", "delete": "Löschen",

View File

@ -546,6 +546,7 @@
"save": "Save", "save": "Save",
"successfully_deleted": "Successfully deleted", "successfully_deleted": "Successfully deleted",
"successfully_saved": "Successfully saved", "successfully_saved": "Successfully saved",
"undo": "Undo",
"yes": "Yes" "yes": "Yes"
}, },
"components": { "components": {
@ -1734,6 +1735,7 @@
"editor": { "editor": {
"activate_user": "Activate user", "activate_user": "Activate user",
"active": "Active", "active": "Active",
"admin": "Administrator",
"caption": "View user", "caption": "View user",
"change_password": "Change password", "change_password": "Change password",
"confirm_user_deletion": "Are you sure you want to delete {name}?", "confirm_user_deletion": "Are you sure you want to delete {name}?",
@ -1747,6 +1749,7 @@
"owner": "Owner", "owner": "Owner",
"rename_user": "Rename user", "rename_user": "Rename user",
"system_generated": "System generated", "system_generated": "System generated",
"system_generated_users_not_editable": "Unable to update system generated users.",
"system_generated_users_not_removable": "Unable to remove system generated users.", "system_generated_users_not_removable": "Unable to remove system generated users.",
"unnamed_user": "Unnamed User", "unnamed_user": "Unnamed User",
"update_user": "Update", "update_user": "Update",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Presión del aire", "air_pressure": "Presión del aire",
"humidity": "Humedad", "humidity": "Humedad",
"precipitation": "Precipitación",
"temperature": "Temperatura", "temperature": "Temperatura",
"visibility": "Visibilidad", "visibility": "Visibilidad",
"wind_speed": "Velocidad del viento" "wind_speed": "Velocidad del viento"
@ -531,7 +532,9 @@
"wnw": "ONO", "wnw": "ONO",
"wsw": "OSO" "wsw": "OSO"
}, },
"forecast": "Pronóstico" "forecast": "Pronóstico",
"high": "Máxima",
"low": "Mínima"
} }
}, },
"common": { "common": {
@ -1117,7 +1120,7 @@
"info": "Home Assistant Cloud proporciona una conexión remota segura a tu instancia mientras estás fuera de casa.", "info": "Home Assistant Cloud proporciona una conexión remota segura a tu instancia mientras estás fuera de casa.",
"instance_is_available": "Tu instancia está disponible en", "instance_is_available": "Tu instancia está disponible en",
"instance_will_be_available": "Tu instancia estará disponible en", "instance_will_be_available": "Tu instancia estará disponible en",
"link_learn_how_it_works": "Aprender cómo funciona", "link_learn_how_it_works": "Aprende cómo funciona",
"title": "Control remoto" "title": "Control remoto"
}, },
"sign_out": "Cerrar sesión", "sign_out": "Cerrar sesión",
@ -1517,11 +1520,11 @@
"cant_edit_yaml": "Los paneles de control definidos en YAML no se pueden editar desde la IU. Cámbialos en configuration.yaml.", "cant_edit_yaml": "Los paneles de control definidos en YAML no se pueden editar desde la IU. Cámbialos en configuration.yaml.",
"caption": "Paneles de control", "caption": "Paneles de control",
"conf_mode": { "conf_mode": {
"storage": "Controlado por la interfaz de usuario", "storage": "Controlado por la IU",
"yaml": "Archivo YAML" "yaml": "Archivo YAML"
}, },
"confirm_delete": "¿Estás seguro de que quieres eliminar este panel de control?", "confirm_delete": "¿Estás seguro de que quieres eliminar este panel de control?",
"default_dashboard": "Este es el panel predeterminado", "default_dashboard": "Este es el panel de control predeterminado",
"detail": { "detail": {
"create": "Crear", "create": "Crear",
"delete": "Eliminar", "delete": "Eliminar",
@ -1649,7 +1652,7 @@
"headers": { "headers": {
"name": "Nombre" "name": "Nombre"
}, },
"introduction": "El editor de escenas te permite crear y editar escenas. En el enlace siguiente puedes leer las instrucciones para asegurarte de que has configurado Home Assistant correctamente.", "introduction": "El editor de escenas te permite crear y editar escenas. Por favor, sigue el siguiente enlace para leer las instrucciones para asegurarte de que has configurado Home Assistant correctamente.",
"learn_more": "Saber más sobre las escenas", "learn_more": "Saber más sobre las escenas",
"no_scenes": "No pudimos encontrar ninguna escena editable", "no_scenes": "No pudimos encontrar ninguna escena editable",
"only_editable": "Solo las escenas definidas en scenes.yaml son editables.", "only_editable": "Solo las escenas definidas en scenes.yaml son editables.",
@ -1679,7 +1682,7 @@
"headers": { "headers": {
"name": "Nombre" "name": "Nombre"
}, },
"introduction": "El editor de scripts te permite crear y editar scripts. En el enlace siguiente puedes leer las instrucciones para asegurarte de que has configurado Home Assistant correctamente.", "introduction": "El editor de scripts te permite crear y editar scripts. Por favor, sigue el siguiente enlace para leer las instrucciones para asegurarte de que has configurado Home Assistant correctamente.",
"learn_more": "Saber más sobre los scripts", "learn_more": "Saber más sobre los scripts",
"no_scripts": "No hemos encontrado ningún script editable", "no_scripts": "No hemos encontrado ningún script editable",
"show_info": "Mostrar información sobre el script", "show_info": "Mostrar información sobre el script",
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "Activar usuario", "activate_user": "Activar usuario",
"active": "Activo", "active": "Activo",
"admin": "Administrador",
"caption": "Ver usuario", "caption": "Ver usuario",
"change_password": "Cambiar la contraseña", "change_password": "Cambiar la contraseña",
"confirm_user_deletion": "¿Seguro que quieres eliminar {name}?", "confirm_user_deletion": "¿Seguro que quieres eliminar {name}?",
@ -1744,6 +1748,7 @@
"owner": "Propietario", "owner": "Propietario",
"rename_user": "Renombrar usuario", "rename_user": "Renombrar usuario",
"system_generated": "Generado por el sistema", "system_generated": "Generado por el sistema",
"system_generated_users_not_editable": "No se pueden actualizar los usuarios generados por el sistema.",
"system_generated_users_not_removable": "No se pueden eliminar los usuarios generados por el sistema.", "system_generated_users_not_removable": "No se pueden eliminar los usuarios generados por el sistema.",
"unnamed_user": "Usuario sin nombre", "unnamed_user": "Usuario sin nombre",
"update_user": "Actualizar", "update_user": "Actualizar",
@ -2175,6 +2180,7 @@
"attribute": "Atributo", "attribute": "Atributo",
"camera_image": "Entidad de cámara", "camera_image": "Entidad de cámara",
"camera_view": "Vista de cámara", "camera_view": "Vista de cámara",
"double_tap_action": "Acción de doble toque",
"entities": "Entidades", "entities": "Entidades",
"entity": "Entidad", "entity": "Entidad",
"hold_action": "Acción de mantener", "hold_action": "Acción de mantener",
@ -2225,6 +2231,7 @@
"default_zoom": "Zoom predeterminado", "default_zoom": "Zoom predeterminado",
"description": "La tarjeta Mapa que te permite mostrar entidades en un mapa.", "description": "La tarjeta Mapa que te permite mostrar entidades en un mapa.",
"geo_location_sources": "Fuentes de geolocalización", "geo_location_sources": "Fuentes de geolocalización",
"hours_to_show": "Horas para mostrar",
"name": "Mapa", "name": "Mapa",
"source": "Fuente" "source": "Fuente"
}, },
@ -2281,6 +2288,10 @@
"name": "Pronóstico del tiempo" "name": "Pronóstico del tiempo"
} }
}, },
"cardpicker": {
"custom_card": "Personalizado",
"no_description": "No hay descripción disponible."
},
"edit_card": { "edit_card": {
"add": "Añadir tarjeta", "add": "Añadir tarjeta",
"delete": "Eliminar tarjeta", "delete": "Eliminar tarjeta",
@ -2608,7 +2619,7 @@
"language": { "language": {
"dropdown_label": "Idioma", "dropdown_label": "Idioma",
"header": "Idioma", "header": "Idioma",
"link_promo": "Ayudar traduciendo" "link_promo": "Ayuda a traducir"
}, },
"logout": "Cerrar sesión", "logout": "Cerrar sesión",
"logout_text": "¿Estás seguro de que quieres cerrar la sesión?", "logout_text": "¿Estás seguro de que quieres cerrar la sesión?",
@ -2623,7 +2634,7 @@
"empty_state": "Aún no tienes tokens de acceso de larga duración.", "empty_state": "Aún no tienes tokens de acceso de larga duración.",
"header": "Tokens de acceso de larga duración", "header": "Tokens de acceso de larga duración",
"last_used": "Último uso el {date} desde {location}", "last_used": "Último uso el {date} desde {location}",
"learn_auth_requests": "Aprender cómo realizar solicitudes autenticadas.", "learn_auth_requests": "Aprende cómo realizar solicitudes autenticadas.",
"not_used": "Nunca ha sido usado", "not_used": "Nunca ha sido usado",
"prompt_copy_token": "Copia tu token de acceso. No se mostrará de nuevo.", "prompt_copy_token": "Copia tu token de acceso. No se mostrará de nuevo.",
"prompt_name": "¿Nombre?" "prompt_name": "¿Nombre?"
@ -2664,7 +2675,7 @@
"dropdown_label": "Tema", "dropdown_label": "Tema",
"error_no_theme": "No hay temas disponibles", "error_no_theme": "No hay temas disponibles",
"header": "Tema", "header": "Tema",
"link_promo": "Saber más sobre los temas" "link_promo": "Aprende sobre los temas"
}, },
"vibrate": { "vibrate": {
"description": "Activar o deshabilitar la vibración en este dispositivo al controlar dispositivos.", "description": "Activar o deshabilitar la vibración en este dispositivo al controlar dispositivos.",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Pression atmosphérique", "air_pressure": "Pression atmosphérique",
"humidity": "Humidité", "humidity": "Humidité",
"precipitation": "Précipitation",
"temperature": "Température", "temperature": "Température",
"visibility": "Visibilité", "visibility": "Visibilité",
"wind_speed": "Vitesse du vent" "wind_speed": "Vitesse du vent"
@ -531,7 +532,9 @@
"wnw": "O-NO", "wnw": "O-NO",
"wsw": "O-SO" "wsw": "O-SO"
}, },
"forecast": "Prévisions" "forecast": "Prévisions",
"high": "Haute",
"low": "Faible"
} }
}, },
"common": { "common": {
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "Activer l'utilisateur", "activate_user": "Activer l'utilisateur",
"active": "Actif", "active": "Actif",
"admin": "Administrateur",
"caption": "Voir l'utilisateur", "caption": "Voir l'utilisateur",
"change_password": "Changer le mot de passe", "change_password": "Changer le mot de passe",
"confirm_user_deletion": "Êtes-vous sûr de vouloir supprimer {name} ?", "confirm_user_deletion": "Êtes-vous sûr de vouloir supprimer {name} ?",
@ -1744,6 +1748,7 @@
"owner": "Propriétaire", "owner": "Propriétaire",
"rename_user": "Renommer l'utilisateur", "rename_user": "Renommer l'utilisateur",
"system_generated": "Généré par le système", "system_generated": "Généré par le système",
"system_generated_users_not_editable": "Impossible de mettre à jour les utilisateurs générés par le système.",
"system_generated_users_not_removable": "Impossible de supprimer les utilisateurs générés par le système.", "system_generated_users_not_removable": "Impossible de supprimer les utilisateurs générés par le système.",
"unnamed_user": "Utilisateur sans nom", "unnamed_user": "Utilisateur sans nom",
"update_user": "Mise à jour", "update_user": "Mise à jour",
@ -2225,6 +2230,7 @@
"default_zoom": "Zoom par défaut", "default_zoom": "Zoom par défaut",
"description": "La carte Carte vous permet d'afficher des entités sur une carte.", "description": "La carte Carte vous permet d'afficher des entités sur une carte.",
"geo_location_sources": "Sources de géolocalisation", "geo_location_sources": "Sources de géolocalisation",
"hours_to_show": "Heures à montrer",
"name": "Carte", "name": "Carte",
"source": "Source" "source": "Source"
}, },
@ -2281,6 +2287,10 @@
"name": "Prévisions Météo" "name": "Prévisions Météo"
} }
}, },
"cardpicker": {
"custom_card": "Personnalisé",
"no_description": "Aucune description disponible."
},
"edit_card": { "edit_card": {
"add": "Ajouter une action", "add": "Ajouter une action",
"delete": "Supprimer", "delete": "Supprimer",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "기압", "air_pressure": "기압",
"humidity": "습도", "humidity": "습도",
"precipitation": "강수량",
"temperature": "기온", "temperature": "기온",
"visibility": "시정", "visibility": "시정",
"wind_speed": "풍속" "wind_speed": "풍속"
@ -531,7 +532,9 @@
"wnw": "서북서", "wnw": "서북서",
"wsw": "서남서" "wsw": "서남서"
}, },
"forecast": "일기 예보" "forecast": "일기 예보",
"high": "높음",
"low": "낮음"
} }
}, },
"common": { "common": {
@ -630,7 +633,7 @@
"entity_id": "구성요소 ID", "entity_id": "구성요소 ID",
"icon": "아이콘 재정의", "icon": "아이콘 재정의",
"icon_error": "아이콘은 접두사:아이콘이름 형식이어야 합니다. 예: mdi:home", "icon_error": "아이콘은 접두사:아이콘이름 형식이어야 합니다. 예: mdi:home",
"name": "대체 이름", "name": "이름 재정의",
"note": "참고: 아직 모든 통합 구성요소에 적용되지 않을 수 있습니다.", "note": "참고: 아직 모든 통합 구성요소에 적용되지 않을 수 있습니다.",
"unavailable": "이 구성요소는 현재 사용할 수 없습니다.", "unavailable": "이 구성요소는 현재 사용할 수 없습니다.",
"update": "업데이트" "update": "업데이트"
@ -731,7 +734,7 @@
"more_info_settings": { "more_info_settings": {
"back": "뒤로가기", "back": "뒤로가기",
"entity_id": "구성요소 ID", "entity_id": "구성요소 ID",
"name": "대체 이름", "name": "이름 재정의",
"save": "저장" "save": "저장"
}, },
"options_flow": { "options_flow": {
@ -1370,7 +1373,7 @@
"enabled_description": "비활성화 된 구성요소는 Home Assistant 에 추가되지 않습니다.", "enabled_description": "비활성화 된 구성요소는 Home Assistant 에 추가되지 않습니다.",
"enabled_label": "구성요소 활성화", "enabled_label": "구성요소 활성화",
"entity_id": "구성요소 ID", "entity_id": "구성요소 ID",
"name": "대체 이름", "name": "이름 재정의",
"note": "참고 : 아직 모든 통합 구성요소에 적용되지 않을 수 있습니다.", "note": "참고 : 아직 모든 통합 구성요소에 적용되지 않을 수 있습니다.",
"unavailable": "이 구성요소는 현재 사용할 수 없습니다.", "unavailable": "이 구성요소는 현재 사용할 수 없습니다.",
"update": "업데이트" "update": "업데이트"
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "사용자 활성화", "activate_user": "사용자 활성화",
"active": "활성화", "active": "활성화",
"admin": "관리자",
"caption": "사용자 보기", "caption": "사용자 보기",
"change_password": "비밀번호 변경", "change_password": "비밀번호 변경",
"confirm_user_deletion": "{name} 을(를) 삭제하시겠습니까?", "confirm_user_deletion": "{name} 을(를) 삭제하시겠습니까?",
@ -1744,6 +1748,7 @@
"owner": "소유자", "owner": "소유자",
"rename_user": "사용자 이름 변경", "rename_user": "사용자 이름 변경",
"system_generated": "시스템 자동 생성", "system_generated": "시스템 자동 생성",
"system_generated_users_not_editable": "시스템 자동 생성 사용자는 업데이트할 수 없습니다.",
"system_generated_users_not_removable": "시스템 자동 생성 사용자는 제거할 수 없습니다.", "system_generated_users_not_removable": "시스템 자동 생성 사용자는 제거할 수 없습니다.",
"unnamed_user": "이름이 없는 사용자", "unnamed_user": "이름이 없는 사용자",
"update_user": "업데이트", "update_user": "업데이트",
@ -2175,6 +2180,7 @@
"attribute": "속성", "attribute": "속성",
"camera_image": "카메라 구성요소", "camera_image": "카메라 구성요소",
"camera_view": "카메라 뷰", "camera_view": "카메라 뷰",
"double_tap_action": "더블 탭 동작",
"entities": "구성요소", "entities": "구성요소",
"entity": "구성요소", "entity": "구성요소",
"hold_action": "길게 누르기 동작", "hold_action": "길게 누르기 동작",
@ -2225,6 +2231,7 @@
"default_zoom": "기본 확대", "default_zoom": "기본 확대",
"description": "지도 카드는 지도에 구성요소를 표시할 수 있습니다.", "description": "지도 카드는 지도에 구성요소를 표시할 수 있습니다.",
"geo_location_sources": "위치정보 소스", "geo_location_sources": "위치정보 소스",
"hours_to_show": "표시 시간",
"name": "지도", "name": "지도",
"source": "소스" "source": "소스"
}, },
@ -2281,6 +2288,10 @@
"name": "날씨 예보" "name": "날씨 예보"
} }
}, },
"cardpicker": {
"custom_card": "사용자 정의",
"no_description": "상세정보가 없습니다"
},
"edit_card": { "edit_card": {
"add": "카드 추가하기", "add": "카드 추가하기",
"delete": "카드 삭제", "delete": "카드 삭제",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Loftdrock", "air_pressure": "Loftdrock",
"humidity": "Fiichtegkeet", "humidity": "Fiichtegkeet",
"precipitation": "Nidderschlag",
"temperature": "Temperatur", "temperature": "Temperatur",
"visibility": "Visibilitéit", "visibility": "Visibilitéit",
"wind_speed": "Wandvitesse" "wind_speed": "Wandvitesse"
@ -531,7 +532,9 @@
"wnw": "WNW", "wnw": "WNW",
"wsw": "WSW" "wsw": "WSW"
}, },
"forecast": "Prognose" "forecast": "Prognose",
"high": "Héich",
"low": "Niddreg"
} }
}, },
"common": { "common": {
@ -807,6 +810,10 @@
"areas": { "areas": {
"caption": "Lëscht vun de Beräicher", "caption": "Lëscht vun de Beräicher",
"create_area": "Beräich erstellen", "create_area": "Beräich erstellen",
"data_table": {
"area": "Beräich",
"devices": "Apparater"
},
"delete": { "delete": {
"confirmation_text": "All Apparater an dësem Beräich ginn néirens zougewisen.", "confirmation_text": "All Apparater an dësem Beräich ginn néirens zougewisen.",
"confirmation_title": "Sécher fir dëse Beräich ze läsche?" "confirmation_title": "Sécher fir dëse Beräich ze läsche?"
@ -1049,6 +1056,9 @@
"delete_confirm": "Sécher fir dës Automatisme ze läschen?", "delete_confirm": "Sécher fir dës Automatisme ze läschen?",
"edit_automation": "Automatisme änneren", "edit_automation": "Automatisme änneren",
"header": "Automatismen editéieren", "header": "Automatismen editéieren",
"headers": {
"name": "Numm"
},
"introduction": "Den Automatismen-Editor erméiglecht et fir Automatismen z'erstellen an ze änneren. Lies w.e.g. [d'Instruktioune](https://home-assistant.io/docs/automation/editor/) fir sécher ze stellen dass den Home Assistant richteg agestallt ass.", "introduction": "Den Automatismen-Editor erméiglecht et fir Automatismen z'erstellen an ze änneren. Lies w.e.g. [d'Instruktioune](https://home-assistant.io/docs/automation/editor/) fir sécher ze stellen dass den Home Assistant richteg agestallt ass.",
"learn_more": "Méi iwwert Automatioune liesen", "learn_more": "Méi iwwert Automatioune liesen",
"no_automations": "Keen Automatismus fir ze ännere fonnt", "no_automations": "Keen Automatismus fir ze ännere fonnt",
@ -1329,6 +1339,7 @@
}, },
"info": "Informatioune vum Apparat", "info": "Informatioune vum Apparat",
"name": "Numm", "name": "Numm",
"no_devices": "Keng Apparater",
"scene": { "scene": {
"create": "Zeen mat Apparat erstellen", "create": "Zeen mat Apparat erstellen",
"no_scenes": "Keng Zeenen", "no_scenes": "Keng Zeenen",
@ -1631,6 +1642,9 @@
"delete_scene": "Zeen läschen", "delete_scene": "Zeen läschen",
"edit_scene": "Zeen änneren", "edit_scene": "Zeen änneren",
"header": "Zeen Editeur", "header": "Zeen Editeur",
"headers": {
"name": "Numm"
},
"introduction": "De Zeenen Editeur erlaabt Iech Zeenen z'erstellen an z'änneren. Follegt de Link hei ënnendrënner fir d'Instruktiounen ze liese fir sécher ze stellen, datt Dir den Home Assistant richteg konfiguréiert hutt.", "introduction": "De Zeenen Editeur erlaabt Iech Zeenen z'erstellen an z'änneren. Follegt de Link hei ënnendrënner fir d'Instruktiounen ze liese fir sécher ze stellen, datt Dir den Home Assistant richteg konfiguréiert hutt.",
"learn_more": "Méi iwwert Zeene léieren", "learn_more": "Méi iwwert Zeene léieren",
"no_scenes": "Keng Zeene fir ze ännere fonnt", "no_scenes": "Keng Zeene fir ze ännere fonnt",
@ -1658,9 +1672,13 @@
"add_script": "Skript dobäisetze", "add_script": "Skript dobäisetze",
"edit_script": "Skript änneren", "edit_script": "Skript änneren",
"header": "Skript Editeur", "header": "Skript Editeur",
"headers": {
"name": "Numm"
},
"introduction": "De Skript Editeur erlaabt Iech Skripten ze erstellen an z'änneren. Follegt de Link hei ënnendrënner fir d'Instruktiounen ze liese fir sécher ze stellen, datt Dir den Home Assistant richteg konfiguréiert hutt", "introduction": "De Skript Editeur erlaabt Iech Skripten ze erstellen an z'änneren. Follegt de Link hei ënnendrënner fir d'Instruktiounen ze liese fir sécher ze stellen, datt Dir den Home Assistant richteg konfiguréiert hutt",
"learn_more": "Méi iwwert Skripten léieren", "learn_more": "Méi iwwert Skripten léieren",
"no_scripts": "Keng Skripte fir ze ännere fonnt", "no_scripts": "Keng Skripte fir ze ännere fonnt",
"show_info": "Informatiounen vum Skript uweisen",
"trigger_script": "Skript ausléisen" "trigger_script": "Skript ausléisen"
} }
}, },
@ -1718,14 +1736,21 @@
"group": "Gruppe", "group": "Gruppe",
"group_update_failed": "Feeler bei der aktualiséiereung vum Gruppe", "group_update_failed": "Feeler bei der aktualiséiereung vum Gruppe",
"id": "ID", "id": "ID",
"name": "Numm",
"owner": "Proprietär", "owner": "Proprietär",
"rename_user": "Benotzer ëmbenennen", "rename_user": "Benotzer ëmbenennen",
"system_generated": "Vum System generéiert", "system_generated": "Vum System generéiert",
"system_generated_users_not_removable": "Ka keng System generéiert Benotzer läschen.", "system_generated_users_not_removable": "Ka keng System generéiert Benotzer läschen.",
"unnamed_user": "Benotzer ouni Numm", "unnamed_user": "Benotzer ouni Numm",
"update_user": "Aktualiséieren",
"user_rename_failed": "Feeler beim ëmbenennen vum Benotzer:" "user_rename_failed": "Feeler beim ëmbenennen vum Benotzer:"
}, },
"picker": { "picker": {
"headers": {
"group": "Grupp",
"name": "Numm",
"system": "System"
},
"system_generated": "Vum System generéiert", "system_generated": "Vum System generéiert",
"title": "Benotzer" "title": "Benotzer"
} }
@ -2126,6 +2151,9 @@
"description": "D'Entity Filter Kaart erlaabt Iech eng Lëscht vun Entitéiten ze definéieren déi nëmmen ugewise gi wann se an engem bestëmmten Zoustand sinn.", "description": "D'Entity Filter Kaart erlaabt Iech eng Lëscht vun Entitéiten ze definéieren déi nëmmen ugewise gi wann se an engem bestëmmten Zoustand sinn.",
"name": "Entitéite Filter" "name": "Entitéite Filter"
}, },
"entity": {
"name": "Entitéit"
},
"gauge": { "gauge": {
"description": "D'Gauge Kaart ass eng Basis Kaart déi Sensor Date visuell duerstellt.", "description": "D'Gauge Kaart ass eng Basis Kaart déi Sensor Date visuell duerstellt.",
"name": "Skala", "name": "Skala",
@ -2138,8 +2166,10 @@
}, },
"generic": { "generic": {
"aspect_ratio": "Säiteverhältnis", "aspect_ratio": "Säiteverhältnis",
"attribute": "Attribut",
"camera_image": "Kamera Entitéit", "camera_image": "Kamera Entitéit",
"camera_view": "Kamera Usiicht", "camera_view": "Kamera Usiicht",
"double_tap_action": "Aktioun beim 2-mol tippen",
"entities": "Entitéiten", "entities": "Entitéiten",
"entity": "Entitéit", "entity": "Entitéit",
"hold_action": "Aktioun beim unhalen", "hold_action": "Aktioun beim unhalen",
@ -2190,6 +2220,7 @@
"default_zoom": "Standard Zoom", "default_zoom": "Standard Zoom",
"description": "Kaarte Kaart erméiglecht d'Visualisatioun vun Entitéiten op enger Kaart.", "description": "Kaarte Kaart erméiglecht d'Visualisatioun vun Entitéiten op enger Kaart.",
"geo_location_sources": "Quell vun der Geolokalisatioun", "geo_location_sources": "Quell vun der Geolokalisatioun",
"hours_to_show": "Stonnen uweisen",
"name": "Kaart", "name": "Kaart",
"source": "Quell" "source": "Quell"
}, },
@ -2246,6 +2277,10 @@
"name": "Wiederprevisioune" "name": "Wiederprevisioune"
} }
}, },
"cardpicker": {
"custom_card": "Personnaliséiert",
"no_description": "Keng Beschreiwung verfügbar"
},
"edit_card": { "edit_card": {
"add": "Kaart dobäisetzen", "add": "Kaart dobäisetzen",
"delete": "Läschen", "delete": "Läschen",
@ -2310,6 +2345,7 @@
"save_config": { "save_config": {
"cancel": "Vergiess et", "cancel": "Vergiess et",
"close": "Zoumaachen", "close": "Zoumaachen",
"empty_config": "Mat engem eidelen Tableau de Bord ufänken",
"header": "Kontroll iwwert Loveloce UI iwwerhuelen", "header": "Kontroll iwwert Loveloce UI iwwerhuelen",
"para": "Standardméisseg verwalt Home Assistant de Benotzer Interface an aktualiséiert en soubal nei Entitéiten oder Lovelace-Komponenten disponibel sinn. Wann dir d'Kontrolle iwwerhuelt, kënne mir keng automatesch Ännerung méi fir iech maachen.", "para": "Standardméisseg verwalt Home Assistant de Benotzer Interface an aktualiséiert en soubal nei Entitéiten oder Lovelace-Komponenten disponibel sinn. Wann dir d'Kontrolle iwwerhuelt, kënne mir keng automatesch Ännerung méi fir iech maachen.",
"para_sure": "Sécher fir d'Kontrolle iwwert de Benotzer Interface z'iwwerhuelen?", "para_sure": "Sécher fir d'Kontrolle iwwert de Benotzer Interface z'iwwerhuelen?",
@ -2558,6 +2594,11 @@
"submit": "Ofschécken" "submit": "Ofschécken"
}, },
"current_user": "Dir sidd aktuell ageloggt als {fullName}.", "current_user": "Dir sidd aktuell ageloggt als {fullName}.",
"dashboard": {
"description": "Wiel ee Tableau de Bord als Standard op dësem Apparat.",
"dropdown_label": "Tableau de Bord",
"header": "Tableau de Bord"
},
"force_narrow": { "force_narrow": {
"description": "Dës Optioun verstoppt d'Säite Läischt esou wéi op engem mobillen Apparat.", "description": "Dës Optioun verstoppt d'Säite Läischt esou wéi op engem mobillen Apparat.",
"header": "Säite Läischt ëmmer verstoppen" "header": "Säite Läischt ëmmer verstoppen"

View File

@ -9,13 +9,13 @@
"config_entry": { "config_entry": {
"disabled_by": { "disabled_by": {
"config_entry": "Konfigurer oppføring", "config_entry": "Konfigurer oppføring",
"integration": "Integrering", "integration": "Integrasjon",
"user": "Bruker" "user": "Bruker"
} }
}, },
"domain": { "domain": {
"alarm_control_panel": "Alarm kontrollpanel", "alarm_control_panel": "Alarm kontrollpanel",
"automation": "Automatisering", "automation": "Automasjon",
"binary_sensor": "Binær sensor", "binary_sensor": "Binær sensor",
"calendar": "Kalender", "calendar": "Kalender",
"camera": "Kamera", "camera": "Kamera",
@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Lufttrykk", "air_pressure": "Lufttrykk",
"humidity": "Luftfuktighet", "humidity": "Luftfuktighet",
"precipitation": "Nedbør",
"temperature": "Temperatur", "temperature": "Temperatur",
"visibility": "Sikt", "visibility": "Sikt",
"wind_speed": "Vindstyrke" "wind_speed": "Vindstyrke"
@ -531,7 +532,9 @@
"wnw": "VNV", "wnw": "VNV",
"wsw": "VSV" "wsw": "VSV"
}, },
"forecast": "Prognose" "forecast": "Prognose",
"high": "Høy",
"low": "Lav"
} }
}, },
"common": { "common": {
@ -578,11 +581,11 @@
}, },
"related-items": { "related-items": {
"area": "Område", "area": "Område",
"automation": "Del av følgende automatiseringer", "automation": "Del av følgende automasjoner",
"device": "Enhet", "device": "Enhet",
"entity": "Beslektede entiteter", "entity": "Beslektede entiteter",
"group": "Del av følgende grupper", "group": "Del av følgende grupper",
"integration": "Integrering", "integration": "Integrasjoner",
"no_related_found": "Finner ingen relaterte elementer.", "no_related_found": "Finner ingen relaterte elementer.",
"scene": "Del av følgende scener", "scene": "Del av følgende scener",
"script": "Del av følgende skript" "script": "Del av følgende skript"
@ -685,7 +688,7 @@
}, },
"not_editable": "Kan ikke redigeres", "not_editable": "Kan ikke redigeres",
"not_editable_text": "Denne entiteten kan ikke endres fra brukergrensesnittet fordi den er definert i configuration.yaml.", "not_editable_text": "Denne entiteten kan ikke endres fra brukergrensesnittet fordi den er definert i configuration.yaml.",
"platform_not_loaded": "{platform}-integreringen er ikke lastet inn. Legg til konfigurasjonen ved å legge til 'default_config:' eller '{platform}:'.", "platform_not_loaded": "{platform}-integrasjonen er ikke lastet inn. Legg til konfigurasjonen ved å legge til 'default_config:' eller '{platform}:'.",
"required_error_msg": "Dette feltet er påkrevd", "required_error_msg": "Dette feltet er påkrevd",
"yaml_not_editable": "Innstillingene for denne entiteten kan ikke redigeres fra brukergrensesnittet. Bare entiteter som er konfigurert fra brukergrensesnittet, kan konfigureres fra brukergrensesnittet." "yaml_not_editable": "Innstillingene for denne entiteten kan ikke redigeres fra brukergrensesnittet. Bare entiteter som er konfigurert fra brukergrensesnittet, kan konfigureres fra brukergrensesnittet."
}, },
@ -698,7 +701,7 @@
"restored": { "restored": {
"confirm_remove_text": "Er du sikker på at du vil fjerne denne entiteten?", "confirm_remove_text": "Er du sikker på at du vil fjerne denne entiteten?",
"confirm_remove_title": "Vil du fjerne entiteten?", "confirm_remove_title": "Vil du fjerne entiteten?",
"not_provided": "Denne entiteten er ikke tilgjengelig for øyeblikket og er foreldreløs til en fjernet, endret eller ikke-fungerende integrering eller enhet.", "not_provided": "Denne entiteten er ikke tilgjengelig for øyeblikket og er foreldreløs til en fjernet, endret eller ikke-fungerende integrasjon eller enhet.",
"remove_action": "Fjern entitet", "remove_action": "Fjern entitet",
"remove_intro": "Hvis entiteten ikke lenger er i bruk, kan du rense den opp ved å fjerne den." "remove_intro": "Hvis entiteten ikke lenger er i bruk, kan du rense den opp ved å fjerne den."
}, },
@ -812,6 +815,10 @@
"areas": { "areas": {
"caption": "Områder", "caption": "Områder",
"create_area": "OPPRETT OMRÅDE", "create_area": "OPPRETT OMRÅDE",
"data_table": {
"area": "Område",
"devices": "Enheter"
},
"delete": { "delete": {
"confirmation_text": "Alle enheter som tilhører dette området vil ikke bli tildelt.", "confirmation_text": "Alle enheter som tilhører dette området vil ikke bli tildelt.",
"confirmation_title": "Er du sikker på at du vil slette dette området?" "confirmation_title": "Er du sikker på at du vil slette dette området?"
@ -943,14 +950,14 @@
}, },
"unsupported_condition": "Ikke-støttet tilstand: {condition}" "unsupported_condition": "Ikke-støttet tilstand: {condition}"
}, },
"default_name": "Ny automatisering", "default_name": "Ny automasjon",
"description": { "description": {
"label": "Beskrivelse", "label": "Beskrivelse",
"placeholder": "Valgfri beskrivelse" "placeholder": "Valgfri beskrivelse"
}, },
"edit_ui": "Rediger med UI", "edit_ui": "Rediger med UI",
"edit_yaml": "Rediger som YAML", "edit_yaml": "Rediger som YAML",
"enable_disable": "Aktivere/deaktivere automatisering", "enable_disable": "Aktivere/deaktivere automasjon",
"introduction": "Bruk automasjon for å få liv i hjemmet ditt", "introduction": "Bruk automasjon for å få liv i hjemmet ditt",
"load_error_not_editable": "Kun automasjoner i automations.yaml kan redigeres.", "load_error_not_editable": "Kun automasjoner i automations.yaml kan redigeres.",
"load_error_unknown": "Feil ved lasting av automasjon ({err_no}).", "load_error_unknown": "Feil ved lasting av automasjon ({err_no}).",
@ -961,7 +968,7 @@
"delete_confirm": "Er du sikker på at du vil slette dette?", "delete_confirm": "Er du sikker på at du vil slette dette?",
"duplicate": "Dupliser", "duplicate": "Dupliser",
"header": "Utløsere", "header": "Utløsere",
"introduction": "Utløsere er det som starter en automatiseringsregel. Det er mulig å spesifisere flere utløsere for samme regel. Når en utløser aktiveres, vil Home Assistant bekrefte vilkårene, hvis noen, og kjøre handlingen. \n\n[Lær mer om utløsere.](https://home-assistant.io/docs/automation/trigger/)", "introduction": "Utløsere er det som starter en automasjonsregel. Det er mulig å spesifisere flere utløsere for samme regel. Når en utløser aktiveres, vil Home Assistant bekrefte vilkårene - hvis noen - og utføre handlingen. \n\n[Lær mer om utløsere.](https://home-assistant.io/docs/automation/trigger/)",
"learn_more": "Lær mer om utløsere", "learn_more": "Lær mer om utløsere",
"name": "Utløse", "name": "Utløse",
"type_select": "Utløser", "type_select": "Utløser",
@ -1049,17 +1056,20 @@
"unsaved_confirm": "Du har endringer som ikke er lagret. Er du sikker på at du vil forlate?" "unsaved_confirm": "Du har endringer som ikke er lagret. Er du sikker på at du vil forlate?"
}, },
"picker": { "picker": {
"add_automation": "Legg til automatisering", "add_automation": "Legg til automasjon",
"delete_automation": "Slett automasjon", "delete_automation": "Slett automasjon",
"delete_confirm": "Er du sikker på at du vil slette denne automatiseringen?", "delete_confirm": "Er du sikker på at du vil slette denne automasjonen?",
"edit_automation": "Rediger automasjon", "edit_automation": "Rediger automasjon",
"header": "Automasjonsredigering", "header": "Automasjonsredigering",
"headers": {
"name": "Navn"
},
"introduction": "Automasjonsredigeringen lar deg lage og redigere automasjoner. Følg lenken under for å forsikre deg om at du har konfigurert Home Assistant riktig.", "introduction": "Automasjonsredigeringen lar deg lage og redigere automasjoner. Følg lenken under for å forsikre deg om at du har konfigurert Home Assistant riktig.",
"learn_more": "Lær mer om automasjoner", "learn_more": "Lær mer om automasjoner",
"no_automations": "Vi kunne ikke finne noen redigerbare automasjoner", "no_automations": "Vi kunne ikke finne noen redigerbare automasjoner",
"only_editable": "Bare automasjoner definert i automations.yaml kan redigeres.", "only_editable": "Bare automasjoner definert i automations.yaml kan redigeres.",
"pick_automation": "Velg automasjon for å redigere", "pick_automation": "Velg automasjon for å redigere",
"show_info_automation": "Vis informasjon om automatisering" "show_info_automation": "Vis informasjon om automasjon"
} }
}, },
"cloud": { "cloud": {
@ -1122,7 +1132,7 @@
"loading": "Laster inn ...", "loading": "Laster inn ...",
"manage": "Administrer", "manage": "Administrer",
"no_hooks_yet": "Ser ut som du ikke har noen webhooks ennå. Kom i gang ved å konfigurere en ", "no_hooks_yet": "Ser ut som du ikke har noen webhooks ennå. Kom i gang ved å konfigurere en ",
"no_hooks_yet_link_automation": "webhook automatisering", "no_hooks_yet_link_automation": "webhook-automasjon",
"no_hooks_yet_link_integration": "webhook-basert integrasjon", "no_hooks_yet_link_integration": "webhook-basert integrasjon",
"no_hooks_yet2": " eller ved å opprette en ", "no_hooks_yet2": " eller ved å opprette en ",
"title": "Webhooks" "title": "Webhooks"
@ -1302,9 +1312,9 @@
"conditions": { "conditions": {
"caption": "Bare gjør noe hvis..." "caption": "Bare gjør noe hvis..."
}, },
"create": "Lag automatisering med enheten", "create": "Lag automasjon med enheten",
"no_automations": "Ingen automatiseringer", "no_automations": "Ingen automasjoner",
"no_device_automations": "Det er ingen automatiseringer tilgjengelig for denne enheten.", "no_device_automations": "Det er ingen automasjoner tilgjengelig for denne enheten.",
"triggers": { "triggers": {
"caption": "Gjør noe når ..." "caption": "Gjør noe når ..."
} }
@ -1318,7 +1328,7 @@
"area": "Område", "area": "Område",
"battery": "Batteri", "battery": "Batteri",
"device": "Enhet", "device": "Enhet",
"integration": "Integrering", "integration": "Integrasjon",
"manufacturer": "Produsent", "manufacturer": "Produsent",
"model": "Modell", "model": "Modell",
"no_devices": "Ingen enheter" "no_devices": "Ingen enheter"
@ -1334,6 +1344,7 @@
}, },
"info": "Enhetsinformasjon", "info": "Enhetsinformasjon",
"name": "Navn", "name": "Navn",
"no_devices": "Ingen enheter",
"scene": { "scene": {
"create": "Lag scene med enheten", "create": "Lag scene med enheten",
"no_scenes": "Ingen scener", "no_scenes": "Ingen scener",
@ -1388,7 +1399,7 @@
"headers": { "headers": {
"enabled": "Aktivert", "enabled": "Aktivert",
"entity_id": "Entitets-ID", "entity_id": "Entitets-ID",
"integration": "Integrering", "integration": "Integrasjon",
"name": "Navn", "name": "Navn",
"status": "" "status": ""
}, },
@ -1399,7 +1410,7 @@
"button": "Fjern valgte", "button": "Fjern valgte",
"confirm_partly_text": "Du kan bare fjerne {removable} av de valgte {selected} enhetene. Enheter kan bare fjernes når integrasjonen ikke lenger leverer enhetene. Noen ganger må du starte Home Assistant på nytt før du kan fjerne enhetene til en fjernet integrasjon. Er du sikker på at du vil fjerne de flyttbare enhetene?", "confirm_partly_text": "Du kan bare fjerne {removable} av de valgte {selected} enhetene. Enheter kan bare fjernes når integrasjonen ikke lenger leverer enhetene. Noen ganger må du starte Home Assistant på nytt før du kan fjerne enhetene til en fjernet integrasjon. Er du sikker på at du vil fjerne de flyttbare enhetene?",
"confirm_partly_title": "Bare {number} valgte enheter kan fjernes.", "confirm_partly_title": "Bare {number} valgte enheter kan fjernes.",
"confirm_text": "Du bør fjerne dem fra Lovelace config og automatiseringer hvis de inneholder disse enhetene.", "confirm_text": "Du bør fjerne dem fra Lovelace-konfigurasjonen og automasjoner hvis de inneholder disse entitetene.",
"confirm_title": "Vil du fjerne {number} enheter?" "confirm_title": "Vil du fjerne {number} enheter?"
}, },
"selected": "{number} valgte", "selected": "{number} valgte",
@ -1417,7 +1428,7 @@
"header": "Konfigurer Home Assistant", "header": "Konfigurer Home Assistant",
"helpers": { "helpers": {
"caption": "Hjelpere", "caption": "Hjelpere",
"description": "Elementer som kan bidra til å bygge automatiseringer.", "description": "Elementer som kan bidra til å bygge automasjoner.",
"dialog": { "dialog": {
"add_helper": "Legg hjelper", "add_helper": "Legg hjelper",
"add_platform": "Legg til {platform}", "add_platform": "Legg til {platform}",
@ -1473,7 +1484,7 @@
}, },
"failed_create_area": "Kunne ikke opprette område.", "failed_create_area": "Kunne ikke opprette område.",
"finish": "Fullfør", "finish": "Fullfør",
"loading_first_time": "Vent mens integreringen installeres", "loading_first_time": "Vent mens integrasjonen installeres",
"name_new_area": "Navn på det nye området?", "name_new_area": "Navn på det nye området?",
"not_all_required_fields": "Ikke alle obligatoriske felt er fylt ut.", "not_all_required_fields": "Ikke alle obligatoriske felt er fylt ut.",
"submit": "Send inn" "submit": "Send inn"
@ -1487,7 +1498,7 @@
"ignore": { "ignore": {
"confirm_delete_ignore": "Dette vil få integrasjonen til å vises i de oppdagede integrasjonene dine igjen når den blir oppdaget. Dette kan kreve omstart eller ta litt tid.", "confirm_delete_ignore": "Dette vil få integrasjonen til å vises i de oppdagede integrasjonene dine igjen når den blir oppdaget. Dette kan kreve omstart eller ta litt tid.",
"confirm_delete_ignore_title": "Slutt å ignorere {name}?", "confirm_delete_ignore_title": "Slutt å ignorere {name}?",
"confirm_ignore": "Er du sikker på at du ikke vil konfigurere denne integreringen? Du kan angre dette ved å klikke på «Vis ignorerte integreringer» i overflow-menyen øverst til høyre.", "confirm_ignore": "Er du sikker på at du ikke vil konfigurere denne integrasjonen? Du kan angre ved å klikke på «Vis ignorerte integrasjoner» i overflow-menyen øverst til høyre.",
"confirm_ignore_title": "Ignorer oppdaging av {name}?", "confirm_ignore_title": "Ignorer oppdaging av {name}?",
"hide_ignored": "Skjul ignorerte integrasjoner", "hide_ignored": "Skjul ignorerte integrasjoner",
"ignore": "Ignorer", "ignore": "Ignorer",
@ -1593,12 +1604,12 @@
"device_tracker_pick": "Velg en enhet å spore", "device_tracker_pick": "Velg en enhet å spore",
"device_tracker_picked": "Spor enhet", "device_tracker_picked": "Spor enhet",
"link_integrations_page": "Integrasjonsside", "link_integrations_page": "Integrasjonsside",
"link_presence_detection_integrations": "Integrering av tilstedeværelsesdeteksjon", "link_presence_detection_integrations": "Integrasjon for tilstedeværelsesdeteksjon",
"linked_user": "Koblet bruker", "linked_user": "Koblet bruker",
"name": "Navn", "name": "Navn",
"name_error_msg": "Navn er påkrevd", "name_error_msg": "Navn er påkrevd",
"new_person": "Ny person", "new_person": "Ny person",
"no_device_tracker_available_intro": "Når du har enheter som indikerer en persons tilstedeværelse, vil du kunne tilordne dem til en person her. Du kan legge til den første enheten ved å legge til en integrering av tilstedeværelses gjenkjenning fra integrerings siden.", "no_device_tracker_available_intro": "Når du har enheter som indikerer en persons tilstedeværelse, vil du kunne tilordne dem til en person herfra. Du kan legge til den første enheten ved å legge til en integrasjon for tilstedeværelsesgjenkjenning fra integrasjonssiden.",
"update": "Oppdater" "update": "Oppdater"
}, },
"introduction": "Her kan du definere hver person av interesse i Home Assistant.", "introduction": "Her kan du definere hver person av interesse i Home Assistant.",
@ -1638,6 +1649,9 @@
"delete_scene": "Slett scene", "delete_scene": "Slett scene",
"edit_scene": "Rediger scene", "edit_scene": "Rediger scene",
"header": "Sceneditor", "header": "Sceneditor",
"headers": {
"name": "Navn"
},
"introduction": "Sceneditoren lar deg lage og redigere scener. Følg lenken nedenfor for å lese instruksjonene for å forsikre deg om at du har konfigurert Home Assistant riktig.", "introduction": "Sceneditoren lar deg lage og redigere scener. Følg lenken nedenfor for å lese instruksjonene for å forsikre deg om at du har konfigurert Home Assistant riktig.",
"learn_more": "Lær mer om scener", "learn_more": "Lær mer om scener",
"no_scenes": "Vi fant ingen redigerbare scener", "no_scenes": "Vi fant ingen redigerbare scener",
@ -1665,9 +1679,13 @@
"add_script": "Legg til skript", "add_script": "Legg til skript",
"edit_script": "Rediger skript", "edit_script": "Rediger skript",
"header": "Skriptredigering", "header": "Skriptredigering",
"headers": {
"name": "Navn"
},
"introduction": "Skripteditoren lar deg lage og redigere skript. Følg lenken nedenfor for å lese instruksjonene for å forsikre deg om at du har konfigurert Home Assistant riktig.", "introduction": "Skripteditoren lar deg lage og redigere skript. Følg lenken nedenfor for å lese instruksjonene for å forsikre deg om at du har konfigurert Home Assistant riktig.",
"learn_more": "Lær mer om skript", "learn_more": "Lær mer om skript",
"no_scripts": "Vi kunne ikke finne noen redigerbare skript", "no_scripts": "Vi kunne ikke finne noen redigerbare skript",
"show_info": "Vis informasjon om skript",
"trigger_script": "Utløse skript" "trigger_script": "Utløse skript"
} }
}, },
@ -1725,14 +1743,21 @@
"group": "Gruppe", "group": "Gruppe",
"group_update_failed": "Gruppeoppdatering mislyktes:", "group_update_failed": "Gruppeoppdatering mislyktes:",
"id": "Id", "id": "Id",
"name": "Navn",
"owner": "Eier", "owner": "Eier",
"rename_user": "Gi nytt navn til bruker", "rename_user": "Gi nytt navn til bruker",
"system_generated": "System generert", "system_generated": "System generert",
"system_generated_users_not_removable": "Kan ikke fjerne systemgenererte brukere.", "system_generated_users_not_removable": "Kan ikke fjerne systemgenererte brukere.",
"unnamed_user": "Bruker uten navn", "unnamed_user": "Bruker uten navn",
"update_user": "Oppdater",
"user_rename_failed": "Brukernavn mislyktes:" "user_rename_failed": "Brukernavn mislyktes:"
}, },
"picker": { "picker": {
"headers": {
"group": "Gruppe",
"name": "Navn",
"system": "System"
},
"system_generated": "System generert", "system_generated": "System generert",
"title": "Brukere" "title": "Brukere"
} }
@ -1862,7 +1887,7 @@
"name": "Navn", "name": "Navn",
"new_zone": "Ny sone", "new_zone": "Ny sone",
"passive": "Passiv", "passive": "Passiv",
"passive_note": "Passive soner er skjult i grensesnittet og brukes ikke som sted for enhetssporere. Dette er nyttig hvis du bare vil bruke det til automatiseringer.", "passive_note": "Passive soner er skjult i grensesnittet og brukes ikke som sted for enhetssporere. Dette er nyttig hvis du bare vil bruke dem til automasjoner.",
"radius": "", "radius": "",
"required_error_msg": "Dette feltet er påkrevd", "required_error_msg": "Dette feltet er påkrevd",
"update": "Oppdater" "update": "Oppdater"
@ -1871,7 +1896,7 @@
"edit_home_zone_narrow": "Radiusen til hjemsonen kan ikke redigeres fra frontend ennå. Plasseringen kan endres fra den generelle konfigurasjonen.", "edit_home_zone_narrow": "Radiusen til hjemsonen kan ikke redigeres fra frontend ennå. Plasseringen kan endres fra den generelle konfigurasjonen.",
"go_to_core_config": "Gå til generell konfigurasjon?", "go_to_core_config": "Gå til generell konfigurasjon?",
"home_zone_core_config": "Plasseringen av hjemmesonen kan redigeres fra den generelle konfigurasjonssiden. Radiusen til hjemsonen kan ikke redigeres fra frontend ennå. Vil du gå til den generelle konfigurasjonen?", "home_zone_core_config": "Plasseringen av hjemmesonen kan redigeres fra den generelle konfigurasjonssiden. Radiusen til hjemsonen kan ikke redigeres fra frontend ennå. Vil du gå til den generelle konfigurasjonen?",
"introduction": "Med soner kan du angi bestemte områder på jorden. Når en person er innenfor en sone, vil staten ta navnet fra sonen. Soner kan også brukes som en utløser eller tilstand i automatiserings oppsett.", "introduction": "Med soner kan du angi bestemte områder på jorden. Når en person er innenfor en sone, vil tilstanden til lokasjonen ta navnet fra sonen. Soner kan også brukes som en utløser eller tilstand i automasjoner.",
"no_zones_created_yet": "Det ser ut til at du ikke har opprettet noen soner enda." "no_zones_created_yet": "Det ser ut til at du ikke har opprettet noen soner enda."
}, },
"zwave": { "zwave": {
@ -2135,6 +2160,9 @@
"description": "Entity Filter-kortet lar deg definere en liste over entiteter du bare vil spore når de er i en viss tilstand.", "description": "Entity Filter-kortet lar deg definere en liste over entiteter du bare vil spore når de er i en viss tilstand.",
"name": "Entitetsfilter" "name": "Entitetsfilter"
}, },
"entity": {
"name": "Entitet"
},
"gauge": { "gauge": {
"description": "Gauge-kortet er et grunnleggende kort som gjør det mulig å se sensordata visuelt.", "description": "Gauge-kortet er et grunnleggende kort som gjør det mulig å se sensordata visuelt.",
"name": "Måler", "name": "Måler",
@ -2147,8 +2175,10 @@
}, },
"generic": { "generic": {
"aspect_ratio": "Størrelsesforholdet", "aspect_ratio": "Størrelsesforholdet",
"attribute": "Attributtet",
"camera_image": "Kameraentitet", "camera_image": "Kameraentitet",
"camera_view": "Kameravisning", "camera_view": "Kameravisning",
"double_tap_action": "Dobbelttrykk Handling",
"entities": "Entiteter", "entities": "Entiteter",
"entity": "Entitet", "entity": "Entitet",
"hold_action": "Hold handling", "hold_action": "Hold handling",
@ -2199,6 +2229,7 @@
"default_zoom": "Standard zoom", "default_zoom": "Standard zoom",
"description": "Kartkortet som lar deg vise enheter på et kart.", "description": "Kartkortet som lar deg vise enheter på et kart.",
"geo_location_sources": "Kilder for geolokasjon", "geo_location_sources": "Kilder for geolokasjon",
"hours_to_show": "Timer som skal vises",
"name": "Kart", "name": "Kart",
"source": "Kilde" "source": "Kilde"
}, },
@ -2216,7 +2247,7 @@
"name": "Bildeelementer" "name": "Bildeelementer"
}, },
"picture-entity": { "picture-entity": {
"description": "Picture Entity-kortet viser en entitet i form av et bilde. I stedet for bilder fra URL, kan det også vise bilde av kameraenheter.", "description": "Picture Entity-kortet viser en entitet i form av et bilde. I stedet for bilder fra URL, kan det også vise bilde av kameraentiteter.",
"name": "Bildeoppføring" "name": "Bildeoppføring"
}, },
"picture-glance": { "picture-glance": {
@ -2255,6 +2286,10 @@
"name": "Værmelding" "name": "Værmelding"
} }
}, },
"cardpicker": {
"custom_card": "Tilpasset",
"no_description": "Ingen beskrivelse tilgjengelig."
},
"edit_card": { "edit_card": {
"add": "Legg til kort", "add": "Legg til kort",
"delete": "Slett kort", "delete": "Slett kort",
@ -2319,6 +2354,7 @@
"save_config": { "save_config": {
"cancel": "Glem det", "cancel": "Glem det",
"close": "Lukk", "close": "Lukk",
"empty_config": "Start med et tomt instrumentbord",
"header": "Ta kontroll over Lovelace brukergrensesnittet ditt", "header": "Ta kontroll over Lovelace brukergrensesnittet ditt",
"para": "Som standard vil Home Assistant opprettholde brukergrensesnittet ditt, oppdatere det når nye enheter eller Lovelace UI-komponenter blir tilgjengelige. Hvis du tar kontroll, vil vi ikke lenger gjøre endringer automatisk for deg.", "para": "Som standard vil Home Assistant opprettholde brukergrensesnittet ditt, oppdatere det når nye enheter eller Lovelace UI-komponenter blir tilgjengelige. Hvis du tar kontroll, vil vi ikke lenger gjøre endringer automatisk for deg.",
"para_sure": "Er du sikker på at du vil ta kontroll over brukergrensesnittet ditt?", "para_sure": "Er du sikker på at du vil ta kontroll over brukergrensesnittet ditt?",
@ -2568,6 +2604,11 @@
"submit": "Send inn" "submit": "Send inn"
}, },
"current_user": "Du er logget inn som {fullName}.", "current_user": "Du er logget inn som {fullName}.",
"dashboard": {
"description": "Velg et standard dashbord for denne enheten.",
"dropdown_label": "Dashboard",
"header": "Dashboard"
},
"force_narrow": { "force_narrow": {
"description": "Dette vil skjule sidepanelet som standard, tilsvarende opplevelsen på en mobil.", "description": "Dette vil skjule sidepanelet som standard, tilsvarende opplevelsen på en mobil.",
"header": "Skjul alltid sidepanelet" "header": "Skjul alltid sidepanelet"

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "Luchtdruk", "air_pressure": "Luchtdruk",
"humidity": "Vochtigheid", "humidity": "Vochtigheid",
"precipitation": "Neerslag",
"temperature": "Temperatuur", "temperature": "Temperatuur",
"visibility": "Zicht", "visibility": "Zicht",
"wind_speed": "Windsnelheid" "wind_speed": "Windsnelheid"
@ -531,7 +532,9 @@
"wnw": "WNW", "wnw": "WNW",
"wsw": "WZW" "wsw": "WZW"
}, },
"forecast": "Verwachting" "forecast": "Verwachting",
"high": "hoog",
"low": "Laag"
} }
}, },
"common": { "common": {
@ -2175,6 +2178,7 @@
"attribute": "Kenmerk", "attribute": "Kenmerk",
"camera_image": "Camera-entiteit", "camera_image": "Camera-entiteit",
"camera_view": "Cameraweergave", "camera_view": "Cameraweergave",
"double_tap_action": "Dubbele tik Actie",
"entities": "Entiteiten", "entities": "Entiteiten",
"entity": "Entiteit", "entity": "Entiteit",
"hold_action": "Actie vasthouden", "hold_action": "Actie vasthouden",
@ -2225,6 +2229,7 @@
"default_zoom": "Standaard zoom", "default_zoom": "Standaard zoom",
"description": "Met de Map-kaart kun je entiteiten op een kaart kunt weergeven.", "description": "Met de Map-kaart kun je entiteiten op een kaart kunt weergeven.",
"geo_location_sources": "Geolocatiebronnen", "geo_location_sources": "Geolocatiebronnen",
"hours_to_show": "Uren om weer te geven",
"name": "Kaart", "name": "Kaart",
"source": "Bron" "source": "Bron"
}, },
@ -2281,6 +2286,10 @@
"name": "Weersverwachting" "name": "Weersverwachting"
} }
}, },
"cardpicker": {
"custom_card": "Aangepaste UI's:",
"no_description": "Er is geen beschrijving beschikbaar"
},
"edit_card": { "edit_card": {
"add": "Kaart toevoegen", "add": "Kaart toevoegen",
"delete": "Verwijder kaart", "delete": "Verwijder kaart",

View File

@ -1731,6 +1731,7 @@
"editor": { "editor": {
"activate_user": "Активировать", "activate_user": "Активировать",
"active": "Активен", "active": "Активен",
"admin": "Администратор",
"caption": "Просмотр пользователя", "caption": "Просмотр пользователя",
"change_password": "Изменить пароль", "change_password": "Изменить пароль",
"confirm_user_deletion": "Вы уверены, что хотите удалить {name}?", "confirm_user_deletion": "Вы уверены, что хотите удалить {name}?",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "气压", "air_pressure": "气压",
"humidity": "湿度", "humidity": "湿度",
"precipitation": "降水量",
"temperature": "温度", "temperature": "温度",
"visibility": "能见度", "visibility": "能见度",
"wind_speed": "风速" "wind_speed": "风速"
@ -531,7 +532,9 @@
"wnw": "西北偏西", "wnw": "西北偏西",
"wsw": "西南偏西" "wsw": "西南偏西"
}, },
"forecast": "预报" "forecast": "预报",
"high": "高",
"low": "低"
} }
}, },
"common": { "common": {
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "激活用户", "activate_user": "激活用户",
"active": "激活", "active": "激活",
"admin": "管理员",
"caption": "用户信息", "caption": "用户信息",
"change_password": "更改密码", "change_password": "更改密码",
"confirm_user_deletion": "您确定要删除{name}吗?", "confirm_user_deletion": "您确定要删除{name}吗?",
@ -1744,6 +1748,7 @@
"owner": "所有者", "owner": "所有者",
"rename_user": "重命名用户", "rename_user": "重命名用户",
"system_generated": "系统生成", "system_generated": "系统生成",
"system_generated_users_not_editable": "无法更新系统生成的用户。",
"system_generated_users_not_removable": "无法删除系统生成的用户。", "system_generated_users_not_removable": "无法删除系统生成的用户。",
"unnamed_user": "未命名的用户", "unnamed_user": "未命名的用户",
"update_user": "更新", "update_user": "更新",
@ -2175,6 +2180,7 @@
"attribute": "属性", "attribute": "属性",
"camera_image": "相机实体", "camera_image": "相机实体",
"camera_view": "相机视图", "camera_view": "相机视图",
"double_tap_action": "双击动作",
"entities": "实体", "entities": "实体",
"entity": "实体", "entity": "实体",
"hold_action": "保持操作", "hold_action": "保持操作",
@ -2225,6 +2231,7 @@
"default_zoom": "默认缩放", "default_zoom": "默认缩放",
"description": "“地图”卡片用于在地图上显示实体。", "description": "“地图”卡片用于在地图上显示实体。",
"geo_location_sources": "地理位置来源", "geo_location_sources": "地理位置来源",
"hours_to_show": "显示时间",
"name": "地图", "name": "地图",
"source": "位置来源" "source": "位置来源"
}, },
@ -2281,6 +2288,10 @@
"name": "天气预报" "name": "天气预报"
} }
}, },
"cardpicker": {
"custom_card": "自定义",
"no_description": "没有描述。"
},
"edit_card": { "edit_card": {
"add": "添加卡片", "add": "添加卡片",
"delete": "删除", "delete": "删除",

View File

@ -509,6 +509,7 @@
"attributes": { "attributes": {
"air_pressure": "大氣壓", "air_pressure": "大氣壓",
"humidity": "濕度", "humidity": "濕度",
"precipitation": "降雨量",
"temperature": "溫度", "temperature": "溫度",
"visibility": "顯示選項", "visibility": "顯示選項",
"wind_speed": "風速" "wind_speed": "風速"
@ -531,7 +532,9 @@
"wnw": "西北西", "wnw": "西北西",
"wsw": "西南西" "wsw": "西南西"
}, },
"forecast": "預報" "forecast": "預報",
"high": "高",
"low": "低"
} }
}, },
"common": { "common": {
@ -1731,6 +1734,7 @@
"editor": { "editor": {
"activate_user": "激活用戶", "activate_user": "激活用戶",
"active": "啟用", "active": "啟用",
"admin": "管理員",
"caption": "檢視用戶", "caption": "檢視用戶",
"change_password": "更改密碼", "change_password": "更改密碼",
"confirm_user_deletion": "確定要刪除 {name}", "confirm_user_deletion": "確定要刪除 {name}",
@ -1744,6 +1748,7 @@
"owner": "擁有者", "owner": "擁有者",
"rename_user": "重命名用戶", "rename_user": "重命名用戶",
"system_generated": "系統產生", "system_generated": "系統產生",
"system_generated_users_not_editable": "無法更新系統產生用戶",
"system_generated_users_not_removable": "無法移除系統產生用戶", "system_generated_users_not_removable": "無法移除系統產生用戶",
"unnamed_user": "未命名用戶", "unnamed_user": "未命名用戶",
"update_user": "更新", "update_user": "更新",
@ -2175,6 +2180,7 @@
"attribute": "屬性", "attribute": "屬性",
"camera_image": "攝影機物件", "camera_image": "攝影機物件",
"camera_view": "攝影機視角", "camera_view": "攝影機視角",
"double_tap_action": "雙點擊觸發",
"entities": "物件", "entities": "物件",
"entity": "物件", "entity": "物件",
"hold_action": "保持觸發", "hold_action": "保持觸發",
@ -2225,6 +2231,7 @@
"default_zoom": "預設大小", "default_zoom": "預設大小",
"description": "地圖面板可供顯示地圖物件。", "description": "地圖面板可供顯示地圖物件。",
"geo_location_sources": "地理位置來源", "geo_location_sources": "地理位置來源",
"hours_to_show": "顯示小時",
"name": "地圖面板", "name": "地圖面板",
"source": "來源" "source": "來源"
}, },
@ -2281,6 +2288,10 @@
"name": "天氣預報面板" "name": "天氣預報面板"
} }
}, },
"cardpicker": {
"custom_card": "自訂面板",
"no_description": "無描述可使用。"
},
"edit_card": { "edit_card": {
"add": "新增面板", "add": "新增面板",
"delete": "刪除面板", "delete": "刪除面板",