fix: show the action button inside a button-group only if there are extensions registered
by moving the calculation of the extension controllers from the action-menu element into the action element itself, we can save a few states, simplify the calculation, and conditionally render the action-menu element ensuring, that the UUI styling is correctly applied
This commit is contained in:
@@ -1,85 +1,24 @@
|
|||||||
import type { CSSResultGroup } from '@umbraco-cms/backoffice/external/lit';
|
|
||||||
import { css, html, customElement, property, state, nothing, repeat } from '@umbraco-cms/backoffice/external/lit';
|
import { css, html, customElement, property, state, nothing, repeat } from '@umbraco-cms/backoffice/external/lit';
|
||||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||||
import {
|
import type { ManifestWorkspaceActionMenuItem } from '@umbraco-cms/backoffice/extension-registry';
|
||||||
umbExtensionsRegistry,
|
|
||||||
type ManifestWorkspaceActionMenuItem,
|
|
||||||
} from '@umbraco-cms/backoffice/extension-registry';
|
|
||||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||||
import type { UUIInterfaceColor, UUIInterfaceLook } from '@umbraco-cms/backoffice/external/uui';
|
import type { UUIInterfaceColor, UUIInterfaceLook } from '@umbraco-cms/backoffice/external/uui';
|
||||||
import {
|
import type { UmbExtensionElementAndApiInitializer } from '@umbraco-cms/backoffice/extension-api';
|
||||||
type UmbExtensionElementAndApiInitializer,
|
|
||||||
UmbExtensionsElementAndApiInitializer,
|
|
||||||
} from '@umbraco-cms/backoffice/extension-api';
|
|
||||||
|
|
||||||
function ExtensionApiArgsMethod(manifest: ManifestWorkspaceActionMenuItem) {
|
|
||||||
return [{ meta: manifest.meta }];
|
|
||||||
}
|
|
||||||
@customElement('umb-workspace-action-menu')
|
@customElement('umb-workspace-action-menu')
|
||||||
export class UmbWorkspaceActionMenuElement extends UmbLitElement {
|
export class UmbWorkspaceActionMenuElement extends UmbLitElement {
|
||||||
#extensionsController?: UmbExtensionsElementAndApiInitializer<
|
|
||||||
ManifestWorkspaceActionMenuItem,
|
|
||||||
'workspaceActionMenuItem',
|
|
||||||
ManifestWorkspaceActionMenuItem
|
|
||||||
>;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* The workspace actions to filter the available actions by.
|
|
||||||
* @example ['Umb.WorkspaceAction.Document.Save', 'Umb.WorkspaceAction.Document.SaveAndPublishNew']
|
|
||||||
*/
|
|
||||||
@property({ attribute: false })
|
|
||||||
public set forWorkspaceActions(value: Array<string>) {
|
|
||||||
if (value === this._forWorkspaceActions) return;
|
|
||||||
this._forWorkspaceActions = value;
|
|
||||||
this._filter = (action) => {
|
|
||||||
return Array.isArray(action.forWorkspaceActions)
|
|
||||||
? action.forWorkspaceActions.some((alias) => this.forWorkspaceActions.includes(alias))
|
|
||||||
: this.forWorkspaceActions.includes(action.forWorkspaceActions);
|
|
||||||
};
|
|
||||||
this.#observeExtensions();
|
|
||||||
}
|
|
||||||
public get forWorkspaceActions(): Array<string> {
|
|
||||||
return this._forWorkspaceActions;
|
|
||||||
}
|
|
||||||
private _forWorkspaceActions: Array<string> = [];
|
|
||||||
|
|
||||||
@state()
|
|
||||||
_filter?: (action: ManifestWorkspaceActionMenuItem) => boolean;
|
|
||||||
|
|
||||||
@property()
|
@property()
|
||||||
look: UUIInterfaceLook = 'secondary';
|
look: UUIInterfaceLook = 'secondary';
|
||||||
|
|
||||||
@property()
|
@property()
|
||||||
color: UUIInterfaceColor = 'default';
|
color: UUIInterfaceColor = 'default';
|
||||||
|
|
||||||
@state()
|
@property({ type: Array, attribute: false })
|
||||||
_items: Array<UmbExtensionElementAndApiInitializer<ManifestWorkspaceActionMenuItem>> = [];
|
items: Array<UmbExtensionElementAndApiInitializer<ManifestWorkspaceActionMenuItem>> = [];
|
||||||
|
|
||||||
@state()
|
@state()
|
||||||
_popoverOpen = false;
|
_popoverOpen = false;
|
||||||
|
|
||||||
#observeExtensions(): void {
|
|
||||||
this.#extensionsController?.destroy();
|
|
||||||
if (this._filter) {
|
|
||||||
this.#extensionsController = new UmbExtensionsElementAndApiInitializer<
|
|
||||||
ManifestWorkspaceActionMenuItem,
|
|
||||||
'workspaceActionMenuItem',
|
|
||||||
ManifestWorkspaceActionMenuItem
|
|
||||||
>(
|
|
||||||
this,
|
|
||||||
umbExtensionsRegistry,
|
|
||||||
'workspaceActionMenuItem',
|
|
||||||
ExtensionApiArgsMethod,
|
|
||||||
this._filter,
|
|
||||||
(extensionControllers) => {
|
|
||||||
this._items = extensionControllers;
|
|
||||||
},
|
|
||||||
undefined, // We can leave the alias to undefined, as we destroy this our selfs.
|
|
||||||
);
|
|
||||||
//this.#extensionsController.elementProperties = this.#elProps;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#onPopoverToggle(event: ToggleEvent) {
|
#onPopoverToggle(event: ToggleEvent) {
|
||||||
// TODO: This ignorer is just neede for JSON SCHEMA TO WORK, As its not updated with latest TS jet.
|
// TODO: This ignorer is just neede for JSON SCHEMA TO WORK, As its not updated with latest TS jet.
|
||||||
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
||||||
@@ -88,7 +27,7 @@ export class UmbWorkspaceActionMenuElement extends UmbLitElement {
|
|||||||
}
|
}
|
||||||
|
|
||||||
override render() {
|
override render() {
|
||||||
return this._items && this._items.length > 0
|
return this.items?.length
|
||||||
? html`
|
? html`
|
||||||
<uui-button
|
<uui-button
|
||||||
id="popover-trigger"
|
id="popover-trigger"
|
||||||
@@ -106,13 +45,11 @@ export class UmbWorkspaceActionMenuElement extends UmbLitElement {
|
|||||||
@toggle=${this.#onPopoverToggle}>
|
@toggle=${this.#onPopoverToggle}>
|
||||||
<umb-popover-layout>
|
<umb-popover-layout>
|
||||||
<uui-scroll-container>
|
<uui-scroll-container>
|
||||||
${this._items.length > 0
|
${repeat(
|
||||||
? repeat(
|
this.items,
|
||||||
this._items,
|
|
||||||
(ext) => ext.alias,
|
(ext) => ext.alias,
|
||||||
(ext) => ext.component,
|
(ext) => ext.component,
|
||||||
)
|
)}
|
||||||
: ''}
|
|
||||||
</uui-scroll-container>
|
</uui-scroll-container>
|
||||||
</umb-popover-layout>
|
</umb-popover-layout>
|
||||||
</uui-popover-container>
|
</uui-popover-container>
|
||||||
@@ -120,7 +57,7 @@ export class UmbWorkspaceActionMenuElement extends UmbLitElement {
|
|||||||
: nothing;
|
: nothing;
|
||||||
}
|
}
|
||||||
|
|
||||||
static override styles: CSSResultGroup = [
|
static override styles = [
|
||||||
UmbTextStyles,
|
UmbTextStyles,
|
||||||
css`
|
css`
|
||||||
:host {
|
:host {
|
||||||
@@ -143,7 +80,6 @@ export class UmbWorkspaceActionMenuElement extends UmbLitElement {
|
|||||||
#popover-trigger {
|
#popover-trigger {
|
||||||
--uui-button-padding-top-factor: 0.5;
|
--uui-button-padding-top-factor: 0.5;
|
||||||
--uui-button-padding-bottom-factor: 0.1;
|
--uui-button-padding-bottom-factor: 0.1;
|
||||||
--uui-button-border-radius: 0;
|
|
||||||
}
|
}
|
||||||
`,
|
`,
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -1,12 +1,18 @@
|
|||||||
import type { UmbWorkspaceAction } from '../workspace-action.interface.js';
|
import type { UmbWorkspaceAction } from '../workspace-action.interface.js';
|
||||||
import { UmbActionExecutedEvent } from '@umbraco-cms/backoffice/event';
|
import { UmbActionExecutedEvent } from '@umbraco-cms/backoffice/event';
|
||||||
import { html, customElement, property, state, ifDefined } from '@umbraco-cms/backoffice/external/lit';
|
import { html, customElement, property, state, ifDefined, when } from '@umbraco-cms/backoffice/external/lit';
|
||||||
import type { UUIButtonState } from '@umbraco-cms/backoffice/external/uui';
|
import type { UUIButtonState } from '@umbraco-cms/backoffice/external/uui';
|
||||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||||
import type {
|
import {
|
||||||
ManifestWorkspaceAction,
|
umbExtensionsRegistry,
|
||||||
MetaWorkspaceActionDefaultKind,
|
type ManifestWorkspaceAction,
|
||||||
|
type ManifestWorkspaceActionMenuItem,
|
||||||
|
type MetaWorkspaceActionDefaultKind,
|
||||||
} from '@umbraco-cms/backoffice/extension-registry';
|
} from '@umbraco-cms/backoffice/extension-registry';
|
||||||
|
import {
|
||||||
|
type UmbExtensionElementAndApiInitializer,
|
||||||
|
UmbExtensionsElementAndApiInitializer,
|
||||||
|
} from '@umbraco-cms/backoffice/extension-api';
|
||||||
|
|
||||||
import '../../workspace-action-menu/index.js';
|
import '../../workspace-action-menu/index.js';
|
||||||
|
|
||||||
@@ -17,13 +23,15 @@ export class UmbWorkspaceActionElement<
|
|||||||
> extends UmbLitElement {
|
> extends UmbLitElement {
|
||||||
#manifest?: ManifestWorkspaceAction<MetaType>;
|
#manifest?: ManifestWorkspaceAction<MetaType>;
|
||||||
#api?: ApiType;
|
#api?: ApiType;
|
||||||
|
#extensionsController?: UmbExtensionsElementAndApiInitializer<
|
||||||
|
ManifestWorkspaceActionMenuItem,
|
||||||
|
'workspaceActionMenuItem',
|
||||||
|
ManifestWorkspaceActionMenuItem
|
||||||
|
>;
|
||||||
|
|
||||||
@state()
|
@state()
|
||||||
private _buttonState?: UUIButtonState;
|
private _buttonState?: UUIButtonState;
|
||||||
|
|
||||||
@state()
|
|
||||||
private _aliases: Array<string> = [];
|
|
||||||
|
|
||||||
@state()
|
@state()
|
||||||
_href?: string;
|
_href?: string;
|
||||||
|
|
||||||
@@ -60,6 +68,9 @@ export class UmbWorkspaceActionElement<
|
|||||||
return this.#api;
|
return this.#api;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@state()
|
||||||
|
private _items: Array<UmbExtensionElementAndApiInitializer<ManifestWorkspaceActionMenuItem>> = [];
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a list of original and overwritten aliases of workspace actions for the action.
|
* Create a list of original and overwritten aliases of workspace actions for the action.
|
||||||
*/
|
*/
|
||||||
@@ -77,7 +88,8 @@ export class UmbWorkspaceActionElement<
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
this._aliases = Array.from(aliases);
|
|
||||||
|
this.#observeExtensions(Array.from(aliases));
|
||||||
}
|
}
|
||||||
|
|
||||||
private async _onClick(event: MouseEvent) {
|
private async _onClick(event: MouseEvent) {
|
||||||
@@ -108,9 +120,31 @@ export class UmbWorkspaceActionElement<
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
override render() {
|
#observeExtensions(aliases: string[]): void {
|
||||||
|
this.#extensionsController?.destroy();
|
||||||
|
this.#extensionsController = new UmbExtensionsElementAndApiInitializer<
|
||||||
|
ManifestWorkspaceActionMenuItem,
|
||||||
|
'workspaceActionMenuItem',
|
||||||
|
ManifestWorkspaceActionMenuItem
|
||||||
|
>(
|
||||||
|
this,
|
||||||
|
umbExtensionsRegistry,
|
||||||
|
'workspaceActionMenuItem',
|
||||||
|
ExtensionApiArgsMethod,
|
||||||
|
(action) => {
|
||||||
|
return Array.isArray(action.forWorkspaceActions)
|
||||||
|
? action.forWorkspaceActions.some((alias) => aliases.includes(alias))
|
||||||
|
: aliases.includes(action.forWorkspaceActions);
|
||||||
|
},
|
||||||
|
(extensionControllers) => {
|
||||||
|
this._items = extensionControllers;
|
||||||
|
},
|
||||||
|
undefined, // We can leave the alias to undefined, as we destroy this our selfs.
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
#renderButton() {
|
||||||
return html`
|
return html`
|
||||||
<uui-button-group>
|
|
||||||
<uui-button
|
<uui-button
|
||||||
id="action-button"
|
id="action-button"
|
||||||
.href=${this._href}
|
.href=${this._href}
|
||||||
@@ -122,13 +156,25 @@ export class UmbWorkspaceActionElement<
|
|||||||
)}
|
)}
|
||||||
.disabled=${this._isDisabled}
|
.disabled=${this._isDisabled}
|
||||||
.state=${this._buttonState}></uui-button>
|
.state=${this._buttonState}></uui-button>
|
||||||
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
|
#renderActionMenu() {
|
||||||
|
return html`
|
||||||
<umb-workspace-action-menu
|
<umb-workspace-action-menu
|
||||||
.forWorkspaceActions=${this._aliases}
|
.items=${this._items}
|
||||||
color="${this.#manifest?.meta.color || 'default'}"
|
color="${this.#manifest?.meta.color || 'default'}"
|
||||||
look="${this.#manifest?.meta.look || 'default'}"></umb-workspace-action-menu>
|
look="${this.#manifest?.meta.look || 'default'}"></umb-workspace-action-menu>
|
||||||
</uui-button-group>
|
|
||||||
`;
|
`;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override render() {
|
||||||
|
return when(
|
||||||
|
this._items.length,
|
||||||
|
() => html` <uui-button-group> ${this.#renderButton()} ${this.#renderActionMenu()} </uui-button-group> `,
|
||||||
|
() => this.#renderButton(),
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export default UmbWorkspaceActionElement;
|
export default UmbWorkspaceActionElement;
|
||||||
@@ -138,3 +184,7 @@ declare global {
|
|||||||
'umb-workspace-action': UmbWorkspaceActionElement;
|
'umb-workspace-action': UmbWorkspaceActionElement;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function ExtensionApiArgsMethod(manifest: ManifestWorkspaceActionMenuItem) {
|
||||||
|
return [{ meta: manifest.meta }];
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user