Add support for safe area insets (#6473)

This commit is contained in:
Bram Kragten 2020-07-30 18:27:27 +02:00 committed by GitHub
parent 07fceeab5a
commit ca4f573be0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
41 changed files with 443 additions and 749 deletions

View File

@ -38,6 +38,7 @@ export class HaDialog extends MwcDialog {
} }
.mdc-dialog__actions { .mdc-dialog__actions {
justify-content: var(--justify-action-buttons, flex-end); justify-content: var(--justify-action-buttons, flex-end);
padding-bottom: max(env(safe-area-inset-bottom), 8px);
} }
.mdc-dialog__container { .mdc-dialog__container {
align-items: var(--vertial-align-dialog, center); align-items: var(--vertial-align-dialog, center);
@ -50,6 +51,12 @@ export class HaDialog extends MwcDialog {
position: var(--dialog-content-position, relative); position: var(--dialog-content-position, relative);
padding: var(--dialog-content-padding, 20px 24px); padding: var(--dialog-content-padding, 20px 24px);
} }
:host([hideactions]) .mdc-dialog .mdc-dialog__content {
padding-bottom: max(
var(--dialog-content-padding, 20px),
env(safe-area-inset-bottom)
);
}
.mdc-dialog .mdc-dialog__surface { .mdc-dialog .mdc-dialog__surface {
position: var(--dialog-surface-position, relative); position: var(--dialog-surface-position, relative);
min-height: var(--mdc-dialog-min-height, auto); min-height: var(--mdc-dialog-min-height, auto);

View File

@ -126,7 +126,7 @@ class HaSidebar extends LitElement {
// property used only in css // property used only in css
// @ts-ignore // @ts-ignore
@property({ type: Boolean, reflect: true }) private _rtl = false; @property({ type: Boolean, reflect: true }) public rtl = false;
private _mouseLeaveTimeout?: number; private _mouseLeaveTimeout?: number;
@ -312,6 +312,7 @@ class HaSidebar extends LitElement {
hass.panelUrl !== oldHass.panelUrl || hass.panelUrl !== oldHass.panelUrl ||
hass.user !== oldHass.user || hass.user !== oldHass.user ||
hass.localize !== oldHass.localize || hass.localize !== oldHass.localize ||
hass.language !== oldHass.language ||
hass.states !== oldHass.states || hass.states !== oldHass.states ||
hass.defaultPanel !== oldHass.defaultPanel hass.defaultPanel !== oldHass.defaultPanel
); );
@ -339,12 +340,14 @@ class HaSidebar extends LitElement {
return; return;
} }
this._rtl = computeRTL(this.hass); const oldHass = changedProps.get("hass") as HomeAssistant | undefined;
if (!oldHass || oldHass.language !== this.hass.language) {
this.rtl = computeRTL(this.hass);
}
if (!SUPPORT_SCROLL_IF_NEEDED) { if (!SUPPORT_SCROLL_IF_NEEDED) {
return; return;
} }
const oldHass = changedProps.get("hass") as HomeAssistant | undefined;
if (!oldHass || oldHass.panelUrl !== this.hass.panelUrl) { if (!oldHass || oldHass.panelUrl !== this.hass.panelUrl) {
const selectedEl = this.shadowRoot!.querySelector(".iron-selected"); const selectedEl = this.shadowRoot!.querySelector(".iron-selected");
if (selectedEl) { if (selectedEl) {
@ -496,9 +499,12 @@ class HaSidebar extends LitElement {
width: 64px; width: 64px;
} }
:host([expanded]) { :host([expanded]) {
width: 256px; width: calc(256px + env(safe-area-inset-left));
}
:host([rtl]) {
border-right: 0;
border-left: 1px solid var(--divider-color);
} }
.menu { .menu {
box-sizing: border-box; box-sizing: border-box;
height: 65px; height: 65px;
@ -512,18 +518,25 @@ class HaSidebar extends LitElement {
background-color: var(--primary-background-color); background-color: var(--primary-background-color);
font-size: 20px; font-size: 20px;
align-items: center; align-items: center;
padding-left: calc(8.5px + env(safe-area-inset-left));
}
:host([rtl]) .menu {
padding-left: 8.5px;
padding-right: calc(8.5px + env(safe-area-inset-right));
} }
:host([expanded]) .menu { :host([expanded]) .menu {
width: 256px; width: calc(256px + env(safe-area-inset-left));
}
:host([rtl][expanded]) .menu {
width: calc(256px + env(safe-area-inset-right));
} }
.menu mwc-icon-button { .menu mwc-icon-button {
color: var(--sidebar-icon-color); color: var(--sidebar-icon-color);
} }
:host([expanded]) .menu mwc-icon-button { :host([expanded]) .menu mwc-icon-button {
margin-right: 23px; margin-right: 23px;
} }
:host([expanded][_rtl]) .menu mwc-icon-button { :host([expanded][rtl]) .menu mwc-icon-button {
margin-right: 0px; margin-right: 0px;
margin-left: 23px; margin-left: 23px;
} }
@ -551,12 +564,18 @@ class HaSidebar extends LitElement {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
box-sizing: border-box; box-sizing: border-box;
height: calc(100% - 196px); height: calc(100% - 196px - env(safe-area-inset-bottom));
overflow-y: auto; overflow-y: auto;
overflow-x: hidden; overflow-x: hidden;
scrollbar-color: var(--scrollbar-thumb-color) transparent; scrollbar-color: var(--scrollbar-thumb-color) transparent;
scrollbar-width: thin; scrollbar-width: thin;
background: none; background: none;
margin-left: env(safe-area-inset-left);
}
:host([rtl]) paper-listbox {
margin-left: initial;
margin-right: env(safe-area-inset-right);
} }
a { a {
@ -580,7 +599,7 @@ class HaSidebar extends LitElement {
:host([expanded]) paper-icon-item { :host([expanded]) paper-icon-item {
width: 240px; width: 240px;
} }
:host([_rtl]) paper-icon-item { :host([rtl]) paper-icon-item {
padding-left: auto; padding-left: auto;
padding-right: 12px; padding-right: 12px;
} }
@ -656,6 +675,11 @@ class HaSidebar extends LitElement {
} }
.notifications-container { .notifications-container {
display: flex; display: flex;
margin-left: env(safe-area-inset-left);
}
:host([rtl]) .notifications-container {
margin-left: initial;
margin-right: env(safe-area-inset-right);
} }
.notifications { .notifications {
cursor: pointer; cursor: pointer;
@ -664,18 +688,23 @@ class HaSidebar extends LitElement {
flex: 1; flex: 1;
} }
.profile { .profile {
margin-left: env(safe-area-inset-left);
}
:host([rtl]) .profile {
margin-left: initial;
margin-right: env(safe-area-inset-right);
} }
.profile paper-icon-item { .profile paper-icon-item {
padding-left: 4px; padding-left: 4px;
} }
:host([_rtl]) .profile paper-icon-item { :host([rtl]) .profile paper-icon-item {
padding-left: auto; padding-left: auto;
padding-right: 4px; padding-right: 4px;
} }
.profile .item-text { .profile .item-text {
margin-left: 8px; margin-left: 8px;
} }
:host([_rtl]) .profile .item-text { :host([rtl]) .profile .item-text {
margin-right: 8px; margin-right: 8px;
} }
@ -735,7 +764,7 @@ class HaSidebar extends LitElement {
font-weight: 500; font-weight: 500;
} }
:host([_rtl]) .menu mwc-icon-button { :host([rtl]) .menu mwc-icon-button {
-webkit-transform: scaleX(-1); -webkit-transform: scaleX(-1);
transform: scaleX(-1); transform: scaleX(-1);
} }

View File

@ -165,7 +165,6 @@ class DialogConfigEntrySystemOptions extends LitElement {
haStyleDialog, haStyleDialog,
css` css`
ha-paper-dialog { ha-paper-dialog {
min-width: 400px;
max-width: 500px; max-width: 500px;
} }
.init-spinner { .init-spinner {

View File

@ -29,9 +29,17 @@ export class HuiNotificationDrawer extends EventsMixin(
width: calc(100% - 32px); width: calc(100% - 32px);
} }
div[main-title] {
padding-left: env(safe-area-inset-left);
padding-right: env(safe-area-inset-right);
}
.notifications { .notifications {
overflow-y: auto; overflow-y: auto;
padding-top: 16px; padding-top: 16px;
padding-left: env(safe-area-inset-left);
padding-right: env(safe-area-inset-right);
padding-bottom: env(safe-area-inset-bottom);
height: calc(100% - 65px); height: calc(100% - 65px);
box-sizing: border-box; box-sizing: border-box;
background-color: var(--primary-background-color); background-color: var(--primary-background-color);

View File

@ -1,4 +1,4 @@
<meta name='viewport' content='width=device-width, user-scalable=no'> <meta name='viewport' content='width=device-width, user-scalable=no, viewport-fit=cover'>
<style> <style>
body { body {
font-family: Roboto, sans-serif; font-family: Roboto, sans-serif;
@ -7,6 +7,6 @@
font-weight: 400; font-weight: 400;
margin: 0; margin: 0;
padding: 0; padding: 0;
height: 100vh; height: 100%;
} }
</style> </style>

View File

@ -5,14 +5,16 @@
<link rel="preload" href="<%= latestAppJS %>" as="script" crossorigin="use-credentials" /> <link rel="preload" href="<%= latestAppJS %>" as="script" crossorigin="use-credentials" />
<%= renderTemplate('_header') %> <%= renderTemplate('_header') %>
<title>Home Assistant</title> <title>Home Assistant</title>
<link rel="mask-icon" href="/static/icons/mask-icon.svg" color="#03a9f4" />
<link <link
rel="apple-touch-icon" rel="apple-touch-icon"
sizes="180x180" sizes="180x180"
href="/static/icons/favicon-apple-180x180.png" href="/static/icons/favicon-apple-180x180.png"
/> />
<link rel="mask-icon" href="/static/icons/mask-icon.svg" color="#03a9f4" />
<meta name="apple-itunes-app" content="app-id=1099568401" /> <meta name="apple-itunes-app" content="app-id=1099568401" />
<meta name="apple-mobile-web-app-capable" content="yes" /> <meta name="apple-mobile-web-app-capable" content="yes" />
<meta name="apple-mobile-web-app-status-bar-style" content="default">
<meta name="apple-mobile-web-app-title" content="Home Assistant">
<meta <meta
name="msapplication-square70x70logo" name="msapplication-square70x70logo"
content="/static/icons/tile-win-70x70.png" content="/static/icons/tile-win-70x70.png"

View File

@ -77,6 +77,8 @@ class HaAppLayout extends customElements.get("app-header-layout") {
/* Using 'transform' will cause 'position: fixed' elements to behave like /* Using 'transform' will cause 'position: fixed' elements to behave like
'position: absolute' relative to this element. */ 'position: absolute' relative to this element. */
transform: translate(0); transform: translate(0);
margin-left: env(safe-area-inset-left);
margin-right: env(safe-area-inset-right);
} }
@media print { @media print {

View File

@ -60,6 +60,11 @@ class HassSubpage extends LitElement {
background-color: var(--primary-background-color); background-color: var(--primary-background-color);
} }
:host([narrow]) {
width: 100%;
position: fixed;
}
.toolbar { .toolbar {
display: flex; display: flex;
align-items: center; align-items: center;

View File

@ -26,9 +26,9 @@ import { computeRTLDirection } from "../common/util/compute_rtl";
export class HaTabsSubpageDataTable extends LitElement { export class HaTabsSubpageDataTable extends LitElement {
@property({ attribute: false }) public hass!: HomeAssistant; @property({ attribute: false }) public hass!: HomeAssistant;
@property() public isWide!: boolean; @property({ type: Boolean }) public isWide = false;
@property({ type: Boolean, reflect: true }) public narrow!: boolean; @property({ type: Boolean, reflect: true }) public narrow = false;
/** /**
* Object with the columns. * Object with the columns.
@ -110,6 +110,7 @@ export class HaTabsSubpageDataTable extends LitElement {
<hass-tabs-subpage <hass-tabs-subpage
.hass=${this.hass} .hass=${this.hass}
.narrow=${this.narrow} .narrow=${this.narrow}
.isWide=${this.isWide}
.backPath=${this.backPath} .backPath=${this.backPath}
.backCallback=${this.backCallback} .backCallback=${this.backCallback}
.route=${this.route} .route=${this.route}
@ -168,38 +169,37 @@ export class HaTabsSubpageDataTable extends LitElement {
? html` ? html`
<div slot="header"> <div slot="header">
<slot name="header"> <slot name="header">
<slot name="header"> <div class="table-header">
<div class="table-header"> <search-input
<search-input .filter=${this.filter}
.filter=${this.filter} no-label-float
no-label-float no-underline
no-underline @value-changed=${this._handleSearchChange}
@value-changed=${this._handleSearchChange} .label=${this.hass.localize(
.label=${this.hass.localize( "ui.components.data-table.search"
"ui.components.data-table.search" )}
)} >
> </search-input>
</search-input> ${this.activeFilters
${this.activeFilters ? html`<div class="active-filters">
? html`<div class="active-filters"> ${this.hass.localize(
${this.hass.localize( "ui.panel.config.filtering.filtering_by"
"ui.panel.config.filtering.filtering_by" )}
)} ${this.activeFilters.join(", ")}
${this.activeFilters.join(", ")} <mwc-button @click=${this._clearFilter}
<mwc-button @click=${this._clearFilter} >${this.hass.localize(
>${this.hass.localize( "ui.panel.config.filtering.clear"
"ui.panel.config.filtering.clear" )}</mwc-button
)}</mwc-button >
> </div>`
</div>` : ""}
: ""} </div>
</div></slot </slot>
></slot
>
</div> </div>
` `
: html` <div slot="header"></div> `} : html` <div slot="header"></div> `}
</ha-data-table> </ha-data-table>
<div slot="fab"><slot name="fab"></slot></div>
</hass-tabs-subpage> </hass-tabs-subpage>
`; `;
} }

View File

@ -22,6 +22,7 @@ import "../components/ha-svg-icon";
import "../components/ha-icon"; import "../components/ha-icon";
import "../components/ha-tab"; import "../components/ha-tab";
import { restoreScroll } from "../common/decorators/restore-scroll"; import { restoreScroll } from "../common/decorators/restore-scroll";
import { computeRTL } from "../common/util/compute_rtl";
export interface PageNavigation { export interface PageNavigation {
path: string; path: string;
@ -53,6 +54,11 @@ class HassTabsSubpage extends LitElement {
@property({ type: Boolean, reflect: true }) public narrow = false; @property({ type: Boolean, reflect: true }) public narrow = false;
@property({ type: Boolean, reflect: true, attribute: "is-wide" })
public isWide = false;
@property({ type: Boolean, reflect: true }) public rtl = false;
@internalProperty() private _activeTab?: PageNavigation; @internalProperty() private _activeTab?: PageNavigation;
// @ts-ignore // @ts-ignore
@ -107,6 +113,14 @@ class HassTabsSubpage extends LitElement {
`${this.route.prefix}${this.route.path}`.includes(tab.path) `${this.route.prefix}${this.route.path}`.includes(tab.path)
); );
} }
if (changedProperties.has("hass")) {
const oldHass = changedProperties.get("hass") as
| HomeAssistant
| undefined;
if (!oldHass || oldHass.language !== this.hass.language) {
this.rtl = computeRTL(this.hass);
}
}
} }
protected render(): TemplateResult { protected render(): TemplateResult {
@ -152,6 +166,7 @@ class HassTabsSubpage extends LitElement {
<div class="content" @scroll=${this._saveScrollPos}> <div class="content" @scroll=${this._saveScrollPos}>
<slot></slot> <slot></slot>
</div> </div>
<div id="fab"><slot name="fab"></slot></div>
`; `;
} }
@ -184,6 +199,11 @@ class HassTabsSubpage extends LitElement {
background-color: var(--primary-background-color); background-color: var(--primary-background-color);
} }
:host([narrow]) {
width: 100%;
position: fixed;
}
ha-menu-button { ha-menu-button {
margin-right: 24px; margin-right: 24px;
} }
@ -215,9 +235,10 @@ class HassTabsSubpage extends LitElement {
background-color: var(--sidebar-background-color); background-color: var(--sidebar-background-color);
border-top: 1px solid var(--divider-color); border-top: 1px solid var(--divider-color);
justify-content: space-between; justify-content: space-between;
z-index: 1; z-index: 2;
font-size: 12px; font-size: 12px;
width: 100%; width: 100%;
padding-bottom: env(safe-area-inset-bottom);
} }
#tabbar:not(.bottom-bar) { #tabbar:not(.bottom-bar) {
@ -247,7 +268,11 @@ class HassTabsSubpage extends LitElement {
.content { .content {
position: relative; position: relative;
width: 100%; width: calc(
100% - env(safe-area-inset-left) - env(safe-area-inset-right)
);
margin-left: env(safe-area-inset-left);
margin-right: env(safe-area-inset-right);
height: calc(100% - 65px); height: calc(100% - 65px);
overflow-y: auto; overflow-y: auto;
overflow: auto; overflow: auto;
@ -256,6 +281,30 @@ class HassTabsSubpage extends LitElement {
:host([narrow]) .content { :host([narrow]) .content {
height: calc(100% - 128px); height: calc(100% - 128px);
height: calc(100% - 128px - env(safe-area-inset-bottom));
}
#fab {
position: fixed;
right: calc(16px + env(safe-area-inset-right));
bottom: calc(16px + env(safe-area-inset-bottom));
z-index: 1;
}
:host([narrow]) #fab {
bottom: calc(84px + env(safe-area-inset-bottom));
}
#fab[is-wide] {
bottom: 24px;
right: 24px;
}
:host([rtl]) #fab {
right: auto;
left: calc(16px + env(safe-area-inset-left));
}
:host([rtl][is-wide]) #fab {
bottom: 24px;
left: 24px;
right: auto;
} }
`; `;
} }

View File

@ -152,16 +152,13 @@ class HomeAssistantMain extends LitElement {
--app-drawer-width: 64px; --app-drawer-width: 64px;
} }
:host([expanded]) { :host([expanded]) {
--app-drawer-width: 256px; --app-drawer-width: calc(256px + env(safe-area-inset-left));
} }
partial-panel-resolver, partial-panel-resolver,
ha-sidebar { ha-sidebar {
/* allow a light tap highlight on the actual interface elements */ /* allow a light tap highlight on the actual interface elements */
-webkit-tap-highlight-color: rgba(0, 0, 0, 0.1); -webkit-tap-highlight-color: rgba(0, 0, 0, 0.1);
} }
partial-panel-resolver {
height: 100%;
}
`; `;
} }
} }

View File

@ -11,7 +11,7 @@ import {
} from "lit-element"; } from "lit-element";
import { styleMap } from "lit-html/directives/style-map"; import { styleMap } from "lit-html/directives/style-map";
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import "@material/mwc-checkbox"; import "@material/mwc-checkbox";
@ -63,7 +63,7 @@ class PanelCalendar extends LitElement {
protected render(): TemplateResult { protected render(): TemplateResult {
return html` return html`
<app-header-layout> <ha-app-layout>
<app-header fixed slot="header"> <app-header fixed slot="header">
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -106,7 +106,7 @@ class PanelCalendar extends LitElement {
@view-changed=${this._handleViewChanged} @view-changed=${this._handleViewChanged}
></ha-full-calendar> ></ha-full-calendar>
</div> </div>
</app-header-layout> </ha-app-layout>
`; `;
} }

View File

@ -38,7 +38,6 @@ import {
showAreaRegistryDetailDialog, showAreaRegistryDetailDialog,
} from "./show-dialog-area-registry-detail"; } from "./show-dialog-area-registry-detail";
import { mdiPlus } from "@mdi/js"; import { mdiPlus } from "@mdi/js";
import { computeRTL } from "../../../common/util/compute_rtl";
@customElement("ha-config-areas-dashboard") @customElement("ha-config-areas-dashboard")
export class HaConfigAreasDashboard extends LitElement { export class HaConfigAreasDashboard extends LitElement {
@ -106,6 +105,7 @@ export class HaConfigAreasDashboard extends LitElement {
<hass-tabs-subpage-data-table <hass-tabs-subpage-data-table
.hass=${this.hass} .hass=${this.hass}
.narrow=${this.narrow} .narrow=${this.narrow}
.isWide=${this.isWide}
back-path="/config" back-path="/config"
.tabs=${configSections.integrations} .tabs=${configSections.integrations}
.route=${this.route} .route=${this.route}
@ -123,18 +123,16 @@ export class HaConfigAreasDashboard extends LitElement {
icon="hass:help-circle" icon="hass:help-circle"
@click=${this._showHelp} @click=${this._showHelp}
></ha-icon-button> ></ha-icon-button>
<mwc-fab
slot="fab"
title="${this.hass.localize(
"ui.panel.config.areas.picker.create_area"
)}"
@click=${this._createArea}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass!)}
title="${this.hass.localize(
"ui.panel.config.areas.picker.create_area"
)}"
@click=${this._createArea}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -183,28 +181,6 @@ export class HaConfigAreasDashboard extends LitElement {
--app-header-background-color: var(--sidebar-background-color); --app-header-background-color: var(--sidebar-background-color);
--app-header-text-color: var(--sidebar-text-color); --app-header-text-color: var(--sidebar-text-color);
} }
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[is-wide][rtl] {
bottom: 24px;
left: 24px;
right: auto;
}
`; `;
} }
} }

View File

@ -13,9 +13,7 @@ import {
PropertyValues, PropertyValues,
TemplateResult, TemplateResult,
} from "lit-element"; } from "lit-element";
import { classMap } from "lit-html/directives/class-map";
import { navigate } from "../../../common/navigate"; import { navigate } from "../../../common/navigate";
import { computeRTL } from "../../../common/util/compute_rtl";
import "../../../components/ha-card"; import "../../../components/ha-card";
import "../../../components/ha-svg-icon"; import "../../../components/ha-svg-icon";
import "@material/mwc-fab"; import "@material/mwc-fab";
@ -46,6 +44,7 @@ import "./trigger/ha-automation-trigger";
import { HaDeviceTrigger } from "./trigger/types/ha-automation-trigger-device"; import { HaDeviceTrigger } from "./trigger/types/ha-automation-trigger-device";
import { mdiContentSave } from "@mdi/js"; import { mdiContentSave } from "@mdi/js";
import { PaperListboxElement } from "@polymer/paper-listbox"; import { PaperListboxElement } from "@polymer/paper-listbox";
import { classMap } from "lit-html/directives/class-map";
const MODES = ["single", "restart", "queued", "parallel"]; const MODES = ["single", "restart", "queued", "parallel"];
const MODES_MAX = ["queued", "parallel"]; const MODES_MAX = ["queued", "parallel"];
@ -72,7 +71,7 @@ export class HaAutomationEditor extends LitElement {
@internalProperty() private _config?: AutomationConfig; @internalProperty() private _config?: AutomationConfig;
@internalProperty() private _dirty?: boolean; @internalProperty() private _dirty = false;
@internalProperty() private _errors?: string; @internalProperty() private _errors?: string;
@ -312,16 +311,10 @@ export class HaAutomationEditor extends LitElement {
` `
: ""} : ""}
<mwc-fab <mwc-fab
?is-wide="${this.isWide}" slot="fab"
?narrow="${this.narrow}" class=${classMap({ dirty: this._dirty })}
?dirty="${this._dirty}" .title=${this.hass.localize("ui.panel.config.automation.editor.save")}
.title="${this.hass.localize(
"ui.panel.config.automation.editor.save"
)}"
@click=${this._saveAutomation} @click=${this._saveAutomation}
class="${classMap({
rtl: computeRTL(this.hass),
})}"
> >
<ha-svg-icon slot="icon" path=${mdiContentSave}></ha-svg-icon> <ha-svg-icon slot="icon" path=${mdiContentSave}></ha-svg-icon>
</mwc-fab> </mwc-fab>
@ -542,35 +535,12 @@ export class HaAutomationEditor extends LitElement {
margin-right: 8px; margin-right: 8px;
} }
mwc-fab { mwc-fab {
position: fixed; position: relative;
bottom: 16px; bottom: calc(-80px - env(safe-area-inset-bottom));
right: 16px; transition: bottom 0.3s;
z-index: 3;
margin-bottom: -80px;
transition: margin-bottom 0.3s;
} }
mwc-fab.dirty {
mwc-fab[is-wide] { bottom: 0;
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
margin-bottom: -140px;
}
mwc-fab[dirty] {
margin-bottom: 0;
}
mwc-fab.rtl {
right: auto;
left: 16px;
}
mwc-fab[is-wide].rtl {
bottom: 24px;
right: auto;
left: 24px;
} }
`, `,
]; ];

View File

@ -1,13 +1,12 @@
import "../../../components/ha-icon-button"; import "../../../components/ha-icon-button";
import "@polymer/paper-tooltip/paper-tooltip"; import "@polymer/paper-tooltip/paper-tooltip";
import { import {
css,
CSSResultArray,
customElement, customElement,
html, html,
LitElement, LitElement,
property, property,
TemplateResult, TemplateResult,
CSSResult,
} from "lit-element"; } from "lit-element";
import { ifDefined } from "lit-html/directives/if-defined"; import { ifDefined } from "lit-html/directives/if-defined";
import memoizeOne from "memoize-one"; import memoizeOne from "memoize-one";
@ -15,7 +14,6 @@ import { isComponentLoaded } from "../../../common/config/is_component_loaded";
import { formatDateTime } from "../../../common/datetime/format_date_time"; import { formatDateTime } from "../../../common/datetime/format_date_time";
import { fireEvent } from "../../../common/dom/fire_event"; import { fireEvent } from "../../../common/dom/fire_event";
import { computeStateName } from "../../../common/entity/compute_state_name"; import { computeStateName } from "../../../common/entity/compute_state_name";
import { computeRTL } from "../../../common/util/compute_rtl";
import { DataTableColumnContainer } from "../../../components/data-table/ha-data-table"; import { DataTableColumnContainer } from "../../../components/data-table/ha-data-table";
import "../../../components/entity/ha-entity-toggle"; import "../../../components/entity/ha-entity-toggle";
import "@material/mwc-fab"; import "@material/mwc-fab";
@ -169,19 +167,16 @@ class HaAutomationPicker extends LitElement {
)} )}
hasFab hasFab
> >
<mwc-fab
slot="fab"
title=${this.hass.localize(
"ui.panel.config.automation.picker.add_automation"
)}
@click=${this._createNew}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<mwc-fab
slot="fab"
?is-wide=${this.isWide}
?narrow=${this.narrow}
title=${this.hass.localize(
"ui.panel.config.automation.picker.add_automation"
)}
?rtl=${computeRTL(this.hass)}
@click=${this._createNew}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -207,37 +202,8 @@ class HaAutomationPicker extends LitElement {
}); });
} }
static get styles(): CSSResultArray { static get styles(): CSSResult {
return [ return haStyle;
haStyle,
css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
cursor: pointer;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[rtl][is-wide] {
bottom: 24px;
right: auto;
left: 24px;
}
`,
];
} }
} }

View File

@ -1,4 +1,4 @@
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import { import {
@ -127,7 +127,7 @@ class HaConfigDashboard extends LitElement {
} }
return html` return html`
<app-header-layout> <ha-app-layout>
<app-header fixed slot="header"> <app-header fixed slot="header">
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -138,7 +138,7 @@ class HaConfigDashboard extends LitElement {
</app-header> </app-header>
${content} ${content}
</app-header-layout> </ha-app-layout>
`; `;
} }

View File

@ -241,6 +241,7 @@ export class EntityRegistrySettings extends LitElement {
display: flex; display: flex;
justify-content: space-between; justify-content: space-between;
padding: 8px; padding: 8px;
padding-bottom: max(env(safe-area-inset-bottom), 8px);
background-color: var(--mdc-theme-surface, #fff); background-color: var(--mdc-theme-surface, #fff);
} }
ha-switch { ha-switch {

View File

@ -5,8 +5,6 @@ import "@polymer/paper-listbox/paper-listbox";
import "@polymer/paper-tooltip/paper-tooltip"; import "@polymer/paper-tooltip/paper-tooltip";
import { HassEntity } from "home-assistant-js-websocket"; import { HassEntity } from "home-assistant-js-websocket";
import { import {
css,
CSSResult,
customElement, customElement,
html, html,
LitElement, LitElement,
@ -34,7 +32,6 @@ import { HELPER_DOMAINS } from "./const";
import { showHelperDetailDialog } from "./show-dialog-helper-detail"; import { showHelperDetailDialog } from "./show-dialog-helper-detail";
import "../../../components/ha-svg-icon"; import "../../../components/ha-svg-icon";
import { mdiPlus } from "@mdi/js"; import { mdiPlus } from "@mdi/js";
import { computeRTL } from "../../../common/util/compute_rtl";
@customElement("ha-config-helpers") @customElement("ha-config-helpers")
export class HaConfigHelpers extends LitElement { export class HaConfigHelpers extends LitElement {
@ -160,18 +157,16 @@ export class HaConfigHelpers extends LitElement {
"ui.panel.config.helpers.picker.no_helpers" "ui.panel.config.helpers.picker.no_helpers"
)} )}
> >
<mwc-fab
slot="fab"
title="${this.hass.localize(
"ui.panel.config.helpers.picker.add_helper"
)}"
@click=${this._createHelpler}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass!)}
title="${this.hass.localize(
"ui.panel.config.helpers.picker.add_helper"
)}"
@click=${this._createHelpler}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -215,31 +210,4 @@ export class HaConfigHelpers extends LitElement {
private _createHelpler() { private _createHelpler() {
showHelperDetailDialog(this); showHelperDetailDialog(this);
} }
static get styles(): CSSResult {
return css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[is-wide][rtl] {
bottom: 24px;
left: 24px;
right: auto;
}
`;
}
} }

View File

@ -21,7 +21,6 @@ import { HASSDomEvent } from "../../../common/dom/fire_event";
import "../../../common/search/search-input"; import "../../../common/search/search-input";
import { caseInsensitiveCompare } from "../../../common/string/compare"; import { caseInsensitiveCompare } from "../../../common/string/compare";
import { LocalizeFunc } from "../../../common/translations/localize"; import { LocalizeFunc } from "../../../common/translations/localize";
import { computeRTL } from "../../../common/util/compute_rtl";
import { nextRender } from "../../../common/util/render-status"; import { nextRender } from "../../../common/util/render-status";
import "../../../components/entity/ha-state-icon"; import "../../../components/entity/ha-state-icon";
import "../../../components/ha-button-menu"; import "../../../components/ha-button-menu";
@ -459,12 +458,10 @@ class HaConfigIntegrations extends SubscribeMixin(LitElement) {
: ""} : ""}
</div> </div>
<mwc-fab <mwc-fab
slot="fab"
aria-label=${this.hass.localize("ui.panel.config.integrations.new")} aria-label=${this.hass.localize("ui.panel.config.integrations.new")}
title=${this.hass.localize("ui.panel.config.integrations.new")} title=${this.hass.localize("ui.panel.config.integrations.new")}
@click=${this._createFlow} @click=${this._createFlow}
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass!)}
> >
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon> <ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab> </mwc-fab>
@ -714,28 +711,6 @@ class HaConfigIntegrations extends SubscribeMixin(LitElement) {
h2 { h2 {
margin-top: 0; margin-top: 0;
} }
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[is-wide][rtl] {
bottom: 24px;
left: 24px;
right: auto;
}
`, `,
]; ];
} }

View File

@ -19,6 +19,7 @@ import { mdiNetwork, mdiFolderMultipleOutline, mdiPlus } from "@mdi/js";
import "../../../../../layouts/hass-tabs-subpage"; import "../../../../../layouts/hass-tabs-subpage";
import type { PageNavigation } from "../../../../../layouts/hass-tabs-subpage"; import type { PageNavigation } from "../../../../../layouts/hass-tabs-subpage";
import { computeRTL } from "../../../../../common/util/compute_rtl"; import { computeRTL } from "../../../../../common/util/compute_rtl";
import "@material/mwc-button/mwc-button";
export const zhaTabs: PageNavigation[] = [ export const zhaTabs: PageNavigation[] = [
{ {
@ -81,10 +82,8 @@ class ZHAConfigDashboard extends LitElement {
</div>` </div>`
: ""} : ""}
</ha-card> </ha-card>
<a href="/config/zha/add"> <a href="/config/zha/add" slot="fab">
<mwc-fab <mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
title=${this.hass.localize("ui.panel.config.zha.add_device")} title=${this.hass.localize("ui.panel.config.zha.add_device")}
?rtl=${computeRTL(this.hass)} ?rtl=${computeRTL(this.hass)}
> >
@ -104,30 +103,6 @@ class ZHAConfigDashboard extends LitElement {
margin-top: 16px; margin-top: 16px;
max-width: 500px; max-width: 500px;
} }
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[rtl][is-wide] {
bottom: 24px;
right: auto;
left: 24px;
}
`, `,
]; ];
} }

View File

@ -23,7 +23,6 @@ import "../../../../../layouts/hass-tabs-subpage-data-table";
import { HomeAssistant, Route } from "../../../../../types"; import { HomeAssistant, Route } from "../../../../../types";
import { sortZHAGroups, formatAsPaddedHex } from "./functions"; import { sortZHAGroups, formatAsPaddedHex } from "./functions";
import { zhaTabs } from "./zha-config-dashboard"; import { zhaTabs } from "./zha-config-dashboard";
import { computeRTL } from "../../../../../common/util/compute_rtl";
import { mdiPlus } from "@mdi/js"; import { mdiPlus } from "@mdi/js";
import { haStyle } from "../../../../../resources/styles"; import { haStyle } from "../../../../../resources/styles";
@ -126,17 +125,14 @@ export class ZHAGroupsDashboard extends LitElement {
.data=${this._formattedGroups(this._groups)} .data=${this._formattedGroups(this._groups)}
@row-click=${this._handleRowClicked} @row-click=${this._handleRowClicked}
> >
<a href="/config/zha/group-add" slot="fab">
<mwc-fab
title=${this.hass!.localize("ui.panel.config.zha.groups.add_group")}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</a>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<a href="/config/zha/group-add">
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
title=${this.hass!.localize("ui.panel.config.zha.groups.add_group")}
?rtl=${computeRTL(this.hass)}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</a>
`; `;
} }
@ -153,31 +149,6 @@ export class ZHAGroupsDashboard extends LitElement {
return [ return [
haStyle, haStyle,
css` css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[rtl][is-wide] {
bottom: 24px;
right: auto;
left: 24px;
}
a { a {
color: var(--primary-color); color: var(--primary-color);
} }

View File

@ -1,8 +1,6 @@
import "@material/mwc-fab"; import "@material/mwc-fab";
import "@polymer/paper-tooltip/paper-tooltip"; import "@polymer/paper-tooltip/paper-tooltip";
import { import {
css,
CSSResult,
customElement, customElement,
html, html,
LitElement, LitElement,
@ -37,7 +35,6 @@ import { lovelaceTabs } from "../ha-config-lovelace";
import { showDashboardDetailDialog } from "./show-dialog-lovelace-dashboard-detail"; import { showDashboardDetailDialog } from "./show-dialog-lovelace-dashboard-detail";
import "../../../../components/ha-svg-icon"; import "../../../../components/ha-svg-icon";
import { mdiPlus } from "@mdi/js"; import { mdiPlus } from "@mdi/js";
import { computeRTL } from "../../../../common/util/compute_rtl";
@customElement("ha-config-lovelace-dashboards") @customElement("ha-config-lovelace-dashboards")
export class HaConfigLovelaceDashboards extends LitElement { export class HaConfigLovelaceDashboards extends LitElement {
@ -225,18 +222,16 @@ export class HaConfigLovelaceDashboards extends LitElement {
id="url_path" id="url_path"
hasFab hasFab
> >
<mwc-fab
slot="fab"
title="${this.hass.localize(
"ui.panel.config.lovelace.dashboards.picker.add_dashboard"
)}"
@click=${this._addDashboard}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass)}
title="${this.hass.localize(
"ui.panel.config.lovelace.dashboards.picker.add_dashboard"
)}"
@click=${this._addDashboard}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -311,26 +306,4 @@ export class HaConfigLovelaceDashboards extends LitElement {
}, },
}); });
} }
static get styles(): CSSResult {
return css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
left: 16px;
right: auto;
}
`;
}
} }

View File

@ -5,8 +5,6 @@ import "@polymer/paper-listbox/paper-listbox";
import "@polymer/paper-tooltip/paper-tooltip"; import "@polymer/paper-tooltip/paper-tooltip";
import "@material/mwc-fab"; import "@material/mwc-fab";
import { import {
css,
CSSResult,
customElement, customElement,
html, html,
LitElement, LitElement,
@ -41,7 +39,6 @@ import { lovelaceTabs } from "../ha-config-lovelace";
import { showResourceDetailDialog } from "./show-dialog-lovelace-resource-detail"; import { showResourceDetailDialog } from "./show-dialog-lovelace-resource-detail";
import "../../../../components/ha-svg-icon"; import "../../../../components/ha-svg-icon";
import { mdiPlus } from "@mdi/js"; import { mdiPlus } from "@mdi/js";
import { computeRTL } from "../../../../common/util/compute_rtl";
@customElement("ha-config-lovelace-resources") @customElement("ha-config-lovelace-resources")
export class HaConfigLovelaceRescources extends LitElement { export class HaConfigLovelaceRescources extends LitElement {
@ -106,18 +103,16 @@ export class HaConfigLovelaceRescources extends LitElement {
@row-click=${this._editResource} @row-click=${this._editResource}
hasFab hasFab
> >
<mwc-fab
slot="fab"
title=${this.hass.localize(
"ui.panel.config.lovelace.resources.picker.add_resource"
)}
@click=${this._addResource}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass!)}
title=${this.hass.localize(
"ui.panel.config.lovelace.resources.picker.add_resource"
)}
@click=${this._addResource}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -203,31 +198,4 @@ export class HaConfigLovelaceRescources extends LitElement {
}, },
}); });
} }
static get styles(): CSSResult {
return css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[is-wide][rtl] {
bottom: 24px;
left: 24px;
right: auto;
}
`;
}
} }

View File

@ -32,7 +32,6 @@ import {
} from "./show-dialog-person-detail"; } from "./show-dialog-person-detail";
import "../../../components/ha-svg-icon"; import "../../../components/ha-svg-icon";
import { mdiPlus } from "@mdi/js"; import { mdiPlus } from "@mdi/js";
import { computeRTL } from "../../../common/util/compute_rtl";
class HaConfigPerson extends LitElement { class HaConfigPerson extends LitElement {
@property({ attribute: false }) public hass?: HomeAssistant; @property({ attribute: false }) public hass?: HomeAssistant;
@ -123,17 +122,14 @@ class HaConfigPerson extends LitElement {
` `
: ""} : ""}
</ha-config-section> </ha-config-section>
<mwc-fab
slot="fab"
title="${hass.localize("ui.panel.config.person.add_person")}"
@click=${this._createPerson}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage> </hass-tabs-subpage>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass!)}
title="${hass.localize("ui.panel.config.person.add_person")}"
@click=${this._createPerson}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -243,28 +239,6 @@ class HaConfigPerson extends LitElement {
ha-card.storage paper-item { ha-card.storage paper-item {
cursor: pointer; cursor: pointer;
} }
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[is-wide][rtl] {
bottom: 24px;
left: 24px;
right: auto;
}
`; `;
} }
} }

View File

@ -13,7 +13,6 @@ import { ifDefined } from "lit-html/directives/if-defined";
import memoizeOne from "memoize-one"; import memoizeOne from "memoize-one";
import { fireEvent } from "../../../common/dom/fire_event"; import { fireEvent } from "../../../common/dom/fire_event";
import { computeStateName } from "../../../common/entity/compute_state_name"; import { computeStateName } from "../../../common/entity/compute_state_name";
import { computeRTL } from "../../../common/util/compute_rtl";
import { DataTableColumnContainer } from "../../../components/data-table/ha-data-table"; import { DataTableColumnContainer } from "../../../components/data-table/ha-data-table";
import "@material/mwc-fab"; import "@material/mwc-fab";
import { forwardHaptic } from "../../../data/haptics"; import { forwardHaptic } from "../../../data/haptics";
@ -152,17 +151,16 @@ class HaSceneDashboard extends LitElement {
icon="hass:help-circle" icon="hass:help-circle"
@click=${this._showHelp} @click=${this._showHelp}
></ha-icon-button> ></ha-icon-button>
<a href="/config/scene/edit/new" slot="fab">
<mwc-fab
title=${this.hass.localize(
"ui.panel.config.scene.picker.add_scene"
)}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</a>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<a href="/config/scene/edit/new">
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
title=${this.hass.localize("ui.panel.config.scene.picker.add_scene")}
?rtl=${computeRTL(this.hass)}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</a>
`; `;
} }
@ -208,31 +206,6 @@ class HaSceneDashboard extends LitElement {
return [ return [
haStyle, haStyle,
css` css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[rtl][is-wide] {
bottom: 24px;
right: auto;
left: 24px;
}
a { a {
color: var(--primary-color); color: var(--primary-color);
} }

View File

@ -399,14 +399,10 @@ export class HaSceneEditor extends SubscribeMixin(LitElement) {
: ""} : ""}
</div> </div>
<mwc-fab <mwc-fab
?is-wide=${this.isWide} slot="fab"
?narrow=${this.narrow}
?dirty=${this._dirty}
.title=${this.hass.localize("ui.panel.config.scene.editor.save")} .title=${this.hass.localize("ui.panel.config.scene.editor.save")}
@click=${this._saveScene} @click=${this._saveScene}
class=${classMap({ class=${classMap({ dirty: this._dirty })}
rtl: computeRTL(this.hass),
})}
> >
<ha-svg-icon slot="icon" path=${mdiContentSave}></ha-svg-icon> <ha-svg-icon slot="icon" path=${mdiContentSave}></ha-svg-icon>
</mwc-fab> </mwc-fab>
@ -731,7 +727,7 @@ export class HaSceneEditor extends SubscribeMixin(LitElement) {
font-weight: bold; font-weight: bold;
color: var(--error-color); color: var(--error-color);
} }
.content { ha-config-section:last-child {
padding-bottom: 20px; padding-bottom: 20px;
} }
.triggers, .triggers,
@ -778,35 +774,12 @@ export class HaSceneEditor extends SubscribeMixin(LitElement) {
color: var(--primary-color); color: var(--primary-color);
} }
mwc-fab { mwc-fab {
position: fixed; position: relative;
bottom: 16px; bottom: calc(-80px - env(safe-area-inset-bottom));
right: 16px; transition: bottom 0.3s;
z-index: 1;
margin-bottom: -80px;
transition: margin-bottom 0.3s;
} }
mwc-fab.dirty {
mwc-fab[is-wide] { bottom: 0;
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
margin-bottom: -140px;
}
mwc-fab[dirty] {
margin-bottom: 0;
}
mwc-fab.rtl {
right: auto;
left: 16px;
}
mwc-fab[is-wide].rtl {
bottom: 24px;
right: auto;
left: 24px;
} }
`, `,
]; ];

View File

@ -57,7 +57,7 @@ export class HaScriptEditor extends LitElement {
@internalProperty() private _idError = false; @internalProperty() private _idError = false;
@internalProperty() private _dirty?: boolean; @internalProperty() private _dirty = false;
@internalProperty() private _errors?: string; @internalProperty() private _errors?: string;
@ -228,14 +228,12 @@ export class HaScriptEditor extends LitElement {
</div> </div>
</div> </div>
<mwc-fab <mwc-fab
?is-wide=${this.isWide} slot="fab"
?narrow=${this.narrow} .title=${this.hass.localize("ui.common.save")}
?dirty=${this._dirty}
.title="${this.hass.localize("ui.common.save")}"
@click=${this._saveScript} @click=${this._saveScript}
class="${classMap({ class=${classMap({
rtl: computeRTL(this.hass), dirty: this._dirty,
})}" })}
> >
<ha-svg-icon slot="icon" path=${mdiContentSave}></ha-svg-icon> <ha-svg-icon slot="icon" path=${mdiContentSave}></ha-svg-icon>
</mwc-fab> </mwc-fab>
@ -441,35 +439,12 @@ export class HaScriptEditor extends LitElement {
color: var(--primary-color); color: var(--primary-color);
} }
mwc-fab { mwc-fab {
position: fixed; position: relative;
bottom: 16px; bottom: calc(-80px - env(safe-area-inset-bottom));
right: 16px; transition: bottom 0.3s;
z-index: 3;
margin-bottom: -80px;
transition: margin-bottom 0.3s;
} }
mwc-fab.dirty {
mwc-fab[is-wide] { bottom: 0;
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
margin-bottom: -140px;
}
mwc-fab[dirty] {
margin-bottom: 0;
}
mwc-fab.rtl {
right: auto;
left: 16px;
}
mwc-fab[is-wide].rtl {
bottom: 24px;
right: auto;
left: 24px;
} }
`, `,
]; ];

View File

@ -1,8 +1,7 @@
import "../../../components/ha-icon-button"; import "../../../components/ha-icon-button";
import { HassEntity } from "home-assistant-js-websocket"; import { HassEntity } from "home-assistant-js-websocket";
import { import {
css, CSSResult,
CSSResultArray,
customElement, customElement,
html, html,
LitElement, LitElement,
@ -146,19 +145,19 @@ class HaScriptPicker extends LitElement {
icon="hass:help-circle" icon="hass:help-circle"
@click=${this._showHelp} @click=${this._showHelp}
></ha-icon-button> ></ha-icon-button>
<a href="/config/script/edit/new" slot="fab">
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
title="${this.hass.localize(
"ui.panel.config.script.picker.add_script"
)}"
?rtl=${computeRTL(this.hass)}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</a>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<a href="/config/script/edit/new">
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
title="${this.hass.localize(
"ui.panel.config.script.picker.add_script"
)}"
?rtl=${computeRTL(this.hass)}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</a>
`; `;
} }
@ -199,36 +198,8 @@ class HaScriptPicker extends LitElement {
}); });
} }
static get styles(): CSSResultArray { static get styles(): CSSResult {
return [ return haStyle;
haStyle,
css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[rtl][is-wide] {
bottom: 24px;
right: auto;
left: 24px;
}
`,
];
} }
} }

View File

@ -1,5 +1,4 @@
import { import {
css,
customElement, customElement,
LitElement, LitElement,
property, property,
@ -8,7 +7,6 @@ import {
import { html } from "lit-html"; import { html } from "lit-html";
import memoizeOne from "memoize-one"; import memoizeOne from "memoize-one";
import { HASSDomEvent } from "../../../common/dom/fire_event"; import { HASSDomEvent } from "../../../common/dom/fire_event";
import { computeRTL } from "../../../common/util/compute_rtl";
import { import {
DataTableColumnContainer, DataTableColumnContainer,
RowClickedEvent, RowClickedEvent,
@ -98,16 +96,14 @@ export class HaConfigUsers extends LitElement {
@row-click=${this._editUser} @row-click=${this._editUser}
hasFab hasFab
> >
<mwc-fab
slot="fab"
.title=${this.hass.localize("ui.panel.config.users.picker.add_user")}
@click=${this._addUser}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage-data-table> </hass-tabs-subpage-data-table>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
.title=${this.hass.localize("ui.panel.config.users.picker.add_user")}
@click=${this._addUser}
?rtl=${computeRTL(this.hass)}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -166,31 +162,4 @@ export class HaConfigUsers extends LitElement {
}, },
}); });
} }
static get styles() {
return css`
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[rtl] {
right: auto;
left: 16px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl][is-wide] {
bottom: 24px;
right: auto;
left: 24px;
}
`;
}
} }

View File

@ -51,7 +51,6 @@ import type { HomeAssistant, Route } from "../../../types";
import "../ha-config-section"; import "../ha-config-section";
import { configSections } from "../ha-panel-config"; import { configSections } from "../ha-panel-config";
import { showZoneDetailDialog } from "./show-dialog-zone-detail"; import { showZoneDetailDialog } from "./show-dialog-zone-detail";
import { computeRTL } from "../../../common/util/compute_rtl";
@customElement("ha-config-zone") @customElement("ha-config-zone")
export class HaConfigZone extends SubscribeMixin(LitElement) { export class HaConfigZone extends SubscribeMixin(LitElement) {
@ -255,17 +254,14 @@ export class HaConfigZone extends SubscribeMixin(LitElement) {
</div> </div>
` `
: ""} : ""}
<mwc-fab
slot="fab"
title=${hass.localize("ui.panel.config.zone.add_zone")}
@click=${this._createZone}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
</hass-tabs-subpage> </hass-tabs-subpage>
<mwc-fab
?is-wide=${this.isWide}
?narrow=${this.narrow}
?rtl=${computeRTL(this.hass)}
title="${hass.localize("ui.panel.config.zone.add_zone")}"
@click=${this._createZone}
>
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab>
`; `;
} }
@ -544,23 +540,6 @@ export class HaConfigZone extends SubscribeMixin(LitElement) {
ha-card paper-item { ha-card paper-item {
cursor: pointer; cursor: pointer;
} }
mwc-fab {
position: fixed;
bottom: 16px;
right: 16px;
z-index: 1;
}
mwc-fab[is-wide] {
bottom: 24px;
right: 24px;
}
mwc-fab[narrow] {
bottom: 84px;
}
mwc-fab[rtl] {
left: 24px;
right: auto;
}
`; `;
} }
} }

View File

@ -1,4 +1,4 @@
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import { computeRTL } from "../../common/util/compute_rtl"; import { computeRTL } from "../../common/util/compute_rtl";
@ -56,7 +56,7 @@ class HaPanelHistory extends LitElement {
protected render() { protected render() {
return html` return html`
<app-header-layout> <ha-app-layout>
<app-header slot="header" fixed> <app-header slot="header" fixed>
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -93,7 +93,7 @@ class HaPanelHistory extends LitElement {
</state-history-charts> </state-history-charts>
`} `}
</div> </div>
</app-header-layout> </ha-app-layout>
`; `;
} }

View File

@ -1,4 +1,3 @@
import "@polymer/app-layout/app-header-layout/app-header-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import "../../components/ha-icon-button"; import "../../components/ha-icon-button";
@ -6,6 +5,7 @@ import "../../components/ha-circular-progress";
import { computeRTL } from "../../common/util/compute_rtl"; import { computeRTL } from "../../common/util/compute_rtl";
import "../../components/entity/ha-entity-picker"; import "../../components/entity/ha-entity-picker";
import "../../components/ha-menu-button"; import "../../components/ha-menu-button";
import "../../layouts/ha-app-layout";
import "./ha-logbook"; import "./ha-logbook";
import { import {
LitElement, LitElement,
@ -74,7 +74,7 @@ export class HaPanelLogbook extends LitElement {
protected render() { protected render() {
return html` return html`
<app-header-layout> <ha-app-layout>
<app-header slot="header" fixed> <app-header slot="header" fixed>
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -126,7 +126,7 @@ export class HaPanelLogbook extends LitElement {
.entries=${this._entries} .entries=${this._entries}
.userIdToName=${this._userIdToName} .userIdToName=${this._userIdToName}
></ha-logbook>`} ></ha-logbook>`}
</app-header-layout> </ha-app-layout>
`; `;
} }

View File

@ -137,68 +137,67 @@ export class HuiUnusedEntities extends LitElement {
} }
return html` return html`
${!this.narrow <div class="container">
? html` ${!this.narrow
<ha-card ? html`
header="${this.hass.localize( <ha-card
"ui.panel.lovelace.unused_entities.title" header="${this.hass.localize(
)}" "ui.panel.lovelace.unused_entities.title"
> )}"
<div class="card-content"> >
${this.hass.localize( <div class="card-content">
"ui.panel.lovelace.unused_entities.available_entities" ${this.hass.localize(
)} "ui.panel.lovelace.unused_entities.available_entities"
${this.lovelace.mode === "storage" )}
? html` ${this.lovelace.mode === "storage"
<br />${this.hass.localize( ? html`
"ui.panel.lovelace.unused_entities.select_to_add" <br />${this.hass.localize(
)} "ui.panel.lovelace.unused_entities.select_to_add"
` )}
: ""} `
</div> : ""}
</ha-card> </div>
` </ha-card>
: ""} `
<ha-data-table : ""}
.columns=${this._columns(this.narrow!)} <ha-data-table
.data=${this._unusedEntities.map((entity) => { .columns=${this._columns(this.narrow!)}
const stateObj = this.hass!.states[entity]; .data=${this._unusedEntities.map((entity) => {
return { const stateObj = this.hass!.states[entity];
icon: "", return {
entity_id: entity, icon: "",
stateObj, entity_id: entity,
name: computeStateName(stateObj), stateObj,
domain: computeDomain(entity), name: computeStateName(stateObj),
last_changed: stateObj!.last_changed, domain: computeDomain(entity),
}; last_changed: stateObj!.last_changed,
})} };
.id=${"entity_id"} })}
selectable .id=${"entity_id"}
@selection-changed=${this._handleSelectionChanged} selectable
.dir=${computeRTLDirection(this.hass)} @selection-changed=${this._handleSelectionChanged}
.searchLabel=${this.hass.localize( .dir=${computeRTLDirection(this.hass)}
"ui.panel.lovelace.unused_entities.search" .searchLabel=${this.hass.localize(
)} "ui.panel.lovelace.unused_entities.search"
.noDataText=${this.hass.localize( )}
"ui.panel.lovelace.unused_entities.no_data" .noDataText=${this.hass.localize(
)} "ui.panel.lovelace.unused_entities.no_data"
></ha-data-table> )}
></ha-data-table>
${this._selectedEntities.length </div>
? html` <div
<mwc-fab class="fab ${classMap({
class="${classMap({ rtl: computeRTL(this.hass),
rtl: computeRTL(this.hass), selected: this._selectedEntities.length,
})}" })}"
.label=${this.hass.localize( >
"ui.panel.lovelace.editor.edit_card.add" <mwc-fab
)} .label=${this.hass.localize("ui.panel.lovelace.editor.edit_card.add")}
@click=${this._addToLovelaceView} @click=${this._addToLovelaceView}
> >
<ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon> <ha-svg-icon slot="icon" path=${mdiPlus}></ha-svg-icon>
</mwc-fab> </mwc-fab>
` </div>
: ""}
`; `;
} }
@ -240,8 +239,11 @@ export class HuiUnusedEntities extends LitElement {
return css` return css`
:host { :host {
background: var(--lovelace-background); background: var(--lovelace-background);
}
.container {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
height: 100%;
} }
ha-card { ha-card {
--ha-card-box-shadow: none; --ha-card-box-shadow: none;
@ -252,15 +254,30 @@ export class HuiUnusedEntities extends LitElement {
flex-grow: 1; flex-grow: 1;
margin-top: -20px; margin-top: -20px;
} }
mwc-fab { .fab {
overflow: hidden;
position: absolute; position: absolute;
right: 16px; right: 0;
bottom: 16px; bottom: 0;
padding: 16px;
padding-right: calc(16px + env(safe-area-inset-right));
padding-bottom: calc(16px + env(safe-area-inset-bottom));
z-index: 1; z-index: 1;
} }
mwc-fab.rtl { .fab.rtl {
left: 16px; right: initial;
right: auto; left: 0;
bottom: 0;
padding-right: 16px;
padding-left: calc(16px + env(safe-area-inset-left));
}
mwc-fab {
position: relative;
bottom: calc(-80px - env(safe-area-inset-bottom));
transition: bottom 0.3s;
}
.fab.selected mwc-fab {
bottom: 0;
} }
`; `;
} }

View File

@ -1,5 +1,5 @@
import "@material/mwc-button"; import "@material/mwc-button";
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import "../../components/ha-icon-button"; import "../../components/ha-icon-button";
@ -51,8 +51,8 @@ class LovelaceFullConfigEditor extends LitElement {
public render(): TemplateResult | void { public render(): TemplateResult | void {
return html` return html`
<app-header-layout> <ha-app-layout>
<app-header> <app-header slot="header">
<app-toolbar> <app-toolbar>
<ha-icon-button <ha-icon-button
icon="hass:close" icon="hass:close"
@ -98,7 +98,7 @@ class LovelaceFullConfigEditor extends LitElement {
> >
</ha-code-editor> </ha-code-editor>
</div> </div>
</app-header-layout> </ha-app-layout>
`; `;
} }
@ -114,7 +114,7 @@ class LovelaceFullConfigEditor extends LitElement {
--code-mirror-height: 100%; --code-mirror-height: 100%;
} }
app-header-layout { ha-app-layout {
height: 100vh; height: 100vh;
} }

View File

@ -68,7 +68,7 @@ class HUIRoot extends LitElement {
@property() public columns?: number; @property() public columns?: number;
@property() public narrow?: boolean; @property({ type: Boolean }) public narrow = false;
@property() public route?: { path: string; prefix: string }; @property() public route?: { path: string; prefix: string };
@ -694,7 +694,8 @@ class HUIRoot extends LitElement {
min-height: 100%; min-height: 100%;
} }
paper-tabs { paper-tabs {
margin-left: 12px; margin-left: max(env(safe-area-inset-left), 12px);
margin-right: env(safe-area-inset-right);
--paper-tabs-selection-bar-color: var(--text-primary-color, #fff); --paper-tabs-selection-bar-color: var(--text-primary-color, #fff);
text-transform: uppercase; text-transform: uppercase;
} }

View File

@ -350,7 +350,7 @@ export class HUIView extends LitElement {
:host { :host {
display: block; display: block;
box-sizing: border-box; box-sizing: border-box;
padding: 4px 4px 0; padding: 4px 4px env(safe-area-inset-bottom);
transform: translateZ(0); transform: translateZ(0);
position: relative; position: relative;
color: var(--primary-text-color); color: var(--primary-text-color);
@ -383,15 +383,15 @@ export class HUIView extends LitElement {
mwc-fab { mwc-fab {
position: sticky; position: sticky;
float: right; float: right;
bottom: 16px; right: calc(16px + env(safe-area-inset-right));
right: 16px; bottom: calc(16px + env(safe-area-inset-bottom));
z-index: 1; z-index: 1;
} }
mwc-fab.rtl { mwc-fab.rtl {
float: left; float: left;
right: auto; right: auto;
left: 16px; left: calc(16px + env(safe-area-inset-left));
} }
@media (max-width: 500px) { @media (max-width: 500px) {

View File

@ -1,5 +1,5 @@
import "@material/mwc-button"; import "@material/mwc-button";
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import "@polymer/paper-input/paper-textarea"; import "@polymer/paper-input/paper-textarea";
@ -76,7 +76,7 @@ class HaPanelMailbox extends EventsMixin(LocalizeMixin(PolymerElement)) {
} }
</style> </style>
<app-header-layout> <ha-app-layout>
<app-header slot="header" fixed> <app-header slot="header" fixed>
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -124,7 +124,7 @@ class HaPanelMailbox extends EventsMixin(LocalizeMixin(PolymerElement)) {
</template> </template>
</ha-card> </ha-card>
</div> </div>
</app-header-layout> </ha-app-layout>
`; `;
} }

View File

@ -12,6 +12,7 @@ import { defaultRadiusColor } from "../../data/zone";
import LocalizeMixin from "../../mixins/localize-mixin"; import LocalizeMixin from "../../mixins/localize-mixin";
import "./ha-entity-marker"; import "./ha-entity-marker";
import "../../styles/polymer-ha-style"; import "../../styles/polymer-ha-style";
import "../../layouts/ha-app-layout";
/* /*
* @appliesMixin LocalizeMixin * @appliesMixin LocalizeMixin
@ -21,7 +22,7 @@ class HaPanelMap extends LocalizeMixin(PolymerElement) {
return html` return html`
<style include="ha-style"> <style include="ha-style">
#map { #map {
height: calc(100% - 64px); height: calc(100vh - 64px);
width: 100%; width: 100%;
z-index: 0; z-index: 0;
} }
@ -31,18 +32,24 @@ class HaPanelMap extends LocalizeMixin(PolymerElement) {
} }
</style> </style>
<app-toolbar> <ha-app-layout>
<ha-menu-button hass="[[hass]]" narrow="[[narrow]]"></ha-menu-button> <app-header fixed slot="header">
<div main-title>[[localize('panel.map')]]</div> <app-toolbar>
<template is="dom-if" if="[[computeShowEditZone(hass)]]"> <ha-menu-button
<ha-icon-button hass="[[hass]]"
icon="hass:pencil" narrow="[[narrow]]"
on-click="openZonesEditor" ></ha-menu-button>
></ha-icon-button> <div main-title>[[localize('panel.map')]]</div>
</template> <template is="dom-if" if="[[computeShowEditZone(hass)]]">
</app-toolbar> <ha-icon-button
icon="hass:pencil"
<div id="map"></div> on-click="openZonesEditor"
></ha-icon-button>
</template>
</app-toolbar>
</app-header>
<div id="map"></div>
</ha-app-layout>
`; `;
} }

View File

@ -1,5 +1,5 @@
import "@material/mwc-button"; import "@material/mwc-button";
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import "@polymer/paper-item/paper-item"; import "@polymer/paper-item/paper-item";
@ -70,7 +70,7 @@ class HaPanelProfile extends LitElement {
protected render(): TemplateResult { protected render(): TemplateResult {
return html` return html`
<app-header-layout> <ha-app-layout>
<app-header slot="header" fixed> <app-header slot="header" fixed>
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -178,7 +178,7 @@ class HaPanelProfile extends LitElement {
@hass-refresh-tokens=${this._refreshRefreshTokens} @hass-refresh-tokens=${this._refreshRefreshTokens}
></ha-long-lived-access-tokens-card> ></ha-long-lived-access-tokens-card>
</div> </div>
</app-header-layout> </ha-app-layout>
`; `;
} }
@ -211,6 +211,7 @@ class HaPanelProfile extends LitElement {
display: block; display: block;
max-width: 600px; max-width: 600px;
margin: 0 auto; margin: 0 auto;
padding-bottom: env(safe-area-inset-bottom);
} }
.content > * { .content > * {

View File

@ -1,4 +1,4 @@
import "@polymer/app-layout/app-header-layout/app-header-layout"; import "../../layouts/ha-app-layout";
import "@polymer/app-layout/app-header/app-header"; import "@polymer/app-layout/app-header/app-header";
import "@polymer/app-layout/app-toolbar/app-toolbar"; import "@polymer/app-layout/app-toolbar/app-toolbar";
import "@polymer/paper-checkbox/paper-checkbox"; import "@polymer/paper-checkbox/paper-checkbox";
@ -68,7 +68,7 @@ class HaPanelShoppingList extends LocalizeMixin(PolymerElement) {
} }
</style> </style>
<app-header-layout> <ha-app-layout>
<app-header slot="header" fixed> <app-header slot="header" fixed>
<app-toolbar> <app-toolbar>
<ha-menu-button <ha-menu-button
@ -138,7 +138,7 @@ class HaPanelShoppingList extends LocalizeMixin(PolymerElement) {
[[localize('ui.panel.shopping-list.microphone_tip')]] [[localize('ui.panel.shopping-list.microphone_tip')]]
</div> </div>
</div> </div>
</app-header-layout> </ha-app-layout>
`; `;
} }

View File

@ -202,9 +202,10 @@ export const haStyleDialog = css`
.paper-dialog-buttons { .paper-dialog-buttons {
align-items: flex-end; align-items: flex-end;
padding: 8px; padding: 8px;
padding-bottom: max(env(safe-area-inset-bottom), 8px);
} }
@media all and (min-width: 450px) { @media all and (min-width: 450px) and (min-height: 500px) {
ha-paper-dialog { ha-paper-dialog {
min-width: 400px; min-width: 400px;
} }
@ -214,13 +215,21 @@ export const haStyleDialog = css`
paper-dialog, paper-dialog,
ha-paper-dialog { ha-paper-dialog {
margin: 0; margin: 0;
width: 100% !important; width: calc(
100% - env(safe-area-inset-right) - env(safe-area-inset-left)
) !important;
min-width: calc(
100% - env(safe-area-inset-right) - env(safe-area-inset-left)
) !important;
max-width: calc(
100% - env(safe-area-inset-right) - env(safe-area-inset-left)
) !important;
max-height: calc(100% - 64px); max-height: calc(100% - 64px);
position: fixed !important; position: fixed !important;
bottom: 0px; bottom: 0px;
left: 0px; left: env(safe-area-inset-left);
right: 0px; right: env(safe-area-inset-right);
overflow: scroll; overflow: scroll;
border-bottom-left-radius: 0px; border-bottom-left-radius: 0px;
border-bottom-right-radius: 0px; border-bottom-right-radius: 0px;
@ -244,8 +253,12 @@ export const haStyleDialog = css`
/* make dialog fullscreen on small screens */ /* make dialog fullscreen on small screens */
@media all and (max-width: 450px), all and (max-height: 500px) { @media all and (max-width: 450px), all and (max-height: 500px) {
ha-dialog { ha-dialog {
--mdc-dialog-min-width: 100vw; --mdc-dialog-min-width: calc(
--mdc-dialog-max-width: 100vw; 100vw - env(safe-area-inset-right) - env(safe-area-inset-left)
);
--mdc-dialog-max-width: calc(
100vw - env(safe-area-inset-right) - env(safe-area-inset-left)
);
--mdc-dialog-min-height: 100%; --mdc-dialog-min-height: 100%;
--mdc-dialog-max-height: 100%; --mdc-dialog-max-height: 100%;
--mdc-shape-medium: 0px; --mdc-shape-medium: 0px;