Merge pull request #2106 from umbraco/v14/feature/property-validation-mandatory-indicator
Feature: Property label mandatory indicator
This commit is contained in:
@@ -1,19 +1,17 @@
|
||||
import type { UmbPropertyEditorConfig } from '../../../property-editor/index.js';
|
||||
import type { UmbPropertyTypeModel } from '../../types.js';
|
||||
import { css, customElement, html, ifDefined, property, state } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbContentPropertyContext } from '@umbraco-cms/backoffice/content';
|
||||
import type { UmbDataTypeDetailModel } from '@umbraco-cms/backoffice/data-type';
|
||||
import { UmbDataTypeDetailRepository } from '@umbraco-cms/backoffice/data-type';
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import { css, html, ifDefined, customElement, property, state } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import type { UmbObserverController } from '@umbraco-cms/backoffice/observable-api';
|
||||
import { umbExtensionsRegistry } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import type { UmbDataTypeDetailModel } from '@umbraco-cms/backoffice/data-type';
|
||||
import type { UmbObserverController } from '@umbraco-cms/backoffice/observable-api';
|
||||
|
||||
@customElement('umb-property-type-based-property')
|
||||
export class UmbPropertyTypeBasedPropertyElement extends UmbLitElement {
|
||||
@property({ type: Object, attribute: false })
|
||||
public get property(): UmbPropertyTypeModel | undefined {
|
||||
return this._property;
|
||||
}
|
||||
public set property(value: UmbPropertyTypeModel | undefined) {
|
||||
const oldProperty = this._property;
|
||||
this._property = value;
|
||||
@@ -21,6 +19,9 @@ export class UmbPropertyTypeBasedPropertyElement extends UmbLitElement {
|
||||
this._observeDataType(this._property?.dataType.unique);
|
||||
}
|
||||
}
|
||||
public get property(): UmbPropertyTypeModel | undefined {
|
||||
return this._property;
|
||||
}
|
||||
private _property?: UmbPropertyTypeModel;
|
||||
|
||||
@property({ type: String, attribute: 'data-path' })
|
||||
@@ -73,16 +74,19 @@ export class UmbPropertyTypeBasedPropertyElement extends UmbLitElement {
|
||||
}
|
||||
|
||||
override render() {
|
||||
return this._propertyEditorUiAlias && this._property?.alias
|
||||
? html`<umb-property
|
||||
.dataPath=${this.dataPath}
|
||||
.alias=${this._property.alias}
|
||||
.label=${this._property.name}
|
||||
.description=${this._property.description ?? undefined}
|
||||
.appearance=${this._property.appearance}
|
||||
property-editor-ui-alias=${ifDefined(this._propertyEditorUiAlias)}
|
||||
.config=${this._dataTypeData}></umb-property>`
|
||||
: '';
|
||||
if (!this._propertyEditorUiAlias || !this._property?.alias) return;
|
||||
return html`
|
||||
<umb-property
|
||||
.dataPath=${this.dataPath}
|
||||
.alias=${this._property.alias}
|
||||
.label=${this._property.name}
|
||||
.description=${this._property.description ?? undefined}
|
||||
.appearance=${this._property.appearance}
|
||||
property-editor-ui-alias=${ifDefined(this._propertyEditorUiAlias)}
|
||||
.config=${this._dataTypeData}
|
||||
.validation=${this._property.validation}>
|
||||
</umb-property>
|
||||
`;
|
||||
}
|
||||
|
||||
static override styles = [
|
||||
|
||||
@@ -51,7 +51,7 @@ export class UmbPropertyLayoutElement extends UmbLitElement {
|
||||
public description = '';
|
||||
|
||||
/**
|
||||
* @description Make the property appear invalid
|
||||
* @description Make the property appear invalid.
|
||||
* @type {boolean}
|
||||
* @attr
|
||||
* @default undefined
|
||||
@@ -59,11 +59,20 @@ export class UmbPropertyLayoutElement extends UmbLitElement {
|
||||
@property({ type: Boolean, reflect: true })
|
||||
public invalid?: boolean;
|
||||
|
||||
/**
|
||||
* @description Display a mandatory indicator.
|
||||
* @type {boolean}
|
||||
* @attr
|
||||
* @default false
|
||||
*/
|
||||
@property({ type: Boolean, reflect: true })
|
||||
public mandatory?: boolean;
|
||||
|
||||
override render() {
|
||||
// TODO: Only show alias on label if user has access to DocumentType within settings:
|
||||
return html`
|
||||
<div id="headerColumn">
|
||||
<uui-label id="label" title=${this.alias}>
|
||||
<uui-label id="label" title=${this.alias} ?required=${this.mandatory}>
|
||||
${this.localize.string(this.label)}
|
||||
${when(this.invalid, () => html`<uui-badge color="danger" attention>!</uui-badge>`)}
|
||||
</uui-label>
|
||||
|
||||
@@ -14,27 +14,39 @@ import type { UmbVariantId } from '@umbraco-cms/backoffice/variant';
|
||||
import type { UmbPropertyEditorConfigProperty } from '@umbraco-cms/backoffice/property-editor';
|
||||
import { UmbPropertyEditorConfigCollection } from '@umbraco-cms/backoffice/property-editor';
|
||||
import type { UmbPropertyEditorUiElement } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type { UmbPropertyTypeAppearanceModel } from '@umbraco-cms/backoffice/content-type';
|
||||
import type {
|
||||
UmbPropertyTypeAppearanceModel,
|
||||
UmbPropertyTypeValidationModel,
|
||||
} from '@umbraco-cms/backoffice/content-type';
|
||||
|
||||
export class UmbPropertyContext<ValueType = any> extends UmbContextBase<UmbPropertyContext<ValueType>> {
|
||||
#alias = new UmbStringState(undefined);
|
||||
public readonly alias = this.#alias.asObservable();
|
||||
|
||||
#label = new UmbStringState(undefined);
|
||||
public readonly label = this.#label.asObservable();
|
||||
|
||||
#description = new UmbStringState(undefined);
|
||||
public readonly description = this.#description.asObservable();
|
||||
|
||||
#appearance = new UmbObjectState<UmbPropertyTypeAppearanceModel | undefined>(undefined);
|
||||
public readonly appearance = this.#appearance.asObservable();
|
||||
|
||||
#value = new UmbDeepState<ValueType | undefined>(undefined);
|
||||
public readonly value = this.#value.asObservable();
|
||||
|
||||
#configValues = new UmbArrayState<UmbPropertyEditorConfigProperty>([], (x) => x.alias);
|
||||
public readonly configValues = this.#configValues.asObservable();
|
||||
|
||||
#config = new UmbClassState<UmbPropertyEditorConfigCollection | undefined>(undefined);
|
||||
public readonly config = this.#config.asObservable();
|
||||
|
||||
#validation = new UmbObjectState<UmbPropertyTypeValidationModel | undefined>(undefined);
|
||||
public readonly validation = this.#validation.asObservable();
|
||||
|
||||
private _editor = new UmbBasicState<UmbPropertyEditorUiElement | undefined>(undefined);
|
||||
public readonly editor = this._editor.asObservable();
|
||||
|
||||
setEditor(editor: UmbPropertyEditorUiElement | undefined) {
|
||||
this._editor.setValue(editor ?? undefined);
|
||||
}
|
||||
@@ -108,24 +120,28 @@ export class UmbPropertyContext<ValueType = any> extends UmbContextBase<UmbPrope
|
||||
public getAlias(): string | undefined {
|
||||
return this.#alias.getValue();
|
||||
}
|
||||
|
||||
public setLabel(label: string | undefined): void {
|
||||
this.#label.setValue(label);
|
||||
}
|
||||
public getLabel(): string | undefined {
|
||||
return this.#label.getValue();
|
||||
}
|
||||
|
||||
public setDescription(description: string | undefined): void {
|
||||
this.#description.setValue(description);
|
||||
}
|
||||
public getDescription(): string | undefined {
|
||||
return this.#description.getValue();
|
||||
}
|
||||
|
||||
public setAppearance(appearance: UmbPropertyTypeAppearanceModel | undefined): void {
|
||||
this.#appearance.setValue(appearance);
|
||||
}
|
||||
public getAppearance(): UmbPropertyTypeAppearanceModel | undefined {
|
||||
return this.#appearance.getValue();
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the value of this property.
|
||||
* @param value {ValueType} the whole value to be set
|
||||
@@ -143,12 +159,14 @@ export class UmbPropertyContext<ValueType = any> extends UmbContextBase<UmbPrope
|
||||
public getValue(): ValueType | undefined {
|
||||
return this.#value.getValue();
|
||||
}
|
||||
|
||||
public setConfig(config: Array<UmbPropertyEditorConfigProperty> | undefined): void {
|
||||
this.#configValues.setValue(config ?? []);
|
||||
}
|
||||
public getConfig(): Array<UmbPropertyEditorConfigProperty> | undefined {
|
||||
return this.#configValues.getValue();
|
||||
}
|
||||
|
||||
public setVariantId(variantId: UmbVariantId | undefined): void {
|
||||
this.#variantId.setValue(variantId);
|
||||
}
|
||||
@@ -156,6 +174,13 @@ export class UmbPropertyContext<ValueType = any> extends UmbContextBase<UmbPrope
|
||||
return this.#variantId.getValue();
|
||||
}
|
||||
|
||||
public setValidation(validation: UmbPropertyTypeValidationModel | undefined): void {
|
||||
this.#validation.setValue(validation);
|
||||
}
|
||||
public getValidation(): UmbPropertyTypeValidationModel | undefined {
|
||||
return this.#validation.getValue();
|
||||
}
|
||||
|
||||
public resetValue(): void {
|
||||
this.setValue(undefined); // TODO: We should get the value from the server aka. the value from the persisted data. (Most workspaces holds this data, via dataset) [NL]
|
||||
}
|
||||
|
||||
@@ -1,21 +1,24 @@
|
||||
import { UmbPropertyContext } from './property.context.js';
|
||||
import type { ManifestPropertyEditorUi } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { umbExtensionsRegistry } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import { css, html, customElement, property, state, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { css, customElement, html, property, state, nothing } from '@umbraco-cms/backoffice/external/lit';
|
||||
import { createExtensionElement } from '@umbraco-cms/backoffice/extension-api';
|
||||
import type { UmbObserverController } from '@umbraco-cms/backoffice/observable-api';
|
||||
import { umbExtensionsRegistry } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import { UmbLitElement } from '@umbraco-cms/backoffice/lit-element';
|
||||
import type {
|
||||
UmbPropertyEditorConfigCollection,
|
||||
UmbPropertyEditorConfig,
|
||||
} from '@umbraco-cms/backoffice/property-editor';
|
||||
import { UmbTextStyles } from '@umbraco-cms/backoffice/style';
|
||||
import {
|
||||
UmbBindValidationMessageToFormControl,
|
||||
UmbFormControlValidator,
|
||||
UmbObserveValidationStateController,
|
||||
} from '@umbraco-cms/backoffice/validation';
|
||||
import type { UmbPropertyTypeAppearanceModel } from '@umbraco-cms/backoffice/content-type';
|
||||
import type { ManifestPropertyEditorUi } from '@umbraco-cms/backoffice/extension-registry';
|
||||
import type {
|
||||
UmbPropertyEditorConfigCollection,
|
||||
UmbPropertyEditorConfig,
|
||||
} from '@umbraco-cms/backoffice/property-editor';
|
||||
import type {
|
||||
UmbPropertyTypeAppearanceModel,
|
||||
UmbPropertyTypeValidationModel,
|
||||
} from '@umbraco-cms/backoffice/content-type';
|
||||
import type { UmbObserverController } from '@umbraco-cms/backoffice/observable-api';
|
||||
|
||||
/**
|
||||
* @element umb-property
|
||||
@@ -112,6 +115,17 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
return this.#propertyContext.getConfig();
|
||||
}
|
||||
|
||||
/**
|
||||
* Validation: Validation settings for the property.
|
||||
*/
|
||||
@property({ type: Object, attribute: false })
|
||||
public set validation(validation: UmbPropertyTypeValidationModel | undefined) {
|
||||
this.#propertyContext.setValidation(validation);
|
||||
}
|
||||
public get validation() {
|
||||
return this.#propertyContext.getValidation();
|
||||
}
|
||||
|
||||
/**
|
||||
* DataPath, declare the path to the value of the data that this property represents.
|
||||
* @public
|
||||
@@ -152,6 +166,9 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
@state()
|
||||
private _orientation: 'horizontal' | 'vertical' = 'horizontal';
|
||||
|
||||
@state()
|
||||
private _mandatory?: boolean;
|
||||
|
||||
#propertyContext = new UmbPropertyContext(this);
|
||||
|
||||
#controlValidator?: UmbFormControlValidator;
|
||||
@@ -169,6 +186,7 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
},
|
||||
null,
|
||||
);
|
||||
|
||||
this.observe(
|
||||
this.#propertyContext.label,
|
||||
(label) => {
|
||||
@@ -176,6 +194,7 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
},
|
||||
null,
|
||||
);
|
||||
|
||||
this.observe(
|
||||
this.#propertyContext.description,
|
||||
(description) => {
|
||||
@@ -183,6 +202,7 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
},
|
||||
null,
|
||||
);
|
||||
|
||||
this.observe(
|
||||
this.#propertyContext.variantDifference,
|
||||
(variantDifference) => {
|
||||
@@ -190,6 +210,7 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
},
|
||||
null,
|
||||
);
|
||||
|
||||
this.observe(
|
||||
this.#propertyContext.appearance,
|
||||
(appearance) => {
|
||||
@@ -197,6 +218,14 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
},
|
||||
null,
|
||||
);
|
||||
|
||||
this.observe(
|
||||
this.#propertyContext.validation,
|
||||
(validation) => {
|
||||
this._mandatory = validation?.mandatory;
|
||||
},
|
||||
null,
|
||||
);
|
||||
}
|
||||
|
||||
private _onPropertyEditorChange = (e: CustomEvent): void => {
|
||||
@@ -297,10 +326,11 @@ export class UmbPropertyElement extends UmbLitElement {
|
||||
return html`
|
||||
<umb-property-layout
|
||||
id="layout"
|
||||
.alias=${this._alias}
|
||||
.label=${this._label}
|
||||
.description=${this._description}
|
||||
.alias=${this._alias ?? ''}
|
||||
.label=${this._label ?? ''}
|
||||
.description=${this._description ?? ''}
|
||||
.orientation=${this._orientation ?? 'horizontal'}
|
||||
?mandatory=${this._mandatory}
|
||||
?invalid=${this._invalid}>
|
||||
${this.#renderPropertyActionMenu()}
|
||||
${this._variantDifference
|
||||
|
||||
Reference in New Issue
Block a user