mirror of
https://github.com/home-assistant/frontend.git
synced 2025-07-29 12:16:39 +00:00
Z-Wave Config Panel Updates (#3349)
* Display network status, hide buttons if network is stopped. * travis/lint updates * Review comments * Add translations * lint * Missed a translation * lint again... * Fix unsubscribe function? * lint again * Remove state_str * Code review comments * fix for lit re-rendering & possible undefined value
This commit is contained in:
parent
e99d6f8e6a
commit
b4dd971829
18
src/data/zwave.ts
Normal file
18
src/data/zwave.ts
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
import { HomeAssistant } from "../types";
|
||||||
|
|
||||||
|
export interface ZWaveNetworkStatus {
|
||||||
|
state: number;
|
||||||
|
}
|
||||||
|
|
||||||
|
export const ZWAVE_NETWORK_STATE_STOPPED = 0;
|
||||||
|
export const ZWAVE_NETWORK_STATE_FAILED = 1;
|
||||||
|
export const ZWAVE_NETWORK_STATE_STARTED = 5;
|
||||||
|
export const ZWAVE_NETWORK_STATE_AWAKED = 7;
|
||||||
|
export const ZWAVE_NETWORK_STATE_READY = 10;
|
||||||
|
|
||||||
|
export const fetchNetworkStatus = (
|
||||||
|
hass: HomeAssistant
|
||||||
|
): Promise<ZWaveNetworkStatus> =>
|
||||||
|
hass.callWS({
|
||||||
|
type: "zwave/network_status",
|
||||||
|
});
|
@ -1,4 +1,5 @@
|
|||||||
import "@polymer/paper-icon-button/paper-icon-button";
|
import "@polymer/paper-icon-button/paper-icon-button";
|
||||||
|
import "@polymer/paper-spinner/paper-spinner";
|
||||||
|
|
||||||
import {
|
import {
|
||||||
css,
|
css,
|
||||||
@ -9,14 +10,24 @@ import {
|
|||||||
property,
|
property,
|
||||||
TemplateResult,
|
TemplateResult,
|
||||||
} from "lit-element";
|
} from "lit-element";
|
||||||
|
import { UnsubscribeFunc } from "home-assistant-js-websocket";
|
||||||
|
|
||||||
import { haStyle } from "../../../resources/styles";
|
import { haStyle } from "../../../resources/styles";
|
||||||
import { HomeAssistant } from "../../../types";
|
import { HomeAssistant } from "../../../types";
|
||||||
|
import {
|
||||||
|
fetchNetworkStatus,
|
||||||
|
ZWaveNetworkStatus,
|
||||||
|
ZWAVE_NETWORK_STATE_STOPPED,
|
||||||
|
ZWAVE_NETWORK_STATE_STARTED,
|
||||||
|
ZWAVE_NETWORK_STATE_AWAKED,
|
||||||
|
ZWAVE_NETWORK_STATE_READY,
|
||||||
|
} from "../../../data/zwave";
|
||||||
|
|
||||||
import "../../../components/buttons/ha-call-api-button";
|
import "../../../components/buttons/ha-call-api-button";
|
||||||
import "../../../components/buttons/ha-call-service-button";
|
import "../../../components/buttons/ha-call-service-button";
|
||||||
import "../../../components/ha-service-description";
|
import "../../../components/ha-service-description";
|
||||||
import "../../../components/ha-card";
|
import "../../../components/ha-card";
|
||||||
|
import "../../../components/ha-icon";
|
||||||
import "../ha-config-section";
|
import "../ha-config-section";
|
||||||
|
|
||||||
@customElement("zwave-network")
|
@customElement("zwave-network")
|
||||||
@ -24,12 +35,28 @@ export class ZwaveNetwork extends LitElement {
|
|||||||
@property() public hass!: HomeAssistant;
|
@property() public hass!: HomeAssistant;
|
||||||
@property() public isWide!: boolean;
|
@property() public isWide!: boolean;
|
||||||
@property() private _showHelp = false;
|
@property() private _showHelp = false;
|
||||||
|
@property() private _networkStatus?: ZWaveNetworkStatus;
|
||||||
|
@property() private _unsubs: Array<Promise<UnsubscribeFunc>> = [];
|
||||||
|
|
||||||
|
public disconnectedCallback(): void {
|
||||||
|
this._unsubscribe();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected firstUpdated(changedProps): void {
|
||||||
|
super.firstUpdated(changedProps);
|
||||||
|
this._getNetworkStatus();
|
||||||
|
this._subscribe();
|
||||||
|
}
|
||||||
|
|
||||||
protected render(): TemplateResult | void {
|
protected render(): TemplateResult | void {
|
||||||
return html`
|
return html`
|
||||||
<ha-config-section .isWide="${this.isWide}">
|
<ha-config-section .isWide="${this.isWide}">
|
||||||
<div style="position: relative" slot="header">
|
<div style="position: relative" slot="header">
|
||||||
<span>Z-Wave Network Management</span>
|
<span>
|
||||||
|
${this.hass!.localize(
|
||||||
|
"ui.panel.config.zwave.network_management.header"
|
||||||
|
)}
|
||||||
|
</span>
|
||||||
<paper-icon-button
|
<paper-icon-button
|
||||||
class="toggle-help-icon"
|
class="toggle-help-icon"
|
||||||
@click="${this._onHelpTap}"
|
@click="${this._onHelpTap}"
|
||||||
@ -37,162 +64,168 @@ export class ZwaveNetwork extends LitElement {
|
|||||||
></paper-icon-button>
|
></paper-icon-button>
|
||||||
</div>
|
</div>
|
||||||
<span slot="introduction">
|
<span slot="introduction">
|
||||||
Run commands that affect the Z-Wave network. You won't get feedback on
|
${this.hass!.localize(
|
||||||
whether the command succeeded, but you can look in the OZW Log to try
|
"ui.panel.config.zwave.network_management.introduction"
|
||||||
to figure out.
|
)}
|
||||||
</span>
|
</span>
|
||||||
|
|
||||||
<ha-card class="content">
|
${this._networkStatus
|
||||||
<div class="card-actions">
|
? html`
|
||||||
<ha-call-service-button
|
<ha-card class="content network-status">
|
||||||
.hass=${this.hass}
|
<div class="details">
|
||||||
domain="zwave"
|
${this._networkStatus.state === ZWAVE_NETWORK_STATE_STOPPED
|
||||||
service="add_node_secure"
|
? html`
|
||||||
>
|
<ha-icon icon="hass:close"></ha-icon>
|
||||||
Add Node Secure
|
${this.hass!.localize(
|
||||||
</ha-call-service-button>
|
"ui.panel.config.zwave.network_status.network_stopped"
|
||||||
<ha-service-description
|
)}
|
||||||
.hass=${this.hass}
|
`
|
||||||
domain="zwave"
|
: this._networkStatus.state === ZWAVE_NETWORK_STATE_STARTED
|
||||||
service="add_node_secure"
|
? html`
|
||||||
?hidden=${!this._showHelp}
|
<paper-spinner active></paper-spinner>
|
||||||
>
|
${this.hass!.localize(
|
||||||
</ha-service-description>
|
"ui.panel.config.zwave.network_status.network_starting"
|
||||||
|
)}<br />
|
||||||
<ha-call-service-button
|
<small>
|
||||||
.hass=${this.hass}
|
${this.hass!.localize(
|
||||||
domain="zwave"
|
"ui.panel.config.zwave.network_status.network_starting_note"
|
||||||
service="add_node"
|
)}
|
||||||
>
|
</small>
|
||||||
Add Node
|
`
|
||||||
</ha-call-service-button>
|
: this._networkStatus.state === ZWAVE_NETWORK_STATE_AWAKED
|
||||||
<ha-service-description
|
? html`
|
||||||
.hass=${this.hass}
|
<ha-icon icon="hass:checkbox-marked-circle"> </ha-icon>
|
||||||
domain="zwave"
|
${this.hass!.localize(
|
||||||
service="add_node"
|
"ui.panel.config.zwave.network_status.network_started"
|
||||||
?hidden=${!this._showHelp}
|
)}<br />
|
||||||
>
|
<small>
|
||||||
</ha-service-description>
|
${this.hass!.localize(
|
||||||
|
"ui.panel.config.zwave.network_status.network_started_note_some_queried"
|
||||||
<ha-call-service-button
|
)}
|
||||||
.hass=${this.hass}
|
</small>
|
||||||
domain="zwave"
|
`
|
||||||
service="remove_node"
|
: this._networkStatus.state === ZWAVE_NETWORK_STATE_READY
|
||||||
>
|
? html`
|
||||||
Remove Node
|
${this.hass!.localize(
|
||||||
</ha-call-service-button>
|
"ui.panel.config.zwave.network_status.network_started"
|
||||||
<ha-service-description
|
)}<br />
|
||||||
.hass=${this.hass}
|
<small>
|
||||||
domain="zwave"
|
${this.hass!.localize(
|
||||||
service="remove_node"
|
"ui.panel.config.zwave.network_status.network_started_note_all_queried"
|
||||||
?hidden=${!this._showHelp}
|
)}
|
||||||
>
|
</small>
|
||||||
</ha-service-description>
|
`
|
||||||
</div>
|
: ""}
|
||||||
<div class="card-actions warning">
|
</div>
|
||||||
<ha-call-service-button
|
<div class="card-actions">
|
||||||
.hass=${this.hass}
|
${this._networkStatus.state >= ZWAVE_NETWORK_STATE_AWAKED
|
||||||
domain="zwave"
|
? html`
|
||||||
service="cancel_command"
|
${this._generateServiceButton("stop_network")}
|
||||||
>
|
${this._generateServiceButton("heal_network")}
|
||||||
Cancel Command
|
${this._generateServiceButton("test_network")}
|
||||||
</ha-call-service-button>
|
`
|
||||||
<ha-service-description
|
: html`
|
||||||
.hass=${this.hass}
|
${this._generateServiceButton("start_network")}
|
||||||
domain="zwave"
|
`}
|
||||||
service="cancel_command"
|
</div>
|
||||||
?hidden=${!this._showHelp}
|
${this._networkStatus.state >= ZWAVE_NETWORK_STATE_AWAKED
|
||||||
>
|
? html`
|
||||||
</ha-service-description>
|
<div class="card-actions">
|
||||||
</div>
|
${this._generateServiceButton("soft_reset")}
|
||||||
<div class="card-actions">
|
<ha-call-api-button
|
||||||
<ha-call-service-button
|
.hass=${this.hass}
|
||||||
.hass=${this.hass}
|
path="zwave/saveconfig"
|
||||||
domain="zwave"
|
>
|
||||||
service="heal_network"
|
${this.hass!.localize(
|
||||||
>
|
"ui.panel.config.zwave.services.save_config"
|
||||||
Heal Network
|
)}
|
||||||
</ha-call-service-button>
|
</ha-call-api-button>
|
||||||
<ha-service-description
|
</div>
|
||||||
.hass=${this.hass}
|
`
|
||||||
domain="zwave"
|
: ""}
|
||||||
service="heal_network"
|
</ha-card>
|
||||||
?hidden=${!this._showHelp}
|
${this._networkStatus.state >= ZWAVE_NETWORK_STATE_AWAKED
|
||||||
></ha-service-description>
|
? html`
|
||||||
|
<ha-card class="content">
|
||||||
<ha-call-service-button
|
<div class="card-actions">
|
||||||
.hass=${this.hass}
|
${this._generateServiceButton("add_node_secure")}
|
||||||
domain="zwave"
|
${this._generateServiceButton("add_node")}
|
||||||
service="start_network"
|
${this._generateServiceButton("remove_node")}
|
||||||
>
|
</div>
|
||||||
Start Network
|
<div class="card-actions">
|
||||||
</ha-call-service-button>
|
${this._generateServiceButton("cancel_command")}
|
||||||
<ha-service-description
|
</div>
|
||||||
.hass=${this.hass}
|
</ha-card>
|
||||||
domain="zwave"
|
`
|
||||||
service="start_network"
|
: ""}
|
||||||
?hidden=${!this._showHelp}
|
`
|
||||||
>
|
: ""}
|
||||||
</ha-service-description>
|
|
||||||
|
|
||||||
<ha-call-service-button
|
|
||||||
.hass=${this.hass}
|
|
||||||
domain="zwave"
|
|
||||||
service="stop_network"
|
|
||||||
>
|
|
||||||
Stop Network
|
|
||||||
</ha-call-service-button>
|
|
||||||
<ha-service-description
|
|
||||||
.hass=${this.hass}
|
|
||||||
domain="zwave"
|
|
||||||
service="stop_network"
|
|
||||||
?hidden=${!this._showHelp}
|
|
||||||
>
|
|
||||||
</ha-service-description>
|
|
||||||
|
|
||||||
<ha-call-service-button
|
|
||||||
.hass=${this.hass}
|
|
||||||
domain="zwave"
|
|
||||||
service="soft_reset"
|
|
||||||
>
|
|
||||||
Soft Reset
|
|
||||||
</ha-call-service-button>
|
|
||||||
<ha-service-description
|
|
||||||
.hass=${this.hass}
|
|
||||||
domain="zwave"
|
|
||||||
service="soft_reset"
|
|
||||||
?hidden=${!this._showHelp}
|
|
||||||
>
|
|
||||||
</ha-service-description>
|
|
||||||
|
|
||||||
<ha-call-service-button
|
|
||||||
.hass=${this.hass}
|
|
||||||
domain="zwave"
|
|
||||||
service="test_network"
|
|
||||||
>
|
|
||||||
Test Network
|
|
||||||
</ha-call-service-button>
|
|
||||||
<ha-service-description
|
|
||||||
.hass=${this.hass}
|
|
||||||
domain="zwave"
|
|
||||||
service="test_network"
|
|
||||||
?hidden=${!this._showHelp}
|
|
||||||
>
|
|
||||||
</ha-service-description>
|
|
||||||
|
|
||||||
<ha-call-api-button .hass=${this.hass} path="zwave/saveconfig">
|
|
||||||
Save Config
|
|
||||||
</ha-call-api-button>
|
|
||||||
</div>
|
|
||||||
</ha-card>
|
|
||||||
</ha-config-section>
|
</ha-config-section>
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async _getNetworkStatus(): Promise<void> {
|
||||||
|
this._networkStatus = await fetchNetworkStatus(this.hass!);
|
||||||
|
}
|
||||||
|
|
||||||
|
private _subscribe(): void {
|
||||||
|
this._unsubs = [
|
||||||
|
"zwave.network_start",
|
||||||
|
"zwave.network_stop",
|
||||||
|
"zwave.network_ready",
|
||||||
|
"zwave.network_complete",
|
||||||
|
"zwave.network_complete_some_dead",
|
||||||
|
].map((e) =>
|
||||||
|
this.hass!.connection.subscribeEvents(
|
||||||
|
(event) => this._handleEvent(event),
|
||||||
|
e
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
private _unsubscribe(): void {
|
||||||
|
while (this._unsubs.length) {
|
||||||
|
this._unsubs.pop()!.then((unsub) => unsub());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private _handleEvent(event) {
|
||||||
|
if (event.event_type === "zwave.network_start") {
|
||||||
|
// Optimistically set the state, wait 1s and poll the backend
|
||||||
|
// The backend will still report a state of 0 when the 'network_start'
|
||||||
|
// event is first fired.
|
||||||
|
if (this._networkStatus) {
|
||||||
|
this._networkStatus = { ...this._networkStatus, state: 5 };
|
||||||
|
}
|
||||||
|
setTimeout(() => this._getNetworkStatus, 1000);
|
||||||
|
} else {
|
||||||
|
this._getNetworkStatus();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private _onHelpTap(): void {
|
private _onHelpTap(): void {
|
||||||
this._showHelp = !this._showHelp;
|
this._showHelp = !this._showHelp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private _generateServiceButton(service: string) {
|
||||||
|
return html`
|
||||||
|
<ha-call-service-button
|
||||||
|
.hass=${this.hass}
|
||||||
|
domain="zwave"
|
||||||
|
service="${service}"
|
||||||
|
>
|
||||||
|
${this.hass!.localize("ui.panel.config.zwave.services." + service)}
|
||||||
|
</ha-call-service-button>
|
||||||
|
<ha-service-description
|
||||||
|
.hass=${this.hass}
|
||||||
|
domain="zwave"
|
||||||
|
service="${service}"
|
||||||
|
?hidden=${!this._showHelp}
|
||||||
|
>
|
||||||
|
</ha-service-description>
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
static get styles(): CSSResult[] {
|
static get styles(): CSSResult[] {
|
||||||
return [
|
return [
|
||||||
haStyle,
|
haStyle,
|
||||||
@ -201,6 +234,26 @@ export class ZwaveNetwork extends LitElement {
|
|||||||
margin-top: 24px;
|
margin-top: 24px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.network-status {
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.network-status div.details {
|
||||||
|
font-size: 1.5rem;
|
||||||
|
padding: 24px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.network-status ha-icon {
|
||||||
|
display: block;
|
||||||
|
margin: 0px auto 16px;
|
||||||
|
width: 48px;
|
||||||
|
height: 48px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.network-status small {
|
||||||
|
font-size: 1rem;
|
||||||
|
}
|
||||||
|
|
||||||
ha-card {
|
ha-card {
|
||||||
margin: 0 auto;
|
margin: 0 auto;
|
||||||
max-width: 600px;
|
max-width: 600px;
|
||||||
|
@ -921,7 +921,31 @@
|
|||||||
},
|
},
|
||||||
"zwave": {
|
"zwave": {
|
||||||
"caption": "Z-Wave",
|
"caption": "Z-Wave",
|
||||||
"description": "Manage your Z-Wave network"
|
"description": "Manage your Z-Wave network",
|
||||||
|
"network_management": {
|
||||||
|
"header": "Z-Wave Network Management",
|
||||||
|
"introduction": "Run commands that affect the Z-Wave network. You won't get feedback on whether most commands succeeded, but you can check the OZW Log to try to find out."
|
||||||
|
},
|
||||||
|
"network_status": {
|
||||||
|
"network_stopped": "Z-Wave Network Stopped",
|
||||||
|
"network_starting": "Starting Z-Wave Network...",
|
||||||
|
"network_starting_note": "This may take a while depending on the size of your network.",
|
||||||
|
"network_started": "Z-Wave Network Started",
|
||||||
|
"network_started_note_some_queried": "Awake nodes have been queried. Sleeping nodes will be queried when they wake.",
|
||||||
|
"network_started_note_all_queried": "All nodes have been queried."
|
||||||
|
},
|
||||||
|
"services": {
|
||||||
|
"start_network": "Start Network",
|
||||||
|
"stop_network": "Stop Network",
|
||||||
|
"heal_network": "Heal Network",
|
||||||
|
"test_network": "Test Network",
|
||||||
|
"soft_reset": "Soft Reset",
|
||||||
|
"save_config": "Save Config",
|
||||||
|
"add_node_secure": "Add Node Secure",
|
||||||
|
"add_node": "Add Node",
|
||||||
|
"remove_node": "Remove Node",
|
||||||
|
"cancel_command": "Cancel Command"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"history": {
|
"history": {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user