import * as _zenstone_preset_provider from '@zenstone/preset-provider';
import { PresetText, PresetTextCallback } from '@zenstone/preset-provider';
import { RemoteLoadState, RemoteLoaderEventsDefinition, RemoteAsset, RemoteLoaderAssetsProps, RemoteLoaderCallbacks } from '@zenstone/use-remote-loader';
import * as react from 'react';
import { ComponentType, CSSProperties, ComponentProps, ReactNode, RefObject, Dispatch, SetStateAction } from 'react';
import { Position } from 'monaco-editor';
import * as react_jsx_runtime from 'react/jsx-runtime';

declare const useMonacoDebug: (scopeName?: string | string[], isDebug?: boolean) => {
    debug: (...args: unknown[]) => void;
};

declare const MonacoWorkerLabels: {
    readonly editor: readonly [];
    readonly ts: readonly ["typescript", "javascript"];
    readonly html: readonly ["html", "handlebars", "razor"];
    readonly json: readonly ["json"];
    readonly css: readonly ["css", "scss", "less"];
};
declare enum MonacoLoaderProcess {
    Initializing = "Initializing",
    Loading = "Loading",
    Preparing = "Preparing",
    Completed = "Completed"
}
declare enum MonacoReadyState {
    Prepare = 0,
    Mounting = 1,
    Mounted = 2
}

/**
 * 错误 Keys
 */
type MonacoPresetErrorsKeys = 'ERR_WORKERS_EMPTY' | 'ERR_NO_EDITOR_WORKER' | 'ERR_NO_CONTAINER' | 'ERR_INVALID_PRELOAD_PROCESS' | 'ERR_INVALID_CODE_INPUT' | 'ERR_MONACO_UNDEFINED' | 'ERR_UNKNOWN';
type DownloadingParams = {
    isFetchDownload?: boolean;
    percent: number;
};
/**
 * 预设文本
 */
type MonacoPresetTexts = Record<MonacoPresetErrorsKeys, _PresetText> & {
    [MonacoLoaderProcess.Initializing]: _PresetText;
    [MonacoLoaderProcess.Loading]: _PresetTextCallback<DownloadingParams>;
    [MonacoLoaderProcess.Preparing]: _PresetText;
    [MonacoLoaderProcess.Completed]: _PresetText;
};
type MonacoTexts = MonacoPresetTexts & {
    [K in Exclude<string, keyof MonacoPresetTexts>]: _PresetText | _PresetTextCallback;
};
declare const initTexts: () => MonacoPresetTexts;

/**
 * 错误显示组件
 */
type MonacoPresetErrorDisplayProps = _CommonProps & {
    scope?: string;
    error: unknown;
    withContainer?: boolean;
    defaultText?: string;
};
type MonacoPresetLoaderSharedProps = _CommonProps & {
    showText?: boolean;
    progressBar?: MonacoPresetProgressBarProps['mode'];
    dir?: 'row' | 'column';
    width?: CSSProperties['width'];
    withContainer?: boolean;
    defaultText?: string;
};
/**
 * 加载器组件
 */
type MonacoPresetLoaderProps<Q = object> = MonacoPresetLoaderSharedProps & {
    process: MonacoLoaderProcess;
    isFetchDownload?: boolean;
    percent: number;
    state: RemoteLoadState<Q>;
};
type MonacoPresetProgressBarProps = {
    mode?: boolean | 'linear' | 'circular';
    indeterminate?: boolean;
    percent?: number;
    width?: CSSProperties['width'];
};
/**
 * 预设组件
 */
type MonacoPresetComponents = {
    ErrorDisplay: ComponentType<MonacoPresetErrorDisplayProps>;
    Loader: ComponentType<MonacoPresetLoaderProps>;
    ProgressBar: ComponentType<MonacoPresetProgressBarProps>;
};
type MonacoComponents = MonacoPresetComponents & {
    [K in Exclude<string, keyof MonacoPresetComponents>]: ComponentType;
};
declare const initComponents: () => MonacoPresetComponents;

declare const useMonacoPreset: () => {
    getComponent: <N extends string>(name: N) => MonacoComponents[N] | undefined;
    makeChildren: <N extends string>(name: N, props: ComponentProps<MonacoComponents[N]>) => react.ReactNode | null;
    getText: <Key extends string, Params extends MonacoTexts[Key] extends infer T ? T extends MonacoTexts[Key] ? T extends _zenstone_preset_provider.PresetTextCallback<infer P> ? P : unknown : never : never>(key: Key, params?: Params | undefined) => string;
    selectText: <Key extends string, Params_1 extends MonacoTexts[Key] extends infer T ? T extends MonacoTexts[Key] ? T extends _zenstone_preset_provider.PresetTextCallback<infer P> ? P : unknown : never : never>(text: string | null | undefined, key: Key, params?: Params_1 | undefined) => string;
};
type TextsParams<T> = T extends _PresetTextCallback<infer P> ? P : unknown;
declare const useMonacoText: <Key extends keyof MonacoTexts, Params extends TextsParams<MonacoTexts[Key]>>(key: Key, params?: Params) => string;
declare const useMonacoSelectText: <Key extends keyof MonacoTexts, Params extends TextsParams<MonacoTexts[Key]>>(text: string | null | undefined, key: Key, params?: Params) => string;
declare const useMonacoCreateElement: <Name extends keyof MonacoComponents>(name: Name, props: ComponentProps<MonacoComponents[Name]>) => react.ReactNode;

type UseMonacoLoaderTextOptions = {
    defaultText?: string;
    process: MonacoLoaderProcess;
    isFetchDownload?: boolean;
    percent: number;
};
declare const useMonacoLoaderText: ({ defaultText, process, isFetchDownload, percent, }: UseMonacoLoaderTextOptions) => string;

type MonacoTransientStateImagingInput = {
    editor?: monaco.editor.IStandaloneCodeEditor;
    model?: monaco.editor.ITextModel;
};
type MonacoTransientStateImage = {
    position?: Position | null;
    scroll?: monaco.editor.INewScrollPosition;
    source?: string;
};
declare const useMonacoTransientState: () => {
    imaging: ({ editor, model, }: MonacoTransientStateImagingInput) => MonacoTransientStateImage;
};

type _PresetText = PresetText;
type _PresetTextCallback<Params = any> = PresetTextCallback<Params>;
type _MaybePromise<T> = T | Promise<T>;
type _ItOrCallback<T> = T | (() => T);
type _CommonProps = {
    className?: string;
    style?: CSSProperties;
};
type _CommonWithChildrenProps = _CommonProps & {
    children?: ReactNode;
};
/**
 * 事件定义
 *
 * 以 `Record<EventName, EventParams>` 表达
 *
 * 注意 `EventParams` 应该是一个 object 结构
 */
type EventsDefinition = Record<PropertyKey, any>;
/**
 * 事件添加监听器
 *
 * 只用于表达接口实现
 */
interface EventEmitter<E extends EventsDefinition = EventsDefinition> {
    on: <N extends keyof E>(name: N, callback: (params: E[N]) => _MaybePromise<void>) => void;
    off: <N extends keyof E>(name: N, callback: (params: E[N]) => _MaybePromise<void>) => void;
    emit: <N extends keyof E, P = E[N]>(name: N, params: P) => _MaybePromise<void>;
}
/**
 * 单个事件以函数方式的声明
 *
 * 可以是单个函数，或者是多个函数的数组
 */
type EventCallbackDeclaration<T> = ((params: T) => _MaybePromise<void>) | ((params: T) => _MaybePromise<void>[]);
/**
 * 多个事件的函数式声明
 */
type EventsCallbacks<E extends EventsDefinition = EventsDefinition> = Partial<{
    [Key in keyof E]: EventCallbackDeclaration<E[Key]>;
}>;
/**
 * 事件委托者
 */
interface EventsDelegator<E extends EventsDefinition = EventsDefinition> {
    inject(emitter?: EventEmitter<E>): void;
    eject(emitter?: EventEmitter<E>): void;
}
type EventsRecord<O extends object, E extends EventsDefinition = EventsDefinition> = {
    [K in Exclude<keyof O, 'toString' | keyof EventsDelegator>]?: keyof E | (keyof E)[];
};
/**
 * 有效的事件输入类型联合
 */
type EventsInput<E extends EventsDefinition = EventsDefinition> = EventEmitter<E> | EventsCallbacks<E> | EventsDelegator<E>;
type MonacoUpdateLifecycleParams = {
    lifecycleId: number;
    emitter: EventEmitter<MonacoEventsDefinition>;
    monaco?: typeof monaco;
    query?: object;
};
type MonacoMountingParams = {
    monaco: typeof monaco;
};
type MonacoModelPrepareParams = {
    input: MonacoCodeInput;
    language?: monaco.languages.ILanguageExtensionPoint;
    extname?: string;
    uri?: monaco.Uri;
    monaco: typeof monaco;
    editor?: monaco.editor.IStandaloneCodeEditor;
};
type MonacoModelCreateParams = MonacoModelPrepareParams & {
    model: monaco.editor.ITextModel;
};
type MonacoModelChangeParams = MonacoModelCreateParams & {
    event: monaco.editor.IModelContentChangedEvent;
};
type MonacoModelDisposeParams = MonacoModelCreateParams;
type MonacoInputChangeParams = {
    monaco?: typeof monaco;
    input: MonacoCodeInput;
};
type MonacoEditorPrepareParams = {
    mode: 'code' | string;
    monaco: typeof monaco;
    editor?: monaco.editor.IStandaloneCodeEditor;
    model?: monaco.editor.ITextModel;
    image: MonacoTransientStateImage;
};
type MonacoEditorMountParams = {
    mode: 'code' | string;
    monaco: typeof monaco;
    editor: monaco.editor.IStandaloneCodeEditor;
    model?: monaco.editor.ITextModel;
    image: MonacoTransientStateImage;
};
type MonacoEditorDisposeParams = MonacoEditorPrepareParams;
type MonacoEditorFocusAndBlurParams = {
    mode: 'code' | string;
    monaco: typeof monaco;
    editor: monaco.editor.IStandaloneCodeEditor;
    model?: monaco.editor.ITextModel;
};
type MonacoEventsDefinition = RemoteLoaderEventsDefinition & {
    mounting: MonacoMountingParams;
    prepareModel: MonacoModelPrepareParams;
    createModel: MonacoModelCreateParams;
    changeModel: MonacoModelChangeParams;
    disposeModel: MonacoModelDisposeParams;
    changeInput: MonacoInputChangeParams;
    prepareEditor: MonacoEditorPrepareParams;
    /**
     * Editor 挂载成功事件
     */
    mountEditor: MonacoEditorMountParams;
    disposeEditor: MonacoEditorDisposeParams;
};
type MonacoFileCodeInput = {
    filename: string;
    source?: string;
    uri?: string;
    model?: monaco.editor.ITextModel;
};
type MonacoModelInput = monaco.editor.ITextModel;
type MonacoCodeInput = MonacoFileCodeInput;
type MonacoThemeColors = {
    primary: string;
    secondary: string;
    success: string;
    error: string;
    background: string;
    text: string;
    borderColor: string;
};
type MonacoCompleteTheme = {
    name: string;
    displayName: string;
    colors: MonacoThemeColors;
    isDark: boolean;
    data: monaco.editor.IStandaloneThemeData;
};
type MonacoCustomTheme = {
    name: string;
    displayName: string;
    colors: Partial<MonacoThemeColors>;
    isDark: boolean;
    data: monaco.editor.IStandaloneThemeData;
};
type MonacoThemeFrag = {
    name?: string;
    isDark?: boolean;
    colors?: Partial<MonacoThemeColors>;
};
type MonacoThemeInput = undefined | null | boolean | MonacoThemeFrag | string;
type MonacoThemeSkeleton = {
    name: string;
    isDark: boolean;
    colors: MonacoThemeColors;
};
type MonacoCustomThemeCallback = () => MonacoCustomTheme;
type MonacoExtendEnvironment = monaco.Environment & {
    locale?: string;
};

type MonacoPresetRepos = {
    jsdelivr: string | URL;
    unpkg: string | URL;
    jsdmirror: string | URL;
};
type MonacoRepos = MonacoPresetRepos & {
    [K in Exclude<string, keyof MonacoPresetRepos>]: string | URL;
};
declare const setupMonacoRepos: (data: Partial<MonacoRepos>) => void;
declare const monacoRepo: <K extends string>(key: K) => MonacoRepos[K];
declare const repoUrlOf: (repoName: keyof MonacoRepos, path?: string) => URL;
type MonacoConfiguration = {
    version: string;
    repo: keyof MonacoRepos;
    assetsBaseUrl?: string | URL;
    assetsOf: (path?: string) => URL;
};
declare const setupMonaco: (data: Partial<MonacoConfiguration>) => void;
declare const monacoConfig: <K extends keyof MonacoConfiguration>(key: K) => MonacoConfiguration[K];
declare const monacoAssetsOf: (path?: string) => URL;
declare const monacoBaseUrl: (ver?: string) => URL;

declare const MonacoPresetThemes: {
    readonly vs: MonacoCompleteTheme;
    readonly 'vs-dark': MonacoCompleteTheme;
    readonly 'hc-light': MonacoCustomTheme;
    readonly 'hc-black': MonacoCustomTheme;
};
declare const isMonacoBuiltinTheme: (name: string) => name is keyof typeof MonacoPresetThemes;
declare const revertMonacoThemeSkeleton: (input: _ItOrCallback<MonacoThemeInput>) => MonacoThemeSkeleton;
declare const isMonacoCustomTheme: (obj: unknown) => obj is MonacoCustomTheme;
declare const isMonacoThemeData: (obj: unknown) => obj is monaco.editor.IStandaloneThemeData;

declare const isWorkerKey: (key: string, value?: string | null) => boolean;
declare const isMainKey: (key: string, value?: string | null) => boolean;
declare const isWorkerAsset: (asset: RemoteAsset) => asset is RemoteAsset & {
    labels: string[];
};

type KeysMatching<T, V> = {
    [K in keyof T]-?: T[K] extends V ? K : never;
}[keyof T];
type IgnoreMethods = 'registerEvent' | 'inject' | 'eject' | 'toString' | 'setOptions' | 'debug';
declare enum EventsDebug {
    base = 2
}
type EventsDelegatorOptions = {
    debug?: boolean | EventsDebug | number;
    [key: string]: unknown;
};
declare abstract class BaseEventsDelegator<Events extends EventsDefinition = EventsDefinition, Options extends EventsDelegatorOptions = EventsDelegatorOptions> implements EventsDelegator<Events> {
    #private;
    protected scopeName?: string | string[];
    options: Options;
    constructor(options?: Partial<Options>);
    get isDebug(): boolean;
    get isDebugBase(): boolean;
    debug(...args: unknown[]): this;
    setOptions: (options: Partial<Options>) => this;
    register(methodName: Exclude<KeysMatching<this, () => unknown>, IgnoreMethods> | string | (Exclude<KeysMatching<this, () => unknown>, IgnoreMethods> | string)[] | {
        [K in Exclude<KeysMatching<this, () => unknown>, IgnoreMethods> | string]?: keyof Events;
    }, event?: keyof Events): this;
    inject: (emitter?: EventEmitter<Events>) => void;
    eject: (emitter?: EventEmitter<Events>) => void;
}

declare const isEventsDelegator: <E extends EventsDefinition = EventsDefinition>(obj: unknown) => obj is EventsDelegator<E>;
declare const isEventEmitter: <E extends EventsDefinition = EventsDefinition>(obj: unknown) => obj is EventEmitter<E>;
declare const initEventEmitter: <E extends EventsDefinition = EventsDefinition>(input: EventsInput<E> | null | undefined, create?: <E_1 extends EventsDefinition = EventsDefinition>() => EventEmitter<E_1>) => EventEmitter<E>;
type LinkEventMode = 'on' | 'off';
declare const linkEvents: <E extends EventsDefinition = EventsDefinition>(emitter: EventEmitter<E>, input: EventsCallbacks<E> | EventsDelegator<E>, mode?: LinkEventMode) => EventEmitter<E>;
declare const useEventEmitterRef: <E extends EventsDefinition = EventsDefinition>(input: EventsInput<E> | null | undefined) => react.RefObject<EventEmitter<E> | undefined>;

type MakeConfigurable<T extends object> = [
    (data: Partial<T>) => void,
    <K extends keyof T>(key: K) => T[K]
];
declare const makeConfigurable: <T extends object>(presets: T) => MakeConfigurable<T>;

declare const extractExtname: (path: string) => string | undefined;
declare const isFileInput: (input: unknown) => input is MonacoFileCodeInput;
declare const updateMonacoEnvironment: (vars: Partial<MonacoExtendEnvironment>) => void;
declare const debugOutput: (scopeName?: string | string[], ...args: unknown[]) => void;

type MonacoLoaderProps<Query = object> = (Omit<RemoteLoaderAssetsProps<Query>, 'key' | 'assets'> & RemoteLoaderCallbacks<Query>) & {
    assets?: RemoteAsset[];
    isBlobWorker?: boolean;
    children?: ReactNode;
    emitter?: EventEmitter<MonacoEventsDefinition>;
} & MonacoPresetLoaderSharedProps;
declare const MonacoLoader: <Query = object>({ baseUrl: iBaseUrl, assets: iAssets, query, isFetchDownload, isCompressed, isBlobWorker, showText, progressBar, dir, width, withContainer, defaultText, children, emitter, className, style, shouldPreload: iShouldPreload, ...props }: MonacoLoaderProps<Query>) => react_jsx_runtime.JSX.Element;

/******************************************************************************
 * 总体
 ******************************************************************************/
type PresetStyleVars = {
    '--rmBackdropBg': CSSProperties['backgroundColor'];
    '--rmBackdropZIndex': CSSProperties['zIndex'];
    '--rmGap': CSSProperties['gap'];
    '--rmBorderColor': CSSProperties['borderColor'];
    '--rmTextColor': CSSProperties['color'];
};

type MonacoContextType = {
    monacoRef: RefObject<typeof monaco | undefined>;
    emitterRef: RefObject<EventEmitter<MonacoEventsDefinition> | undefined>;
    error: unknown;
    setError: Dispatch<SetStateAction<unknown>>;
    readyState: MonacoReadyState;
    setReadyState: Dispatch<SetStateAction<MonacoReadyState>>;
    lifecycleId: number;
    findLanguage(extname?: string | null): monaco.languages.ILanguageExtensionPoint | undefined;
    refMonaco(): typeof monaco;
    extendThemes(): void;
};
type MonacoProviderProps = {
    texts?: Partial<MonacoTexts>;
    components?: Partial<MonacoComponents>;
    loader?: MonacoLoaderProps;
    events?: EventEmitter<MonacoEventsDefinition> | EventsCallbacks<MonacoEventsDefinition>;
    style?: Partial<PresetStyleVars & CSSProperties>;
    className?: string;
    children?: ReactNode;
    onInit?: (params: MonacoUpdateLifecycleParams) => void;
    onUpdateLifecycle?: (params: MonacoUpdateLifecycleParams) => void;
};
declare const MonacoProvider: ({ texts, components, loader, events, style, className, children, onInit, onUpdateLifecycle, ...props }: MonacoProviderProps) => react_jsx_runtime.JSX.Element;
declare const useMonaco: () => MonacoContextType;

type MonacoCodeEditorRef = MonacoContextType & {
    containerRef: RefObject<HTMLDivElement | null>;
    inputRef: RefObject<MonacoCodeInput>;
    modelRef: RefObject<monaco.editor.ITextModel | undefined>;
    editorRef: RefObject<monaco.editor.IStandaloneCodeEditor | undefined>;
};
type MonacoCodeEditorProps = {
    input: MonacoCodeInput;
    debug?: boolean;
    options?: Partial<Omit<monaco.editor.IStandaloneEditorConstructionOptions, 'value' | 'model'>>;
    className?: string;
    style?: CSSProperties;
    onPrepareModel?: (params: MonacoModelPrepareParams) => void;
    onCreateModel?: (params: MonacoModelCreateParams) => void;
    onChangeModel?: (params: MonacoModelChangeParams) => void;
    onDisposeModel?: (params: MonacoModelDisposeParams) => void;
    onChangeInput?: (params: MonacoInputChangeParams) => void;
    onPrepareEditor?: (params: MonacoEditorPrepareParams) => void;
    onMountEditor?: (params: MonacoEditorMountParams) => void;
    onDisposeEditor?: (params: MonacoEditorDisposeParams) => void;
    onFocus?: (params: MonacoEditorFocusAndBlurParams) => void;
    onBlur?: (params: MonacoEditorFocusAndBlurParams) => void;
};
declare const MonacoCodeEditor: react.ForwardRefExoticComponent<MonacoCodeEditorProps & react.RefAttributes<MonacoCodeEditorRef>>;

export { BaseEventsDelegator, EventsDebug, MonacoCodeEditor, MonacoLoader, MonacoLoaderProcess, MonacoPresetThemes, MonacoProvider, MonacoReadyState, MonacoWorkerLabels, debugOutput, extractExtname, initComponents, initEventEmitter, initTexts, isEventEmitter, isEventsDelegator, isFileInput, isMainKey, isMonacoBuiltinTheme, isMonacoCustomTheme, isMonacoThemeData, isWorkerAsset, isWorkerKey, linkEvents, makeConfigurable, monacoAssetsOf, monacoBaseUrl, monacoConfig, monacoRepo, repoUrlOf, revertMonacoThemeSkeleton, setupMonaco, setupMonacoRepos, updateMonacoEnvironment, useEventEmitterRef, useMonaco, useMonacoCreateElement, useMonacoDebug, useMonacoLoaderText, useMonacoPreset, useMonacoSelectText, useMonacoText, useMonacoTransientState };
export type { DownloadingParams, EventCallbackDeclaration, EventEmitter, EventsCallbacks, EventsDefinition, EventsDelegator, EventsDelegatorOptions, EventsInput, EventsRecord, LinkEventMode, MakeConfigurable, MonacoCodeEditorProps, MonacoCodeEditorRef, MonacoCodeInput, MonacoCompleteTheme, MonacoComponents, MonacoConfiguration, MonacoContextType, MonacoCustomTheme, MonacoCustomThemeCallback, MonacoEditorDisposeParams, MonacoEditorFocusAndBlurParams, MonacoEditorMountParams, MonacoEditorPrepareParams, MonacoEventsDefinition, MonacoExtendEnvironment, MonacoFileCodeInput, MonacoInputChangeParams, MonacoLoaderProps, MonacoModelChangeParams, MonacoModelCreateParams, MonacoModelDisposeParams, MonacoModelInput, MonacoModelPrepareParams, MonacoMountingParams, MonacoPresetComponents, MonacoPresetErrorDisplayProps, MonacoPresetErrorsKeys, MonacoPresetLoaderProps, MonacoPresetLoaderSharedProps, MonacoPresetProgressBarProps, MonacoPresetTexts, MonacoProviderProps, MonacoTexts, MonacoThemeColors, MonacoThemeFrag, MonacoThemeInput, MonacoThemeSkeleton, MonacoTransientStateImage, MonacoTransientStateImagingInput, MonacoUpdateLifecycleParams, UseMonacoLoaderTextOptions, _CommonProps, _CommonWithChildrenProps, _ItOrCallback, _MaybePromise, _PresetText, _PresetTextCallback };
