Big restructuring - repo is now a full home assistant config directory

This commit is contained in:
Martin Bauer
2019-06-30 19:37:32 +02:00
parent d35b9e132e
commit 808727ad92
79 changed files with 14378 additions and 27 deletions

View File

@@ -0,0 +1,168 @@
import {
HassEntity,
} from "home-assistant-js-websocket";
import {HomeAssistant} from "./home-assistant-interface";
const supportsFeature = (
stateObj: HassEntity,
feature: number
): boolean => {
// tslint:disable-next-line:no-bitwise
return (stateObj.attributes.supported_features! & feature) !== 0;
};
/* eslint-enable no-bitwise */
export class CoverEntity {
public hass: HomeAssistant;
public stateObj: HassEntity;
private _attr: { [key: string]: any; };
private _feat: any;
constructor(hass : HomeAssistant, stateObj) {
this.hass = hass;
this.stateObj = stateObj;
this._attr = stateObj.attributes;
this._feat = this._attr.supported_features;
}
get isFullyOpen() {
if (this._attr.current_position !== undefined) {
return this._attr.current_position === 100;
}
return this.stateObj.state === "open";
}
get isFullyClosed() {
if (this._attr.current_position !== undefined) {
return this._attr.current_position === 0;
}
return this.stateObj.state === "closed";
}
get isFullyOpenTilt() {
return this._attr.current_tilt_position === 100;
}
get isFullyClosedTilt() {
return this._attr.current_tilt_position === 0;
}
get isOpening() {
return this.stateObj.state === "opening";
}
get isClosing() {
return this.stateObj.state === "closing";
}
get supportsOpen() {
return supportsFeature(this.stateObj, 1);
}
get supportsClose() {
return supportsFeature(this.stateObj, 2);
}
get supportsSetPosition() {
return supportsFeature(this.stateObj, 4);
}
get supportsStop() {
return supportsFeature(this.stateObj, 8);
}
get supportsOpenTilt() {
return supportsFeature(this.stateObj, 16);
}
get supportsCloseTilt() {
return supportsFeature(this.stateObj, 32);
}
get supportsStopTilt() {
return supportsFeature(this.stateObj, 64);
}
get supportsSetTiltPosition() {
return supportsFeature(this.stateObj, 128);
}
get isTiltOnly() {
const supportsCover =
this.supportsOpen || this.supportsClose || this.supportsStop;
const supportsTilt =
this.supportsOpenTilt || this.supportsCloseTilt || this.supportsStopTilt;
return supportsTilt && !supportsCover;
}
openCover() {
this.callService("open_cover");
}
closeCover() {
this.callService("close_cover");
}
stopCover() {
this.callService("stop_cover");
}
openCoverTilt() {
this.callService("open_cover_tilt");
}
closeCoverTilt() {
this.callService("close_cover_tilt");
}
stopCoverTilt() {
this.callService("stop_cover_tilt");
}
setCoverPosition(position) {
this.callService("set_cover_position", { position });
}
setCoverTiltPosition(tiltPosition) {
this.callService("set_cover_tilt_position", {
tilt_position: tiltPosition,
});
}
// helper method
callService(service, data = {}) {
data['entity_id'] = this.stateObj.entity_id;
this.hass.callService("cover", service, data);
}
}
export const supportsOpen = (stateObj) => supportsFeature(stateObj, 1);
export const supportsClose = (stateObj) => supportsFeature(stateObj, 2);
export const supportsSetPosition = (stateObj) => supportsFeature(stateObj, 4);
export const supportsStop = (stateObj) => supportsFeature(stateObj, 8);
export const supportsOpenTilt = (stateObj) => supportsFeature(stateObj, 16);
export const supportsCloseTilt = (stateObj) => supportsFeature(stateObj, 32);
export const supportsStopTilt = (stateObj) => supportsFeature(stateObj, 64);
export const supportsSetTiltPosition = (stateObj) =>
supportsFeature(stateObj, 128);
export function isTiltOnly(stateObj) {
const supportsCover =
supportsOpen(stateObj) || supportsClose(stateObj) || supportsStop(stateObj);
const supportsTilt =
supportsOpenTilt(stateObj) ||
supportsCloseTilt(stateObj) ||
supportsStopTilt(stateObj);
return supportsTilt && !supportsCover;
}

View File

@@ -0,0 +1,26 @@
import {Connection, HassConfig, HassEntities, HassServices, MessageBase} from "home-assistant-js-websocket";
export interface HomeAssistant {
connection: Connection;
connected: boolean;
states: HassEntities;
services: HassServices;
config: HassConfig;
callService: (
domain: string,
service: string,
serviceData?: { [key: string]: any }
) => Promise<void>;
callApi: <T>(
method: "GET" | "POST" | "PUT" | "DELETE",
path: string,
parameters?: { [key: string]: any }
) => Promise<T>;
fetchWithAuth: (
path: string,
init?: { [key: string]: any }
) => Promise<Response>;
sendWS: (msg: MessageBase) => void;
callWS: <T>(msg: MessageBase) => Promise<T>;
}

View File

@@ -0,0 +1,140 @@
import {LitElement, html, customElement, property, TemplateResult} from "lit-element";
import {CoverEntity} from "./cover-model"
import {HomeAssistant} from "./home-assistant-interface";
export interface CustomCoverStateCardConfig {
type: string;
entity: string;
name?: string;
}
@customElement("state-card-custom-cover")
export class StateCardCustomCover extends LitElement {
@property() public hass?: HomeAssistant;
@property() private _config?: CustomCoverStateCardConfig;
@property()
public get stateObj() {
if (this.hass && this._config)
return this.hass.states[this._config.entity];
else
return null;
}
@property() public inDialog: boolean = false;
public setConfig(config: CustomCoverStateCardConfig | undefined) {
if (!config || !config.entity) {
throw new Error("Invalid configuration");
}
this._config = config;
}
get entityObj(): CoverEntity {
if (this.hass && this.stateObj)
return new CoverEntity(this.hass, this.stateObj);
else
throw new Error("Trying to get entityObj before setting hass & config");
}
public static getCardSize(): number {
return 1;
}
protected stateInfoTemplate() {
return html`
State info template
`;
}
protected render(): TemplateResult | void {
if (!this._config || !this.hass) {
return html``;
}
const entityObj = this.entityObj;
const stateObj = this.hass.states[this._config.entity];
if (!stateObj) {
return html`
<hui-warning
>Does not work :(</hui-warning
>
`;
}
return html`
<style include="iron-flex iron-flex-alignment"></style>
<style>
:host {
line-height: 1.5;
}
.state {
white-space: nowrap;
}
[invisible] {
visibility: hidden !important;
}
</style>
<hui-generic-entity-row .config="${this._config}" .hass="${this.hass}">
<div class="state">
<paper-icon-button
icon="hass:menu"
@click=${this.onHalfOpenTap}
></paper-icon-button>
<paper-icon-button
icon="hass:arrow-up"
@click=${this.onOpenTap}
.disabled="${this.computeOpenDisabled(stateObj, this.entityObj)}"
></paper-icon-button>
<paper-icon-button
icon="hass:stop"
@click=${this.onStopTap}
></paper-icon-button>
<paper-icon-button
icon="hass:arrow-down"
@click=${this.onCloseTap}
.disabled="${this.computeClosedDisabled(stateObj, entityObj)}"
></paper-icon-button>
</div>
</hui-generic-entity-row>
`;
}
computeOpenDisabled(stateObj, entityObj) {
const assumedState = stateObj.attributes.assumed_state === true;
return (entityObj.isFullyOpen || entityObj.isOpening) && !assumedState;
}
computeClosedDisabled(stateObj, entityObj) {
const assumedState = stateObj.attributes.assumed_state === true;
return (entityObj.isFullyClosed || entityObj.isClosing) && !assumedState;
}
private onHalfOpenTap(ev) {
const stateObj = this.hass!.states[this._config!.entity];
ev.stopPropagation();
this.entityObj.setCoverPosition(stateObj.attributes['half_position']);
}
private onOpenTap(ev) {
ev.stopPropagation();
this.entityObj.openCover();
}
private onCloseTap(ev) {
ev.stopPropagation();
this.entityObj.closeCover();
}
private onStopTap(ev) {
ev.stopPropagation();
this.entityObj.stopCover();
}
}