diff --git a/src/components/ha-grid-size-picker.ts b/src/components/ha-grid-size-picker.ts index 6ae6b7b37d75..f62fc5c01dc5 100644 --- a/src/components/ha-grid-size-picker.ts +++ b/src/components/ha-grid-size-picker.ts @@ -20,7 +20,7 @@ export class HaGridSizeEditor extends LitElement { @property({ attribute: false }) public value?: GridSizeValue; - @property({ attribute: false }) public rows = 6; + @property({ attribute: false }) public rows = 8; @property({ attribute: false }) public columns = 4; @@ -205,7 +205,7 @@ export class HaGridSizeEditor extends LitElement { .preview { position: relative; grid-area: preview; - aspect-ratio: 1 / 1; + aspect-ratio: 1 / 1.2; } .preview > div { position: absolute; diff --git a/src/components/tile/ha-tile-icon.ts b/src/components/tile/ha-tile-icon.ts index f5ebe8863c52..f1cd7ec633ce 100644 --- a/src/components/tile/ha-tile-icon.ts +++ b/src/components/tile/ha-tile-icon.ts @@ -17,7 +17,7 @@ export class HaTileIcon extends LitElement { return css` :host { --tile-icon-color: var(--disabled-color); - --mdc-icon-size: 24px; + --mdc-icon-size: 22px; } .shape::before { content: ""; @@ -32,9 +32,9 @@ export class HaTileIcon extends LitElement { } .shape { position: relative; - width: 40px; - height: 40px; - border-radius: 20px; + width: 36px; + height: 36px; + border-radius: 18px; display: flex; align-items: center; justify-content: center; diff --git a/src/components/tile/ha-tile-image.ts b/src/components/tile/ha-tile-image.ts index fc29eb57d0c5..143f4c176b1c 100644 --- a/src/components/tile/ha-tile-image.ts +++ b/src/components/tile/ha-tile-image.ts @@ -25,9 +25,9 @@ export class HaTileImage extends LitElement { return css` .image { position: relative; - width: 40px; - height: 40px; - border-radius: 20px; + width: 36px; + height: 36px; + border-radius: 18px; display: flex; flex: none; align-items: center; diff --git a/src/components/tile/ha-tile-info.ts b/src/components/tile/ha-tile-info.ts index b28e3730772a..68123eee6f1e 100644 --- a/src/components/tile/ha-tile-info.ts +++ b/src/components/tile/ha-tile-info.ts @@ -33,7 +33,7 @@ export class HaTileInfo extends LitElement { flex-direction: column; align-items: flex-start; justify-content: center; - min-height: 40px; + height: 36px; } span { text-overflow: ellipsis; diff --git a/src/panels/lovelace/card-features/common/card-feature-styles.ts b/src/panels/lovelace/card-features/common/card-feature-styles.ts new file mode 100644 index 000000000000..6a0fdcb1c092 --- /dev/null +++ b/src/panels/lovelace/card-features/common/card-feature-styles.ts @@ -0,0 +1,30 @@ +import { css } from "lit"; + +export const cardFeatureStyles = css` + ha-control-select-menu { + box-sizing: border-box; + --control-select-menu-height: var(--feature-height); + --control-select-menu-border-radius: var(--feature-border-radius); + line-height: 1.2; + display: block; + width: 100%; + } + ha-control-select { + --control-select-color: var(--feature-color); + --control-select-padding: 0; + --control-select-thickness: var(--feature-height); + --control-select-border-radius: var(--feature-border-radius); + --control-select-button-border-radius: var(--feature-border-radius); + } + ha-control-button-group { + --control-button-group-spacing: var(--feature-button-spacing); + --control-button-group-thickness: var(--feature-height); + } + ha-control-slider { + --control-slider-color: var(--feature-color); + --control-slider-background: var(--feature-color); + --control-slider-background-opacity: 0.2; + --control-slider-thickness: var(--feature-height); + --control-slider-border-radius: var(--feature-border-radius); + } +`; diff --git a/src/panels/lovelace/card-features/hui-alarm-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-alarm-modes-card-feature.ts index 2572f237c409..425f6b90e1d7 100644 --- a/src/panels/lovelace/card-features/hui-alarm-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-alarm-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiShieldOff } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, state } from "lit/decorators"; import { styleMap } from "lit/directives/style-map"; import memoizeOne from "memoize-one"; @@ -21,6 +21,7 @@ import { import { UNAVAILABLE } from "../../../data/entity"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; import { AlarmModesCardFeatureConfig } from "./types"; @@ -135,44 +136,26 @@ class HuiAlarmModeCardFeature } return html` -
- - -
+ + `; } static get styles() { - return css` - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-card-feature.ts b/src/panels/lovelace/card-features/hui-card-feature.ts new file mode 100644 index 000000000000..a65fbd5ad587 --- /dev/null +++ b/src/panels/lovelace/card-features/hui-card-feature.ts @@ -0,0 +1,51 @@ +import type { HassEntity } from "home-assistant-js-websocket"; +import { LitElement, html, nothing } from "lit"; +import { customElement, property } from "lit/decorators"; +import { HomeAssistant } from "../../../types"; +import type { HuiErrorCard } from "../cards/hui-error-card"; +import { createCardFeatureElement } from "../create-element/create-card-feature-element"; +import type { LovelaceCardFeature } from "../types"; +import type { LovelaceCardFeatureConfig } from "./types"; + +@customElement("hui-card-feature") +export class HuiCardFeature extends LitElement { + @property({ attribute: false }) public hass!: HomeAssistant; + + @property({ attribute: false }) public stateObj!: HassEntity; + + @property({ attribute: false }) public feature?: LovelaceCardFeatureConfig; + + @property({ attribute: false }) public color?: string; + + private _element?: LovelaceCardFeature | HuiErrorCard; + + private _getFeatureElement(feature: LovelaceCardFeatureConfig) { + if (!this._element) { + this._element = createCardFeatureElement(feature); + return this._element; + } + + return this._element; + } + + protected render() { + if (!this.feature) { + return nothing; + } + + const element = this._getFeatureElement(this.feature); + + if (this.hass) { + element.hass = this.hass; + (element as LovelaceCardFeature).stateObj = this.stateObj; + (element as LovelaceCardFeature).color = this.color; + } + return html`${element}`; + } +} + +declare global { + interface HTMLElementTagNameMap { + "hui-card-feature": HuiCardFeature; + } +} diff --git a/src/panels/lovelace/card-features/hui-card-features.ts b/src/panels/lovelace/card-features/hui-card-features.ts index 101561c78d80..c0c8bb94292a 100644 --- a/src/panels/lovelace/card-features/hui-card-features.ts +++ b/src/panels/lovelace/card-features/hui-card-features.ts @@ -1,17 +1,8 @@ import type { HassEntity } from "home-assistant-js-websocket"; -import { - CSSResultGroup, - LitElement, - TemplateResult, - css, - html, - nothing, -} from "lit"; +import { CSSResultGroup, LitElement, css, html, nothing } from "lit"; import { customElement, property } from "lit/decorators"; import { HomeAssistant } from "../../../types"; -import type { HuiErrorCard } from "../cards/hui-error-card"; -import { createCardFeatureElement } from "../create-element/create-card-feature-element"; -import type { LovelaceCardFeature } from "../types"; +import "./hui-card-feature"; import type { LovelaceCardFeatureConfig } from "./types"; @customElement("hui-card-features") @@ -24,44 +15,23 @@ export class HuiCardFeatures extends LitElement { @property({ attribute: false }) public color?: string; - private _featuresElements = new WeakMap< - LovelaceCardFeatureConfig, - LovelaceCardFeature | HuiErrorCard - >(); - - private _getFeatureElement(feature: LovelaceCardFeatureConfig) { - if (!this._featuresElements.has(feature)) { - const element = createCardFeatureElement(feature); - this._featuresElements.set(feature, element); - return element; - } - - return this._featuresElements.get(feature)!; - } - - private renderFeature( - featureConf: LovelaceCardFeatureConfig, - stateObj: HassEntity - ): TemplateResult { - const element = this._getFeatureElement(featureConf); - - if (this.hass) { - element.hass = this.hass; - (element as LovelaceCardFeature).stateObj = stateObj; - (element as LovelaceCardFeature).color = this.color; - } - - return html`${element}`; - } - protected render() { if (!this.features) { return nothing; } return html` - ${this.features.map((featureConf) => - this.renderFeature(featureConf, this.stateObj) - )} +
+ ${this.features.map( + (feature) => html` + + ` + )} +
`; } @@ -69,8 +39,24 @@ export class HuiCardFeatures extends LitElement { return css` :host { --feature-color: var(--state-icon-color); + --feature-padding: 12px; + --feature-height: 42px; + --feature-border-radius: 12px; + --feature-button-spacing: 12px; + position: relative; + width: 100%; + } + .container { + position: relative; display: flex; flex-direction: column; + padding: var(--feature-padding); + padding-top: 0px; + gap: var(--feature-padding); + width: 100%; + height: 100%; + box-sizing: border-box; + justify-content: space-evenly; } `; } diff --git a/src/panels/lovelace/card-features/hui-climate-fan-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-climate-fan-modes-card-feature.ts index 3cfa5624b54c..fb07ce89e54f 100644 --- a/src/panels/lovelace/card-features/hui-climate-fan-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-climate-fan-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiFan } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { stopPropagation } from "../../../common/dom/stop_propagation"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -14,8 +14,9 @@ import { ClimateEntity, ClimateEntityFeature } from "../../../data/climate"; import { UNAVAILABLE } from "../../../data/entity"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { ClimateFanModesCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { ClimateFanModesCardFeatureConfig } from "./types"; export const supportsClimateFanModesCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -140,79 +141,55 @@ class HuiClimateFanModesCardFeature if (this._config.style === "icons") { return html` -
- - -
+ + `; } return html` -
- - ${this._currentFanMode - ? html`` - : html` `} - ${options.map( - (option) => html` - - ${option.icon}${option.label} - - ` - )} - -
+ + ${this._currentFanMode + ? html`` + : html` `} + ${options.map( + (option) => html` + + ${option.icon}${option.label} + + ` + )} + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-climate-hvac-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-climate-hvac-modes-card-feature.ts index 3eab79b85ea3..65cf59959f26 100644 --- a/src/panels/lovelace/card-features/hui-climate-hvac-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-climate-hvac-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiThermostat } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { styleMap } from "lit/directives/style-map"; import { stopPropagation } from "../../../common/dom/stop_propagation"; @@ -19,6 +19,7 @@ import { import { UNAVAILABLE } from "../../../data/entity"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; import { ClimateHvacModesCardFeatureConfig } from "./types"; @@ -139,79 +140,56 @@ class HuiClimateHvacModesCardFeature if (this._config.style === "dropdown") { return html` -
- - ${this._currentHvacMode - ? html` - - ` - : html` - - `} - ${options.map( - (option) => html` - - ${option.icon}${option.label} - + + ${this._currentHvacMode + ? html` + ` - )} - -
+ : html` + + `} + ${options.map( + (option) => html` + + ${option.icon}${option.label} + + ` + )} + `; } return html` -
- - -
+ + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - ha-control-select { - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-climate-preset-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-climate-preset-modes-card-feature.ts index 5cd1e233e53c..90178bcb1d24 100644 --- a/src/panels/lovelace/card-features/hui-climate-preset-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-climate-preset-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiTuneVariant } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { stopPropagation } from "../../../common/dom/stop_propagation"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -14,8 +14,9 @@ import { ClimateEntity, ClimateEntityFeature } from "../../../data/climate"; import { UNAVAILABLE } from "../../../data/entity"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { ClimatePresetModesCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { ClimatePresetModesCardFeatureConfig } from "./types"; export const supportsClimatePresetModesCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -142,84 +143,57 @@ class HuiClimatePresetModesCardFeature if (this._config.style === "icons") { return html` -
- - -
- `; - } - - return html` -
- - ${this._currentPresetMode - ? html`` - : html` - - `} - ${options.map( - (option) => html` - - ${option.icon}${option.label} - - ` - )} - -
+ + `; + } + + return html` + + ${this._currentPresetMode + ? html`` + : html` + + `} + ${options.map( + (option) => html` + + ${option.icon}${option.label} + + ` + )} + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-climate-swing-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-climate-swing-modes-card-feature.ts index adc88c1948d0..b61f0966006b 100644 --- a/src/panels/lovelace/card-features/hui-climate-swing-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-climate-swing-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiArrowOscillating } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { stopPropagation } from "../../../common/dom/stop_propagation"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -14,8 +14,9 @@ import { ClimateEntity, ClimateEntityFeature } from "../../../data/climate"; import { UNAVAILABLE } from "../../../data/entity"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { ClimateSwingModesCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { ClimateSwingModesCardFeatureConfig } from "./types"; export const supportsClimateSwingModesCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -142,82 +143,58 @@ class HuiClimateSwingModesCardFeature if (this._config.style === "icons") { return html` -
- - -
+ + `; } return html` -
- - ${this._currentSwingMode - ? html`` - : html` `} - ${options.map( - (option) => html` - - ${option.icon}${option.label} - - ` - )} - -
+ + ${this._currentSwingMode + ? html`` + : html` `} + ${options.map( + (option) => html` + + ${option.icon}${option.label} + + ` + )} + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-cover-open-close-card-feature.ts b/src/panels/lovelace/card-features/hui-cover-open-close-card-feature.ts index 18581123610d..06a7eca48e58 100644 --- a/src/panels/lovelace/card-features/hui-cover-open-close-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-cover-open-close-card-feature.ts @@ -1,6 +1,6 @@ import { mdiStop } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing } from "lit"; +import { html, LitElement, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import { @@ -18,6 +18,7 @@ import { } from "../../../data/cover"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { CoverOpenCloseCardFeatureConfig } from "./types"; export const supportsCoverOpenCloseCardFeature = (stateObj: HassEntity) => { @@ -128,12 +129,7 @@ class HuiCoverOpenCloseCardFeature } static get styles() { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-cover-position-card-feature.ts b/src/panels/lovelace/card-features/hui-cover-position-card-feature.ts index af7e8a5f233d..43fadb8bda2f 100644 --- a/src/panels/lovelace/card-features/hui-cover-position-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-cover-position-card-feature.ts @@ -1,5 +1,5 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing } from "lit"; +import { html, LitElement, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { styleMap } from "lit/directives/style-map"; import { computeCssColor } from "../../../common/color/compute-color"; @@ -10,10 +10,11 @@ import { stateColorCss } from "../../../common/entity/state_color"; import { supportsFeature } from "../../../common/entity/supports-feature"; import { CoverEntityFeature } from "../../../data/cover"; import { UNAVAILABLE } from "../../../data/entity"; +import { DOMAIN_ATTRIBUTES_UNITS } from "../../../data/entity_attributes"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { CoverPositionCardFeatureConfig } from "./types"; -import { DOMAIN_ATTRIBUTES_UNITS } from "../../../data/entity_attributes"; export const supportsCoverPositionCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -72,32 +73,31 @@ class HuiCoverPositionCardFeature : stateColorCss(this.stateObj); const style = { - "--color": color, + "--feature-color": color, // Use open color for inactive state to avoid grey slider that looks disabled "--state-cover-inactive-color": openColor, }; return html` -
- -
+ `; } @@ -112,19 +112,7 @@ class HuiCoverPositionCardFeature } static get styles() { - return css` - ha-control-slider { - --control-slider-color: var(--color); - --control-slider-background: var(--color); - --control-slider-background-opacity: 0.2; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-cover-tilt-card-feature.ts b/src/panels/lovelace/card-features/hui-cover-tilt-card-feature.ts index d09c71aa627e..9fbee23208e0 100644 --- a/src/panels/lovelace/card-features/hui-cover-tilt-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-cover-tilt-card-feature.ts @@ -1,19 +1,20 @@ import { mdiArrowBottomLeft, mdiArrowTopRight, mdiStop } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing } from "lit"; +import { LitElement, html, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import { supportsFeature } from "../../../common/entity/supports-feature"; import "../../../components/ha-control-button"; import "../../../components/ha-control-button-group"; import { + CoverEntityFeature, canCloseTilt, canOpenTilt, canStopTilt, - CoverEntityFeature, } from "../../../data/cover"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { CoverTiltCardFeatureConfig } from "./types"; export const supportsCoverTiltCardFeature = (stateObj: HassEntity) => { @@ -120,12 +121,7 @@ class HuiCoverTiltCardFeature } static get styles() { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-cover-tilt-position-card-feature.ts b/src/panels/lovelace/card-features/hui-cover-tilt-position-card-feature.ts index 48e1a809c592..5942c7004545 100644 --- a/src/panels/lovelace/card-features/hui-cover-tilt-position-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-cover-tilt-position-card-feature.ts @@ -13,6 +13,7 @@ import { DOMAIN_ATTRIBUTES_UNITS } from "../../../data/entity_attributes"; import { generateTiltSliderTrackBackgroundGradient } from "../../../state-control/cover/ha-state-control-cover-tilt-position"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { CoverTiltPositionCardFeatureConfig } from "./types"; const GRADIENT = generateTiltSliderTrackBackgroundGradient(); @@ -72,33 +73,32 @@ class HuiCoverTiltPositionCardFeature : stateColorCss(this.stateObj); const style = { - "--color": color, + "--feature-color": color, // Use open color for inactive state to avoid grey slider that looks disabled "--state-cover-inactive-color": openColor, }; return html` -
- -
-
+ +
`; } @@ -113,24 +113,15 @@ class HuiCoverTiltPositionCardFeature } static get styles() { - return css` - ha-control-slider { - /* Force inactive state to be colored for the slider */ - --control-slider-color: var(--color); - --control-slider-background: var(--color); - --control-slider-background-opacity: 0.2; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - .gradient { - background: -webkit-linear-gradient(left, ${GRADIENT}); - opacity: 0.6; - } - `; + return [ + cardFeatureStyles, + css` + .gradient { + background: -webkit-linear-gradient(left, ${GRADIENT}); + opacity: 0.6; + } + `, + ]; } } diff --git a/src/panels/lovelace/card-features/hui-fan-preset-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-fan-preset-modes-card-feature.ts index d1cfb0fcc296..51c054e26f1d 100644 --- a/src/panels/lovelace/card-features/hui-fan-preset-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-fan-preset-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiTuneVariant } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { stopPropagation } from "../../../common/dom/stop_propagation"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -10,12 +10,13 @@ import "../../../components/ha-control-select"; import type { ControlSelectOption } from "../../../components/ha-control-select"; import "../../../components/ha-control-select-menu"; import type { HaControlSelectMenu } from "../../../components/ha-control-select-menu"; -import { FanEntity, FanEntityFeature } from "../../../data/fan"; import { UNAVAILABLE } from "../../../data/entity"; +import { FanEntity, FanEntityFeature } from "../../../data/fan"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { FanPresetModesCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { FanPresetModesCardFeatureConfig } from "./types"; export const supportsFanPresetModesCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -139,84 +140,57 @@ class HuiFanPresetModesCardFeature if (this._config.style === "icons") { return html` -
- - -
- `; - } - - return html` -
- - ${this._currentPresetMode - ? html`` - : html` - - `} - ${options.map( - (option) => html` - - ${option.icon}${option.label} - - ` - )} - -
+ + `; + } + + return html` + + ${this._currentPresetMode + ? html`` + : html` + + `} + ${options.map( + (option) => html` + + ${option.icon}${option.label} + + ` + )} + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-fan-speed-card-feature.ts b/src/panels/lovelace/card-features/hui-fan-speed-card-feature.ts index 932c3a93d214..9ebc5b3ebb6f 100644 --- a/src/panels/lovelace/card-features/hui-fan-speed-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-fan-speed-card-feature.ts @@ -24,6 +24,7 @@ import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; import { FanSpeedCardFeatureConfig } from "./types"; import { DOMAIN_ATTRIBUTES_UNITS } from "../../../data/entity_attributes"; +import { cardFeatureStyles } from "./common/card-feature-styles"; export const supportsFanSpeedCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -88,35 +89,11 @@ class HuiFanSpeedCardFeature extends LitElement implements LovelaceCardFeature { const speed = fanPercentageToSpeed(this.stateObj, percentage); return html` -
- - -
- `; - } - - const value = Math.max(Math.round(percentage), 0); - - return html` -
- -
+ > + + `; + } + + const value = Math.max(Math.round(percentage), 0); + + return html` + `; } @@ -153,28 +150,16 @@ class HuiFanSpeedCardFeature extends LitElement implements LovelaceCardFeature { } static get styles() { - return css` - ha-control-slider { - --control-slider-color: var(--feature-color); - --control-slider-background: var(--feature-color); - --control-slider-background-opacity: 0.2; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-background: var(--feature-color); - --control-select-background-opacity: 0.2; - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return [ + cardFeatureStyles, + css` + ha-control-select { + /* Color the background to match the slider style */ + --control-select-background: var(--feature-color); + --control-select-background-opacity: 0.2; + } + `, + ]; } } diff --git a/src/panels/lovelace/card-features/hui-humidifier-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-humidifier-modes-card-feature.ts index ee5176f9adba..510d94685737 100644 --- a/src/panels/lovelace/card-features/hui-humidifier-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-humidifier-modes-card-feature.ts @@ -1,6 +1,6 @@ import { mdiTuneVariant } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { stopPropagation } from "../../../common/dom/stop_propagation"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -17,8 +17,9 @@ import { } from "../../../data/humidifier"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { HumidifierModesCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { HumidifierModesCardFeatureConfig } from "./types"; export const supportsHumidifierModesCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -143,79 +144,55 @@ class HuiHumidifierModesCardFeature if (this._config.style === "icons") { return html` -
- - -
+ + `; } return html` -
- - ${this._currentMode - ? html`` - : html``} - ${options.map( - (option) => html` - - ${option.icon}${option.label} - - ` - )} - -
+ + ${this._currentMode + ? html`` + : html``} + ${options.map( + (option) => html` + + ${option.icon}${option.label} + + ` + )} + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-humidifier-toggle-card-feature.ts b/src/panels/lovelace/card-features/hui-humidifier-toggle-card-feature.ts index 647da49f1a1e..a1c2abba64a8 100644 --- a/src/panels/lovelace/card-features/hui-humidifier-toggle-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-humidifier-toggle-card-feature.ts @@ -1,6 +1,6 @@ import { mdiPower, mdiWaterPercent } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { LitElement, PropertyValues, TemplateResult, css, html } from "lit"; +import { LitElement, PropertyValues, TemplateResult, html } from "lit"; import { customElement, property, state } from "lit/decorators"; import { styleMap } from "lit/directives/style-map"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -11,6 +11,7 @@ import { UNAVAILABLE } from "../../../data/entity"; import { HumidifierEntity, HumidifierState } from "../../../data/humidifier"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { HumidifierToggleCardFeatureConfig } from "./types"; export const supportsHumidifierToggleCardFeature = (stateObj: HassEntity) => { @@ -95,37 +96,23 @@ class HuiHumidifierToggleCardFeature })); return html` -
- - -
+ + `; } static get styles() { - return css` - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-lawn-mower-commands-card-feature.ts b/src/panels/lovelace/card-features/hui-lawn-mower-commands-card-feature.ts index 52ec9c59d25d..de74459b0108 100644 --- a/src/panels/lovelace/card-features/hui-lawn-mower-commands-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-lawn-mower-commands-card-feature.ts @@ -1,6 +1,6 @@ import { mdiHomeImportOutline, mdiPause, mdiPlay } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { LitElement, css, html, nothing } from "lit"; +import { LitElement, html, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import { supportsFeature } from "../../../common/entity/supports-feature"; @@ -14,6 +14,7 @@ import { } from "../../../data/lawn_mower"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { LAWN_MOWER_COMMANDS, LawnMowerCommand, @@ -171,12 +172,7 @@ class HuiLawnMowerCommandCardFeature } static get styles() { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-light-brightness-card-feature.ts b/src/panels/lovelace/card-features/hui-light-brightness-card-feature.ts index 7eeeb3d3bd6b..3390f01e654c 100644 --- a/src/panels/lovelace/card-features/hui-light-brightness-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-light-brightness-card-feature.ts @@ -1,5 +1,5 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing } from "lit"; +import { html, LitElement, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import { stateActive } from "../../../common/entity/state_active"; @@ -8,6 +8,7 @@ import { UNAVAILABLE } from "../../../data/entity"; import { lightSupportsBrightness } from "../../../data/light"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { LightBrightnessCardFeatureConfig } from "./types"; export const supportsLightBrightnessCardFeature = (stateObj: HassEntity) => { @@ -58,19 +59,17 @@ class HuiLightBrightnessCardFeature : undefined; return html` -
- -
+ `; } @@ -85,19 +84,7 @@ class HuiLightBrightnessCardFeature } static get styles() { - return css` - ha-control-slider { - --control-slider-color: var(--feature-color); - --control-slider-background: var(--feature-color); - --control-slider-background-opacity: 0.2; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-light-color-temp-card-feature.ts b/src/panels/lovelace/card-features/hui-light-color-temp-card-feature.ts index fa7ed6b9d93a..f7a71b4ecee2 100644 --- a/src/panels/lovelace/card-features/hui-light-color-temp-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-light-color-temp-card-feature.ts @@ -16,6 +16,7 @@ import { LightColorMode, lightSupportsColorMode } from "../../../data/light"; import { generateColorTemperatureGradient } from "../../../dialogs/more-info/components/lights/light-color-temp-picker"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { LightColorTempCardFeatureConfig } from "./types"; export const supportsLightColorTempCardFeature = (stateObj: HassEntity) => { @@ -73,23 +74,21 @@ class HuiLightColorTempCardFeature const gradient = this._generateTemperatureGradient(minKelvin!, maxKelvin); return html` -
- -
+ `; } @@ -108,22 +107,18 @@ class HuiLightColorTempCardFeature } static get styles() { - return css` - ha-control-slider { - --control-slider-color: var(--feature-color); - --control-slider-background: -webkit-linear-gradient( - left, - var(--gradient) - ); - --control-slider-background-opacity: 1; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return [ + cardFeatureStyles, + css` + ha-control-slider { + --control-slider-background: -webkit-linear-gradient( + left, + var(--gradient) + ); + --control-slider-background-opacity: 1; + } + `, + ]; } } diff --git a/src/panels/lovelace/card-features/hui-lock-commands-card-feature.ts b/src/panels/lovelace/card-features/hui-lock-commands-card-feature.ts index 19d737bb2172..1c321134fd87 100644 --- a/src/panels/lovelace/card-features/hui-lock-commands-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-lock-commands-card-feature.ts @@ -1,6 +1,6 @@ import { mdiLock, mdiLockOpenVariant } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { CSSResultGroup, LitElement, css, html, nothing } from "lit"; +import { CSSResultGroup, LitElement, html, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -14,6 +14,7 @@ import { } from "../../../data/lock"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { LockCommandsCardFeatureConfig } from "./types"; export const supportsLockCommandsCardFeature = (stateObj: HassEntity) => { @@ -88,12 +89,7 @@ class HuiLockCommandsCardFeature } static get styles(): CSSResultGroup { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-lock-open-door-card-feature.ts b/src/panels/lovelace/card-features/hui-lock-open-door-card-feature.ts index 298daabb559f..a5a046228983 100644 --- a/src/panels/lovelace/card-features/hui-lock-open-door-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-lock-open-door-card-feature.ts @@ -15,6 +15,7 @@ import { import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; import { LockOpenDoorCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; export const supportsLockOpenDoorCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -112,35 +113,34 @@ class HuiLockOpenDoorCardFeature } static get styles(): CSSResultGroup { - return css` - ha-control-button { - font-size: 14px; - } - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - .open-button { - width: 130px; - } - .open-button.confirm { - --control-button-background-color: var(--warning-color); - } - .open-done { - font-size: 14px; - line-height: 14px; - display: flex; - align-items: center; - justify-content: center; - flex-direction: row; - gap: 8px; - font-weight: 500; - color: var(--success-color); - margin: 0 12px 12px 12px; - height: 40px; - text-align: center; - } - `; + return [ + cardFeatureStyles, + css` + ha-control-button { + font-size: 14px; + } + .open-button { + width: 130px; + } + .open-button.confirm { + --control-button-background-color: var(--warning-color); + } + .open-done { + font-size: 14px; + line-height: 14px; + display: flex; + align-items: center; + justify-content: center; + flex-direction: row; + gap: 8px; + font-weight: 500; + color: var(--success-color); + margin: 0 12px 12px 12px; + height: 40px; + text-align: center; + } + `, + ]; } } diff --git a/src/panels/lovelace/card-features/hui-numeric-input-card-feature.ts b/src/panels/lovelace/card-features/hui-numeric-input-card-feature.ts index e725a446ab7b..50ab4a5d6fe8 100644 --- a/src/panels/lovelace/card-features/hui-numeric-input-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-numeric-input-card-feature.ts @@ -1,16 +1,17 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing, PropertyValues } from "lit"; +import { html, LitElement, nothing, PropertyValues } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; -import { isUnavailableState } from "../../../data/entity"; -import { HomeAssistant } from "../../../types"; -import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { NumericInputCardFeatureConfig } from "./types"; import "../../../components/ha-control-button"; import "../../../components/ha-control-button-group"; import "../../../components/ha-control-number-buttons"; import "../../../components/ha-control-slider"; import "../../../components/ha-icon"; +import { isUnavailableState } from "../../../data/entity"; +import { HomeAssistant } from "../../../types"; +import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; +import { NumericInputCardFeatureConfig } from "./types"; export const supportsNumericInputCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -81,50 +82,36 @@ class HuiNumericInputCardFeature const stateObj = this.stateObj; + if (this._config.style === "buttons") { + return html` + + `; + } return html` -
- ${this._config.style === "buttons" - ? html`` - : html``} -
+ `; } static get styles() { - return css` - ha-control-number-buttons { - width: auto; - } - ha-control-slider { - --control-slider-color: var(--feature-color); - --control-slider-background: var(--feature-color); - --control-slider-background-opacity: 0.2; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-select-options-card-feature.ts b/src/panels/lovelace/card-features/hui-select-options-card-feature.ts index 60b99116e44e..8f63910ca48e 100644 --- a/src/panels/lovelace/card-features/hui-select-options-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-select-options-card-feature.ts @@ -1,5 +1,5 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing, PropertyValues } from "lit"; +import { html, LitElement, nothing, PropertyValues } from "lit"; import { customElement, property, query, state } from "lit/decorators"; import { stopPropagation } from "../../../common/dom/stop_propagation"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -10,8 +10,9 @@ import { InputSelectEntity } from "../../../data/input_select"; import { SelectEntity } from "../../../data/select"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { SelectOptionsCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { SelectOptionsCardFeatureConfig } from "./types"; export const supportsSelectOptionsCardFeature = (stateObj: HassEntity) => { const domain = computeDomain(stateObj.entity_id); @@ -119,45 +120,30 @@ class HuiSelectOptionsCardFeature ); return html` -
- - ${options.map( - (option) => html` - - ${this.hass!.formatEntityState(stateObj, option)} - - ` - )} - -
+ + ${options.map( + (option) => html` + + ${this.hass!.formatEntityState(stateObj, option)} + + ` + )} + `; } static get styles() { - return css` - ha-control-select-menu { - box-sizing: border-box; - --control-select-menu-height: 40px; - --control-select-menu-border-radius: 10px; - line-height: 1.2; - display: block; - width: 100%; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-target-humidity-card-feature.ts b/src/panels/lovelace/card-features/hui-target-humidity-card-feature.ts index 2f637d050b50..cb10385bc636 100644 --- a/src/panels/lovelace/card-features/hui-target-humidity-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-target-humidity-card-feature.ts @@ -1,5 +1,5 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing, PropertyValues } from "lit"; +import { html, LitElement, nothing, PropertyValues } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import "../../../components/ha-control-slider"; @@ -7,6 +7,7 @@ import { UNAVAILABLE } from "../../../data/entity"; import { HumidifierEntity } from "../../../data/humidifier"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { TargetHumidityCardFeatureConfig } from "./types"; export const supportsTargetHumidityCardFeature = (stateObj: HassEntity) => { @@ -84,39 +85,22 @@ class HuiTargetHumidityCardFeature } return html` -
- -
+ `; } static get styles() { - return css` - ha-control-slider { - --control-slider-color: var(--feature-color); - --control-slider-background: var(--feature-color); - --control-slider-background-opacity: 0.2; - --control-slider-thickness: 40px; - --control-slider-border-radius: 10px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-target-temperature-card-feature.ts b/src/panels/lovelace/card-features/hui-target-temperature-card-feature.ts index 638eeab585c0..7ed7bdb3f2f0 100644 --- a/src/panels/lovelace/card-features/hui-target-temperature-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-target-temperature-card-feature.ts @@ -1,5 +1,5 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, nothing, PropertyValues } from "lit"; +import { html, LitElement, nothing, PropertyValues } from "lit"; import { customElement, property, state } from "lit/decorators"; import { styleMap } from "lit/directives/style-map"; import { UNIT_F } from "../../../common/const"; @@ -18,6 +18,7 @@ import { } from "../../../data/water_heater"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { TargetTemperatureCardFeatureConfig } from "./types"; type Target = "value" | "low" | "high"; @@ -283,12 +284,7 @@ class HuiTargetTemperatureCardFeature } static get styles() { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-update-actions-card-feature.ts b/src/panels/lovelace/card-features/hui-update-actions-card-feature.ts index a2f9ddb8adcc..173a32883dcd 100644 --- a/src/panels/lovelace/card-features/hui-update-actions-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-update-actions-card-feature.ts @@ -1,6 +1,6 @@ import { mdiCancel, mdiCellphoneArrowDown } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { LitElement, css, html, nothing } from "lit"; +import { LitElement, html, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import { stateActive } from "../../../common/entity/state_active"; @@ -16,6 +16,7 @@ import { import { showUpdateBackupDialogParams } from "../../../dialogs/update_backup/show-update-backup-dialog"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { UpdateActionsCardFeatureConfig } from "./types"; export const DEFAULT_UPDATE_BACKUP_OPTION = "ask"; @@ -149,12 +150,7 @@ class HuiUpdateActionsCardFeature } static get styles() { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-vacuum-commands-card-feature.ts b/src/panels/lovelace/card-features/hui-vacuum-commands-card-feature.ts index 02ceff183cf6..228d3032d7cf 100644 --- a/src/panels/lovelace/card-features/hui-vacuum-commands-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-vacuum-commands-card-feature.ts @@ -8,7 +8,7 @@ import { mdiTargetVariant, } from "@mdi/js"; import { HassEntity } from "home-assistant-js-websocket"; -import { LitElement, css, html, nothing } from "lit"; +import { LitElement, html, nothing } from "lit"; import { customElement, property, state } from "lit/decorators"; import { computeDomain } from "../../../common/entity/compute_domain"; import { supportsFeature } from "../../../common/entity/supports-feature"; @@ -25,6 +25,7 @@ import { } from "../../../data/vacuum"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { VACUUM_COMMANDS, VacuumCommand, @@ -210,12 +211,7 @@ class HuiVacuumCommandCardFeature } static get styles() { - return css` - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/card-features/hui-water-heater-operation-modes-card-feature.ts b/src/panels/lovelace/card-features/hui-water-heater-operation-modes-card-feature.ts index f676b16ca699..a1c7c6690b41 100644 --- a/src/panels/lovelace/card-features/hui-water-heater-operation-modes-card-feature.ts +++ b/src/panels/lovelace/card-features/hui-water-heater-operation-modes-card-feature.ts @@ -1,5 +1,5 @@ import { HassEntity } from "home-assistant-js-websocket"; -import { css, html, LitElement, PropertyValues, TemplateResult } from "lit"; +import { html, LitElement, PropertyValues, TemplateResult } from "lit"; import { customElement, property, state } from "lit/decorators"; import { styleMap } from "lit/directives/style-map"; import { computeDomain } from "../../../common/entity/compute_domain"; @@ -18,8 +18,9 @@ import { } from "../../../data/water_heater"; import { HomeAssistant } from "../../../types"; import { LovelaceCardFeature, LovelaceCardFeatureEditor } from "../types"; -import { WaterHeaterOperationModesCardFeatureConfig } from "./types"; +import { cardFeatureStyles } from "./common/card-feature-styles"; import { filterModes } from "./common/filter-modes"; +import { WaterHeaterOperationModesCardFeatureConfig } from "./types"; export const supportsWaterHeaterOperationModesCardFeature = ( stateObj: HassEntity @@ -118,41 +119,23 @@ class HuiWaterHeaterOperationModeCardFeature })); return html` -
- - -
+ + `; } static get styles() { - return css` - ha-control-select { - --control-select-color: var(--feature-color); - --control-select-padding: 0; - --control-select-thickness: 40px; - --control-select-border-radius: 10px; - --control-select-button-border-radius: 10px; - } - ha-control-button-group { - margin: 0 12px 12px 12px; - --control-button-group-spacing: 12px; - } - .container { - padding: 0 12px 12px 12px; - width: auto; - } - `; + return cardFeatureStyles; } } diff --git a/src/panels/lovelace/cards/hui-tile-card.ts b/src/panels/lovelace/cards/hui-tile-card.ts index 419b5bdfc63d..50d283814339 100644 --- a/src/panels/lovelace/cards/hui-tile-card.ts +++ b/src/panels/lovelace/cards/hui-tile-card.ts @@ -113,8 +113,7 @@ export class HuiTileCard extends LitElement implements LovelaceCard { let grid_min_columns = 2; let grid_rows = 1; if (this._config?.features?.length) { - const featureHeight = Math.ceil((this._config.features.length * 2) / 3); - grid_rows += featureHeight; + grid_rows += this._config.features.length; } if (this._config?.vertical) { grid_rows++; @@ -279,51 +278,53 @@ export class HuiTileCard extends LitElement implements LovelaceCard { > -
-
- ${imageUrl - ? html` - - ` - : html` - - - - `} - ${renderTileBadge(stateObj, this.hass)} +
+
+
+ ${imageUrl + ? html` + + ` + : html` + + + + `} + ${renderTileBadge(stateObj, this.hass)} +
+
- + ${this._config.features + ? html` + + ` + : nothing}
- ${this._config.features - ? html` - - ` - : nothing} `; } @@ -371,31 +372,43 @@ export class HuiTileCard extends LitElement implements LovelaceCard { margin: calc(-1 * var(--ha-card-border-width, 1px)); overflow: hidden; } + .container { + margin: calc(-1 * var(--ha-card-border-width, 1px)); + display: flex; + flex-direction: column; + flex: 1; + } .content { + position: relative; display: flex; flex-direction: row; align-items: center; - padding: 12px; + padding: 0 10px; + min-height: var(--row-height, 56px); + flex: 1; + pointer-events: none; } .vertical { flex-direction: column; text-align: center; + justify-content: center; } .vertical .icon-container { - margin-bottom: 12px; + margin-bottom: 10px; margin-right: 0; margin-inline-start: initial; margin-inline-end: initial; } .vertical ha-tile-info { width: 100%; + flex: none; } .icon-container { position: relative; flex: none; - margin-right: 12px; + margin-right: 10px; margin-inline-start: initial; - margin-inline-end: 12px; + margin-inline-end: 10px; direction: var(--direction); transition: transform 180ms ease-in-out; } @@ -414,8 +427,8 @@ export class HuiTileCard extends LitElement implements LovelaceCard { inset-inline-end: -3px; inset-inline-start: initial; } - .icon-container:not([role="button"]) { - pointer-events: none; + .icon-container[role="button"] { + pointer-events: auto; } .icon-container[role="button"]:focus-visible, .icon-container[role="button"]:active { @@ -423,11 +436,9 @@ export class HuiTileCard extends LitElement implements LovelaceCard { } ha-tile-info { position: relative; - flex: 1; min-width: 0; transition: background-color 180ms ease-in-out; box-sizing: border-box; - pointer-events: none; } hui-card-features { --feature-color: var(--tile-color); diff --git a/src/panels/lovelace/sections/hui-grid-section.ts b/src/panels/lovelace/sections/hui-grid-section.ts index 47e33c71025c..c29334cd51e8 100644 --- a/src/panels/lovelace/sections/hui-grid-section.ts +++ b/src/panels/lovelace/sections/hui-grid-section.ts @@ -214,7 +214,7 @@ export class GridSection extends LitElement implements LovelaceSectionElement { --column-count: 4; --row-gap: var(--ha-section-grid-row-gap, 8px); --column-gap: var(--ha-section-grid-column-gap, 8px); - --row-height: 66px; + --row-height: var(--ha-section-grid-row-height, 56px); display: flex; flex-direction: column; gap: var(--row-gap);