From 031d9362d6927bcc6fbc262432e0aff075f9e937 Mon Sep 17 00:00:00 2001 From: Dermot Duffy Date: Mon, 18 Oct 2021 22:30:44 -0700 Subject: [PATCH] Fix element rendering. --- src/card.ts | 28 ++++++++++++++++++++++++---- src/components/elements.ts | 23 +++++++++++++++-------- src/components/menu.ts | 10 ---------- 3 files changed, 39 insertions(+), 22 deletions(-) diff --git a/src/card.ts b/src/card.ts index 0e6afb46..99eca1f2 100644 --- a/src/card.ts +++ b/src/card.ts @@ -119,6 +119,9 @@ export class FrigateCard extends LitElement { // Information about the most recently loaded media item. protected _mediaInfo: MediaLoadInfo | null = null; + // Array of dynamic menu buttons to be added to menu. + protected _dynamicMenuButtons: MenuButton[] = []; + // The frigate camera name to use (may be manually specified or automatically // derived). // Values: @@ -224,7 +227,21 @@ export class FrigateCard extends LitElement { icon: screenfull.isFullscreen ? 'mdi:fullscreen-exit' : 'mdi:fullscreen', }); } - return buttons; + return buttons.concat(this._dynamicMenuButtons); + } + + public _addDynamicMenuButton(button: MenuButton): void { + if (!this._dynamicMenuButtons.includes(button)) { + this._dynamicMenuButtons = [...this._dynamicMenuButtons, button]; + } + this._menu.buttons = this._getMenuButtons(); + } + + public _removeDynamicMenuButton(target: MenuButton): void { + this._dynamicMenuButtons = this._dynamicMenuButtons.filter( + (button) => button != target, + ); + this._menu.buttons = this._getMenuButtons(); } protected async _getFrigateCameraName(): Promise { @@ -733,19 +750,22 @@ export class FrigateCard extends LitElement { ` : ``} - ${!this._message && this.config.elements + ${this.config.elements ? html` { - this._menu.addButton(e.detail); + this._addDynamicMenuButton(e.detail); }} @frigate-card:menu-remove=${(e) => { - this._menu.removeButton(e.detail); + this._removeDynamicMenuButton(e.detail); }} @frigate-card:state-request=${(e) => { + // State filled here must also trigger the + // 'frigate-card-elements' to re-render (by being a property). e.view = this._view; }} > diff --git a/src/components/elements.ts b/src/components/elements.ts index a0da7511..09dad581 100644 --- a/src/components/elements.ts +++ b/src/components/elements.ts @@ -56,6 +56,9 @@ class FrigateCardElementsCore extends LitElement { @property({ attribute: false }) protected elements: PictureElements; + @property({ attribute: false }) + protected view?: View; + protected _root: HTMLElement | null = null; protected _hass!: HomeAssistant & ExtendedHomeAssistant; @@ -72,7 +75,7 @@ class FrigateCardElementsCore extends LitElement { return this; } - protected _createRoot(): void { + protected _createRoot(): HTMLElement { // eslint-disable-next-line @typescript-eslint/no-explicit-any const elementConstructor = customElements.get('hui-conditional-element') as any; if (!elementConstructor) { @@ -92,16 +95,16 @@ class FrigateCardElementsCore extends LitElement { console.error(e, (e as Error).stack); throw new Error(localize('error.invalid_elements_config')); } - this._root = element; + return element; } protected render(): TemplateResult | void { - if (!this._root) { - try { - this._createRoot(); - } catch (e) { - return dispatchErrorMessageEvent(this, (e as Error).message); - } + try { + // Recreate the root on each render to ensure conditional ancestors + // re-fire events as necessary. + this._root = this._createRoot(); + } catch (e) { + return dispatchErrorMessageEvent(this, (e as Error).message); } return html`${this._root || ''}`; } @@ -113,6 +116,9 @@ export class FrigateCardElements extends LitElement { @property({ attribute: false }) protected elements: PictureElements; + @property({ attribute: false }) + protected view!: View; + protected _hass!: HomeAssistant & ExtendedHomeAssistant; @query('frigate-card-elements-core') @@ -168,6 +174,7 @@ export class FrigateCardElements extends LitElement { protected render(): TemplateResult { return html` `; diff --git a/src/components/menu.ts b/src/components/menu.ts index e9a764d9..1651642d 100644 --- a/src/components/menu.ts +++ b/src/components/menu.ts @@ -33,16 +33,6 @@ export class FrigateCardMenu extends LitElement { @property({ attribute: false }) public buttons: MenuButton[] = []; - public addButton(button: MenuButton): void { - if (!this.buttons.includes(button)) { - this.buttons = [...this.buttons, button]; - } - } - - public removeButton(target: MenuButton): void { - this.buttons = this.buttons.filter(button => button != target); - } - // Call the callback. protected _callAction(ev: CustomEvent, button: MenuButton): void { if (this.menuMode.startsWith('hidden-')) {