diff --git a/src/Umbraco.Web.UI.Client/src/packages/core/property-editor/uis/member-group-picker/property-editor-ui-member-group-picker.element.ts b/src/Umbraco.Web.UI.Client/src/packages/core/property-editor/uis/member-group-picker/property-editor-ui-member-group-picker.element.ts index 919c139b95..e223e3fa18 100644 --- a/src/Umbraco.Web.UI.Client/src/packages/core/property-editor/uis/member-group-picker/property-editor-ui-member-group-picker.element.ts +++ b/src/Umbraco.Web.UI.Client/src/packages/core/property-editor/uis/member-group-picker/property-editor-ui-member-group-picker.element.ts @@ -1,66 +1,46 @@ -import type { PropertyValueMap } from '@umbraco-cms/backoffice/external/lit'; import { html, customElement, property, state } from '@umbraco-cms/backoffice/external/lit'; -import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry'; import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element'; -import type { UmbPropertyEditorConfigCollection } from '@umbraco-cms/backoffice/property-editor'; +import { UmbPropertyValueChangeEvent } from '@umbraco-cms/backoffice/property-editor'; +import type { NumberRangeValueType } from '@umbraco-cms/backoffice/models'; import type { UmbInputMemberGroupElement } from '@umbraco-cms/backoffice/member-group'; +import type { UmbPropertyEditorConfigCollection } from '@umbraco-cms/backoffice/property-editor'; +import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry'; /** * @element umb-property-editor-ui-member-group-picker */ @customElement('umb-property-editor-ui-member-group-picker') export class UmbPropertyEditorUIMemberGroupPickerElement extends UmbLitElement implements UmbPropertyEditorUiElement { - // private _value: Array = []; - - // @property({ type: Array }) - // public set value(value: Array) { - // this._value = Array.isArray(value) ? value : value ? [value] : []; - // } - // public get value(): Array { - // return this._value; - // } - - @property({ type: String }) - public value: string = ''; + @property() + public value?: string; public set config(config: UmbPropertyEditorConfigCollection | undefined) { - const validationLimit = config?.find((x) => x.alias === 'validationLimit'); + if (!config) return; - this._limitMin = (validationLimit?.value as any)?.min; - this._limitMax = (validationLimit?.value as any)?.max; + const minMax = config?.getValueByAlias('validationLimit'); + this.min = minMax?.min ?? 0; + this.max = minMax?.max ?? Infinity; } @state() - _items: Array = []; + min = 0; @state() - private _limitMin?: number; - @state() - private _limitMax?: number; + max = Infinity; - protected updated(_changedProperties: PropertyValueMap | Map): void { - super.updated(_changedProperties); - if (_changedProperties.has('value')) { - this._items = this.value ? this.value.split(',') : []; - } - } - - private _onChange(event: CustomEvent) { - //TODO: This is a hack, something changed so now we need to convert the array to a comma separated string to make it work with the server. - const toCommaSeparatedString = (event.target as UmbInputMemberGroupElement).selection.join(','); - // this.value = (event.target as UmbInputMemberGroupElement).selection; - this.value = toCommaSeparatedString; - this.dispatchEvent(new CustomEvent('property-value-change')); + #onChange(event: CustomEvent & { target: UmbInputMemberGroupElement }) { + this.value = event.target.value; + this.dispatchEvent(new UmbPropertyValueChangeEvent()); } render() { return html` - + .min=${this.min} + .max=${this.max} + .value=${this.value ?? ''} + ?showOpenButton=${true} + @change=${this.#onChange}> `; } } diff --git a/src/Umbraco.Web.UI.Client/src/packages/members/member-group/components/input-member-group/input-member-group.element.ts b/src/Umbraco.Web.UI.Client/src/packages/members/member-group/components/input-member-group/input-member-group.element.ts index 565e13a28e..121447158b 100644 --- a/src/Umbraco.Web.UI.Client/src/packages/members/member-group/components/input-member-group/input-member-group.element.ts +++ b/src/Umbraco.Web.UI.Client/src/packages/members/member-group/components/input-member-group/input-member-group.element.ts @@ -1,31 +1,28 @@ import type { UmbMemberGroupItemModel } from '../../repository/index.js'; import { UmbMemberPickerContext } from './input-member-group.context.js'; import { css, html, customElement, property, state, ifDefined, repeat } from '@umbraco-cms/backoffice/external/lit'; -import { UUIFormControlMixin } from '@umbraco-cms/backoffice/external/uui'; -import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element'; -import type { MemberItemResponseModel } from '@umbraco-cms/backoffice/external/backend-api'; import { splitStringToArray } from '@umbraco-cms/backoffice/utils'; -import { UMB_WORKSPACE_MODAL, UmbModalRouteRegistrationController } from '@umbraco-cms/backoffice/modal'; -import { type UmbSorterConfig, UmbSorterController } from '@umbraco-cms/backoffice/sorter'; - -const SORTER_CONFIG: UmbSorterConfig = { - getUniqueOfElement: (element) => { - return element.getAttribute('detail'); - }, - getUniqueOfModel: (modelEntry) => { - return modelEntry; - }, - identifier: 'Umb.SorterIdentifier.InputMemberGroup', - itemSelector: 'uui-ref-node', - containerSelector: 'uui-ref-list', -}; +import { UmbChangeEvent } from '@umbraco-cms/backoffice/event'; +import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element'; +import { UmbSorterController } from '@umbraco-cms/backoffice/sorter'; +import { UmbModalRouteRegistrationController, UMB_WORKSPACE_MODAL } from '@umbraco-cms/backoffice/modal'; +import { UUIFormControlMixin } from '@umbraco-cms/backoffice/external/uui'; @customElement('umb-input-member-group') export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElement, '') { - #sorter = new UmbSorterController(this, { - ...SORTER_CONFIG, + #sorter = new UmbSorterController(this, { + getUniqueOfElement: (element) => { + return element.id; + }, + getUniqueOfModel: (modelEntry) => { + return modelEntry; + }, + identifier: 'Umb.SorterIdentifier.InputMemberGroup', + itemSelector: 'uui-ref-node', + containerSelector: 'uui-ref-list', onChange: ({ model }) => { this.selection = model; + this.dispatchEvent(new UmbChangeEvent()); }, }); @@ -91,7 +88,6 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen @property() public set value(idsString: string) { - // Its with full purpose we don't call super.value, as thats being handled by the observation of the context selection. this.selection = splitStringToArray(idsString); } public get value(): string { @@ -112,7 +108,6 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen constructor() { super(); - // TODO: This would have to be more specific if used in a property editor context... [NL] new UmbModalRouteRegistrationController(this, UMB_WORKSPACE_MODAL) .addAdditionalPath('member-group') .onSetup(() => { @@ -122,10 +117,8 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen this._editMemberGroupPath = routeBuilder({}); }); - this.observe(this.#pickerContext.selection, (selection) => (this.value = selection.join(','))); - this.observe(this.#pickerContext.selectedItems, (selectedItems) => { - this._items = selectedItems; - }); + this.observe(this.#pickerContext.selection, (selection) => (this.value = selection.join(',')), '_observeSelection'); + this.observe(this.#pickerContext.selectedItems, (selectedItems) => (this._items = selectedItems), '_observeItems'); } connectedCallback(): void { @@ -144,16 +137,6 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen ); } - protected _openPicker() { - this.#pickerContext.openPicker({ - hideTreeRoot: true, - }); - } - - protected _requestRemoveItem(item: UmbMemberGroupItemModel) { - this.#pickerContext.requestRemoveItem(item.unique!); - } - protected getFormElement() { return undefined; } @@ -164,29 +147,31 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen }); } - #requestRemoveItem(item: MemberItemResponseModel) { - this.#pickerContext.requestRemoveItem(item.id!); + #removeItem(item: UmbMemberGroupItemModel) { + this.#pickerContext.requestRemoveItem(item.unique); } render() { - return html` ${this.#renderItems()} ${this.#renderAddButton()} `; + return html`${this.#renderItems()} ${this.#renderAddButton()}`; } #renderItems() { if (!this._items) return; - return html` - ${repeat( - this._items, - (item) => item.unique, - (item) => this.#renderItem(item), - )} - `; + return html` + + ${repeat( + this._items, + (item) => item.unique, + (item) => this.#renderItem(item), + )} + + `; } #renderAddButton() { if (this.max === 1 && this.selection.length >= this.max) return; return html``; @@ -194,17 +179,11 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen #renderItem(item: UmbMemberGroupItemModel) { if (!item.unique) return; - // TODO: get the correct variant name - const name = item.name; return html` - + ${this.#renderOpenButton(item)} - this._requestRemoveItem(item)} - label="${this.localize.term('general_remove')} ${name}"> - ${this.localize.term('general_remove')} - + this.#removeItem(item)} label=${this.localize.term('general_remove')}> `; @@ -212,21 +191,18 @@ export class UmbInputMemberGroupElement extends UUIFormControlMixin(UmbLitElemen #renderOpenButton(item: UmbMemberGroupItemModel) { if (!this.showOpenButton) return; - // TODO: get the correct variant name - const name = item.name; return html` - + label="${this.localize.term('general_open')} ${item.name}"> + ${this.localize.term('general_open')} `; } static styles = [ css` - #add-button { + #btn-add { width: 100%; }