import type { UIStoreActions } from '@ui-schema/react/UIStoreActions'; import type { SchemaKeywordType, SchemaTypesType, SomeSchema } from '@ui-schema/ui-schema/CommonTypings'; import type { WidgetMatch } from '@ui-schema/ui-schema/matchWidget'; import type { StoreKeys } from '@ui-schema/ui-schema/ValueStore'; import type { WidgetPayload } from '@ui-schema/ui-schema/Widget'; import type { ComponentType, FunctionComponent, ReactNode, Component } from 'react'; import type { WidgetPluginProps, WidgetPluginType } from '@ui-schema/react/WidgetEngine'; import type { WithOnChange, WithValuePlain } from '@ui-schema/react/UIStore'; import type { UIMetaContextBase } from '@ui-schema/react/UIMeta'; import type { List } from 'immutable'; import type { WidgetsBindingRoot } from '@ui-schema/ui-schema/WidgetsBinding'; import type { WidgetProps } from './Widget.js'; /** * note: we can't use ComponentType here, as it leads to problems with FC vs. others and * throwing errors if a component has optional props, which are defined are required in the binding, * which is of course ok, as a widget can always rely on less, just not more (required) as defined in the shared interface * * @experimental mv into central react and use for any component type? * @todo setup CI test to check against lowest possible react version, so that error doesn't occur, * even if dev setup react is "fixed" (react19 has propTypes any) * @todo care about `ClassComponent` at all or enforce `.FC` usage? */ type MinimalClassComponent

= { new (props: P): Component; displayName?: string; }; export type MinimalComponentType

= { (props: P): ReturnType; displayName?: string; } | MinimalClassComponent

; type WidgetsBinding = WidgetProps> = { [K in SchemaKeywordType]?: MinimalComponentType; } & Record>; export interface NoWidgetProps { storeKeys: StoreKeys; scope?: string; widgetId?: string; } export interface GroupRendererProps { storeKeys: StoreKeys; schema: SomeSchema; noGrid?: boolean; style?: {}; className?: string; spacing?: number; children: ReactNode; } export interface ErrorFallbackProps { error: any | null; storeKeys: StoreKeys; type?: string | List; widget?: string; } export interface BindingComponents { /** * Wrapped around each schema layer, used to catch errors during rendering. */ ErrorFallback?: ComponentType; /** * Wraps any `object` that has no custom widget. */ GroupRenderer?: ComponentType; /** * When used with `isVirtual` in `WidgetEngine`, this component is used to render virtual widgets. */ VirtualRenderer?: ComponentType; /** * When `matchWidget` cannot find a widget and throws an `ErrorNoWidgetMatching`, this component is used. */ NoWidget?: ComponentType; /** * Widget plugins, used by `WidgetEngine` to render a schema layer. */ widgetPlugins?: WidgetPluginType[]; } export interface WidgetMatchProps { widgetName: string | undefined; schemaType: SchemaTypesType; widgets?: Record>; } /** * widget binding * - `C` = own `UIMetaContext` definition * - `TW` = own type widgets definition * - `CW` = own custom widgets definition * @todo support OnChange generics * @todo typing `PWidgetPlugins` strict here leads again to the problem with circular types, but why isn't that the cause with `widgetPlugins`? * switched to `any` here, as the stricter typing comes from mui bindingType and WidgetRenderer atm., * and here it must be as loose as possible to infer it correctly, while there is must be infer all at once. */ export type BindingTypeGeneric = Omit & { widgetPlugins?: MinimalComponentType[]; /** * The component which is rendered inside the WidgetEngine, after any widgetPlugin is applied. */ WidgetRenderer?: MinimalComponentType; widgets?: WidgetsBindingRoot; matchWidget?: (props: WidgetMatchProps) => null | WidgetMatch>; }; export type BindingType = WidgetProps> = Omit & BindingTypeWidgets; export type BindingTypeWidgets = WidgetProps> = { widgetPlugins?: MinimalComponentType, keyof WP>>[]; } & { /** * The component which is rendered inside the WidgetEngine, after any widgetPlugin is applied. */ WidgetRenderer?: MinimalComponentType, keyof WP>>; } & { widgets?: WidgetsBinding; } & { matchWidget?: (props: WidgetMatchProps) => null | WidgetMatch>; }; export {};