/**
* @description Type definitions for UI components and rendering
* @summary Defines types and interfaces used throughout the UI decorators library
* This module contains type definitions for field properties, UI metadata,
* and other structures used in rendering UI components.
* @module ui/types
* @memberOf module:ui-decorators
*/
import { OperationKeys } from "@decaf-ts/db-decorators";
import { ElementSizes, UIKeys, UIMediaBreakPoints } from "./constants";
import { DecafEventHandler } from "./DecafEventHandler";
import { DecafComponent } from "./DecafComponent";
import { Model } from "@decaf-ts/decorator-validation";
import { RenderingEngine } from "./Rendering";
import { CrudOperations } from "@decaf-ts/db-decorators";
/**
* @description Interface for defining a UI field or component
* @summary Represents a renderable UI element with properties and children
* This interface defines the structure of a UI field or component, including
* its tag name, properties, and optional children elements.
*
* @interface FieldDefinition
* @template T Additional properties type (defaults to void)
* @memberOf module:ui-decorators
*
* @property {string} tag - The HTML element or component tag name
* @property {string} [rendererId] - Optional ID of the renderer to use
* @property props - Combined properties for the field
* @property {FieldDefinition[]} [children] - Optional child elements
* @property {UIListItemElementMetadata} [item] - Optional list item metadata
*/
export interface FieldDefinition<T = void> {
tag: string;
rendererId?: string;
props: T & FieldProperties;
children?: FieldDefinition<T>[];
item?: UIListItemElementMetadata;
col?: number | string[];
row?: number | string[];
}
/**
* @description Interface for field properties including validation
* @summary Defines common properties and validation rules for UI fields
* This interface defines the standard properties that can be applied to
* UI fields, including basic attributes and validation rules.
*
* @interface FieldProperties
* @memberOf module:ui-decorators
*
* @property {string} name - The name of the field
* @property {string} path - The full hierarchical path of the field
* @property {string} childOf - The parent path of the immediate parent field, if nested
* @property {string} type - The type of the field (e.g., 'text', 'number')
* @property {string|number|Date} value - The current value of the field
* @property {boolean} [hidden] - Whether the field is hidden
* @property {boolean} [disabled] - Whether the field is disabled
* @property {boolean} [required] - Whether the field is required
* @property {boolean} [readonly] - Whether the field is read-only
* @property {number} [maxLength] - Maximum length for text fields
* @property {number} [minLength] - Minimum length for text fields
* @property {number|Date} [max] - Maximum value for numeric or date fields
* @property {number|Date} [min] - Minimum value for numeric or date fields
* @property {string} [pattern] - Regex pattern for validation
* @property {number} [step] - Step value for numeric fields
* @property {string} [format] - Format string for date fields
* @property {string} [equals] - Field must equal the value of this field
* @property {string} [diff] - Field must differ from the value of this field
* @property {string} [lessThan] - Field must be less than this field
* @property {string} [lessThanOrEqual] - Field must be less than or equal to this field
* @property {string} [greaterThan] - Field must be greater than this field
* @property {string} [greaterThanOrEqual] - Field must be greater than or equal to this field
*/
export interface FieldProperties {
name: string;
path: string;
childOf?: string;
type: string;
value: string | number | Date | string[] | number[] | Date[];
hidden?: boolean | CrudOperationKeys[];
disabled?: boolean;
// Validation
required?: boolean;
readonly?: boolean;
maxLength?: number;
minLength?: number;
max?: number | Date;
min?: number | Date;
pattern?: string;
step?: number;
format?: string;
pk?: string;
subType?: string;
multiple?: boolean;
customTypes?: string | string[];
validationMessage?: string | string[];
options?: Record<string, unknown>[];
row?: number;
col?: number;
page?: number;
// pages?: number | IPagedComponentProperties[];
[UIKeys.EQUALS]?: string;
[UIKeys.DIFF]?: string;
[UIKeys.LESS_THAN]?: string;
[UIKeys.LESS_THAN_OR_EQUAL]?: string;
[UIKeys.GREATER_THAN]?: string;
[UIKeys.GREATER_THAN_OR_EQUAL]?: string;
}
/**
* @typedef UIElementMetadata
* @memberOf module:ui-decorators
*/
export type UIElementMetadata = {
tag: string;
props?: Record<string, any>;
serialize?: boolean;
};
/**
* @typedef UIElementMetadata
* @memberOf module:ui-decorators
*/
export type UIModelMetadata = Omit<UIElementMetadata, "serialize">;
/**
* @typedef UIPropMetadata
* @memberOf module:ui-decorators
*/
export type UIPropMetadata = {
name: string;
stringify: boolean;
};
/**
* @typedef CrudOperationKeys
* @memberOf module:ui-decorators
*/
export type CrudOperationKeys =
| OperationKeys.CREATE
| OperationKeys.READ
| OperationKeys.UPDATE
| OperationKeys.DELETE;
/**
* @typedef UIListPropMetadata
* @memberOf module:ui-decorators
*/
export type UIListPropMetadata = {
name: string;
props: Record<string, any>;
};
/**
* @typedef UIListModelMetadata
* @memberOf module:ui-decorators
*/
export type UIListModelMetadata = {
item: UIListItemElementMetadata;
};
/**
* @typedef UIListItemElementMetadata
* @memberOf module:ui-decorators
*/
export type UIListItemElementMetadata = {
tag: string;
props?: Record<string, any>;
mapper?: Record<string, string>;
};
/**
* @typedef UILayoutMetadata
* @memberOf module:ui-decorators
*/
export type UILayoutMetadata = {
cols?: number;
rows?: number | string[];
props?: Record<string, any>;
};
/**
* @typedef UIClassMetadata
* @memberOf module:ui-decorators
*/
export type UIClassMetadata =
| UILayoutMetadata
| UIModelMetadata
| UIHandlerMetadata
| UIListModelMetadata;
export type UILayoutCol =
| number
| typeof ElementSizes.half
| typeof ElementSizes.full
| typeof ElementSizes.auto
| typeof ElementSizes.expand;
export type UIListItemPosition = "title" | "description" | "info" | "subinfo";
export type UIFunctionLike = (...args: any[]) => any | Promise<any>;
export type UIEventHandler = (
instance: DecafComponent<Model>,
renderEngine: RenderingEngine,
...args: any[]
) => any | Promise<any>;
export type UIEventName = keyof Pick<
DecafEventHandler,
"render" | "initialize" | "handleClick" | "refresh"
>;
export type UIEventProperty = Record<string, UIFunctionLike>;
export type UIHandlerMetadata = {
handlers?: UIEventProperty;
};
/**
* @typedef UILayoutPropMetadata
* @memberOf module:ui-decorators
*/
export type UILayoutPropMetadata = {
name: string;
props: Record<string, any> & {
col: UILayoutCol;
row: number | string[];
};
};
/**
* @description Dismissal role returned by toast actions.
* @summary Represents the role reported when a toast is closed, including the
* default cancel role, custom roles, or an undefined result when no role is set.
*
* @typedef {('cancel' | string | undefined)} DecafToastRole
* @memberOf module:ui-decorators
*/
export type DecafToastRole = "cancel" | string | undefined;
export type UIMediaBreakPointsType =
| UIMediaBreakPoints.SMALL
| UIMediaBreakPoints.MEDIUM
| UIMediaBreakPoints.LARGE
| UIMediaBreakPoints.XLARGE;
export type DecafSpinnerOptions = {
cssClass?: string;
duration?: number;
message?: string;
[key: string]: any;
};
export interface DecafModalOptions<T extends DecafComponent<Model>> {
component: T;
componentProps?: Partial<keyof DecafComponent<Model>> &
Record<string, unknown>;
[key: string]: unknown;
}
export type DecafToastOptions = {
message: string;
duration: 3000;
position: "top" | "bottom" | "middle";
color?: string;
[key: string]: any;
};
/**
* @description Interfaces for UI form components
* @summary Defines interfaces for form fields with CRUD operations
* This module contains interfaces that extend basic field properties with
* CRUD operation information for form generation.
* @module ui/interfaces
* @memberOf module:ui-decorators
*/
/**
* @description Form field interface with CRUD operation information
* @summary Extends basic field properties with a specific CRUD operation
* This interface represents a form field that is associated with a specific
* CRUD operation (Create, Read, Update, Delete). It combines all the standard
* field properties with an operation property.
*
* @interface CrudFormField
* @extends FieldProperties
* @memberOf module:ui-decorators
*
* @property {CrudOperations} operation - The CRUD operation associated with this field
*/
export interface CrudFormField extends FieldProperties {
/**
* @description The CRUD operation associated with this field
* @summary Specifies which operation (Create, Read, Update, Delete) this field is for
*/
operation: CrudOperations;
}
/**
* @description Interface for defining a page/step in a multi-step form or wizard
* @summary Provides metadata for individual pages in stepped model forms
* This interface represents a single page or step in a multi-step form workflow.
* It allows defining optional title and description metadata for each page,
* which can be used to display step indicators, progress bars, or navigation labels.
* Used in conjunction with the @uisteppedmodel decorator.
*
* @interface IPagedComponentProperties
* @memberOf module:ui-decorators
*
* @property {string} [title] - Optional title for the page/step (e.g., "Personal Information")
* @property {string} [description] - Optional description providing additional context for the page
*
* @example
* // Define pages for a multi-step wizard
* const wizardPages: IPagedComponentProperties[] = [
* { title: 'Personal Info', description: 'Enter your basic details' },
* { title: 'Contact', description: 'Provide your contact information' },
* { title: 'Review', description: 'Review and confirm your information' }
* ];
*
* @uisteppedmodel('div', wizardPages, true)
* class RegistrationWizard extends Model {
* // Properties with @uipageprop decorators
* }
*/
export interface IPagedComponentProperties {
title?: string;
description?: string;
pages?: number | IPagedComponentProperties[];
rows?: number | string[];
cols?: number | string[];
}
Source