import { ClassicPreset } from 'rete';
import type { DataflowNode } from 'rete-engine';
import type { AreaExtra } from '../area';
import type { DataType, SocketType } from '../plugins/typed-sockets';
import type { NodeFactory, NodeEditor } from '../editor';
import type { GetRenderTypes } from 'rete-area-plugin/_types/types';
import { type ComponentSupportInterface, type BaseComponent, PythonNodeComponent, R_SocketSelection_NC, type ComponentParams } from '../components';
import { Socket, ExecSocket, Output, Input, Control, InputControl, type InputControlType, type InputControlParams, type SocketValueType, type SocketValueWithDatastructure, type SocketDatastructure } from '../socket';
import type { ConverterNode } from './data/common-data-nodes.svelte';
import type { AreaPlugin, NodeView } from 'rete-area-plugin';
import type { Schemes } from '../schemes';
import type { HTMLInputAttributes } from 'svelte/elements';
import { Rect, type SaveData } from '@selenite/commons';
import { SvelteMap } from 'svelte/reactivity';
/**
 * A map of node classes indexed by their id.
 */
export declare const nodeRegistry: SvelteMap<string, NodeConstructor<Node<Record<string, Socket<SocketType, "scalar" | "array">>, {
    [x: string]: Socket<SocketType, "scalar" | "array">;
}, {
    [x: string]: Control;
}, Record<string, unknown>, Record<string, unknown>>>>;
/**
 * Registers a node class.
 */
export declare function registerNode<Inputs extends {
    [x: string]: Socket<SocketType>;
}, Outputs extends {
    [x: string]: Socket<SocketType>;
}, Controls extends {
    [x: string]: Control;
}, T extends 'abstract' | 'real' = 'real'>(id: string, type?: T): (target: T extends "abstract" ? unknown : NodeConstructor<Node<Inputs, Outputs, Controls>>) => void;
/**
 * Registered converter nodes, from source to target.
 */
export declare const converters: Map<SocketType, Map<SocketType, NodeConstructor<Node<Record<string, Socket<SocketType, "scalar" | "array">>, {
    [x: string]: Socket<SocketType, "scalar" | "array">;
}, {
    [x: string]: Control;
}, Record<string, unknown>, Record<string, unknown>>>>>;
/**
 * Registers a converter node.
 */
export declare function registerConverter<S extends DataType, T extends DataType>(source: S, target: T): (nodeClass: typeof ConverterNode<S, T>) => void;
export declare function hidden(nodeClass: NodeConstructor): void;
export interface OutDataParams {
    socketLabel?: string;
    name: string;
    displayLabel?: boolean;
    displayName?: string;
    isArray?: boolean;
    type?: SocketType;
}
export interface InDataParams<N> {
    socketLabel?: string;
    name: string;
    displayName?: string;
    initial?: unknown;
    control?: InputControlParams<N>;
    isRequired?: boolean;
    isArray?: boolean;
    type?: SocketType;
    index?: number;
}
export interface NodeParams {
    label?: string;
    description?: string;
    name?: string;
    id?: string;
    width?: number;
    height?: number;
    factory?: NodeFactory;
    params?: Record<string, unknown>;
    initialValues?: Node['initialValues'] | Record<string, unknown>;
    state?: Record<string, unknown>;
}
export type NodeSaveData = {
    params: Record<string, unknown>;
    id: string;
    type: string;
    position?: {
        x: number;
        y: number;
    };
    state: Record<string, unknown>;
    inputControlValues: Node['initialValues'];
    selectedInputs: string[];
    selectedOutputs: string[];
};
export type NodeConstructor<N = Node> = {
    new (params?: NodeParams): N;
    id?: string;
    /** Menu path of the node. */
    path?: string[];
    /** Search tags of the node. */
    tags?: string[];
    /** Description of the node. */
    description?: string;
    /** Visibility of node */
    visible?: boolean;
};
/**
 * Decorator that adds a path to a node.
 */
export declare function path<N>(...path: string[]): (target: NodeConstructor<N>) => void;
/**
 * Decorator that adds tags to a node
 */
export declare function tags<N>(...tags: string[]): (target: NodeConstructor<N>) => void;
/**
 * Decorator that adds a description to a node.
 */
export declare function description<N>(description: string): (target: NodeConstructor<N>) => void;
export type SocketsValues<Sockets extends {
    [key in string]: Socket;
}> = {
    [K in keyof Sockets]: SocketValueWithDatastructure<SocketValueType<Sockets[K]['type']>, Sockets[K]['datastructure']>;
};
type DataSocket<T extends Exclude<SocketType, 'exec'> = Exclude<SocketType, 'exec'>> = Socket<T, SocketDatastructure>;
type ExecSocketsKeys<Sockets extends Record<string, DataSocket | ExecSocket>> = {
    [K in keyof Sockets]: Sockets[K] extends DataSocket ? never : K extends string ? K : never;
}[keyof Sockets];
type DataSocketsKeys<Sockets extends Record<string, DataSocket | ExecSocket>> = Exclude<keyof Sockets, ExecSocketsKeys<Sockets>>;
type DataSockets<Sockets extends Record<string, Socket | ExecSocket>> = {
    [K in DataSocketsKeys<Sockets>]: Sockets[K];
};
export declare class Node<Inputs extends Record<string, Socket> = Record<string, Socket>, Outputs extends {
    [key in string]: Socket;
} = {
    [key in string]: Socket;
}, Controls extends {
    [key in string]: Control;
} = {
    [key in string]: Control;
}, State extends Record<string, unknown> = Record<string, unknown>, Params extends Record<string, unknown> = Record<string, unknown>> implements ClassicPreset.Node<Inputs, Outputs, Controls>, DataflowNode, ComponentSupportInterface {
    #private;
    pos: {
        x: number;
        y: number;
    };
    get rect(): Rect;
    visible: boolean;
    get width(): number;
    get height(): number;
    set height(h: number);
    set width(w: number);
    emitResized(): Promise<void>;
    get editor(): NodeEditor | undefined;
    get area(): AreaPlugin<Schemes, AreaExtra> | undefined;
    get view(): NodeView | undefined;
    static description: string;
    static visible: boolean;
    private components;
    static activeFactory: NodeFactory | undefined;
    inEditor: boolean;
    private outData;
    private resolveEndExecutes;
    private naturalFlowExec;
    factory: NodeFactory | undefined;
    protected params: Params;
    static id: string;
    static nodeCounts: number;
    state: {
        name?: string;
    } & Partial<State>;
    get name(): string | undefined;
    set name(n: string);
    description: string | undefined;
    inputs: {
        [key in keyof Inputs]?: Input<Exclude<Inputs[key], undefined>> | undefined;
    };
    outputs: {
        [key in keyof Outputs]?: Output<Exclude<Outputs[key], undefined>> | undefined;
    };
    controls: Controls;
    needsProcessing: boolean;
    sortedInputs: [string, Input<Socket<SocketType, "scalar" | "array">>][];
    sortedOutputs: [string, Output<Socket<SocketType, "scalar" | "array">>][];
    selectedInputs: [string, Input<Socket<SocketType, "scalar" | "array">>][];
    selectedOutputs: [string, Output<Socket<SocketType, "scalar" | "array">>][];
    sortedControls: [string, Control][];
    readonly pythonComponent: PythonNodeComponent;
    readonly socketSelectionComponent: R_SocketSelection_NC;
    readonly ingoingDataConnections: Record<string, Connection<Node, Node>[]>;
    readonly ingoingExecConnections: Record<string, Connection<Node, Node>[]>;
    readonly outgoingDataConnections: Record<string, Connection<Node, Node>[]>;
    readonly outgoingExecConnections: Record<string, Connection<Node, Node>[]>;
    onRemoveIngoingConnection?: (conn: Connection) => void;
    initializePromise?: Promise<void>;
    initialValues?: {
        inputs?: Record<string, unknown>;
        controls?: Record<string, unknown>;
    };
    afterInitialize?: () => void;
    getFactory(): NodeFactory | undefined;
    getState(): Record<string, unknown>;
    addInput<K extends keyof Inputs>(key: K, input: Input<Exclude<Inputs[K], undefined>>): void;
    addOutput<K extends keyof Outputs>(key: K, output: Output<Exclude<Outputs[K], undefined>>): void;
    getConnections(): Connection[];
    outConnections: {
        [x: string]: Connection<Node<Record<string, Socket<SocketType, "scalar" | "array">>, {
            [x: string]: Socket<SocketType, "scalar" | "array">;
        }, {
            [x: string]: Control;
        }, Record<string, unknown>, Record<string, unknown>>, Node<Record<string, Socket<SocketType, "scalar" | "array">>, {
            [x: string]: Socket<SocketType, "scalar" | "array">;
        }, {
            [x: string]: Control;
        }, Record<string, unknown>, Record<string, unknown>>>[];
    };
    inConnections: {
        [x: string]: Connection<Node<Record<string, Socket<SocketType, "scalar" | "array">>, {
            [x: string]: Socket<SocketType, "scalar" | "array">;
        }, {
            [x: string]: Control;
        }, Record<string, unknown>, Record<string, unknown>>, Node<Record<string, Socket<SocketType, "scalar" | "array">>, {
            [x: string]: Socket<SocketType, "scalar" | "array">;
        }, {
            [x: string]: Control;
        }, Record<string, unknown>, Record<string, unknown>>>[];
    };
    constructor(params?: NodeParams);
    label: string;
    get id(): string;
    get previewed(): boolean;
    set previewed(previewed: boolean);
    get selected(): boolean;
    get picked(): boolean;
    hasInput<K extends keyof Inputs>(key: K): boolean;
    removeInput(key: keyof Inputs): void;
    hasOutput<K extends keyof Outputs>(key: K): boolean;
    removeOutput(key: keyof Outputs): void;
    hasControl<K extends keyof Controls>(key: K): boolean;
    addControl<K extends keyof Controls>(key: K, control: Controls[K]): void;
    removeControl(key: keyof Controls): void;
    setState(state: Record<string, unknown>): void;
    getOutgoers(key: string): Node[] | null;
    addComponentByClass<P extends Record<string, unknown>, C extends BaseComponent>(componentClass: new (params: P) => C, params: Omit<P, keyof ComponentParams>): C;
    getPosition(): {
        x: number;
        y: number;
    } | undefined;
    applyState(): void;
    toJSON(): NodeSaveData;
    static fromJSON(data: SaveData<Node>, { factory }: {
        factory?: NodeFactory;
    }): Promise<Node>;
    selectInput(key: string): void;
    deselectInput(key: string): void;
    selectOutput(key: string): void;
    deselectOutput(key: string): void;
    setNaturalFlow(outExec: string | undefined): void;
    getNaturalFlow(): string | undefined;
    fetchInputs(): Promise<SocketsValues<Inputs>>;
    getDataflowEngine(): import("rete-engine").DataflowEngine<Schemes> | undefined;
    getEditor(): NodeEditor | undefined;
    setFactory(nodeFactory: NodeFactory): void;
    getArea(): AreaPlugin<Schemes, AreaExtra> | undefined;
    onEndExecute(): void;
    waitForEndExecutePromise(): Promise<void>;
    inputTypes: Record<string, {
        type: SocketType;
        datastructure: SocketDatastructure;
    }>;
    outputTypes: Record<string, {
        type: SocketType;
        datastructure: SocketDatastructure;
    }>;
    getWaitForChildrenPromises(output: ExecSocketsKeys<Outputs>): Promise<void>;
    execute(input: ExecSocketsKeys<Inputs>, forward: (output: ExecSocketsKeys<Outputs>) => unknown, forwardExec?: boolean): void | Promise<void>;
    addInExec(name?: ExecSocketsKeys<Inputs>, displayName?: string): void;
    addOutData<K extends DataSocketsKeys<Outputs> & string>(key: K, params: {
        datastructure?: Outputs[K]['datastructure'];
        showLabel?: boolean;
        type: Outputs[K]['type'];
        isArray?: boolean;
        label?: string;
        index?: number;
        description?: string;
    }): Socket<Outputs[K]["type"], "scalar" | Outputs[K]["datastructure"]>;
    oldAddOutData({ name, displayName, socketLabel, displayLabel, isArray, type }: OutDataParams): void;
    addInData<K extends DataSocketsKeys<Inputs>>(key: K, params?: {
        type?: Inputs[K]['type'];
        datastructure?: Inputs[K]['datastructure'] extends 'scalar' ? 'scalar' | undefined : Inputs[K]['datastructure'];
        options?: string[];
        control?: Partial<InputControlParams<InputControlType>>;
        label?: string;
        description?: string;
        isRequired?: boolean;
        alwaysShowLabel?: boolean;
        hideLabel?: boolean;
        initial?: SocketValueType<Inputs[K]['type']>;
        index?: number;
        props?: HTMLInputAttributes;
        changeType?: (type: SocketType) => void;
    }): Input<Inputs[K]>;
    oldAddInData<N>({ name, displayName, socketLabel, control, isArray, isRequired, type, index }: InDataParams<N>): Input;
    makeInputControl<T extends InputControlType, D extends SocketDatastructure = SocketDatastructure>(params: InputControlParams<T, D>): InputControl<T>;
    addInputControl<T extends InputControlType>(key: keyof Controls, params: InputControlParams<T>): InputControl<T>;
    addOutExec(name?: ExecSocketsKeys<Outputs>, displayName?: string, isNaturalFlow?: boolean): void;
    processDataflow: () => void;
    getWaitPromises(nodes: Node[]): Promise<void>[];
    getDataWithInputs<K extends DataSocketsKeys<Inputs>>(key: K): Promise<SocketValueWithDatastructure<SocketValueType<Inputs[K]['type']>, Inputs[K]['datastructure']>>;
    getData<K extends DataSocketsKeys<Inputs>>(key: K, inputs?: Record<keyof Inputs, unknown | unknown[]>): SocketValueWithDatastructure<SocketValueType<Inputs[K]['type']>, Inputs[K]['datastructure']>;
    data(inputs?: SocketsValues<Inputs> | undefined): SocketsValues<DataSockets<Outputs>> | Promise<SocketsValues<DataSockets<Outputs>>>;
    setData(key: string, value: unknown): void;
    getOutData(): Record<string, unknown>;
    updateElement(type?: GetRenderTypes<AreaExtra>, id?: string): void;
}
export type ConnectionSaveData = {
    id: string;
    source: string;
    target: string;
    sourceOutput: string;
    targetInput: string;
};
export declare class Connection<A extends Node = Node, B extends Node = Node> extends ClassicPreset.Connection<A, B> {
    visible: boolean;
    get selected(): boolean;
    get picked(): boolean;
    factory?: NodeFactory;
    toJSON(): ConnectionSaveData;
}
export {};
