From eeca7ee4859fd6222922f44ab648e910afc845ae Mon Sep 17 00:00:00 2001 From: leekelleher Date: Thu, 18 Jan 2024 17:07:37 +0000 Subject: [PATCH] [WIP] Dynamic Root --- src/Umbraco.Web.UI.Client/package.json | 1 + .../src/apps/backoffice/backoffice.element.ts | 1 + .../input-document-picker-root.element.ts | 93 ++++++++++++------- .../src/packages/dynamic-root/index.ts | 2 + .../src/packages/dynamic-root/manifests.ts | 7 ++ ...ynamic-root-origin-picker-modal.element.ts | 47 ++++++++++ .../src/packages/dynamic-root/modals/index.ts | 9 ++ .../packages/dynamic-root/modals/manifests.ts | 14 +++ .../packages/dynamic-root/repository/index.ts | 1 + .../dynamic-root/repository/manifests.ts | 3 + .../packages/dynamic-root/umbraco-package.ts | 9 ++ src/Umbraco.Web.UI.Client/tsconfig.json | 1 + .../web-test-runner.config.mjs | 1 + 13 files changed, 158 insertions(+), 31 deletions(-) create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/index.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/manifests.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/dynamic-root-origin-picker-modal.element.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/index.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/manifests.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/index.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/manifests.ts create mode 100644 src/Umbraco.Web.UI.Client/src/packages/dynamic-root/umbraco-package.ts diff --git a/src/Umbraco.Web.UI.Client/package.json b/src/Umbraco.Web.UI.Client/package.json index a756f55069..1038f071b5 100644 --- a/src/Umbraco.Web.UI.Client/package.json +++ b/src/Umbraco.Web.UI.Client/package.json @@ -62,6 +62,7 @@ "./member-type": "./dist-cms/packages/members/member-types/index.js", "./package": "./dist-cms/packages/packages/package/index.js", "./data-type": "./dist-cms/packages/core/data-type/index.js", + "./dynamic-root": "./dist-cms/packages/dynamic-root/index.js", "./language": "./dist-cms/packages/settings/languages/index.js", "./logviewer": "./dist-cms/packages/settings/logviewer/index.js", "./relation-type": "./dist-cms/packages/relations/relation-types/index.js", diff --git a/src/Umbraco.Web.UI.Client/src/apps/backoffice/backoffice.element.ts b/src/Umbraco.Web.UI.Client/src/apps/backoffice/backoffice.element.ts index 84243dafc2..997f5a79fa 100644 --- a/src/Umbraco.Web.UI.Client/src/apps/backoffice/backoffice.element.ts +++ b/src/Umbraco.Web.UI.Client/src/apps/backoffice/backoffice.element.ts @@ -30,6 +30,7 @@ const CORE_PACKAGES = [ import('../../packages/log-viewer/umbraco-package.js'), import('../../packages/health-check/umbraco-package.js'), import('../../packages/static-file/umbraco-package.js'), + import('../../packages/dynamic-root/umbraco-package.js'), ]; @customElement('umb-backoffice') diff --git a/src/Umbraco.Web.UI.Client/src/packages/documents/documents/components/input-document-picker-root/input-document-picker-root.element.ts b/src/Umbraco.Web.UI.Client/src/packages/documents/documents/components/input-document-picker-root/input-document-picker-root.element.ts index 68b5ab60b3..f4f8b4de73 100644 --- a/src/Umbraco.Web.UI.Client/src/packages/documents/documents/components/input-document-picker-root/input-document-picker-root.element.ts +++ b/src/Umbraco.Web.UI.Client/src/packages/documents/documents/components/input-document-picker-root/input-document-picker-root.element.ts @@ -1,8 +1,14 @@ import { UmbDocumentPickerContext } from '../input-document/input-document.context.js'; +import { UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL } from '@umbraco-cms/backoffice/dynamic-root'; import { html, customElement, property, state, ifDefined, repeat } from '@umbraco-cms/backoffice/external/lit'; import { FormControlMixin } from '@umbraco-cms/backoffice/external/uui'; import { UmbLitElement } from '@umbraco-cms/internal/lit-element'; import type { DocumentItemResponseModel } from '@umbraco-cms/backoffice/backend-api'; +import { + UMB_MODAL_MANAGER_CONTEXT_TOKEN, + UmbModalContext, + UmbModalManagerContext, +} from '@umbraco-cms/backoffice/modal'; @customElement('umb-input-document-picker-root') export class UmbInputDocumentPickerRootElement extends FormControlMixin(UmbLitElement) { @@ -24,16 +30,17 @@ export class UmbInputDocumentPickerRootElement extends FormControlMixin(UmbLitEl #documentPickerContext = new UmbDocumentPickerContext(this); - // TODO: DynamicRoot - once feature implemented, wire up context and picker UI. [LK] - #dynamicRootPickerContext = { - openPicker: () => { - throw new Error('DynamicRoot picker has not been implemented yet.'); - }, - }; + private _modalContext?: UmbModalManagerContext; + + #openModal?: UmbModalContext; constructor() { super(); + this.consumeContext(UMB_MODAL_MANAGER_CONTEXT_TOKEN, (instance) => { + this._modalContext = instance; + }); + this.#documentPickerContext.max = 1; this.observe(this.#documentPickerContext.selection, (selection) => (super.value = selection.join(','))); @@ -44,55 +51,79 @@ export class UmbInputDocumentPickerRootElement extends FormControlMixin(UmbLitEl return undefined; } + #openDocumentPicker() { + this.#documentPickerContext.openPicker({ + hideTreeRoot: true, + }); + } + + #openDynamicRootPicker() { + this.#openModal = this._modalContext?.open(UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL, { + data: { testing: 123 }, + }); + this.#openModal?.onSubmit().then((data) => { + console.log('openDynamicRootPicker.onSubmit', data); + }); + } + render() { - return html` - ${this._items - ? html` ${repeat( - this._items, - (item) => item.id, - (item) => this._renderItem(item), - )} - ` - : ''} - ${this.#renderButtons()} - `; + return html`${this.#renderButtons()} ${this.#renderItems()}`; } #renderButtons() { if (this.nodeId) return; - - //TODO: Dynamic paths - return html` + return html` this.#documentPickerContext.openPicker()} + @click=${this.#openDocumentPicker} label=${this.localize.term('contentPicker_defineRootNode')}> this.#dynamicRootPickerContext.openPicker()} + @click=${this.#openDynamicRootPicker} label=${this.localize.term('contentPicker_defineDynamicRoot')}> `; } - private _renderItem(item: DocumentItemResponseModel) { + #renderItems() { + if (!this._items) return; + return html` + ${repeat( + this._items, + (item) => item.id, + (item) => this.#renderItem(item), + )} + `; + } + + #renderItem(item: DocumentItemResponseModel) { if (!item.id) return; return html` - + ${this.#renderIcon(item)} + ${this.#renderIsTrashed(item)} - this.#documentPickerContext.openPicker()} label="Edit document ${item.name}" - >Edit + + ${this.localize.term('general_edit')} + this.#documentPickerContext.requestRemoveItem(item.id!)} - label="Remove document ${item.name}" - >Remove + label="Remove document ${item.name}"> + ${this.localize.term('general_remove')} + `; } + + #renderIcon(item: DocumentItemResponseModel) { + if (!item.icon) return; + return html``; + } + + #renderIsTrashed(item: DocumentItemResponseModel) { + if (!item.isTrashed) return; + return html`Trashed`; + } } export default UmbInputDocumentPickerRootElement; diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/index.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/index.ts new file mode 100644 index 0000000000..736a54915b --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/index.ts @@ -0,0 +1,2 @@ +export * from './modals/index.js'; +export * from './repository/index.js'; diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/manifests.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/manifests.ts new file mode 100644 index 0000000000..4322a89557 --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/manifests.ts @@ -0,0 +1,7 @@ +import { manifests as modalManifests } from './modals/manifests.js'; +import { manifests as repositoryManifests } from './repository/manifests.js'; + +export const manifests = [ + ...modalManifests, + ...repositoryManifests, +]; diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/dynamic-root-origin-picker-modal.element.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/dynamic-root-origin-picker-modal.element.ts new file mode 100644 index 0000000000..e2caf5f367 --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/dynamic-root-origin-picker-modal.element.ts @@ -0,0 +1,47 @@ +import { UmbTextStyles } from '@umbraco-cms/backoffice/style'; +import { css, html, customElement } from '@umbraco-cms/backoffice/external/lit'; +import { + UMB_MODAL_MANAGER_CONTEXT_TOKEN, + UmbModalManagerContext, + UmbModalBaseElement, +} from '@umbraco-cms/backoffice/modal'; + +@customElement('umb-dynamic-root-origin-picker-modal') +export class UmbDynamicRootOriginPickerModalModalElement extends UmbModalBaseElement { + private _modalContext?: UmbModalManagerContext; + + constructor() { + super(); + this.consumeContext(UMB_MODAL_MANAGER_CONTEXT_TOKEN, (instance) => { + this._modalContext = instance; + }); + } + + #close() { + this.modalContext?.reject(); + } + + render() { + return html` + +
+

DynamicRoot Origin Picker Modal

+ +
+
+ Close +
+
+ `; + } + + static styles = [UmbTextStyles, css``]; +} + +export default UmbDynamicRootOriginPickerModalModalElement; + +declare global { + interface HTMLElementTagNameMap { + 'umb-dynamic-root-origin-picker-modal': UmbDynamicRootOriginPickerModalModalElement; + } +} diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/index.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/index.ts new file mode 100644 index 0000000000..5cdcc2eda3 --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/index.ts @@ -0,0 +1,9 @@ +import { UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL_ALIAS } from './manifests.js'; +import { UmbModalToken } from '@umbraco-cms/backoffice/modal'; + +export const UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL = new UmbModalToken(UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL_ALIAS, { + modal: { + type: 'sidebar', + size: 'small', + }, +}); diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/manifests.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/manifests.ts new file mode 100644 index 0000000000..c915e81db3 --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/modals/manifests.ts @@ -0,0 +1,14 @@ +import { ManifestModal } from '@umbraco-cms/backoffice/extension-registry'; + +export const UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL_ALIAS = 'Umb.Modal.DynamicRoot.OriginPicker'; + +const modals: Array = [ + { + type: 'modal', + alias: UMB_DYNAMIC_ROOT_ORIGIN_PICKER_MODAL_ALIAS, + name: 'Choose an origin', + js: () => import('./dynamic-root-origin-picker-modal.element.js'), + }, +]; + +export const manifests = [...modals]; diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/index.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/index.ts new file mode 100644 index 0000000000..ff6d8716e5 --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/index.ts @@ -0,0 +1 @@ +export { UMB_DYNAMIC_ROOT_REPOSITORY_ALIAS } from './manifests.js'; diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/manifests.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/manifests.ts new file mode 100644 index 0000000000..a140a9a729 --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/repository/manifests.ts @@ -0,0 +1,3 @@ +export const UMB_DYNAMIC_ROOT_REPOSITORY_ALIAS = 'Umb.Repository.DynamicRoot'; + +export const manifests = []; diff --git a/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/umbraco-package.ts b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/umbraco-package.ts new file mode 100644 index 0000000000..46eff51dfd --- /dev/null +++ b/src/Umbraco.Web.UI.Client/src/packages/dynamic-root/umbraco-package.ts @@ -0,0 +1,9 @@ +export const name = 'Umbraco.Core.DynamicRoot'; +export const extensions = [ + { + name: 'Dynamic Root Bundle', + alias: 'Umb.Bundle.DynamicRoot', + type: 'bundle', + js: () => import('./manifests.js'), + }, +]; diff --git a/src/Umbraco.Web.UI.Client/tsconfig.json b/src/Umbraco.Web.UI.Client/tsconfig.json index de24c48990..c4c88e5d83 100644 --- a/src/Umbraco.Web.UI.Client/tsconfig.json +++ b/src/Umbraco.Web.UI.Client/tsconfig.json @@ -92,6 +92,7 @@ "@umbraco-cms/backoffice/temporary-file": ["src/packages/core/temporary-file"], "@umbraco-cms/backoffice/data-type": ["./src/packages/core/data-type/index.ts"], + "@umbraco-cms/backoffice/dynamic-root": ["./src/packages/dynamic-root/index.ts"], "@umbraco-cms/backoffice/language": ["./src/packages/settings/languages/index.ts"], "@umbraco-cms/backoffice/logviewer": ["src/packages/log-viewer/index.ts"], "@umbraco-cms/backoffice/relation-types": ["src/packages/relations/relation-types/index.ts"], diff --git a/src/Umbraco.Web.UI.Client/web-test-runner.config.mjs b/src/Umbraco.Web.UI.Client/web-test-runner.config.mjs index 7a0d981ce5..25e576de50 100644 --- a/src/Umbraco.Web.UI.Client/web-test-runner.config.mjs +++ b/src/Umbraco.Web.UI.Client/web-test-runner.config.mjs @@ -107,6 +107,7 @@ export default { '@umbraco-cms/backoffice/package': './src/packages/packages/package/index.ts', '@umbraco-cms/backoffice/data-type': './src/packages/core/data-type/index.ts', + '@umbraco-cms/backoffice/dynamic-root': './src/packages/dynamic-root/index.ts', '@umbraco-cms/backoffice/language': './src/packages/settings/languages/index.ts', '@umbraco-cms/backoffice/logviewer': './src/packages/settings/logviewer/index.ts', '@umbraco-cms/backoffice/relation-type': './src/packages/relations/relation-types/index.ts',