mirror of
https://github.com/home-assistant/frontend.git
synced 2026-02-15 07:25:54 +00:00
Migrate from ha-md-menu to ha-dropdown (#29548)
This commit is contained in:
@@ -9,7 +9,6 @@ import type { HomeAssistant } from "../types";
|
||||
import "./ha-dropdown";
|
||||
import "./ha-dropdown-item";
|
||||
import "./ha-icon-button";
|
||||
import "./ha-md-divider";
|
||||
import "./ha-svg-icon";
|
||||
import "./ha-tooltip";
|
||||
|
||||
|
||||
@@ -1,22 +0,0 @@
|
||||
import { Divider } from "@material/web/divider/internal/divider";
|
||||
import { styles } from "@material/web/divider/internal/divider-styles";
|
||||
import { css } from "lit";
|
||||
import { customElement } from "lit/decorators";
|
||||
|
||||
@customElement("ha-md-divider")
|
||||
export class HaMdDivider extends Divider {
|
||||
static override styles = [
|
||||
styles,
|
||||
css`
|
||||
:host {
|
||||
--md-divider-color: var(--divider-color);
|
||||
}
|
||||
`,
|
||||
];
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
"ha-md-divider": HaMdDivider;
|
||||
}
|
||||
}
|
||||
@@ -1,52 +0,0 @@
|
||||
import { MenuItemEl } from "@material/web/menu/internal/menuitem/menu-item";
|
||||
import { styles } from "@material/web/menu/internal/menuitem/menu-item-styles";
|
||||
import { css } from "lit";
|
||||
import { customElement, property } from "lit/decorators";
|
||||
|
||||
@customElement("ha-md-menu-item")
|
||||
export class HaMdMenuItem extends MenuItemEl {
|
||||
@property({ attribute: false }) clickAction?: (item?: HTMLElement) => void;
|
||||
|
||||
static override styles = [
|
||||
styles,
|
||||
css`
|
||||
:host {
|
||||
--ha-icon-display: block;
|
||||
--md-sys-color-primary: var(--primary-text-color);
|
||||
--md-sys-color-on-primary: var(--primary-text-color);
|
||||
--md-sys-color-secondary: var(--secondary-text-color);
|
||||
--md-sys-color-surface: var(--card-background-color);
|
||||
--md-sys-color-on-surface: var(--primary-text-color);
|
||||
--md-sys-color-on-surface-variant: var(--secondary-text-color);
|
||||
--md-sys-color-secondary-container: rgba(
|
||||
var(--rgb-primary-color),
|
||||
0.15
|
||||
);
|
||||
--md-sys-color-on-secondary-container: var(--text-primary-color);
|
||||
--mdc-icon-size: 16px;
|
||||
|
||||
--md-sys-color-on-primary-container: var(--primary-text-color);
|
||||
--md-sys-color-on-secondary-container: var(--primary-text-color);
|
||||
--md-menu-item-label-text-font: Roboto, sans-serif;
|
||||
}
|
||||
:host(.warning) {
|
||||
--md-menu-item-label-text-color: var(--error-color);
|
||||
--md-menu-item-leading-icon-color: var(--error-color);
|
||||
}
|
||||
::slotted([slot="headline"]) {
|
||||
text-wrap: nowrap;
|
||||
}
|
||||
:host([disabled]) {
|
||||
opacity: 1;
|
||||
--md-menu-item-label-text-color: var(--disabled-text-color);
|
||||
--md-menu-item-leading-icon-color: var(--disabled-text-color);
|
||||
}
|
||||
`,
|
||||
];
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
"ha-md-menu-item": HaMdMenuItem;
|
||||
}
|
||||
}
|
||||
@@ -1,47 +0,0 @@
|
||||
import { Menu } from "@material/web/menu/internal/menu";
|
||||
import { styles } from "@material/web/menu/internal/menu-styles";
|
||||
import type { CloseMenuEvent } from "@material/web/menu/menu";
|
||||
import {
|
||||
CloseReason,
|
||||
KeydownCloseKey,
|
||||
} from "@material/web/menu/internal/controllers/shared";
|
||||
import { css } from "lit";
|
||||
import { customElement } from "lit/decorators";
|
||||
import type { HaMdMenuItem } from "./ha-md-menu-item";
|
||||
|
||||
@customElement("ha-md-menu")
|
||||
export class HaMdMenu extends Menu {
|
||||
connectedCallback(): void {
|
||||
super.connectedCallback();
|
||||
this.addEventListener("close-menu", this._handleCloseMenu);
|
||||
}
|
||||
|
||||
private _handleCloseMenu(ev: CloseMenuEvent) {
|
||||
if (
|
||||
ev.detail.reason.kind === CloseReason.KEYDOWN &&
|
||||
ev.detail.reason.key === KeydownCloseKey.ESCAPE
|
||||
) {
|
||||
return;
|
||||
}
|
||||
(ev.detail.initiator as HaMdMenuItem).clickAction?.(ev.detail.initiator);
|
||||
}
|
||||
|
||||
static override styles = [
|
||||
styles,
|
||||
css`
|
||||
:host {
|
||||
--md-sys-color-surface-container: var(--card-background-color);
|
||||
}
|
||||
`,
|
||||
];
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
"ha-md-menu": HaMdMenu;
|
||||
}
|
||||
|
||||
interface HTMLElementEventMap {
|
||||
"close-menu": CloseMenuEvent;
|
||||
}
|
||||
}
|
||||
@@ -1,3 +1,4 @@
|
||||
import "@home-assistant/webawesome/dist/components/divider/divider";
|
||||
import { consume } from "@lit/context";
|
||||
import {
|
||||
mdiAppleKeyboardCommand,
|
||||
@@ -42,7 +43,6 @@ import "../../../components/ha-icon";
|
||||
import "../../../components/ha-icon-button";
|
||||
import "../../../components/ha-icon-button-prev";
|
||||
import "../../../components/ha-icon-next";
|
||||
import "../../../components/ha-md-divider";
|
||||
import "../../../components/ha-md-list";
|
||||
import "../../../components/ha-md-list-item";
|
||||
import type { PickerComboBoxItem } from "../../../components/ha-picker-combo-box";
|
||||
@@ -657,10 +657,7 @@ class DialogAddAutomationElement
|
||||
.path=${mdiPlus}
|
||||
></ha-svg-icon>
|
||||
</ha-md-list-item>
|
||||
<ha-md-divider
|
||||
role="separator"
|
||||
tabindex="-1"
|
||||
></ha-md-divider>`
|
||||
<wa-divider></wa-divider>`
|
||||
: nothing}
|
||||
${collections.map(
|
||||
(collection, index) => html`
|
||||
@@ -2177,8 +2174,8 @@ class DialogAddAutomationElement
|
||||
width: var(--ha-space-6);
|
||||
}
|
||||
|
||||
ha-md-list-item.paste {
|
||||
border-bottom: 1px solid var(--ha-color-border-neutral-quiet);
|
||||
wa-divider {
|
||||
--spacing: 0;
|
||||
}
|
||||
|
||||
ha-svg-icon.plus {
|
||||
|
||||
@@ -740,7 +740,7 @@ class HaAutomationPicker extends SubscribeMixin(LitElement) {
|
||||
<ha-svg-icon .path=${mdiTransitConnection} slot="icon"></ha-svg-icon>
|
||||
${this.hass.localize("ui.panel.config.automation.editor.show_trace")}
|
||||
</ha-dropdown-item>
|
||||
<ha-md-divider role="separator" tabindex="-1"></ha-md-divider>
|
||||
<wa-divider></wa-divider>
|
||||
<ha-dropdown-item value="duplicate">
|
||||
<ha-svg-icon .path=${mdiContentDuplicate} slot="icon"></ha-svg-icon>
|
||||
${this.hass.localize("ui.panel.config.automation.picker.duplicate")}
|
||||
|
||||
@@ -40,9 +40,6 @@ export const rowStyles = css`
|
||||
.warning ul {
|
||||
margin: 4px 0;
|
||||
}
|
||||
ha-md-menu-item > ha-svg-icon {
|
||||
--mdc-icon-size: 24px;
|
||||
}
|
||||
ha-tooltip {
|
||||
cursor: default;
|
||||
}
|
||||
@@ -272,7 +269,4 @@ export const overflowStyles = css`
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
ha-md-menu-item {
|
||||
--mdc-icon-size: 24px;
|
||||
}
|
||||
`;
|
||||
|
||||
@@ -26,15 +26,16 @@ import type {
|
||||
} from "../../../components/data-table/ha-data-table";
|
||||
import "../../../components/ha-button";
|
||||
import "../../../components/ha-dropdown";
|
||||
import type {
|
||||
HaDropdown,
|
||||
HaDropdownSelectEvent,
|
||||
} from "../../../components/ha-dropdown";
|
||||
import "../../../components/ha-dropdown-item";
|
||||
import "../../../components/ha-fab";
|
||||
import "../../../components/ha-filter-states";
|
||||
import "../../../components/ha-icon";
|
||||
import "../../../components/ha-icon-next";
|
||||
import "../../../components/ha-icon-overflow-menu";
|
||||
import "../../../components/ha-md-menu";
|
||||
import type { HaMdMenu } from "../../../components/ha-md-menu";
|
||||
import "../../../components/ha-md-menu-item";
|
||||
import "../../../components/ha-spinner";
|
||||
import "../../../components/ha-svg-icon";
|
||||
import type {
|
||||
@@ -73,7 +74,6 @@ import { showGenerateBackupDialog } from "./dialogs/show-dialog-generate-backup"
|
||||
import { showNewBackupDialog } from "./dialogs/show-dialog-new-backup";
|
||||
import { showUploadBackupDialog } from "./dialogs/show-dialog-upload-backup";
|
||||
import { downloadBackup } from "./helper/download_backup";
|
||||
import type { HaDropdownSelectEvent } from "../../../components/ha-dropdown";
|
||||
|
||||
interface BackupRow extends DataTableRowData, BackupContent {
|
||||
formatted_type: string;
|
||||
@@ -123,7 +123,11 @@ class HaConfigBackupBackups extends SubscribeMixin(LitElement) {
|
||||
@query("hass-tabs-subpage-data-table", true)
|
||||
private _dataTable!: HaTabsSubpageDataTable;
|
||||
|
||||
@query("#overflow-menu") private _overflowMenu?: HaMdMenu;
|
||||
@query("#overflow-menu") private _overflowMenu?: HaDropdown;
|
||||
|
||||
private _openingOverflow = false;
|
||||
|
||||
private _overflowBackup?: BackupRow;
|
||||
|
||||
public connectedCallback() {
|
||||
super.connectedCallback();
|
||||
@@ -287,12 +291,27 @@ class HaConfigBackupBackups extends SubscribeMixin(LitElement) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (this._overflowMenu.open) {
|
||||
this._overflowMenu.close();
|
||||
if (this._overflowMenu.anchorElement === ev.target) {
|
||||
this._overflowMenu.anchorElement = undefined;
|
||||
return;
|
||||
}
|
||||
this._openingOverflow = true;
|
||||
this._overflowMenu.anchorElement = ev.target;
|
||||
this._overflowMenu.show();
|
||||
this._overflowBackup = ev.target.backup;
|
||||
this._overflowMenu.open = true;
|
||||
};
|
||||
|
||||
private _overflowMenuOpened = () => {
|
||||
this._openingOverflow = false;
|
||||
};
|
||||
|
||||
private _overflowMenuClosed = () => {
|
||||
// changing the anchorElement triggers a close event, ignore it
|
||||
if (this._openingOverflow || !this._overflowMenu) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._overflowMenu.anchorElement = undefined;
|
||||
};
|
||||
|
||||
private _handleGroupingChanged(ev: CustomEvent) {
|
||||
@@ -477,16 +496,21 @@ class HaConfigBackupBackups extends SubscribeMixin(LitElement) {
|
||||
`
|
||||
: nothing}
|
||||
</hass-tabs-subpage-data-table>
|
||||
<ha-md-menu id="overflow-menu" positioning="fixed">
|
||||
<ha-md-menu-item .clickAction=${this._downloadBackup}>
|
||||
<ha-svg-icon slot="start" .path=${mdiDownload}></ha-svg-icon>
|
||||
<ha-dropdown
|
||||
id="overflow-menu"
|
||||
@wa-select=${this._handleOverflowAction}
|
||||
@wa-after-show=${this._overflowMenuOpened}
|
||||
@wa-after-hide=${this._overflowMenuClosed}
|
||||
>
|
||||
<ha-dropdown-item value="download">
|
||||
<ha-svg-icon slot="icon" .path=${mdiDownload}></ha-svg-icon>
|
||||
${this.hass.localize("ui.common.download")}
|
||||
</ha-md-menu-item>
|
||||
<ha-md-menu-item class="warning" .clickAction=${this._deleteBackup}>
|
||||
<ha-svg-icon slot="start" .path=${mdiDelete}></ha-svg-icon>
|
||||
</ha-dropdown-item>
|
||||
<ha-dropdown-item variant="danger" value="delete">
|
||||
<ha-svg-icon slot="icon" .path=${mdiDelete}></ha-svg-icon>
|
||||
${this.hass.localize("ui.common.delete")}
|
||||
</ha-md-menu-item>
|
||||
</ha-md-menu>
|
||||
</ha-dropdown-item>
|
||||
</ha-dropdown>
|
||||
`;
|
||||
}
|
||||
|
||||
@@ -556,16 +580,29 @@ class HaConfigBackupBackups extends SubscribeMixin(LitElement) {
|
||||
navigate(`/config/backup/details/${id}`);
|
||||
}
|
||||
|
||||
private _downloadBackup = async (ev): Promise<void> => {
|
||||
const backup = ev.parentElement.anchorElement.backup;
|
||||
private _handleOverflowAction = (ev: HaDropdownSelectEvent) => {
|
||||
const action = ev.detail.item.value;
|
||||
|
||||
if (action === "download") {
|
||||
this._downloadBackup();
|
||||
return;
|
||||
}
|
||||
|
||||
if (action === "delete") {
|
||||
this._deleteBackup();
|
||||
}
|
||||
};
|
||||
|
||||
private _downloadBackup = async (): Promise<void> => {
|
||||
const backup = this._overflowBackup;
|
||||
if (!backup) {
|
||||
return;
|
||||
}
|
||||
downloadBackup(this.hass, this, backup, this.config);
|
||||
};
|
||||
|
||||
private _deleteBackup = async (ev): Promise<void> => {
|
||||
const backup = ev.parentElement.anchorElement.backup;
|
||||
private _deleteBackup = async (): Promise<void> => {
|
||||
const backup = this._overflowBackup;
|
||||
if (!backup) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -10,10 +10,10 @@ import {
|
||||
mdiUnfoldMoreHorizontal,
|
||||
} from "@mdi/js";
|
||||
|
||||
import "@home-assistant/webawesome/dist/components/divider/divider";
|
||||
import type { HassEntity } from "home-assistant-js-websocket";
|
||||
import { css, type CSSResultGroup, html, LitElement, nothing } from "lit";
|
||||
import { customElement, property, query, state } from "lit/decorators";
|
||||
import { classMap } from "lit/directives/class-map";
|
||||
import memoizeOne from "memoize-one";
|
||||
import type { HASSDomEvent } from "../../../../common/dom/fire_event";
|
||||
import { fireEvent } from "../../../../common/dom/fire_event";
|
||||
@@ -28,15 +28,11 @@ import type {
|
||||
SortingDirection,
|
||||
} from "../../../../components/data-table/ha-data-table";
|
||||
import { showDataTableSettingsDialog } from "../../../../components/data-table/show-dialog-data-table-settings";
|
||||
import "@home-assistant/webawesome/dist/components/divider/divider";
|
||||
import "../../../../components/ha-button";
|
||||
import "../../../../components/ha-dialog";
|
||||
import "../../../../components/ha-dropdown";
|
||||
import type { HaDropdownSelectEvent } from "../../../../components/ha-dropdown";
|
||||
import "../../../../components/ha-dropdown-item";
|
||||
import type { HaMdMenu } from "../../../../components/ha-md-menu";
|
||||
import "../../../../components/ha-md-menu-item";
|
||||
import "../../../../components/ha-md-menu";
|
||||
import "../../../../components/ha-md-divider";
|
||||
import "../../../../components/search-input-outlined";
|
||||
import type {
|
||||
StatisticsMetaData,
|
||||
@@ -112,20 +108,8 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
|
||||
@query("ha-data-table", true) private _dataTable!: HaDataTable;
|
||||
|
||||
@query("#group-by-menu") private _groupByMenu!: HaMdMenu;
|
||||
|
||||
@query("#sort-by-menu") private _sortByMenu!: HaMdMenu;
|
||||
|
||||
@query("search-input-outlined") private _searchInput!: HTMLElement;
|
||||
|
||||
private _toggleGroupBy() {
|
||||
this._groupByMenu.open = !this._groupByMenu.open;
|
||||
}
|
||||
|
||||
private _toggleSortBy() {
|
||||
this._sortByMenu.open = !this._sortByMenu.open;
|
||||
}
|
||||
|
||||
protected firstUpdated() {
|
||||
this._validateStatistics();
|
||||
}
|
||||
@@ -278,37 +262,106 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
|
||||
const sortByMenu = Object.values(columns).find((col) => col.sortable)
|
||||
? html`
|
||||
<ha-assist-chip
|
||||
.label=${localize("ui.components.subpage-data-table.sort_by", {
|
||||
sortColumn: this._sortColumn
|
||||
? ` ${columns[this._sortColumn]?.title || columns[this._sortColumn]?.label}` ||
|
||||
""
|
||||
: "",
|
||||
})}
|
||||
id="sort-by-anchor"
|
||||
@click=${this._toggleSortBy}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="trailing-icon"
|
||||
.path=${mdiMenuDown}
|
||||
></ha-svg-icon>
|
||||
</ha-assist-chip>
|
||||
<ha-dropdown @wa-select=${this._handleSortBy}>
|
||||
<ha-assist-chip
|
||||
slot="trigger"
|
||||
.label=${localize("ui.components.subpage-data-table.sort_by", {
|
||||
sortColumn: this._sortColumn
|
||||
? ` ${columns[this._sortColumn]?.title || columns[this._sortColumn]?.label}` ||
|
||||
""
|
||||
: "",
|
||||
})}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="trailing-icon"
|
||||
.path=${mdiMenuDown}
|
||||
></ha-svg-icon>
|
||||
</ha-assist-chip>
|
||||
${Object.entries(columns).map(([id, column]) =>
|
||||
column.sortable
|
||||
? html`
|
||||
<ha-dropdown-item
|
||||
.value=${id}
|
||||
class=${id === this._sortColumn ? "selected" : ""}
|
||||
>
|
||||
${this._sortColumn === id
|
||||
? html`
|
||||
<ha-svg-icon
|
||||
slot="details"
|
||||
.path=${this._sortDirection === "desc"
|
||||
? mdiArrowDown
|
||||
: mdiArrowUp}
|
||||
></ha-svg-icon>
|
||||
`
|
||||
: nothing}
|
||||
${column.title || column.label}
|
||||
</ha-dropdown-item>
|
||||
`
|
||||
: nothing
|
||||
)}
|
||||
</ha-dropdown>
|
||||
`
|
||||
: nothing;
|
||||
|
||||
const groupByMenu = Object.values(columns).find((col) => col.groupable)
|
||||
? html`
|
||||
<ha-assist-chip
|
||||
.label=${localize("ui.components.subpage-data-table.group_by", {
|
||||
groupColumn: this._groupColumn
|
||||
? ` ${columns[this._groupColumn].title || columns[this._groupColumn].label}`
|
||||
: "",
|
||||
})}
|
||||
id="group-by-anchor"
|
||||
@click=${this._toggleGroupBy}
|
||||
>
|
||||
<ha-svg-icon slot="trailing-icon" .path=${mdiMenuDown}></ha-svg-icon
|
||||
></ha-assist-chip>
|
||||
<ha-dropdown @wa-select=${this._handleOverflowGroupBy}>
|
||||
<ha-assist-chip
|
||||
slot="trigger"
|
||||
.label=${localize("ui.components.subpage-data-table.group_by", {
|
||||
groupColumn: this._groupColumn
|
||||
? ` ${columns[this._groupColumn].title || columns[this._groupColumn].label}`
|
||||
: "",
|
||||
})}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="trailing-icon"
|
||||
.path=${mdiMenuDown}
|
||||
></ha-svg-icon
|
||||
></ha-assist-chip>
|
||||
${Object.entries(columns).map(([id, column]) =>
|
||||
column.groupable
|
||||
? html`
|
||||
<ha-dropdown-item
|
||||
.value=${id}
|
||||
class=${id === this._groupColumn ? "selected" : ""}
|
||||
>
|
||||
${column.title || column.label}
|
||||
</ha-dropdown-item>
|
||||
`
|
||||
: nothing
|
||||
)}
|
||||
<ha-dropdown-item
|
||||
value="none"
|
||||
class=${this._groupColumn === undefined ? "selected" : ""}
|
||||
>
|
||||
${localize("ui.components.subpage-data-table.dont_group_by")}
|
||||
</ha-dropdown-item>
|
||||
<wa-divider></wa-divider>
|
||||
<ha-dropdown-item
|
||||
value="collapse_all"
|
||||
@click=${this._collapseAllGroups}
|
||||
.disabled=${this._groupColumn === undefined}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="icon"
|
||||
.path=${mdiUnfoldLessHorizontal}
|
||||
></ha-svg-icon>
|
||||
${localize(
|
||||
"ui.components.subpage-data-table.collapse_all_groups"
|
||||
)}
|
||||
</ha-dropdown-item>
|
||||
<ha-dropdown-item
|
||||
@click=${this._expandAllGroups}
|
||||
.disabled=${this._groupColumn === undefined}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="icon"
|
||||
.path=${mdiUnfoldMoreHorizontal}
|
||||
></ha-svg-icon>
|
||||
${localize("ui.components.subpage-data-table.expand_all_groups")}
|
||||
</ha-dropdown-item>
|
||||
</ha-dropdown>
|
||||
`
|
||||
: nothing;
|
||||
|
||||
@@ -417,6 +470,7 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
.hiddenColumns=${this.hiddenColumns}
|
||||
@row-click=${this._rowClicked}
|
||||
@selection-changed=${this._handleSelectionChanged}
|
||||
@sorting-changed=${this._handleTableSortingChanged}
|
||||
>
|
||||
${!this.narrow
|
||||
? html`
|
||||
@@ -434,82 +488,6 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
</div>`}
|
||||
</ha-data-table>
|
||||
</div>
|
||||
<ha-md-menu
|
||||
anchor="group-by-anchor"
|
||||
id="group-by-menu"
|
||||
positioning="fixed"
|
||||
>
|
||||
${Object.entries(columns).map(([id, column]) =>
|
||||
column.groupable
|
||||
? html`
|
||||
<ha-md-menu-item
|
||||
.value=${id}
|
||||
@click=${this._handleGroupBy}
|
||||
.selected=${id === this._groupColumn}
|
||||
class=${classMap({ selected: id === this._groupColumn })}
|
||||
>
|
||||
${column.title || column.label}
|
||||
</ha-md-menu-item>
|
||||
`
|
||||
: nothing
|
||||
)}
|
||||
<ha-md-menu-item
|
||||
.value=${undefined}
|
||||
@click=${this._handleGroupBy}
|
||||
.selected=${this._groupColumn === undefined}
|
||||
class=${classMap({ selected: this._groupColumn === undefined })}
|
||||
>
|
||||
${localize("ui.components.subpage-data-table.dont_group_by")}
|
||||
</ha-md-menu-item>
|
||||
<ha-md-divider role="separator" tabindex="-1"></ha-md-divider>
|
||||
<ha-md-menu-item
|
||||
@click=${this._collapseAllGroups}
|
||||
.disabled=${this._groupColumn === undefined}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="start"
|
||||
.path=${mdiUnfoldLessHorizontal}
|
||||
></ha-svg-icon>
|
||||
${localize("ui.components.subpage-data-table.collapse_all_groups")}
|
||||
</ha-md-menu-item>
|
||||
<ha-md-menu-item
|
||||
@click=${this._expandAllGroups}
|
||||
.disabled=${this._groupColumn === undefined}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="start"
|
||||
.path=${mdiUnfoldMoreHorizontal}
|
||||
></ha-svg-icon>
|
||||
${localize("ui.components.subpage-data-table.expand_all_groups")}
|
||||
</ha-md-menu-item>
|
||||
</ha-md-menu>
|
||||
<ha-md-menu anchor="sort-by-anchor" id="sort-by-menu" positioning="fixed">
|
||||
${Object.entries(columns).map(([id, column]) =>
|
||||
column.sortable
|
||||
? html`
|
||||
<ha-md-menu-item
|
||||
.value=${id}
|
||||
@click=${this._handleSortBy}
|
||||
keep-open
|
||||
.selected=${id === this._sortColumn}
|
||||
class=${classMap({ selected: id === this._sortColumn })}
|
||||
>
|
||||
${this._sortColumn === id
|
||||
? html`
|
||||
<ha-svg-icon
|
||||
slot="end"
|
||||
.path=${this._sortDirection === "desc"
|
||||
? mdiArrowDown
|
||||
: mdiArrowUp}
|
||||
></ha-svg-icon>
|
||||
`
|
||||
: nothing}
|
||||
${column.title || column.label}
|
||||
</ha-md-menu-item>
|
||||
`
|
||||
: nothing
|
||||
)}
|
||||
</ha-md-menu>
|
||||
`;
|
||||
}
|
||||
|
||||
@@ -526,8 +504,17 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
this._selected = ev.detail.value;
|
||||
}
|
||||
|
||||
private _handleSortBy(ev) {
|
||||
const columnId = ev.currentTarget.value;
|
||||
private _handleTableSortingChanged(
|
||||
ev: CustomEvent<{ column: string; direction: SortingDirection }>
|
||||
) {
|
||||
const { column, direction } = ev.detail;
|
||||
this._sortColumn = column;
|
||||
this._sortDirection = direction;
|
||||
}
|
||||
|
||||
private _handleSortBy(ev: HaDropdownSelectEvent) {
|
||||
ev.preventDefault(); // keep dropdown open
|
||||
const columnId = ev.detail.item.value;
|
||||
if (!this._sortDirection || this._sortColumn !== columnId) {
|
||||
this._sortDirection = "asc";
|
||||
} else if (this._sortDirection === "asc") {
|
||||
@@ -538,11 +525,29 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
this._sortColumn = columnId;
|
||||
}
|
||||
|
||||
private _handleGroupBy(ev) {
|
||||
this._setGroupColumn(ev.currentTarget.value);
|
||||
}
|
||||
private _handleOverflowGroupBy = (ev: HaDropdownSelectEvent) => {
|
||||
const action = ev.detail.item.value;
|
||||
|
||||
private _setGroupColumn(columnId: string) {
|
||||
if (!action) {
|
||||
return;
|
||||
}
|
||||
|
||||
switch (action) {
|
||||
case "collapse_all":
|
||||
this._collapseAllGroups();
|
||||
return;
|
||||
case "expand_all":
|
||||
this._expandAllGroups();
|
||||
return;
|
||||
case "none":
|
||||
this._setGroupColumn();
|
||||
return;
|
||||
default:
|
||||
this._setGroupColumn(action);
|
||||
}
|
||||
};
|
||||
|
||||
private _setGroupColumn(columnId?: string) {
|
||||
this._groupColumn = columnId;
|
||||
}
|
||||
|
||||
@@ -797,11 +802,19 @@ class HaPanelDevStatistics extends KeyboardShortcutMixin(LitElement) {
|
||||
--dialog-content-padding: 0;
|
||||
}
|
||||
|
||||
#sort-by-anchor,
|
||||
#group-by-anchor,
|
||||
ha-dropdown ha-assist-chip {
|
||||
--md-assist-chip-trailing-space: 8px;
|
||||
}
|
||||
|
||||
ha-dropdown-item.selected {
|
||||
font-weight: var(--ha-font-weight-medium);
|
||||
color: var(--primary-color);
|
||||
background-color: var(--ha-color-fill-primary-quiet-resting);
|
||||
--icon-primary-color: var(--primary-color);
|
||||
}
|
||||
ha-dropdown-item.selected:hover {
|
||||
background-color: var(--ha-color-fill-primary-quiet-hover);
|
||||
}
|
||||
`,
|
||||
];
|
||||
}
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import "@home-assistant/webawesome/dist/components/divider/divider";
|
||||
import {
|
||||
mdiDelete,
|
||||
mdiDevices,
|
||||
@@ -20,13 +21,16 @@ import type {
|
||||
RowClickedEvent,
|
||||
SortingChangedEvent,
|
||||
} from "../../../components/data-table/ha-data-table";
|
||||
import "../../../components/ha-dropdown";
|
||||
import type {
|
||||
HaDropdown,
|
||||
HaDropdownSelectEvent,
|
||||
} from "../../../components/ha-dropdown";
|
||||
import "../../../components/ha-dropdown-item";
|
||||
import "../../../components/ha-fab";
|
||||
import "../../../components/ha-icon";
|
||||
import "../../../components/ha-icon-button";
|
||||
import { renderLabelColorBadge } from "../../../components/ha-label-picker";
|
||||
import "../../../components/ha-md-menu";
|
||||
import type { HaMdMenu } from "../../../components/ha-md-menu";
|
||||
import "../../../components/ha-md-menu-item";
|
||||
import "../../../components/ha-svg-icon";
|
||||
import type {
|
||||
LabelRegistryEntry,
|
||||
@@ -44,12 +48,12 @@ import {
|
||||
} from "../../../dialogs/generic/show-dialog-box";
|
||||
import "../../../layouts/hass-tabs-subpage-data-table";
|
||||
import type { HomeAssistant, Route } from "../../../types";
|
||||
import { configSections } from "../ha-panel-config";
|
||||
import { showLabelDetailDialog } from "./show-dialog-label-detail";
|
||||
import {
|
||||
getCreatedAtTableColumn,
|
||||
getModifiedAtTableColumn,
|
||||
} from "../common/data-table-columns";
|
||||
import { configSections } from "../ha-panel-config";
|
||||
import { showLabelDetailDialog } from "./show-dialog-label-detail";
|
||||
|
||||
@customElement("ha-config-labels")
|
||||
export class HaConfigLabels extends LitElement {
|
||||
@@ -93,10 +97,12 @@ export class HaConfigLabels extends LitElement {
|
||||
})
|
||||
private _activeHiddenColumns?: string[];
|
||||
|
||||
@query("#overflow-menu") private _overflowMenu?: HaMdMenu;
|
||||
@query("#overflow-menu") private _overflowMenu?: HaDropdown;
|
||||
|
||||
private _overflowLabel!: LabelRegistryEntry;
|
||||
|
||||
private _openingOverflow = false;
|
||||
|
||||
private _columns = memoizeOne((localize: LocalizeFunc, narrow: boolean) => {
|
||||
const columns: DataTableColumnContainer<LabelRegistryEntry> = {
|
||||
icon: {
|
||||
@@ -172,13 +178,27 @@ export class HaConfigLabels extends LitElement {
|
||||
return;
|
||||
}
|
||||
|
||||
if (this._overflowMenu.open) {
|
||||
this._overflowMenu.close();
|
||||
if (this._overflowMenu.anchorElement === ev.target) {
|
||||
this._overflowMenu.anchorElement = undefined;
|
||||
return;
|
||||
}
|
||||
this._overflowLabel = ev.target.selected;
|
||||
this._openingOverflow = true;
|
||||
this._overflowMenu.anchorElement = ev.target;
|
||||
this._overflowMenu.show();
|
||||
this._overflowLabel = ev.target.selected;
|
||||
this._overflowMenu.open = true;
|
||||
};
|
||||
|
||||
private _overflowMenuOpened = () => {
|
||||
this._openingOverflow = false;
|
||||
};
|
||||
|
||||
private _overflowMenuClosed = () => {
|
||||
// changing the anchorElement triggers a close event, ignore it
|
||||
if (this._openingOverflow || !this._overflowMenu) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._overflowMenu.anchorElement = undefined;
|
||||
};
|
||||
|
||||
protected firstUpdated(changedProperties: PropertyValues) {
|
||||
@@ -224,32 +244,30 @@ export class HaConfigLabels extends LitElement {
|
||||
<ha-svg-icon slot="icon" .path=${mdiPlus}></ha-svg-icon>
|
||||
</ha-fab>
|
||||
</hass-tabs-subpage-data-table>
|
||||
<ha-md-menu id="overflow-menu" positioning="fixed">
|
||||
<ha-md-menu-item .clickAction=${this._navigateEntities}>
|
||||
<ha-svg-icon slot="start" .path=${mdiShape}></ha-svg-icon>
|
||||
<ha-dropdown
|
||||
id="overflow-menu"
|
||||
@wa-select=${this._handleOverflowAction}
|
||||
@wa-after-show=${this._overflowMenuOpened}
|
||||
@wa-after-hide=${this._overflowMenuClosed}
|
||||
>
|
||||
<ha-dropdown-item value="navigate-entities">
|
||||
<ha-svg-icon slot="icon" .path=${mdiShape}></ha-svg-icon>
|
||||
${this.hass.localize("ui.panel.config.entities.caption")}
|
||||
</ha-md-menu-item>
|
||||
<ha-md-menu-item .clickAction=${this._navigateDevices}>
|
||||
<ha-svg-icon slot="start" .path=${mdiDevices}></ha-svg-icon>
|
||||
</ha-dropdown-item>
|
||||
<ha-dropdown-item value="navigate-devices">
|
||||
<ha-svg-icon slot="icon" .path=${mdiDevices}></ha-svg-icon>
|
||||
${this.hass.localize("ui.panel.config.devices.caption")}
|
||||
</ha-md-menu-item>
|
||||
<ha-md-menu-item .clickAction=${this._navigateAutomations}>
|
||||
<ha-svg-icon slot="start" .path=${mdiRobot}></ha-svg-icon>
|
||||
</ha-dropdown-item>
|
||||
<ha-dropdown-item value="navigate-automations">
|
||||
<ha-svg-icon slot="icon" .path=${mdiRobot}></ha-svg-icon>
|
||||
${this.hass.localize("ui.panel.config.automation.caption")}
|
||||
</ha-md-menu-item>
|
||||
<ha-md-divider role="separator" tabindex="-1"></ha-md-divider>
|
||||
<ha-md-menu-item
|
||||
class="warning"
|
||||
.clickAction=${this._handleRemoveLabelClick}
|
||||
>
|
||||
<ha-svg-icon
|
||||
slot="start"
|
||||
class="warning"
|
||||
.path=${mdiDelete}
|
||||
></ha-svg-icon>
|
||||
</ha-dropdown-item>
|
||||
<wa-divider></wa-divider>
|
||||
<ha-dropdown-item variant="danger" value="remove">
|
||||
<ha-svg-icon slot="icon" .path=${mdiDelete}></ha-svg-icon>
|
||||
${this.hass.localize("ui.common.delete")}
|
||||
</ha-md-menu-item>
|
||||
</ha-md-menu>
|
||||
</ha-dropdown-item>
|
||||
</ha-dropdown>
|
||||
`;
|
||||
}
|
||||
|
||||
@@ -341,6 +359,28 @@ export class HaConfigLabels extends LitElement {
|
||||
}
|
||||
}
|
||||
|
||||
private _handleOverflowAction = (ev: HaDropdownSelectEvent) => {
|
||||
const action = ev.detail.item.value;
|
||||
|
||||
if (!action) {
|
||||
return;
|
||||
}
|
||||
switch (action) {
|
||||
case "navigate-entities":
|
||||
this._navigateEntities();
|
||||
break;
|
||||
case "navigate-devices":
|
||||
this._navigateDevices();
|
||||
break;
|
||||
case "navigate-automations":
|
||||
this._navigateAutomations();
|
||||
break;
|
||||
case "remove":
|
||||
this._handleRemoveLabelClick();
|
||||
break;
|
||||
}
|
||||
};
|
||||
|
||||
private _navigateEntities = () => {
|
||||
navigate(
|
||||
`/config/entities?historyBack=1&label=${this._overflowLabel.label_id}`
|
||||
|
||||
@@ -52,7 +52,6 @@ import "../../../components/ha-filter-labels";
|
||||
import "../../../components/ha-filter-voice-assistants";
|
||||
import "../../../components/ha-icon-button";
|
||||
import "../../../components/ha-icon-overflow-menu";
|
||||
import "../../../components/ha-md-divider";
|
||||
import "../../../components/ha-state-icon";
|
||||
import "../../../components/ha-sub-menu";
|
||||
import "../../../components/ha-svg-icon";
|
||||
|
||||
@@ -54,7 +54,6 @@ import "../../../components/ha-filter-labels";
|
||||
import "../../../components/ha-filter-voice-assistants";
|
||||
import "../../../components/ha-icon-button";
|
||||
import "../../../components/ha-icon-overflow-menu";
|
||||
import "../../../components/ha-md-divider";
|
||||
import "../../../components/ha-sub-menu";
|
||||
import "../../../components/ha-svg-icon";
|
||||
import "../../../components/ha-tooltip";
|
||||
|
||||
Reference in New Issue
Block a user