mirror of
https://github.com/home-assistant/frontend.git
synced 2025-07-23 09:16:38 +00:00
Add yaml mode to view editor (#13926)
This commit is contained in:
parent
2a6ef9b955
commit
6a3ac9116e
@ -1,13 +1,26 @@
|
|||||||
import "@material/mwc-button";
|
import "@material/mwc-button";
|
||||||
|
import { ActionDetail } from "@material/mwc-list";
|
||||||
|
import { mdiCheck, mdiDotsVertical } from "@mdi/js";
|
||||||
import "@polymer/paper-tabs/paper-tab";
|
import "@polymer/paper-tabs/paper-tab";
|
||||||
import "@polymer/paper-tabs/paper-tabs";
|
import "@polymer/paper-tabs/paper-tabs";
|
||||||
import { css, CSSResultGroup, html, LitElement, TemplateResult } from "lit";
|
import {
|
||||||
import { customElement, property, state } from "lit/decorators";
|
css,
|
||||||
|
CSSResultGroup,
|
||||||
|
html,
|
||||||
|
LitElement,
|
||||||
|
PropertyValues,
|
||||||
|
TemplateResult,
|
||||||
|
} from "lit";
|
||||||
|
import { customElement, property, query, state } from "lit/decorators";
|
||||||
|
import { classMap } from "lit/directives/class-map";
|
||||||
import { fireEvent, HASSDomEvent } from "../../../../common/dom/fire_event";
|
import { fireEvent, HASSDomEvent } from "../../../../common/dom/fire_event";
|
||||||
|
import { stopPropagation } from "../../../../common/dom/stop_propagation";
|
||||||
import { navigate } from "../../../../common/navigate";
|
import { navigate } from "../../../../common/navigate";
|
||||||
|
import { deepEqual } from "../../../../common/util/deep-equal";
|
||||||
|
import "../../../../components/ha-alert";
|
||||||
import "../../../../components/ha-circular-progress";
|
import "../../../../components/ha-circular-progress";
|
||||||
import "../../../../components/ha-dialog";
|
import "../../../../components/ha-dialog";
|
||||||
import "../../../../components/ha-alert";
|
import { HaYamlEditor } from "../../../../components/ha-yaml-editor";
|
||||||
import type {
|
import type {
|
||||||
LovelaceBadgeConfig,
|
LovelaceBadgeConfig,
|
||||||
LovelaceCardConfig,
|
LovelaceCardConfig,
|
||||||
@ -20,6 +33,11 @@ import {
|
|||||||
import { haStyleDialog } from "../../../../resources/styles";
|
import { haStyleDialog } from "../../../../resources/styles";
|
||||||
import type { HomeAssistant } from "../../../../types";
|
import type { HomeAssistant } from "../../../../types";
|
||||||
import "../../components/hui-entity-editor";
|
import "../../components/hui-entity-editor";
|
||||||
|
import {
|
||||||
|
DEFAULT_VIEW_LAYOUT,
|
||||||
|
PANEL_VIEW_LAYOUT,
|
||||||
|
VIEWS_NO_BADGE_SUPPORT,
|
||||||
|
} from "../../views/const";
|
||||||
import { addView, deleteView, replaceView } from "../config-util";
|
import { addView, deleteView, replaceView } from "../config-util";
|
||||||
import "../hui-badge-preview";
|
import "../hui-badge-preview";
|
||||||
import { processEditorEntities } from "../process-editor-entities";
|
import { processEditorEntities } from "../process-editor-entities";
|
||||||
@ -31,12 +49,6 @@ import {
|
|||||||
import "./hui-view-editor";
|
import "./hui-view-editor";
|
||||||
import "./hui-view-visibility-editor";
|
import "./hui-view-visibility-editor";
|
||||||
import { EditViewDialogParams } from "./show-edit-view-dialog";
|
import { EditViewDialogParams } from "./show-edit-view-dialog";
|
||||||
import {
|
|
||||||
DEFAULT_VIEW_LAYOUT,
|
|
||||||
PANEL_VIEW_LAYOUT,
|
|
||||||
VIEWS_NO_BADGE_SUPPORT,
|
|
||||||
} from "../../views/const";
|
|
||||||
import { deepEqual } from "../../../../common/util/deep-equal";
|
|
||||||
|
|
||||||
@customElement("hui-dialog-edit-view")
|
@customElement("hui-dialog-edit-view")
|
||||||
export class HuiDialogEditView extends LitElement {
|
export class HuiDialogEditView extends LitElement {
|
||||||
@ -56,6 +68,10 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
|
|
||||||
@state() private _dirty = false;
|
@state() private _dirty = false;
|
||||||
|
|
||||||
|
@state() private _yamlMode = false;
|
||||||
|
|
||||||
|
@query("ha-yaml-editor") private _editor?: HaYamlEditor;
|
||||||
|
|
||||||
private _curTabIndex = 0;
|
private _curTabIndex = 0;
|
||||||
|
|
||||||
get _type(): string {
|
get _type(): string {
|
||||||
@ -67,6 +83,16 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
: this._config.type || DEFAULT_VIEW_LAYOUT;
|
: this._config.type || DEFAULT_VIEW_LAYOUT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected updated(changedProperties: PropertyValues) {
|
||||||
|
if (this._yamlMode && changedProperties.has("_yamlMode")) {
|
||||||
|
const viewConfig = {
|
||||||
|
...this._config,
|
||||||
|
badges: this._badges,
|
||||||
|
};
|
||||||
|
this._editor?.setValue(viewConfig);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public showDialog(params: EditViewDialogParams): void {
|
public showDialog(params: EditViewDialogParams): void {
|
||||||
this._params = params;
|
this._params = params;
|
||||||
|
|
||||||
@ -89,6 +115,7 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
this._params = undefined;
|
this._params = undefined;
|
||||||
this._config = {};
|
this._config = {};
|
||||||
this._badges = [];
|
this._badges = [];
|
||||||
|
this._yamlMode = false;
|
||||||
this._dirty = false;
|
this._dirty = false;
|
||||||
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
fireEvent(this, "dialog-closed", { dialog: this.localName });
|
||||||
}
|
}
|
||||||
@ -111,62 +138,74 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let content;
|
let content;
|
||||||
switch (this._curTab) {
|
|
||||||
case "tab-settings":
|
if (this._yamlMode) {
|
||||||
content = html`
|
content = html`
|
||||||
<hui-view-editor
|
<ha-yaml-editor
|
||||||
.isNew=${this._params.viewIndex === undefined}
|
.hass=${this.hass}
|
||||||
.hass=${this.hass}
|
dialogInitialFocus
|
||||||
.config=${this._config}
|
@value-changed=${this._viewYamlChanged}
|
||||||
@view-config-changed=${this._viewConfigChanged}
|
></ha-yaml-editor>
|
||||||
></hui-view-editor>
|
`;
|
||||||
`;
|
} else {
|
||||||
break;
|
switch (this._curTab) {
|
||||||
case "tab-badges":
|
case "tab-settings":
|
||||||
content = html`
|
content = html`
|
||||||
${this._badges?.length
|
<hui-view-editor
|
||||||
? html`
|
.isNew=${this._params.viewIndex === undefined}
|
||||||
${VIEWS_NO_BADGE_SUPPORT.includes(this._type)
|
.hass=${this.hass}
|
||||||
? html`
|
.config=${this._config}
|
||||||
<ha-alert alert-type="warning">
|
@view-config-changed=${this._viewConfigChanged}
|
||||||
${this.hass!.localize(
|
></hui-view-editor>
|
||||||
"ui.panel.lovelace.editor.edit_badges.view_no_badges"
|
`;
|
||||||
)}
|
break;
|
||||||
</ha-alert>
|
case "tab-badges":
|
||||||
`
|
content = html`
|
||||||
: ""}
|
${this._badges?.length
|
||||||
<div class="preview-badges">
|
? html`
|
||||||
${this._badges.map(
|
${VIEWS_NO_BADGE_SUPPORT.includes(this._type)
|
||||||
(badgeConfig) => html`
|
? html`
|
||||||
<hui-badge-preview
|
<ha-alert alert-type="warning">
|
||||||
.hass=${this.hass}
|
${this.hass!.localize(
|
||||||
.config=${badgeConfig}
|
"ui.panel.lovelace.editor.edit_badges.view_no_badges"
|
||||||
></hui-badge-preview>
|
)}
|
||||||
`
|
</ha-alert>
|
||||||
)}
|
`
|
||||||
</div>
|
: ""}
|
||||||
`
|
<div class="preview-badges">
|
||||||
: ""}
|
${this._badges.map(
|
||||||
<hui-entity-editor
|
(badgeConfig) => html`
|
||||||
.hass=${this.hass}
|
<hui-badge-preview
|
||||||
.entities=${this._badges}
|
.hass=${this.hass}
|
||||||
@entities-changed=${this._badgesChanged}
|
.config=${badgeConfig}
|
||||||
></hui-entity-editor>
|
></hui-badge-preview>
|
||||||
`;
|
`
|
||||||
break;
|
)}
|
||||||
case "tab-visibility":
|
</div>
|
||||||
content = html`
|
`
|
||||||
<hui-view-visibility-editor
|
: ""}
|
||||||
.hass=${this.hass}
|
<hui-entity-editor
|
||||||
.config=${this._config}
|
.hass=${this.hass}
|
||||||
@view-visibility-changed=${this._viewVisibilityChanged}
|
.entities=${this._badges}
|
||||||
></hui-view-visibility-editor>
|
@entities-changed=${this._badgesChanged}
|
||||||
`;
|
></hui-entity-editor>
|
||||||
break;
|
`;
|
||||||
case "tab-cards":
|
break;
|
||||||
content = html` Cards `;
|
case "tab-visibility":
|
||||||
break;
|
content = html`
|
||||||
|
<hui-view-visibility-editor
|
||||||
|
.hass=${this.hass}
|
||||||
|
.config=${this._config}
|
||||||
|
@view-visibility-changed=${this._viewVisibilityChanged}
|
||||||
|
></hui-view-visibility-editor>
|
||||||
|
`;
|
||||||
|
break;
|
||||||
|
case "tab-cards":
|
||||||
|
content = html` Cards `;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return html`
|
return html`
|
||||||
<ha-dialog
|
<ha-dialog
|
||||||
open
|
open
|
||||||
@ -174,31 +213,75 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
escapeKeyAction
|
escapeKeyAction
|
||||||
@closed=${this.closeDialog}
|
@closed=${this.closeDialog}
|
||||||
.heading=${this._viewConfigTitle}
|
.heading=${this._viewConfigTitle}
|
||||||
|
class=${classMap({
|
||||||
|
"yaml-mode": this._yamlMode,
|
||||||
|
})}
|
||||||
>
|
>
|
||||||
<div slot="heading">
|
<div slot="heading">
|
||||||
<h2>${this._viewConfigTitle}</h2>
|
<h2>${this._viewConfigTitle}</h2>
|
||||||
<paper-tabs
|
<ha-button-menu
|
||||||
scrollable
|
slot="icons"
|
||||||
hide-scroll-buttons
|
fixed
|
||||||
.selected=${this._curTabIndex}
|
corner="BOTTOM_END"
|
||||||
@selected-item-changed=${this._handleTabSelected}
|
menuCorner="END"
|
||||||
|
@action=${this._handleAction}
|
||||||
|
@closed=${stopPropagation}
|
||||||
>
|
>
|
||||||
<paper-tab id="tab-settings" dialogInitialFocus
|
<ha-icon-button
|
||||||
>${this.hass!.localize(
|
slot="trigger"
|
||||||
"ui.panel.lovelace.editor.edit_view.tab_settings"
|
.label=${this.hass!.localize("ui.common.menu")}
|
||||||
)}</paper-tab
|
.path=${mdiDotsVertical}
|
||||||
>
|
></ha-icon-button>
|
||||||
<paper-tab id="tab-badges"
|
<mwc-list-item graphic="icon">
|
||||||
>${this.hass!.localize(
|
${this.hass!.localize(
|
||||||
"ui.panel.lovelace.editor.edit_view.tab_badges"
|
"ui.panel.lovelace.editor.edit_view.edit_ui"
|
||||||
)}</paper-tab
|
)}
|
||||||
>
|
${!this._yamlMode
|
||||||
<paper-tab id="tab-visibility"
|
? html`<ha-svg-icon
|
||||||
>${this.hass!.localize(
|
class="selected_menu_item"
|
||||||
"ui.panel.lovelace.editor.edit_view.tab_visibility"
|
slot="graphic"
|
||||||
)}</paper-tab
|
.path=${mdiCheck}
|
||||||
>
|
></ha-svg-icon>`
|
||||||
</paper-tabs>
|
: ``}
|
||||||
|
</mwc-list-item>
|
||||||
|
|
||||||
|
<mwc-list-item graphic="icon">
|
||||||
|
${this.hass!.localize(
|
||||||
|
"ui.panel.lovelace.editor.edit_view.edit_yaml"
|
||||||
|
)}
|
||||||
|
${this._yamlMode
|
||||||
|
? html`<ha-svg-icon
|
||||||
|
class="selected_menu_item"
|
||||||
|
slot="graphic"
|
||||||
|
.path=${mdiCheck}
|
||||||
|
></ha-svg-icon>`
|
||||||
|
: ``}
|
||||||
|
</mwc-list-item>
|
||||||
|
</ha-button-menu>
|
||||||
|
${!this._yamlMode
|
||||||
|
? html`<paper-tabs
|
||||||
|
scrollable
|
||||||
|
hide-scroll-buttons
|
||||||
|
.selected=${this._curTabIndex}
|
||||||
|
@selected-item-changed=${this._handleTabSelected}
|
||||||
|
>
|
||||||
|
<paper-tab id="tab-settings" dialogInitialFocus
|
||||||
|
>${this.hass!.localize(
|
||||||
|
"ui.panel.lovelace.editor.edit_view.tab_settings"
|
||||||
|
)}</paper-tab
|
||||||
|
>
|
||||||
|
<paper-tab id="tab-badges"
|
||||||
|
>${this.hass!.localize(
|
||||||
|
"ui.panel.lovelace.editor.edit_view.tab_badges"
|
||||||
|
)}</paper-tab
|
||||||
|
>
|
||||||
|
<paper-tab id="tab-visibility"
|
||||||
|
>${this.hass!.localize(
|
||||||
|
"ui.panel.lovelace.editor.edit_view.tab_visibility"
|
||||||
|
)}</paper-tab
|
||||||
|
>
|
||||||
|
</paper-tabs>`
|
||||||
|
: ""}
|
||||||
</div>
|
</div>
|
||||||
${content}
|
${content}
|
||||||
${this._params.viewIndex !== undefined
|
${this._params.viewIndex !== undefined
|
||||||
@ -235,6 +318,19 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async _handleAction(ev: CustomEvent<ActionDetail>) {
|
||||||
|
ev.stopPropagation();
|
||||||
|
ev.preventDefault();
|
||||||
|
switch (ev.detail.index) {
|
||||||
|
case 0:
|
||||||
|
this._yamlMode = false;
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
this._yamlMode = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private async _delete(): Promise<void> {
|
private async _delete(): Promise<void> {
|
||||||
if (!this._params) {
|
if (!this._params) {
|
||||||
return;
|
return;
|
||||||
@ -348,6 +444,17 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
this._dirty = true;
|
this._dirty = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private _viewYamlChanged(ev: CustomEvent) {
|
||||||
|
ev.stopPropagation();
|
||||||
|
if (!ev.detail.isValid) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const { badges = [], ...config } = ev.detail.value;
|
||||||
|
this._config = config;
|
||||||
|
this._badges = badges;
|
||||||
|
this._dirty = true;
|
||||||
|
}
|
||||||
|
|
||||||
private _isConfigChanged(): boolean {
|
private _isConfigChanged(): boolean {
|
||||||
return (
|
return (
|
||||||
this._creatingView ||
|
this._creatingView ||
|
||||||
@ -366,6 +473,9 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
return [
|
return [
|
||||||
haStyleDialog,
|
haStyleDialog,
|
||||||
css`
|
css`
|
||||||
|
ha-dialog.yaml-mode {
|
||||||
|
--dialog-content-padding: 0;
|
||||||
|
}
|
||||||
h2 {
|
h2 {
|
||||||
display: block;
|
display: block;
|
||||||
color: var(--primary-text-color);
|
color: var(--primary-text-color);
|
||||||
@ -421,6 +531,22 @@ export class HuiDialogEditView extends LitElement {
|
|||||||
ha-circular-progress[active] {
|
ha-circular-progress[active] {
|
||||||
display: block;
|
display: block;
|
||||||
}
|
}
|
||||||
|
ha-button-menu {
|
||||||
|
color: var(--secondary-text-color);
|
||||||
|
position: absolute;
|
||||||
|
right: 16px;
|
||||||
|
top: 14px;
|
||||||
|
inset-inline-end: 16px;
|
||||||
|
inset-inline-start: initial;
|
||||||
|
direction: var(--direction);
|
||||||
|
}
|
||||||
|
ha-button-menu,
|
||||||
|
ha-icon-button {
|
||||||
|
--mdc-theme-text-primary-on-background: var(--primary-text-color);
|
||||||
|
}
|
||||||
|
.selected_menu_item {
|
||||||
|
color: var(--primary-color);
|
||||||
|
}
|
||||||
.hidden {
|
.hidden {
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
@ -3805,7 +3805,9 @@
|
|||||||
"subview": "Subview",
|
"subview": "Subview",
|
||||||
"subview_helper": "Subviews don't appear in tabs and have a back button.",
|
"subview_helper": "Subviews don't appear in tabs and have a back button.",
|
||||||
"back_path": "Back path (optional)",
|
"back_path": "Back path (optional)",
|
||||||
"back_path_helper": "Only for subviews. If empty, clicking on back button will go to the previous page."
|
"back_path_helper": "Only for subviews. If empty, clicking on back button will go to the previous page.",
|
||||||
|
"edit_ui": "Edit in visual editor",
|
||||||
|
"edit_yaml": "Edit in YAML"
|
||||||
},
|
},
|
||||||
"edit_badges": {
|
"edit_badges": {
|
||||||
"view_no_badges": "Badges are not be supported by the current view type."
|
"view_no_badges": "Badges are not be supported by the current view type."
|
||||||
|
Loading…
x
Reference in New Issue
Block a user