
declare module 'kapix-components-vue3' {
  import { Component, UnwrapRef, PropType, ComputedRef, WatchStopHandle, DefineComponent, StyleValue } from 'vue'
  import { RouteLocationNormalizedLoaded, RouteLocationRaw, Router, NavigationFailure, RouteRecordNormalized } from 'vue-router'
  import { DefineStoreOptionsBase, PiniaCustomProperties, StateTree, Store, _GettersTree, _StoreWithGetters, _StoreWithState, _StoreWithActions, StoreDefinition, defineStore } from 'pinia'
  import { HeadAttrs } from '@vueuse/head'
  import { ViteSSGContext } from 'kapix-vite-ssg'
  import { ScrollOptions } from 'vue-scrollto'
  import type { ToastInterface, PluginOptions, TYPE, POSITION } from '@brackets/vue-toastification'
  import type { ToastID } from '@brackets/vue-toastification/dist/types/types/common'
  import type { ToastContent, ToastOptions } from '@brackets/vue-toastification/dist/types/types/toast'
  import { IEntityModel, IGraphqlRequestQueryOptions } from 'kapix-graphql-prisma-client-type'
  import '@vue/runtime-core'

  export type Nullable<T> = T | null | undefined
  export type KeyValuePair<V = any> = {
    [key: string]: V
  }
  export type PartialAndNullable<T> = {
    [P in keyof T]?: Nullable<T[P]>;
  }
  export type KeyPair = KeyValuePair<string>
  export type KapixBuiltWithOptions = {
    logoOnHomeOnly?: boolean
    hide?: boolean
    appStore?: boolean
  }
  
  export type KapixAnchorOptions = {
    waitPageLoadingDuration?: number
    scrollDuration?: number
  }

  type Translate = (key: string, defaultValue?: Nullable<string | number | Date>, options?: object | Array<any>) => any
  export type UserModule = (ctx: ViteSSGContext, options?: {
    appVersion?: string
    i18n?: {
      factory?: () => any
      $translate?: Translate
    }
    jestMode?: boolean
    kapixBuiltWithOptions?: KapixBuiltWithOptions
    kapixAnchorOptions?: KapixAnchorOptions
  }) => void
  export type KapixPlugin<T = any> = (ctx: ViteSSGContext, options?: T) => void

  export type KapixComponentsPluginType = {
    install: UserModule
  }
  export const install: UserModule
  export const toastificationPlugin: (ctx: ViteSSGContext, options?: PluginOptions) => void
 
  export const useToast: () => ToastInterface & {
    warningAsync: (content: ToastContent, options?: ToastOptions & { type?: TYPE.WARNING | undefined }) => Promise<ToastID>
    successAsync: (content: ToastContent, options?: ToastOptions & { type?: TYPE.SUCCESS | undefined }) => Promise<ToastID>
    errorAsync: (content: ToastContent, options?: ToastOptions & { type?: TYPE.ERROR | undefined }) => Promise<ToastID>
    infoAsync: (content: ToastContent, options?: ToastOptions & { type?: TYPE.INFO | undefined }) => Promise<ToastID>
  }
  export const kapixContext: Partial<ViteSSGContext<true>> & { 
    $route: Nullable<RouteLocationNormalizedLoaded>
    $router: Nullable<Router>
    appVersion?: string
    accessToken?: string
    i18n: {
      $translate: Translate
      factory: () => { locale: string }
    }
    user?: Partial<{
      email: string
      userName: string
      displayName: string
    }>
    config: {
      showKeyboardShortcutTooltip?: Nullable<boolean>
    }
    formatDateProvider?: Promise<(date: Nullable<Date | string | number>, format?: string) => Nullable<Date | string | number>>
    DEBUG?: boolean
    JITSI_BASE_ROOM_NAME?: string
    UPLOADCARE_PUBLIC_KEY?: string
    GOOGLE_MAP_API_KEY?: string
  }
  export type TwitterCard = 'summary' | 'summary_large_image' | 'app' | 'player'
  export type ShowTooltip = (component: Component, tooltipOptions?: { options?: Partial<ITooltipOptions>; context?: KeyValuePair; id?: string }) => Promise<ITooltipInstancePromiseResult>
  export type KaElementVm = {
    getHtmlElement: () => HTMLElement
    scrollTo: (options: { duration?: number; left?: number; top?: number; } = { duration = 700 }) => Promise<void>
    scrollToStart: () => Promise<void>
    scrollToEnd: () => Promise<void>
    showTooltip: ShowTooltip
    closeTooltip <T>(value?: T): Promise<ITooltipInstance>
    closeAllTooltips (): void

    entityItem?: KeyValuePair
    parentList?: {
      addItem: (item?: KeyValuePair) => void
      removeItem: (item?: KeyValuePair) => boolean
    }
  }
  export type KaElementClickEvent = {
    vm?: KaElementVm
    original?: EventTarget
    removeItem: () => boolean
  }
  export type KaElement = {
    value: any
    options: KapixPropType<IPropOptions>
    style: KeyValuePair
    getHtmlElement: () => HTMLElement
    scrollTo: (options: { duration?: number; left?: number; top?: number; } = { duration = 700 }) => Promise<void>
    showTooltip: ShowTooltip
    scrollToStart: () => Promise<void>
    scrollToEnd: () => Promise<void>
    previousDisplay: () => Nullable<string>
    previousOrLoopToLastDisplay: () => Nullable<string>
    nextDisplay: () => Nullable<string>
    nextOrLoopToFirstDisplay: () => Nullable<string>
    display?: Nullable<string>
  }

  export type KaElementMap = {
    [key: string]: KaElement
  }

  export type DialogWrapperOptions = {
    background: boolean | string
    'border-radius': boolean | number | string
    'close-on-back': boolean
    'content-class': string
    depressed: boolean
    fullscreen: boolean
    height: string | number
    'max-width': string | number
    'no-click-animation': boolean
    'overlay-background': boolean | string
    persistent: boolean
    scrollable: boolean
    transition: string
    width: string | number
    onClose: () => void
  }

  export class DialogWrapper {
    constructor (template: Component | (() => any | string) | string, options?: Partial<DialogWrapperOptions>)
    open (options?: Partial<DialogWrapperOptions>)
    close ()
  }

  export type MetaOptions = {
    title: Nullable<string>
    description?: Nullable<string>
    image?: Nullable<string>
    publishedTime?: Nullable<Date>
    modifiedTime?: Nullable<Date>
    canonicalUrl?: Nullable<string>
    twitterCard?: Nullable<TwitterCard>
    twitterSite?: Nullable<string>
    twitterCreator?: Nullable<string>
  }

  // custom pinia store
  export type _CustomStoreThisType<OriginaStore, S extends StateTree, G, A> = UnwrapRef<S>
  & {
    getStoreInstance(storeId?: number): _CustomStoreThisType<OriginaStore, S, G, A>
    getStoreInstances(): Array<_CustomStoreThisType<OriginaStore, S, G, A>>
    newStoreInstance(): _CustomStoreThisType<OriginaStore, S, G, A>
  }
  & OriginaStore
  & _StoreWithGetters<G>
  & _GettersTree<S>
  & _StoreWithActions<A>
  & PiniaCustomProperties

  export declare interface DefineCustomStoreImplementationOptions<OriginaStore, S extends StateTree, G, A> extends DefineStoreOptionsBase<S, Store<string, S, G, A>> {
    state?: () => S

    getters?: G & ThisType<_CustomStoreThisType<OriginaStore, S, G, A>>

    actions?: A & ThisType<_CustomStoreThisType<OriginaStore, S, G, A>>

    hydrate?(storeState: UnwrapRef<S> & OriginaStore, initialState: UnwrapRef<S> & OriginaStore): void
  }

  export type CustomStoreImplementation<OriginalStore, S extends StateTree = {}, G extends _GettersTree<S> = {}, A = {}> =
    Omit<DefineCustomStoreImplementationOptions<OriginalStore, S, G, A>, 'id'>

  export type CustomStoreImplementationInstance<OriginalStore, S extends StateTree = {}, G extends _GettersTree<S> = {}, A = {}> =
    UnwrapRef<S>
    & OriginalStore
    & _StoreWithState<string, S, G, A>
    & _StoreWithGetters<G>
    & _StoreWithActions<A>
    & PiniaCustomProperties

  export interface CustomStoreImplementationOptions { state?: () => KeyValuePair; getters?: KeyValuePair; actions?: KeyValuePair }

  export type MergeCustomStore<OriginaStore> = {
    getStoreInstance(storeId?: Nullable<StoreIdentifier>): MergeCustomStore<OriginaStore>
    getStoreInstances(): Array<MergeCustomStore<OriginaStore>>
    newStoreInstance(storeId?: Nullable<StoreIdentifier>): MergeCustomStore<OriginaStore>
  } & OriginaStore

  // helpers

  /**
   * Add an event listener to an element
   * @param {HTMLElement | Window} el - The element to attach the event to.
   * @param {string} event - The name of the event to listen for.
   * @param handler - The function that will be called when the event is fired.
   * @param [passive=false] - If true, the event handler will be fired when the event is fired by the
   * browser. If false, the event handler will be fired when the event is fired by the user.
   * @returns A function that removes the event listener.
   */
  export const addEvent: (el: HTMLElement | Window, event: string, handler: (args: any) => void, passive: boolean) => undefined | (() => void)

  export interface IOptionsState {
    selected?: Nullable<boolean>
    hover?: Nullable<boolean>
  }

  export type TooltipPlacement = 'auto-start'
  | 'auto'
  | 'auto-end'
  | 'top-start'
  | 'top'
  | 'top-end'
  | 'right-start'
  | 'right'
  | 'right-end'
  | 'bottom-end'
  | 'bottom'
  | 'bottom-start'
  | 'left-end'
  | 'left'
  | 'left-start'

  
  export type KaTooltipPlacement = TooltipPlacement | 'full-screen'
  export interface ITooltipOptions {
    content: string
    placement?: KaTooltipPlacement
    arrow: boolean
    theme: string
    trigger: string
    hideOnClick?: boolean
    history?: boolean
  }
  export interface IGlobalTooltipOptions {
    content: string
    placement: TooltipPlacement
    fullScreen: boolean
    history: boolean
    arrow: boolean
    theme: string
    trigger: string
    hideOnClick: boolean
    hideOnNavigation?: boolean
    onShow: (instance: ITooltipInstance) => void
    onShown: (instance: ITooltipInstance) => void
    onHide: ((instance: ITooltipInstance) => void) | ((instance: ITooltipInstance) => boolean)
    onHidden: (instance: ITooltipInstance) => void
  }
  
  export interface ITooltipInstancePromiseResult<T = any> {
    result?: T
    data: Nullable<KeyValuePair>
    instance: ITooltipInstance
  }
  export interface ITooltipInstance {
    context?: KeyValuePair
    options: KeyValuePair
    visible: boolean
    canClose: boolean
    canCloseAll: boolean
    visiblePromise?: Promise<Omit<ITooltipInstancePromiseResult, 'result'>>
    closePromise?: Promise<ITooltipInstancePromiseResult>
    toggleVisibility: () => Promise<ITooltipInstance>
    show: () => Promise<ITooltipInstance>
    showUntilClose: <T>() => Promise<ITooltipInstancePromiseResult<T>>
    close: <T>(value?: T) => Promise<ITooltipInstance>
    hide: <T>(value?: T) => Promise<ITooltipInstance>
    closeAll: () => ITooltipInstance
    updateOptions: (options: Partial<ITooltipOptions>) => ITooltipInstance
    updateData: (data: KeyValuePair) => ITooltipInstance
    dispose: () => void
  }

  export interface IRegisterTooltipOptions {
    context?: KeyValuePair
    options?: Partial<IGlobalTooltipOptions>
    singletonId?: string
    component: any
  }

  export function registerTooltip (tooltipOptions: IRegisterTooltipOptions): ITooltipInstance

  export type CssUnit = '%' | 'px' | 'vh' | 'vw'
  export type FontFormat = Array<'bold' | 'italic' | 'underlined' | 'strikethrough'>
  export type AlignItem = null | 'stretch' | 'flex-start' | 'center' | 'flex-end'
  export type MixBlendMode = 'multiply' |
    'screen' |
    'overlay' |
    'darken' |
    'lighten'
  export type ImageFit = null | 'cover' | 'contain'
  type IGradientColor = string | { Angle?: number; Colors: string[] }
  type BorderStyle =  'inherit' | 'none' | 'hidden' | 'dotted' | 'dashed' | 'solid' | 'double' | 'groove' | 'ridge' | 'inset'  | 'outset'

  export interface IKaStyle {
    // outer
    position: null | 'absolute' | 'sticky' | 'fixed'
    x: number
    xAlign: AlignItem
    xUnit: CssUnit
    y: number
    yAlign: AlignItem
    yUnit: CssUnit
    zIndex: number
    order: number

    w: number
    widthUnit: CssUnit
    maxWidth: number
    h: number
    heightUnit: CssUnit
    maxHeight: number
    minH: number
    minHUnit: CssUnit
    maxHUnit: CssUnit
    minW: number
    minWUnit: CssUnit
    maxWUnit: CssUnit
    hAlign: AlignItem
    vAlign: AlignItem
    alignSelf: any

    mixBlendMode: MixBlendMode
    img: string | File
    imgFit: ImageFit
    backgroundClip: string
    backgroundColor: IGradientColor
    opacity: number
    color: IGradientColor

    // inner
    innerImg: string | File
    innerImgFit: string
    innerBackgroundClip: string
    innerBackgroundColor: IGradientColor
    innerOpacity: string

    // label
    labelColor: string
    labelFontSize: number
    labelFontFamily: string
    labelFontFormat: FontFormat
    labelWidth: number
    labelWidthUnit: CssUnit
    minLabelWidth: number

    // border
    border: Array<number> | number 
    borderColor: string
    borderRadius: Array<number> | number 
    borderStyle: Array<BorderStyle> | BorderStyle

    // property
    zoom: number
    fontColor: CssColor
    fontSize: number
    fontFamily: string
    fontFormat: FontFormat
    fontWeight: string | number
    fontSizeUnit: CssUnit
    adjustFontSize: boolean
    textAlign: 'justify' | 'left' | 'center' | 'right'
    lineHeight: number
    letterSpace: number
    textShadow: Array<{
      h: number 
      v: number 
      br: number
      c?: string
    }>
    boxShadow: Array<{
      h: number 
      v: number 
      br: number
      sr: number
      c?: string
      inset?: boolean
    }>
    dropShadow: {
      h: number 
      v: number 
      br: number
      c?: string
    }
    blur: number
    textTransform: string
    strokeColor: CssColor
    strokeWidth: number

    padding: string
    paddingUnit: CssUnit
  }
  export interface IPropOptions {
    keyboard?: string[] | string | {
      keys: string[] | string
      name?: Nullable<string>
      contextName?: Nullable<string>
      push?: boolean
      once?: boolean
      focus?: boolean
      propagate?: boolean
    }
    click?: Nullable<(context: KaElementClickEvent) => void>
    mouseover?: Nullable<(context: KaElementClickEvent) => void>
    mouseleave?: Nullable<(context: KaElementClickEvent) => void>
    onLoad?: Nullable<(context: KaElementClickEvent) => void>
    loading?: Nullable<boolean>
    ripple?: boolean
    disabled?: boolean
    showLoadingAsyncClick?: boolean
    $state?: Partial<IOptionsState>
    $inheritState?: Partial<IOptionsState>
    style?: Nullable<PartialAndNullable<IKaStyle>>
    hasTransform?: boolean
    keepAlive?: boolean
    tooltip?: Partial<ITooltipOptions>
    // label
    labelPosition?: 'hidden' | 'top' | 'top-center' | 'left' | 'left-center'  |'left-center-full' | 'right-center'
    // displays
    displays?: Array<string>
    display?: Nullable<string>
    // visibility
    visibilityDelay?: number
    hidden?: false | 0 | null | true
    // seo
    ariaLabel?: Nullable<string>
    href?: Nullable<string | { 
      path?: string; 
      name?: string; 
      hash?: string
      groupByLayout?: boolean
    }>
    animationIn?:
      Nullable<'fadeIn' | 'fadeInDown' | 'fadeInDownBig' | 'fadeInLeft' | 'fadeInLeftBig' | 'fadeInRight' | 'fadeInRightBig' | 'fadeInUp' | 'fadeInUpBig' |
      'bounceIn' | 'bounceInDown' | 'bounceInLeft' | 'bounceInRight' | 'bounceInUp' |
      'rotateIn' | 'rotateInDownLeft' | 'rotateInDownRight' | 'rotateInUpLeft' | 'rotateInUpRight' |
      'bounce' |
      'flash'|
      'pulse'|
      'rubberBand'|
      'shake'| 'headShake'|
      'tada'|
      'wobble'|
      'jello'|
      'flipInX'| 'flipInY'|
      'lightSpeedIn'|
      'jackInTheBox'|
      'rollIn'|
      'zoomIn' | 'zoomInDown'>,
      animationOut?: Nullable<'fadeOut' | 'fadeOutDown' | 'fadeOutDownBig' | 'fadeOutLeft' | 'fadeOutLeftBig' | 'fadeOutRight' | 'fadeOutRightBig' | 'fadeOutUp' | 'fadeOutUpBig' |
      'bounceOut' | 'bounceOutDown' | 'bounceOutLeft' | 'bounceOutRight' | 'bounceOutUp' |
      'rotateOut' | 'rotateOutDownLeft' | 'rotateOutDownRight' | 'rotateOutUpLeft' | 'rotateOutUpRight' |
      'flipOutX' | 'flipOutY'|
      'lightSpeedOut'|
      'hinge'|
      'rollOut'>,
      animation?: Nullable<'in-out' | 'pulse' | 'beat' | 'left-rotation' | 'right-rotation' | 'flash' | 'random' | 'notification' | 'float-vert'>
      // lazy
      lazyOptions?: Nullable<{
        preloadData?: boolean
        throttle?: number,
        once?: boolean,
        intersection?: { threshold: number }
      }>
  }

  type KapixPropType<T> = {
    new(value?: Partial<T>): Partial<T>
    (value: Partial<T>): Partial<T>
  } | PropType<T | null | undefined>
  type ModelValuePropType = PropType<Nullable<string | Array | Object | boolean | Date | number>> // (StringConstructor | ArrayConstructor | ObjectConstructor | BooleanConstructor | DateConstructor | NumberConstructor)[] | null
  
  export type KaProps<Options = {}, ValueType extends PropType = ModelValuePropType> = {
    code: {
      type: StringConstructor
    }
    instanceClass: {
      type: PropType<string | null | undefined>
    }
    data: {
      type: PropType<object | null | undefined> // TODO remove, should be only in container/list etc...
    }
    value: {
      type: ValueType
    }
    'sm-value': {
      type: ValueType
    }
    'xs-value': {
      type: ValueType
    }
    inner: {
      type: PropType<boolean | null | undefined>
    }
    skeleton: {
      type: PropType<boolean | null | undefined>
    }
    // modelValue: {
    //   type: ValueType
    // }
    options: {
      type: KapixPropType<IPropOptions & Options>
    }
    sm: {
      type: KapixPropType<IPropOptions & Options>
    }
    xs: {
      type: KapixPropType<IPropOptions & Options>
    }
    hover: {
      type: KapixPropType<IPropOptions & Options>
    }
    selected: {
      type: KapixPropType<IPropOptions & Options>
    }
    'sm-hover': {
      type: KapixPropType<IPropOptions & Options>
    }
    'xs-hover': {
      type: KapixPropType<IPropOptions & Options>
    }
    'sm-selected': {
      type: KapixPropType<IPropOptions & Options>
    }
    'xs-selected': {
      type: KapixPropType<IPropOptions & Options>
    }
  }
  /* It's a way to create a `kaProps` object that has all the props that can be used with the
  `<ka-input>` component. */
  export const kaProps: KaProps

  /**
   * It returns a set of props that can be used with the `<ka-input>` component.
   * @param {PropType<T> | true | null} type - The type of the input. If you want to use a custom type,
   * you can pass in a string or a type. If you want to use a built-in type, you can pass in a string. If
   * you want to use no type, you can pass in null.
   * @returns A function that returns a function.
   */
  export function inputProps<ExtendType = {}, ValueType = any> (type: PropType<Nullable<ValueType>> | true | null) {
    return {
      ...kaProps as KaProps<PartialAndNullable<{ 
        placeholder: string
        debounce: number
        editable: boolean
        required: boolean
        persistence: null | 'localStorage' | 'sessionStorage'
      }> & ExtendType, PropType<Nullable<ValueType>>>,
      modelValue: {
        type,
        default: undefined
      }
    }
  }

  export function extendsKaProps<Options, ValueType = string | Array | Object | boolean | Date | number> (): KaProps<Options, PropType<Nullable<ValueType>>>

  /**
   * It creates a type that can be used to define props for a component.
   * @param {PropType<T> | true | null} type - the type of the parameter, which is either `"text"`,
   * `"number"`, `"boolean"`, or `"null"`
   * @returns The return value is a dictionary containing the following keys:
   * - value - The value of the property
   * - type - The type of the property
   * - required - Whether the property is required
   * - default - The default value of the property
   * - lazyValue - The value of the property
   * - options - The options of the property
   * - deactivated - Whether the property is deactivated
   */
  export function kapixProps<T> (type: PropType<T> | true | null) {
    return {
      code: {
        type: String,
        default: undefined,
        required: false
      },
      templateClass: {
        type: String,
        default: undefined,
        required: false
      },
      scrollerClass: {
        type: String,
        default: undefined,
        required: false
      },
      value: {
        type: PropType<T>,
        required: false,
        default: undefined
      },
      lazyValue: {
        type,
        required: false,
        default: undefined
      },
      options: {
        type: Object,
        default () {
          return NOOP
        },
        required: true
      },
      deactivated: {
        type: Boolean,
        default: false,
        required: false
      },
      disabled: {
        type: Boolean,
        default: false,
        required: false
      },
      editable: { // to be able to v-bind inputProps
        type: Boolean,
        default: false
      },
      data: { // required to set scrollPosition of list for ex
        type: Object,
        default: null
      },
      md: {
        type: Boolean,
        default: true,
        required: false
      },
      sm: {
        type: Boolean,
        default: false,
        required: false
      },
      xs: {
        type: Boolean,
        default: false,
        required: false
      }
    }
  }

  /**
   * It returns a set of props that can be used to create a kapix input.
   * @param {PropType<T> | true | null} type - The type of the input. If you want to use a custom type,
   * you can pass it here. If you want to use a built-in type, you can pass it as a string. If you want
   * to use a built-in type, but want to use a custom validator,
   * @returns A function that returns a function.
   */
  export function kapixInputProps<T> (type: PropType<T> | true | null) {
    return {
      ...kapixProps(type),
      editable: {
        type: Boolean,
        default: true
      },
      modelValue: {
        type: PropType<T>,
        default: undefined
      }
    }
  }

  // Types
  export type BreakpointName = 'xs' | 'sm' | 'md' | 'lg' | 'xl'

  // Interfaces
  export interface BreakpointThresholds {
    xs: number
    sm: number
    md: number
    lg: number
  }

  export interface IBreakpoint {
    height: number
    lg: boolean
    lgAndDown: boolean
    lgAndUp: boolean
    lgOnly: boolean
    md: boolean
    mdAndDown: boolean
    mdAndUp: boolean
    mdOnly: boolean
    name: BreakpointName
    sm: boolean
    smAndDown: boolean
    smAndUp: boolean
    smOnly: boolean
    width: number
    xl: boolean
    xlOnly: boolean
    xs: boolean
    xsOnly: boolean
    mobile: boolean
    mobileBreakpoint: number | BreakpointName
    thresholds: BreakpointThresholds
    scrollBarWidth: number
    ssr: boolean
  }

  export type TooltipInstance = { component: any; options: KeyValuePair }

  export const tooltips: { instances: Array<TooltipInstance>; containerId: string; closeAll: () => void }

  export const responsiveStore: { breakpoint: IBreakpoint }
  /**
   * It takes a theme object and returns a new theme object with the same properties, but with the
   * responsive suffixes removed.
   * @param {T} theme - T - the theme object
   * @returns A new object with the same properties as the original object, but with the properties that
   * have the responsive suffix removed.
   */
  export function toResponsiveTheme<T = KeyValuePair> (theme: T): T

  export type ThemeCssVarType = 'fontFamily' | 'color' | 'gradientColor' | 'imageViewer' | 'borderRadius' | 'boxShadows' | 'number'

  export type ThemeSchema = KeyValuePair<Nullable<ThemeCssVarType>>
  /**
   * The `appThemeToCssVars` function takes a schema and theme object as input and returns a theme style
   * object with CSS variables based on the schema and theme values.
   * @param schema - A key-value pair object that defines the schema for the theme. The keys represent
   * the names of the theme properties (e.g., 'fontFamily', 'color', 'gradientColor', 'imageViewer'), and
   * the values represent the business type associated with each property (e.g., 'fontFamily',
   * @param {KeyValuePair} theme - The `theme` parameter is an object that contains key-value pairs
   * representing the theme properties. Each key represents a theme property name, and the corresponding
   * value represents the value of that property.
   * @returns The function `appThemeToCssVars` returns an object `themeStyle` which contains CSS variable
   * names as keys and their corresponding values based on the provided `schema` and `theme` parameters.
   */
  export function appThemeToCssVars (schema: ThemeSchema, theme: KeyValuePair): KeyValuePair
 
  /**
   * The function `createAppThemeCssVars` creates and updates CSS variables for a given app theme.
   * @param appData - An object that contains the theme CSS variables.
   */
  export function createAppThemeCssVars (appData: { themeCssVars: KeyValuePair })
  
  /**
   * If the user passes an element, scroll to that element. If the user passes a class name, scroll to
   * the first element with that class name. If the user passes a selector, scroll to the first element
   * that matches that selector. If the user passes a string, scroll to the first element with that ID
   * @param {ScrollOptions} options - ScrollOptions
   * @returns Promise.
   */
  export const scrollTo: (options: ScrollOptions) => Promise<void>

  /**
   * Generate the meta tags for a page
   * @param {MetaOptions} options - MetaOptions
   * @returns An array of objects that contain the name and content of the meta tags.
   */
  export const generateMeta: (options: MetaOptions) => Array<HeadAttrs>

  /**
   * It takes a color value and returns the inverted color value.
   *
   * If the color value is a gradient, it returns the inverted gradient.
   *
   * If the color value is a gradient, and the second parameter is true, it returns the inverted gradient
   * with black or white as the first color.
   *
   * If the color value is a gradient, and the second parameter is false, it returns the inverted
   * gradient with the first color inverted.
   *
   * If the color value is a gradient, and the second parameter is a color, it returns the inverted
   * gradient with the second parameter as the first color.
   *
   * If the color value is a gradient, and the second parameter is a gradient, it returns the inverted
   * gradient with the second parameter as the first gradient.
   *
   * If the color value is a gradient, and the second parameter is a gradient, and the second parameter
   * is a gradient, it returns the inverted gradient with
   * @param value - The value to invert.
   * @param returnBlackOrWhite - If true, the function will return black or white if the color is too
   * dark or too light.
   */
  export const invertGradientColor: (color: Nullable<string | { Angle?: number; Colors: string[] }>, returnBlackOrWhite?: boolean) => string

  /**
   * It takes a color string, converts it to a tinycolor object, inverts the color components, pads each
   * with zeros, and returns the inverted color string
   * @param color - The color to invert.
   * @param returnBlackOrWhite - If true, the function will return either black or white, depending on
   * the luminosity of the color. If false, it will return the inverted color.
   * @returns A function that takes two arguments, color and returnBlackOrWhite.
   */
  export const invertColor: (color: Nullable<string>, returnBlackOrWhite?: boolean) => string

  export const prettifyEmail: (email: Nullable<string>) => string

  export const prettifyName: (phone: Nullable<string>) => string

  export const $first: (conditions: Array<any | undefined>) => any

  export const $isEqual: (val1: any, val2: any) => boolean

  /**
   * It returns true if the current route is the same as the route passed in.
   * @param {RouteLocationRaw} route - RouteLocationRaw
   * @returns A function that returns a boolean.
   */
  export const isCurrentRoute: (route: RouteLocationRaw) => boolean

  /**
   * It checks if the current route is equal to the route passed as a parameter.
   * @param hrefItem - Partial<RouteLocationNormalized>
   * @returns A function that returns a boolean.
   */
  export const isEqualsToCurrentRoute: (hrefItem: Partial<RouteLocationNormalized>) => boolean

  /**
 * The `navigateTo` function is used to navigate to a specific route in a TypeScript application, with
 * options for resetting navigation, using hash navigation, and waiting for scrolling to complete.
 * @param {KeyValuePair | string} route - The route parameter can be either a KeyValuePair object or a
 * string. If it is a string, it represents the path to navigate to. If it starts with a special
 * character, it is treated as a special route and the corresponding guard page is navigated to. If it
 * is a KeyValuePair object, it
 * @param [resetNavigation=false] - A boolean value indicating whether to reset the navigation history
 * or not. If set to true, the navigation history will be cleared before navigating to the new route.
 * If set to false (default), the new route will be added to the navigation history.
 * @param [forceHash=false] - The `forceHash` parameter is a boolean value that determines whether to
 * force the use of the provided hash value in the route. If set to `true`, the provided hash value
 * will be used as is. If set to `false` or not provided, the hash value will be modified to exclude
 * @param [waitScrollTo=true] - The `waitScrollTo` parameter is a boolean flag that determines whether
 * the function should wait for the scroll animation to complete before resolving the navigation
 * promise. If `waitScrollTo` is set to `true`, the function will wait for the scroll animation to
 * complete before resolving the promise. If `wait
 * @returns a Promise that resolves to the result of the navigation operation.
 */
  export const navigateTo: (route: KeyValuePair | string, resetNavigation = false, forceHash = false, waitScrollTo = true) => Promise<void | NavigationFailure | undefined>

  /**
 * The function `getRouteByGuard` takes a router and a guard name as input and returns a route that has
 * the specified guard applied to it.
 * @param {Router} router - The `router` parameter is an instance of the Vue Router. It is used to
 * access the routes defined in the router configuration.
 * @param {string} guardName - The `guardName` parameter is a string that represents the name of the
 * guard. It is used to filter the routes based on the presence of a specific guard in their meta
 * property.
 * @returns a RouteRecordNormalized object or undefined.
 */
export function getRouteByGuard (router: Router, guardName: string): RouteRecordNormalized | undefined

  export type StoreIdentifier = number | string
  /**
   * If we're on the client, return an empty array, otherwise return the fakedStoreIds array.
   * @returns An array of numbers.
   */
  export const initAliveStoreIds: () => StoreIdentifier[]

  /**
   * It tries to parse a float, and if it fails, it returns undefined.
   * @param {any} value - any
   * @returns A function that takes a value and returns a float.
   */
  export function tryParseFloat (value: any, fallback: number): number
  export function tryParseFloat (value: any): Nullable<number>

  /**
 * It tries to parse a string into a JSON object, and if it fails, it returns undefined
 * @param value - Nullable<string>
 * @param {boolean} [noErrorLog] - If true, it will not log the error to the console.
 * @returns The result of the tryParse function.
 */
  export function tryParse<T = any> (value: Nullable<string>, noErrorLog = false): T

  /**
   * It returns a Date object if the value is a Date object or a string that can be parsed into a Date
   * object. Otherwise, it returns null
   * @param {any} value - any
   * @returns A function that takes a value and returns a date or null.
   */
  export function tryParseDate (value: any, fallback: Date): Date
  export function tryParseDate (value: any): Nullable<Date>

  /**
   * It returns a boolean value, or a fallback value if the input is not a boolean
   * @param {any} value - any
   * @param {boolean} [fallback] - The value to return if the value is not a boolean.
   * @returns a boolean value.
   */
  export function tryParseBoolean (value: any, fallback: boolean): boolean
  export function tryParseBoolean (value: any): Nullable<boolean>

  /**
   * It returns true if the `to` and `from` route names are equal
   * @param {RouteLocationNormalized} to - RouteLocationNormalized
   * @param {RouteLocationNormalized} from - RouteLocationNormalized
   * @returns A function that takes two arguments, to and from, and returns a boolean.
   */
  export const isRouteNameEquals: (to: RouteLocationNormalized, from: RouteLocationNormalized) => boolean

  /**
   * It tries to resolve a route using the current router and returns the href if it succeeds
   * @param {KeyValuePair} options - KeyValuePair
   * @returns The route.href is being returned.
   */
  export const tryResolveRoute: (options: KeyValuePair) => string | undefined

  /**
   * If the value is truthy and has a then function, then it's a promise.
   * @param {any} value - any
   * @returns A function that takes a value and returns a boolean.
   */
  export const isPromise: (value: any) => boolean
  /**
   * It returns a promise that resolves after a given number of milliseconds
   * @param {number} [ms] - The number of milliseconds to wait before resolving the promise.
   * @returns A promise that resolves after a set amount of time.
   */
  export const sleep: (ms?: number) => Promise<void>

  export const safeIsEquals: (value: any, other: any) => boolean
    
  interface IRegisterSWOptions {
    immediate?: boolean
    onNeedRefresh?: () => void
    onOfflineReady?: () => void
    /**
     * Called only if `onRegisteredSW` is not provided.
     *
     * @deprecated Use `onRegisteredSW` instead.
     * @param registration The service worker registration if available.
     */
    onRegistered?: (registration: ServiceWorkerRegistration | undefined) => void
    /**
     * Called once the service worker is registered (requires version `0.12.8+`).
     *
     * @param swScriptUrl The service worker script url.
     * @param registration The service worker registration if available.
     */
    onRegisteredSW?: (swScriptUrl: string, registration: ServiceWorkerRegistration | undefined) => void
    onRegisterError?: (error: any) => void
  }
  interface IUseRegisterSWOptions {
    registerSW: (options?: IRegisterSWOptions) => (reloadPage?: boolean) => Promise<void>
    router: Router
    intervalMS?: Nullable<number>
    noToastMessages?: boolean
    getVersion?: () => Promise<string>
  }

  /**
   * It registers a service worker, and then checks for updates every `intervalMS` milliseconds
   * @param {IUseRegisterSWOptions}  - IUseRegisterSWOptions
   */
  export const kaRegisterSW: (options: IUseRegisterSWOptions) => void

  interface IKaGuardOptions {
    isClient?: boolean
    router: Router
    appAuthenticationStore: () => any
  }

  /**
   * It create a guard on the router, redirecting to login page if unauthenticated, and creating redirect_uri
   * @param {IKaGuardOptions}  - IKaGuardOptions
   */
  export const kaAuthGuard: (options: IKaGuardOptions) => void

  /**
   * It returns a proxy object that returns the fallback locale for a given locale
   * @param {string} defaultLanguage - 'en'
   * @param {string} fallbackLanguage - 'en'
   * @param supportedLanguages - ['en', 'fr', 'de', 'es', 'it', 'nl', 'pt', 'ru', 'ja', 'zh', 'ko', 'ar',
   * 'he', 'tr', 'th', 'vi', 'id', 'ms', 'hi', 'bn',
   * @returns A Proxy object.
   */
  export const getFallbackLocale: (defaultLanguage: string, fallbackLanguage: string, supportedLanguages: Array<string>) => KeyValuePair

  export type FileExample = {
    content: string
    additionalImports?: Record<string, string>
  } | string
  
  export type VuejsCodePreviewExample = {
    'Index.vue': FileExample
    [key: string]: FileExample
  } & {
    additionalImports?: Record<string, string>
  }
  
  export interface HubspotField {
    value: any
    name: string
  }
  export interface HubspotOptions {
    version?: 'v3'
    portalId: string
    formGuid: string
    fields: KeyValuePair | HubspotField[]
    toastMessages?: {
      success?: {
        text: string
        options?: (ToastOptions & {
          type?: TYPE.SUCCESS | undefined
        })
      }
      errors?: {
        default?: ({
          text: string
          options?: (ToastOptions & {
            type?: TYPE.ERROR | undefined
          })
        } | undefined)
        [key: string]: ({
          text: string
          options?: (ToastOptions & {
            type?: TYPE.ERROR | undefined
          })
        } | undefined)
      }
    }
  }
  
  /**
   * It takes in a HubspotOptions object, and returns a promise that resolves to the response data from
   * the Hubspot API
   * @param {HubspotOptions} options - HubspotOptions
   * @returns The response from the API call.
   */
  export const sendToHubspot: (options: HubspotOptions) => Promise<any>

  
  /**
   * It opens a new tab if the url is not null
   * @param url - The URL to open.
   * @param {string} [newTab] - If you want to open the link in a new tab, you can pass in the value
   * '_blank'
   */
  export const openUrl: (url: Nullable<string | File>, newTab?: string | undefined) => void

  
  /**
   * If the hostname is 127.0.0.1, then open the same page on localhost
   */
  export const avoid_debug_127_0_0_1: () => void


  /**
 * This function copies a given text to the clipboard using the Clipboard API and returns a promise
 * that resolves when the copy is successful and rejects when it fails.
 * @param {string} value - The value that needs to be copied to the clipboard.
 * @param {HTMLElement} [container] - The optional parameter "container" is an HTMLElement that
 * specifies the container element where the fake button element will be appended to. If no container
 * is specified, the fake button element will be appended to the document body.
 * @returns a Promise that resolves with the success event object if the text is successfully copied to
 * the clipboard, or rejects with the error event object if there was an error copying the text.
 */
  export const textToClipboard: (value: Nullable<string | KeyValuePair>, container?: HTMLElement) => Promise<any>

  type WatchOptions = boolean | {
    immediate?: boolean
    deep?: boolean
    type?: string
  }

  interface SyncStoreOptions {
    props?: KeyValuePair
    propsToWatch?: KeyValuePair<WatchOptions>
  }
  interface SyncEntityStoreOptions<T> extends SyncStoreOptions {
    propName: string
    dataName?: string
    defaultValue: T
  }
  /**
   * The `syncEntityStore` function synchronizes a store with a component's props and provides a computed
   * property for the entity item.
   * @param {any} store - The `store` parameter is the Vuex store object. It is used to synchronize the
   * entity item with the store's state.
   * @param options - An object containing the following properties:
   * @returns The function `syncEntityStore` returns a ComputedRef of type T.
   */
  export function syncEntityStore<T = any> (store: any, options: SyncEntityStoreOptions<T>): ComputedRef<T>

    
  /**
   * The `syncComponentStore` function synchronizes a component store with a given set of options.
   * @param {T} store - The `store` parameter is the component store that you want to synchronize. It can
   * be any object or data structure that represents the state of your component.
   * @param {SyncStoreOptions} [options] - The `options` parameter is an optional object that can be
   * passed to the `syncComponentStore` function. It allows you to customize the behavior of the
   * synchronization process.
   * @returns the result of calling the `syncStore` function with the `store` and `options` arguments,
   * with the `type` property of the `options` object set to `'component'`. The return value is then
   * casted to type `T`.
   */
  export function syncComponentStore<T> (store: T, options?: SyncStoreOptions): T

  /**
   * The function `syncPageStore` synchronizes a store with a page.
   * @param {T} store - The `store` parameter is the object that represents the store you want to
   * synchronize. It can be any type of object, such as a Redux store or a VueX store.
   * @param {SyncStoreOptions} [options] - The `options` parameter is an optional object that can be
   * passed to the `syncPageStore` function. It allows you to customize the behavior of the `syncStore`
   * function that is called internally.
   * @returns the result of calling the `syncStore` function with the `store` and `options` arguments,
   * with the `type` property of `options` set to `'page'`. The return value is then casted to type `T`.
   */
  export function syncPageStore<T> (store: T, options?: SyncStoreOptions): T

  export function provideEntityContext<T extends () => any> (getter: T): void
  
  /**
   * It returns a function that removes the event listener when called.
   * @param {string} eventName - The name of the event you want to listen to.
   * @param handler - The function that will be called when the event is triggered.
   * @returns A function that removes the event listener.
   */
  export function addListener (eventName: string, handler: (context: any) => void): () => void

  /**
   * The function emits an event with a given name and optional value.
   * @param {string} eventName - A string representing the name of the event that will be emitted.
   * @param {any} [value] - The value parameter is an optional parameter of any type. It can be used to
   * pass additional data or information along with the event.
   * @returns The emitEvent function is returning the result of the eventManager.emit(eventName, value)
   * function call.
   */
  export function emitEvent (eventName: string, value?: any)

  // EMAIL
  export interface BrevoEmail {
    sender?: {
      email: string
      name?: string
    }
    to: Array<{ email: string; name?: string }> | string
    subject: string
    htmlContent: string
    apiKey?: string
  }
    
  /**
   * The function `sendBrevoEmail` sends an email using the Brevo API, handling different scenarios such
   * as localhost testing and error handling.
   * @param {BrevoEmail} email - The `email` parameter is an object that contains the details of the
   * email to be sent. It has the following properties:
   * @returns the response from the axios post request.
   */
  export const sendBrevoEmail: (email: BrevoEmail) => Promise<any>

  /**
   * The function removes an item from an array if it exists and returns true, otherwise it returns
   * false.
   * @param array - An array of any type of elements.
   * @param {any} item - The `item` parameter is the element that you want to remove from the `array`.
   * @returns a boolean value. It returns true if the item is successfully removed from the array, and
   * false if the item is not found in the array or if the array is empty.
   */
  export function remove (array: Array<any>, item: any): boolean
  
  /**
   * The function removes all occurrences of items in the listOfItemsToRemove from the array.
   * @param array - An array of any type. It can be nullable, meaning it can be either an array or null.
   * @param listOfItemsToRemove - An array containing the items that need to be removed from the original
   * array.
   */
  export function removeAll (array: Nullable<Array<any>>, listOfItemsToRemove: Nullable<Array<any>>)

  /**
   * The function `sumOfValues` calculates the sum of all numbers in an array, while ignoring any
   * non-numeric values.
   * @param array - An array of nullable values, where each value can be either a string or a number.
   * @returns The function `sumOfValues` returns the sum of all the numbers in the input array. If the
   * array is empty or contains only null or string values, it returns 0.
   */
  export function sumOfValues (array: Array<Nullable<string | number>>): number
      
  /**
   * The function subtracts the values in an array, treating strings as integers if possible.
   * @param array - An array of nullable values, where each value can be either a string or a number.
   * @returns the result of subtracting the values in the given array. If the array is empty, it returns
   * 0.
   */
  export function subtractOfValues (array: Array<Nullable<string | number>>): number 
    
  /**
   * The function calculates the product of all the numeric values in an array, while ignoring any
   * non-numeric values.
   * @param array - An array of nullable values, where each value can be either a string or a number.
   * @returns the product of all the values in the input array.
   */
  export function productOfValues (array: Array<Nullable<string | number>>): number

  /**
   * The function calculates the average of numeric values in an array, while ignoring non-numeric
   * values.
   * @param array - An array of nullable values, where each value can be either a string or a number.
   * @returns the average of the values in the input array.
   */
  export function averageOfValues (array: Array<Nullable<string | number>>): number
  
  // Didacticiel
  interface I18nContent {
    label?: string
    content: string[] | string
  }
  interface I18n {
    native: I18nContent
    [key: string]: I18nContent
  }
  export interface ObjectiveOptions {
    contentPlacement?: TooltipPlacement
    target?: string | ((context: any) => HTMLElement | string)
    avatar?: Partial<IAvatar>
    highlight?: string | ((context: any) => HTMLElement | string)
    canPrevious?: boolean
    isClick?: boolean
    isDbClick?: boolean
    isBlocked?: boolean
    isRequired?: boolean
    i18n: I18n
    skip?: (context: any) => boolean
    onEnter?: (context: any, args: { fromNext: boolean }) => void
    onPrevious?: (context: any) => void
    onNext?: (context: any) => void
    // onLeaveObjective?: (context: any) => void
    // onSpeechEnd?: (context: any) => void
  }
  type RGB = `rgb(${string})`
  type RGBA = `rgba(${string})`
  type HEX = `#${string}`
  type HSL = `hsl(${string})`
  type HSLA = `hsla(${string})`
  type VAR = `var(${string})`
  type CssGlobals = 'inherit' | 'initial' | 'revert' | 'unset'
  type CssColorNames =
  | 'AliceBlue'
  | 'AntiqueWhite'
  | 'Aqua'
  | 'Aquamarine'
  | 'Azure'
  | 'Beige'
  | 'Bisque'
  | 'Black'
  | 'BlanchedAlmond'
  | 'Blue'
  | 'BlueViolet'
  | 'Brown'
  | 'BurlyWood'
  | 'CadetBlue'
  | 'Chartreuse'
  | 'Chocolate'
  | 'Coral'
  | 'CornflowerBlue'
  | 'Cornsilk'
  | 'Crimson'
  | 'Cyan'
  | 'DarkBlue'
  | 'DarkCyan'
  | 'DarkGoldenRod'
  | 'DarkGray'
  | 'DarkGrey'
  | 'DarkGreen'
  | 'DarkKhaki'
  | 'DarkMagenta'
  | 'DarkOliveGreen'
  | 'DarkOrange'
  | 'DarkOrchid'
  | 'DarkRed'
  | 'DarkSalmon'
  | 'DarkSeaGreen'
  | 'DarkSlateBlue'
  | 'DarkSlateGray'
  | 'DarkSlateGrey'
  | 'DarkTurquoise'
  | 'DarkViolet'
  | 'DeepPink'
  | 'DeepSkyBlue'
  | 'DimGray'
  | 'DimGrey'
  | 'DodgerBlue'
  | 'FireBrick'
  | 'FloralWhite'
  | 'ForestGreen'
  | 'Fuchsia'
  | 'Gainsboro'
  | 'GhostWhite'
  | 'Gold'
  | 'GoldenRod'
  | 'Gray'
  | 'Grey'
  | 'Green'
  | 'GreenYellow'
  | 'HoneyDew'
  | 'HotPink'
  | 'IndianRed'
  | 'Indigo'
  | 'Ivory'
  | 'Khaki'
  | 'Lavender'
  | 'LavenderBlush'
  | 'LawnGreen'
  | 'LemonChiffon'
  | 'LightBlue'
  | 'LightCoral'
  | 'LightCyan'
  | 'LightGoldenRodYellow'
  | 'LightGray'
  | 'LightGrey'
  | 'LightGreen'
  | 'LightPink'
  | 'LightSalmon'
  | 'LightSeaGreen'
  | 'LightSkyBlue'
  | 'LightSlateGray'
  | 'LightSlateGrey'
  | 'LightSteelBlue'
  | 'LightYellow'
  | 'Lime'
  | 'LimeGreen'
  | 'Linen'
  | 'Magenta'
  | 'Maroon'
  | 'MediumAquaMarine'
  | 'MediumBlue'
  | 'MediumOrchid'
  | 'MediumPurple'
  | 'MediumSeaGreen'
  | 'MediumSlateBlue'
  | 'MediumSpringGreen'
  | 'MediumTurquoise'
  | 'MediumVioletRed'
  | 'MidnightBlue'
  | 'MintCream'
  | 'MistyRose'
  | 'Moccasin'
  | 'NavajoWhite'
  | 'Navy'
  | 'OldLace'
  | 'Olive'
  | 'OliveDrab'
  | 'Orange'
  | 'OrangeRed'
  | 'Orchid'
  | 'PastelOrange'
  | 'PaleGoldenRod'
  | 'PaleGreen'
  | 'PaleTurquoise'
  | 'PaleVioletRed'
  | 'PapayaWhip'
  | 'PeachPuff'
  | 'Peru'
  | 'Pink'
  | 'Platinum'
  | 'Plum'
  | 'PowderBlue'
  | 'Purple'
  | 'RebeccaPurple'
  | 'Red'
  | 'RosyBrown'
  | 'RoyalBlue'
  | 'SaddleBrown'
  | 'Salmon'
  | 'SandyBrown'
  | 'SeaGreen'
  | 'SeaShell'
  | 'Sienna'
  | 'Silver'
  | 'SkyBlue'
  | 'SlateBlue'
  | 'SlateGray'
  | 'SlateGrey'
  | 'Snow'
  | 'SpringGreen'
  | 'SteelBlue'
  | 'Tan'
  | 'Teal'
  | 'Thistle'
  | 'Tomato'
  | 'Turquoise'
  | 'Violet'
  | 'Wheat'
  | 'White'
  | 'WhiteSmoke'
  | 'Yellow'
  | 'YellowGreen'
  export type CssColor =
  | 'currentColor'
  | 'transparent'
  | RGB
  | RGBA
  | HEX
  | HSL
  | HSLA
  | VAR
  | CssGlobals
  | CssColorNames

  export interface IAvatar {
    topType:
      'NoHair' | 
      'Eyepatch' | 
      'Hat' | 
      'Hijab' | 
      'Turban' | 
      'WinterHat1' | 
      'WinterHat2' | 
      'WinterHat3' | 
      'WinterHat4' | 
      'LongHairBigHair' | 
      'LongHairBob' | 
      'LongHairBun' | 
      'LongHairCurly' | 
      'LongHairCurvy' | 
      'LongHairDreads' | 
      'LongHairFrida' | 
      'LongHairFro' | 
      'LongHairFroBand' | 
      'LongHairNotTooLong' | 
      'LongHairShavedSides' | 
      'LongHairMiaWallace' | 
      'LongHairStraight' | 
      'LongHairStraight2' | 
      'LongHairStraightStrand' | 
      'ShortHairDreads01' | 
      'ShortHairDreads02' | 
      'ShortHairFrizzle' | 
      'ShortHairShaggy' | 
      'ShortHairShaggyMullet' | 
      'ShortHairShortCurly' | 
      'ShortHairShortFlat' | 
      'ShortHairShortRound' | 
      'ShortHairShortWaved' | 
      'ShortHairSides' | 
      'ShortHairTheCaesar' | 
      'ShortHairTheCaesarSidePart'
    accessoriesType: 
      'Blank' | 
      'Kurt' | 
      'Prescription01' | 
      'Prescription02' | 
      'Round' | 
      'Sunglasses' | 
      'Wayfarers'
    topColor: CssColor
    hairColor: CssColor
    facialHairType: 
      'Blank' | 
      'BeardMedium' | 
      'BeardLight' | 
      'BeardMajestic' | 
      'MoustacheFancy' | 
      'MoustacheMagnum'
    facialHairColor: CssColor
    clotheType: 
      'BlazerShirt' | 
      'BlazerSweater' | 
      'CollarSweater' | 
      'GraphicShirt' | 
      'Hoodie' | 
      'Overall' | 
      'ShirtCrewNeck' | 
      'ShirtScoopNeck' | 
      'ShirtVNeck'
    clotheColor: CssColor
    eyeType: 
      'Close' | 
      'Cry' | 
      'Default' | 
      'Dizzy' | 
      'EyeRoll' | 
      'Happy' | 
      'Hearts' | 
      'Side' | 
      'Squint' | 
      'Surprised' | 
      'Wink' | 
      'WinkWacky'
    eyebrowType: 
      'Angry' |
      'AngryNatural' | 
      'Default' | 
      'DefaultNatural' | 
      'FlatNatural' | 
      'FrownNatural' | 
      'RaisedExcited' | 
      'RaisedExcitedNatural' | 
      'SadConcerned' | 
      'SadConcernedNatural' | 
      'UnibrowNatural' | 
      'UpDown' | 
      'UpDownNatural'
    mouthType:
      'Concerned' | 
      'Default' | 
      'Disbelief' | 
      'Eating' | 
      'Grimace' | 
      'Sad' | 
      'ScreamOpen' | 
      'Serious' | 
      'Smile' | 
      'Tongue' | 
      'Twinkle' | 
      'Vomit'
    skinColor:  
      'Tanned' | 
      'Yellow' | 
      'Pale' | 
      'Light' | 
      'Brown' | 
      'DarkBrown' | 
      'Black'
    // avatarStyle: 'Transparent',
    graphicType:
      'Blank' | 
      'Skull' | 
      'SkullOutline' | 
      'Bat' | 
      'Cumbia' | 
      'Deer' | 
      'Hola' | 
      'Selena' | 
      'Diamond' | 
      'Pizza' | 
      'Resist' | 
      'Bear'
  }
  export const defaultAvatars = {
    GUYS: {
      DEFAULT: IAvatar,
      SIMPLE: IAvatar,
      SMILE: IAvatar
    },
    GIRLS: {
      SIMPLE: IAvatar,
      SMILE: IAvatar
    }
  }
  export interface StepOptions {
    target: string | ((context: any) => HTMLElement | string)
    showAvatar?: boolean
    avatar?: Partial<IAvatar>
    showQuickActions?: boolean
    contentPlacement?: TooltipPlacement
    objectives?: ObjectiveOptions[]
    showDidacticielBlocks?: boolean
    i18n: I18n
    onEnter?: (context: any, args: { fromNext: boolean }) => void
    onPrevious?: (context: any) => void
    onNext?: (context: any) => void
    onLeave?: (context: any) => void
    onSpeechEnd?: (context: any) => void
  }
  /**
   * The ScenarioOptions type is a type alias for a dictionary that has three optional members: onStart,
   * onStop, and onComplete.
   *
   * The onStart member is a function that takes a single parameter, context, which is the context object
   * for the scenario.
   *
   * The onStop member is a function that takes a single parameter, context, which is the context object
   * for the scenario.
   *
   * The onComplete member is a function that takes a single parameter, context, which is the context
   * object for the scenario.
   * @property onStart - This is called when the scenario starts.
   * @property onStop - This is called when the scenario is stopped.
   * @property onComplete - This is called when the scenario is completed.
   */
  export interface ScenarioOptions {
    onStart?: (context: any) => void | any
    onStop?: (context: any) => void
    onComplete?: (context: any, didacticiel: Didacticiel) => void
    device?: string
    showObjectivesPanel?: boolean
    avatar?: Partial<IAvatar>
  }
  export class Scenario {
  
    constructor (steps: StepOptions[], options?: ScenarioOptions) {}
  }
  type Difficulty = 1 | 2 | 3
  export interface DidacticielOptions {
    name: string
    templateId?: string
    owner?: string
    label: string
    description?: string
    stars?: Difficulty
    requiredInstance?: boolean
    scenario?: () => Promise<Scenario>
  }
  export class Didacticiel {
    constructor (options: DidacticielOptions) {}
  }
  
  interface IKapixDidacticielOptions {
    didacticiels: Array<Didacticiel>
  }
  export const DidacticielPlugin: { install: (ctx: ViteSSGContext, options: IKapixDidacticielOptions) => void }
  export const didacticielStore: () => {
    getDidacticiel (name: string): Didacticiel
    loadDidacticiel (options: { name: string; skipOnStart?: boolean }): Promise<void>
  }
  // Data
  export interface IScrollableData {
    scrollTop: number
    scrollLeft: number
  }

  export interface ISearchableData {
    loading: boolean
    searching: boolean
    refresh: (delay?: boolean) => void
  }
  
  export interface ISelectableData {
    canSelectPreviousItem: boolean
    canSelectNextItem: boolean
    selectPreviousItem: () => void
    selectNextItem: () => void
  }

  export interface IPaginableData {
    total: number
    pages: number
    pageIndex: number
    pageSize?: number
    canPreviousPage: boolean
    canNextPage: boolean
    previousPage: () => void
    nextPage: () => void
  }

  export function scrollInfo (): IScrollableData

  export interface IFormError {
    message: Nullable<string>
    hasError: boolean
    lastUpdate: Nullable<Date>
    set: (message: Nullable<string>) => void
    validate?: () => Promise<void>
    reset: () => void
    onReset?: () => void
  }

  export interface IFormData<T> extends IScrollableData, ISearchableData, ISelectableData {
    total: number
    validityErrors: false | string
    validityErrorsMap: KeyValuePair<IFormError | undefined>
    isValid: boolean
    item: Partial<T>
    reset: () => void
    validate: () => Promise<{ valid: boolean }>
    resetValidation: () => void
    // crud
    createOrUpdate: () => Promise<Partial<T>>
    create: () => Promise<Partial<T>>
    update: () => Promise<Partial<T>>
    delete: () => Promise<boolean>
  }
  
  export function formInfo<EntityType = any> (item: Partial<EntityType>): IFormData<EntityType>

  export function entityFormInfo<T extends IEntityModel> (
    entityModel: T,
    reactiveService: GraphqlEntityService<any>,
    defaultItem?: Partial<T['$prototype']['entityType'] | T['$prototype']['fullEntityType']>
  ): IFormData<T['$prototype']['fullEntityType']>
  
  export interface IListData<T> extends IScrollableData, IPaginableData, ISelectableData, ISearchableData {
    items: Array<T>
    addItem: (item: Nullable<Partial<T>>) => void
    removeItem: (item: Nullable<Partial<T>>) => boolean
    scrollToPreviousItem: () => void
    scrollToNextItem: () => void
  }
  
  export function listInfo<EntityType = any> (): IListData<EntityType>
  export interface ILatLng {
    lat: number
    lng: number
  }
  export interface IMapData<T> extends IListData<T> {
    zoom: number
    center: Nullable<ILatLng>
  }
  
  export function mapInfo<EntityType = any> (): IMapData<EntityType>

  export interface IShortkeyContext {
    name: Nullable<string>
    modsUsed: Array<string>
    defaultContext: Nullable<string>
    contexts: KeyValuePair<Context> & { All: Context }
  }

  export function getShortkeyContext (): IShortkeyContext
  export function registerShortkey (options: {
    keys: string[]
    push?: boolean
    once?: boolean
    focus?: boolean
    propagate?: boolean
    el?: HTMLElement
    name?: string
    contextName?: string
    action: () => void
  }): () => void
  export function getShortkeyDialog (): ITooltipInstance

  /**
 * The `gqlStringify` function is used to convert a value into a string representation, with special
 * handling for arrays and escaping double quotes.
 * @param {any} value - The `value` parameter is the value that you want to convert to a GraphQL string
 * representation. It can be of any type, such as a string, number, boolean, object, or array.
 * @param [jsonArray=true] - The `jsonArray` parameter is a boolean flag that determines whether the
 * `value` should be converted to a JSON array or not. If `jsonArray` is `true` and the `value` is an
 * array, it will be converted to a JSON array. If `jsonArray` is
 * @returns a string representation of the input value. If the input value is an array and the
 * jsonArray parameter is set to true, the function returns a string representation of the array with
 * each element enclosed in double quotes and separated by commas. If the jsonArray parameter is set to
 * false or the input value is not an array, the function returns a string representation of the input
 * value with all double quotes escaped
 */
  export function gqlStringify (value: any, jsonArray = true): string

    /**
   * The `gqlObjectToGraphData` function converts an object into a string representation that can be used as
   * arguments in a GraphQL query.
   * @param {Object} obj - The `obj` parameter is an object that you want to convert to graph data.
   * @returns a string that represents the input object converted into GraphQL argument data format.
   */
  export function gqlObjectToGraphData (obj: Object): string

  
  export interface IGraphqlEntityServiceModel {
    entity: IEntityModel
    queries: KeyValuePair<(...args: any[]) => Promise<any>>
    mutations: KeyValuePair<(...args: any[]) => Promise<any>>
    appAuthenticationFactory?: () => { lastClientUpdateAt: Nullable<Date> }
    canQuery?: () => boolean
    canMutate?: () => boolean
    debounce?: number
  }

  export class GraphqlEntityService<T extends IGraphqlEntityServiceModel> {
    private reactiveModel = reactive({
      updated: null as Nullable<Date>,
      isLoading: false
    })
  
    public readonly entity: T['entity']
    public readonly queries: T['queries']
    public readonly mutations: T['mutations']
    public readonly reactiveQueries: {
      [key in keyof T['queries']]: <X extends (() => any) = never>(config: {
        callback: (value: Awaited<ReturnType<T['queries'][key]>> | undefined, watcherValue: ReturnType<X>) => void
        isLoading?: (loading: boolean) => void
        immediate?: boolean
        debounce?: number
        default?: () => Awaited<ReturnType<T['queries'][key]>>
        watcher?: X
        arguments?: (watcherValue: ReturnType<X>) => ((Parameters<T['queries'][key]>[0]) | false)
      } | ((value: Awaited<ReturnType<T['queries'][key]>> | undefined) => void)) => WatchStopHandle
    }
  
    public get updatedDateAt () {
      return this.reactiveModel.updated
    }

    public get isLoading () {
      return this.reactiveModel.isLoading
    }
    
    constructor (service: T) {}
  
    refresh () {}
  }

  export function defineGraphqlEntityService<T extends IGraphqlEntityServiceModel> (model: () => T): () => GraphqlEntityService<T>

  export interface IBusinessRule {
    isValid: ((value: any) => boolean) | ((value: any) => Promise<boolean>)
    message: (t: Translate) => string
  }
  
  export const businessRules: {
    required: IBusinessRule
    email: IBusinessRule
    name: IBusinessRule
    phone: IBusinessRule
    siret: IBusinessRule
    siren: IBusinessRule
    bic: IBusinessRule
    cb: IBusinessRule
    iban: IBusinessRule
    licensePlate: IBusinessRule
  }

    
  export type IncludeInValue = Nullable<string | number | Array<any> | KeyValuePair<any>>
  export interface IncludeInOptions {
    insensitive?: boolean
  }

  export function includesIn (value: IncludeInValue, conditionValue: IncludeInValue, options?: IncludeInOptions): boolean
  export function isContainsIn (value: IncludeInValue, conditionValue: IncludeInValue, options?: IncludeInOptions): boolean
  export function endsWith (value: any, conditionValue: any, options?: IncludeInOptions): boolean
  export function startsWith (value: any, conditionValue: any, options?: IncludeInOptions): boolean
  export function isEqualTo (value: any, conditionValue: any, options?: IncludeInOptions): boolean

  /**
   * The function `isStringValidDate` checks if a given string is a valid date string in a specific
   * format.
   * @param dateString - The `dateString` parameter is of type `Nullable<Date | string | number>`, which
   * means it can accept values of type `Date`, `string`, `number`, or `null`.
   * @returns a boolean value.
   */
  export function isStringValidDate (dateString: Nullable<Date | string | number>): dateString is string

  export const formatters = {
    date: {
      YEAR: 'year',
      BIRTHDAY: 'birthday',
      BIRTHDAY_WITH_FRACTION: 'birthdayFraction',
      MONTH: 'absoluteMonth',
      RELATIVE: 'relativeDate',
      RELATIVE_SHORT: 'relativeShort',
      ABSOLUTE_DATE: 'absoluteDate',
      ABSOLUTE_DATETIME: 'absoluteDatetime',
      WEEK_DAY_LONG: 'weekDayLong',
      WEEK_DAY_SHORT: 'weekDayShort',
      TIME: 'time',
      ISO: 'iso',
      NO_FORMATTING: null
    },
    number: {
      NO_FORMATTING: null,
      TRUNC: 'trunc',
      ROUND: 'round',
      COMMAS: 'commas',
      ABBREVIATED: 'abbreviated',
      CURRENCY: 'currency',
      ABBREVIATED_CURRENCY: 'abbreviatedCurrency'
    }
  }

  export interface ICoordinate {
    lat: number
    lng: number 
  }

  /**
   * The function `getUserPosition` is an asynchronous function that attempts to retrieve the user's
   * current position using the Geolocation API, and returns a promise that resolves to the user's
   * position coordinates.
   * @param timeout - The `timeout` parameter is the maximum amount of time (in milliseconds) that the
   * function will wait for the geolocation API to return the user's position. If the API does not
   * respond within this time, the function will return a fallback position.
   * @returns The function `getUserPosition` returns a Promise that resolves to an object of type
   * `ICoordinate`.
   */
  export function getUserPosition (timeout?: number): Promise<ICoordinate>
  
  export interface INotificationMessage {
    id?: string | number
    title: string
    content: NotificationOptions
    displayDate?: Date
    delay?: number
  }
    
  export interface IInternalNotificationMessage extends INotificationMessage {
    index: number
    createdDate: Date
    displayDate: Date
  }


  /**
   * The `createNotification` function creates a new notification message and adds it to the notification
   * queue, with an option to remove it later.
   * @param {INotificationMessage} notification - The `notification` parameter is an object of type
   * `INotificationMessage`. It contains the information for creating a new notification.
   * @returns The function `createNotification` returns a function.
   */
  export function createNotification (notification: INotificationMessage): () => void

    /**
   * The function removes a notification message from an array based on its ID.
   * @param {string} id - The `id` parameter is a string that represents the unique identifier of a
   * notification.
   * @returns either the removed notification object from the `notificationMessages` array if a matching
   * notification is found, or `false` if no matching notification is found.
   */
  export function removeNotification (id: string) : boolean

  export const notificationService = {
    watch () {},
    unwatch () {}
  }

  export function downloadFile (file: File, fileName?: string): void
  export function saveToLocalFile (content: any, fileName: string, contentType: string): void
  export function isLocalhost(): boolean
  
  // Store
  
  interface IDefaultStoreState {
    $aliveStoreIds: StoreIdentifier[]
    $subStoreIds: number
    $storeId: Nullable<StoreIdentifier>
    $emit: (propName: any, value?: any) => void
    $elements: KaElementMap
    $route: Nullable<RouteLocationNormalizedLoaded>
    $router: Nullable<Router>
    $parentPage: KeyValuePair
    $parentComponent: KeyValuePair
  }

  interface IStoreOptions {
    storeId: Nullable<StoreIdentifier>
    storeName: string
    customImplement?: KeyValuePair
    defineStore: typeof defineStore
    onDefineStore?: (useStore: any) => void
  }
  interface IDefineStoreOptions<Id extends string, S extends StateTree, G, A> extends DefineStoreOptionsBase<S, Store<Id, S, G, A>> {
    /**
     * Unique string key to identify the store across the application.
     */
    id: Id
    /**
     * Function to create a fresh state. **Must be an arrow function** to ensure
     * correct typings!
     */
    state?: () => S
    /**
     * Optional object of getters.
     */
    getters?: G & ThisType<UnwrapRef<S> & A & _StoreWithGetters<G> & PiniaCustomProperties & IDefaultStoreState> & _GettersTree<S>
    /**
     * Optional object of actions.
     */
    actions?: A & ThisType<A & UnwrapRef<S> & _StoreWithState<Id, S, G, A> & _StoreWithGetters<G> & PiniaCustomProperties & IDefaultStoreState>
    /**
     * Allows hydrating the store during SSR when complex state (like client side only refs) are used in the store
     * definition and copying the value from `pinia.state` isn't enough.
     *
     * @example
     * If in your `state`, you use any `customRef`s, any `computed`s, or any `ref`s that have a different value on
     * Server and Client, you need to manually hydrate them. e.g., a custom ref that is stored in the local
     * storage:
     *
     * ```ts
     * const useStore = defineStore('main', {
     *   state: () => ({
     *     n: useLocalStorage('key', 0)
     *   }),
     *   hydrate(storeState, initialState) {
     *     // @ts-expect-error: https://github.com/microsoft/TypeScript/issues/43826
     *     storeState.n = useLocalStorage('key', 0)
     *   }
     * })
     * ```
     *
     * @param storeState - the current state in the store
     * @param initialState - initialState
     */
    hydrate?(storeState: UnwrapRef<S>, initialState: UnwrapRef<S>): void
  }
  export function defineStoreFactory<
    S extends StateTree = {},
    G extends _GettersTree<S> = {},
    A = {
      beforeMount?: () => any
      mounted?: () => any
      beforeUnmount?: () => any
      unmounted?: () => any
      serverPrefetch?: () => any
    }
  > ({
    storeId,
    storeName,
    customImplement
  }: IStoreOptions,
  model: Omit<IDefineStoreOptions<string, S, G, A>, 'id'>) {
    return defineStore('', {
      state: () => {
        return model.state?.() as S & IDefaultStoreState
      },
      getters: model.getters as G,
      actions: {
        ...model.actions as A,
        getStoreInstance (storeId?: Nullable<StoreIdentifier>) {
          return this
        },
        getStoreInstances () {
          return [].map(_ => this.getStoreInstance())
        },
        newStoreInstance (storeId?: Nullable<StoreIdentifier>) {
          return this
        }
      }
    })
  }

  // Gantt

  export interface IGanttTask<T = any> {
    id: number | string,
    label: string,
    value: string | ((task: T) => any),
    width: number,
    html?: boolean
    expander?: boolean
    style?: KeyValuePair
  }

  export interface IGanttDateOptions {
    height?: number, //*
    display?: boolean, //*
    widths?: Array<number>,
    maxWidths?: Partial<{ short: number, medium: number, long: number }>,
    formatted?: Partial<{
      long: Array<any>,
      medium: Array<any>,
      short: Array<any>
    }>,
    format?: Partial<{
      //*
      long: (date: Date) => string,
      medium: (date: Date) => string,
      short: (date: Date) => string,
    }>
  }
  export interface IGanttOptions<T = any> {
    taskMapping?: Partial<{
      id: string,
      start: string,
      label: string,
      duration: string,
      progress: string,
      type: string,
      style: string,
      collapsed: string
    }>,
    scope?: Partial<{
      before: number,
      after: number
    }>,
    times?: Partial<{
      timeScale: number
      timeZoom: number, //*
      timePerPixel: number,
      firstTime: Date,
      lastTime: Date,
      firstTaskTime: number,
      lastTaskTime: number,
      totalViewDurationMs: number,
      totalViewDurationPx: number,
      stepDuration: 'hour' | 'day' | 'month',
      steps: Array<any>
    }>,
    row?: Partial<{
      height: number //*
    }>,
    maxRows?: number, //*
    maxHeight?: number, //*
    chart?: Partial<{
      grid: {
        horizontal?: {
          gap?: number
        }
      },
      progress: Partial<{
        width: number, //*
        height: number, //*
        pattern: boolean,
        bar: boolean
      }>,
      text: Partial<{
        offset: number, //*
        xPadding: number, //*
        display: boolean //*
      }>,
      expander: Partial<{
        type: 'chart',
        display: boolean, //*
        displayIfTaskListHidden: boolean, //*
        offset: number, //*
        size: number
      }>
    }>,
    taskList?: Partial<{
      display: boolean, //*
      resizeAfterThreshold: boolean, //*
      widthThreshold: number, //*
      columns: Array<IGanttTask<T>>,
      percent: number, //*
      width: number,
      finalWidth: number,
      widthFromPercentage: number,
      minWidth: number,
      expander: Partial<{
        type: 'task-list',
        size: number,
        columnWidth: number,
        padding: number,
        margin: number,
        straight: boolean
      }>
    }>,
    calendar?: Partial<{
      workingDays: Array<number>, //*
      gap: number, //*
      height: number,
      strokeWidth: number,
      hour: Partial<IGanttDateOptions>,
      day: Partial<IGanttDateOptions>,
      month: Partial<IGanttDateOptions>
    }>,
    locale?: Partial<{
      name: string,
      weekdays: Array<string>,
      weekdaysShort: Array<string>,
      weekdaysMin:  Array<string>,
      months: Array<string>,
      monthsShort: Array<string>,
      weekStart: number,
      relativeTime: Partial<{
        future: string,
        past: string,
        s: string,
        m: string,
        mm: string,
        h: string,
        hh: string,
        d: string,
        dd: string,
        M: string,
        MM: string,
        y: string,
        yy: string
      }>,
      formats: Partial<{
        LT: string,
        LTS: string,
        L: string,
        LL: string,
        LLL: string,
        LLLL: string
      }>,
      ordinal: (n: number) => string
    }>
  } 

  export const NOOP: KeyValuePair
  export const NOOP_ARRAY: Array<any>
  export const NOOP_FUNCTION: () => typeof NOOP
  export const MOUSE_POSITION: Array<Number>
  export interface IEntityContextProvider<T = any> {
    item: T
    dataSource?: Nullable<IDataSourceInstance>
    showSkeleton?: Nullable<boolean>
  }
  export type FlexDirection =  'column' | 'column-reverse' | 'row' | 'row-reverse'
  export type FlexWrap = 1 | 2 | 3

  // common
  export interface ICommonItemSelectionOptions<T extends Array<any> = Array<any>> {
    itemText: string | boolean | ((item: T[number]) => Nullable<string>)
    itemValue: string | boolean | ((item: T[number]) => any)
    itemDisabled: string | boolean | ((item: T[number]) => Nullable<boolean>)
    itemTooltip: string | boolean | ((item: T[number]) => Nullable<string | boolean | Partial<ITooltipOptions>>)
    itemSubtitle: string | boolean | ((item: T[number]) => Nullable<boolean | string>)
    itemStyle: string | boolean | ((item: T[number]) => Nullable<boolean | StyleValue>)
    itemClass: string | boolean | ((item: T[number]) => Nullable<string | boolean | Array<string>>)
    itemIcon: string | boolean | ((item: T[number]) => Nullable<boolean | string>)
    itemIconClass: string | boolean | ((item: T[number]) => Nullable<string | boolean>)
    itemPrependIcon: string | boolean | ((item: T[number]) => Nullable<boolean | string>)
    itemPrependComponent: string | ((item: T[number]) => Nullable<boolean | Component | Promise<Component> | string>)
    itemColor: string | boolean | ((item: T[number]) => Nullable<boolean | string>)
    itemBackgroundColor: string | boolean | ((item: T[number]) => Nullable<boolean | IGradientColor>)
  }
  
  // Ka Container
  type KaContainerInternalOptions = PartialAndNullable<{
    bgType: 0 | 1
    videoOptions: KapixVideoOptions & { src?: Nullable<string> }
    lottieOptions: PartialAndNullable<ILottieOptions>
    style: PartialAndNullable<{
      overflowStyle: 'overlay' | 'hidden'
      flexDirection: FlexDirection
      flexWrap: FlexWrap
    }>
  }> 
  export type KaContainerOptions = IPropOptions & KaContainerInternalOptions
  type KaContainerProps = KaProps<KaContainerInternalOptions> & {
    simple: { type: PropType<boolean | null | undefined> }
    slots: { type: PropType<object | null | undefined> }
  }
  type KaContainerType = DefineComponent<KaContainerProps>
  export const KaContainer: KaContainerType

  // Ka Element
  type KaElementProps = KaProps & {
    componentName: { type: PropType<string | null | undefined> }
    slots: { type: PropType<object | null | undefined> }
  }
  type KaElementType = DefineComponent<KaElementProps>
  export const KaElement: KaElementType

  export const KaForm: KaContainerType

  export const KapixGanttElastic: Component<{
    options?: IGanttOptions
    tasks?: Array<any>
  }>
  export const KapixGanttElasticHeader: Component

  // Kapix Teleport
  type KapixTeleportOptions = {
    to: {
      type: PropType<string | HTMLElement | null | undefined>
    }
    disabled: {
      type: PropType<boolean | null | undefined>
    }
  }
  type KapixTeleportType = DefineComponent<KapixTeleportOptions>
  export const KapixTeleport: KapixTeleportType
  

  // elements
  
  // common options
  type StringOptions = {
    textNoWrap: boolean
  }
  type IconsOptions = {
    prependIcon: string
    prependInnerIcon: string
    appendIcon: string
    appendOuterIcon: string
  }

  export const KapixIcon: Component
  export const KapixAmChart: Component
  // Kapix Avatar
  export type KapixAvatarOptions = PartialAndNullable<{
    speechText: string | string[]
    onSpeechCompleted: () => void
    avatarAnimationDelay: number
  }>
  export const KapixAvatar: Component

  // Kapix Button
  export type KapixButtonOptions = PartialAndNullable<IconsOptions>
  export const KapixButton: Component

  export const KapixCollectionView: Component

  // Kapix Leaflet
  export type KapixLeafletOptions<T extends GraphqlEntityService<IGraphqlEntityServiceModel>> = PartialAndNullable<{
    layers: Array<{
      center?: number
      radius: number
      circleColor: string
      circleFillColor: string
    }>
    showUserPosition: boolean
    mapZoom: number
    tileLayer: string
    coordsProp: string
    initType: 'smart' | 'user' | 'manual'
    initCoords: string | [number, number] | {
      latitude: number
      longitude: number
    } | {
      lat: number
      long: number
    } | {
      type: 'POINT'
      coord: {
        lat: number
        long: number
      }
    }
    minZoom: number
    maxZoom: number
    gestureMode: 'noWheel' | 'googleMap'


    placeholder: string
    items: Array<any>
    orderBy: (items: any) => any
    filter: (item: T) => boolean
    // entity: any
    selectable: boolean
    selectFirstOnLoad: boolean
    selectedItem: any
    editable: boolean
    dataSource: {
      service: GraphqlEntityService
      query?: Partial<IGraphqlRequestQueryOptions<T['entity']>>
    }
    pageIndex: number
    pageSize: number
    minAddedItems: number
    maxAddedItems: number
  }>
  export const KapixLeaflet: Component

  // Kapix List
  export interface IDataSourceQuery {
    skip?: number
    take?: number
    where?: any
    orderBy?: any[]
    select?: any
  }
  export type KapixListOptions<T extends GraphqlEntityService<IGraphqlEntityServiceModel>> = PartialAndNullable<{
    placeholder: string
    placeholderOptions: PartialAndNullable<{
      skeletonRows: number
      img: string
      imgOptions: KapixImageOptions
    }>
    items: Array<any>
    orderBy: (items: Array<Partial<T['entity']['$prototype']['fullEntityType']>>) => any
    filter: (item: Partial<T['entity']['$prototype']['fullEntityType']>) => boolean
    itemCompare: string | ((item: Partial<T['entity']['$prototype']['fullEntityType']>) => boolean)
    selectable: boolean
    selectFirstOnLoad: boolean
    selectedItem: any
    autoScrollToEnd: boolean

    overflow: 'auto' | 'y' | 'x' | 'hidden'
    virtualScroll: boolean
    flexDirection: FlexDirection
    flexWrap: FlexWrap
    entity: T['entity']

    editable: boolean
    dataSource: {
      service?: Nullable<T>
      query?: Partial<IGraphqlRequestQueryOptions<T['entity']>>
      queryName?: string
    }
    pageIndex: number
    pageSize: number
    minAddedItems: number
    maxAddedItems: number
    style: PartialAndNullable<{
      flexDirection: FlexDirection
      flexWrap: FlexWrap
    }>
  }>
  export const KapixList: Component

  // Kapix Color
  export type KapixColorOptions = PartialAndNullable<{
    showText: boolean
    label: string
  }>
  export const KapixColor: Component
  
  export const KapixCustomHtml: Component
  export const KapixGradientColor: Component
  export const KapixHeaderActions: Component
  export const KapixHeader: Component
  export const KapixIframe: Component

  // Kapix Image
  export type ObjectFit = 'cover' | 'contain' | 'fill' | 'scale-down'
  export type KapixImageOptions = PartialAndNullable<{
    alt: string
    imgFit: ObjectFit
    overlay: string
    optimizedImage: boolean
    svgAspectRatio: string
    defaultImage: string | File
    renderSvg: boolean
    svgAspectRatio: string
    loadingIcon: string | boolean
  }>
  export const KapixImage: Component

  export const KapixJitsi: Component

  // Kapix Label
  export type KapixLabelOptions = PartialAndNullable<StringOptions>
  export const KapixLabel: Component

  // Kapix Lottie
  export type KapixLottieOptions = PartialAndNullable<{
    lottieMode: 'p' | 's' | 's-s' | 'c'
    autoplay: boolean
    direction: -1 | 1
    cursorMode: 'h'
    frames: [number, number]
    preserveAspectRatio: string
    scroller: string
    speed: number
    loop: boolean
  }>
  export const KapixLottie: Component
  export const KapixSeparator: Component
  // kapix Social Sharing
  export type KapixSocialSharingOptions = PartialAndNullable<{
    url: string
    socialIcon: string
    showCounter: boolean
    socialType: 'facebook' | 'line' | 'linkedin' | 'twitter' | 'email' | 'google+' | 'live-journal' | 'pinterest' | 'reddit' | 'telegram' | 'tumblr' | 'viber' | 'whatsapp' | 'moi-mir'
  }>
  export const KapixSocialSharing: Component

  // Kapix Text
  export type KapixTextOptions = PartialAndNullable<StringOptions>
  export const KapixText: Component

  export const KapixTextAnime: Component
  export const KapixTextLink: Component
  // Kapix Type Writer
  export type KapixTypeWriterOptions = PartialAndNullable<{
    caretAnimation: 'solid' | 'blink' | 'smooth' | 'phase' | 'expand' | 'no-caret'
    repeat: number
    shuffle: boolean
    initialAction: 'typing' | 'erasing'
    preTypeDelay: number
    typeDelay: number
    preEraseDelay: number
    eraseDelay: number
    eraseStyle: 'backspace' | 'select-back' | 'select-all' | 'clear'
    eraseOnComplete: boolean
  }>
  export const KapixTypeWriter: Component

  // Kapix Video
  export type KapixVideoOptions = PartialAndNullable<{
    autoplay: boolean
    loop: boolean
    fit: ObjectFit
    alt: string
    controls: boolean
    poster: string
    volume: number
  }>
  export const KapixVideo: Component

  export const KapixYoutube: Component
  export const KapixCodePreview: Component

  // Kapix Qr Code
  export type KapixQrCodeOptions =  PartialAndNullable<{
    width: number
    scale: number
    color: string
    bgColor: string
    errorLevel: string
    version: string
    maskPattern: string
    margin: number
    small: boolean

    url: string
    alt: string
  }>
  export const KapixQrCode: Component

  // Kapix Page Router
  export type KapixPageRouterOptions = PartialAndNullable<{
    pageId: string
  }>

  // inputs
  // Kapix Google Address Autocomplete Input
  export type KapixGoogleAddressAutocompleteInputOptions = PartialAndNullable<IconsOptions & {
    country: Array<string>
    resultFields: Array<'adr_address' | 'geometry' | 'name' | 'formatted_address' | 'place_id'>
  }>
  export const KapixGoogleAddressAutocompleteInput: Component

  export const KapixCheckboxInput: Component
  export const KapixColorInput: Component
  export const KapixComboboxInput: Component
  export const KapixDatePickerInput: Component
  export const KapixDateTimePickerInput: Component
  // Kapix Color Input
  export type KapixColorInputOptions = PartialAndNullable<{
    placement: POSITION
  }>
  export const KapixColorInput: Component
  
  // Kapix Calendar Input
  export type KapixCalendarInputOptions = PartialAndNullable<{
    showHeader: boolean
    markerColor: string
    markerDateProp: string
    markers: Array<any>
  }>
  export const KapixCalendarInput: Component
  export const KapixFontAwesomeIconsInput: Component
  export const KapixFontFamilyInput: Component
  export const KapixGradientColorInput: Component

  // Kapix Image Viewer Input
  export type KapixImageViewerInputOptions = PartialAndNullable<{
    pubkey: string
    returnType: 'auto' | 'base64' | 'file'
    showStringInput: boolean
    multiple: boolean
    accept: string
  }> & KapixImageOptions
  export const KapixImageViewerInput: Component

  // Kapix Document Input
  export type KapixDocumentInputOptions = PartialAndNullable<{
    pubkey: string
    returnType: 'auto' | 'base64' | 'file'
    accept: string
    showStringInput: boolean
    multiple: boolean
  }>
  export const KapixDocumentInput: Component

  export const KapixJsonEditorInput: Component
  export const KapixMediaPlayerInput: Component
  export const KapixNavigationPropertyListInput: Component

  // Kapix Rating Input
  export const KapixRatingInput: Component
  export type KapixRatingOptions = PartialAndNullable<{
    halfIncrement: boolean
    starSize: number
    starFullIcon: string
    starEmptyIcon: string
    starHalfIcon: string
    starLength: number
  }>

  export interface IKapixSelectInputOptions<T extends Array<any> = Array<any>> extends ICommonItemSelectionOptions<T> {
    items: T
    itemCompare: string | ((item: T[number]) => any)
    returnObject: boolean
    iconMode: boolean
    noSelectionStyle: boolean
    // data
    dataSource: PartialAndNullable<ICommonItemSelectionOptions<T>> & {
      getAll: {
        url: string
      }
    }
  }
  // Kapix Select Input
  export type KapixSelectInputOptions<T extends Array<any> = Array<any>> = PartialAndNullable<IconsOptions & IKapixSelectInputOptions<T>>
  export const KapixSelectInput: Component

  export const KapixSelectMultipleInput: Component

  // Kapix Slider Input
  export type KapixSliderInputOptions = {
    min: number
    max: number
    step: number
    showNumberInput: boolean

    fullColor: 'currentColor' | string
    emptyColor: string
    dotColor: string
    dotSize: number | string
    thickness: number | string
  } 
  export const KapixSliderInput: Component
  
  // Kapix String Input
  type StringInputOptions = IconsOptions & StringOptions & {
    clearIcon: string
    loader: boolean
    clearable: boolean
    progressValue: number
    rules: keyof typeof businessRules | {
      regex: RegExp
      message?: string
    } | RegExp | IBusinessRule | Array<keyof typeof businessRules | {
      regex: RegExp
      message?: string
    } | RegExp | IBusinessRule>
  } 
  export type KapixStringInputOptions = PartialAndNullable<StringInputOptions>
  export type KapixPasswordInputOptions = PartialAndNullable<StringInputOptions & {
    showEyeIcon: boolean
    showPasswordIcon: string
    hidePasswordIcon: string
  }>
  export const KapixStringInput: Component

  // Kapix Number Input
  export type KapixNumberInputOptions = PartialAndNullable<StringInputOptions & {
    min: number
    max: number
    float: boolean
    precision: number
    step: number
  }>
  export const KapixNumberInput: Component

  // Kapix Switch Input
  export type KapixSwitchInputOptions = PartialAndNullable<{
    toggleInset: boolean
  }>
  export const KapixSwitchInput: Component

  export const KapixTextAreaInput: Component
  export const KapixTextEditorInput: Component

  // KapixTimePickerInput
  export type KapixTimePickerInputOptions = PartialAndNullable<StringInputOptions>
  export const KapixTimePickerInput: Component

  // Kapix Date Picker
  export type KapixDatePickerOptions = PartialAndNullable<StringInputOptions> & KapixCalendarInputOptions
  export const KapixDatePicker: Component

  export const KapixToggleButtonInput: Component
  export const KapixYesNoInput: Component
  export const KapixGetAvatarInput: Component
  export const KapixGravatarImgInput: Component
  export const KapixLottiePlayerInput: Component

  // Kapix Auto Complete Input
  export interface IKapixAutoCompleteInputOptions<
    T extends Array<any> = Array<any>,
    G extends GraphqlEntityService<IGraphqlEntityServiceModel> = never
  > extends ICommonItemSelectionOptions<T> {
    items: T
    autoCompleteDisplayMode: null | 1 | 2
    
    chipColor: string
    chipBackground: string
    noSelectionStyle: boolean
    // data
    dataSource: PartialAndNullable<ICommonItemSelectionOptions<Array<Partial<G['entity']['$prototype']['fullEntityType']>>>> & {
      service: G
      query?: Partial<IGraphqlRequestQueryOptions<G['entity']>>
    }
    menuPlacement: TooltipPlacement
    deletableChips: boolean
    sensitiveCase: boolean
    distinct: boolean
    allowUserInput: boolean
    maxSelectedItems: number
  }
  export type KapixAutoCompleteInputOptions<
    T extends Array<any> = Array<any>,
    G extends GraphqlEntityService<IGraphqlEntityServiceModel> = never
  > = PartialAndNullable<IconsOptions & IKapixAutoCompleteInputOptions<T, G>>
  export const KapixAutoCompleteInput: Component

  export const KapixVideoPlayerInput: Component
  export const KapixYoutubeInput: Component

  interface ILottieOptions {
    preserveAspectRatio: string
    src: string | File
    frames: Array<number>
    interactivityOptions: {
      mode: 'self-scroll' | 'scroll' | 'cursor'
      actions: Array<any>
    }
    loop: boolean
    autoplay: boolean
  }

  
  declare module '@vue/runtime-core' {
    export interface GlobalComponents {
      'KaElement': KaElementType
      'ka-element': KaElementType
      'KaContainer': KaContainerType
      'ka-container': KaContainerType
      'KaForm': KaContainerType
      'ka-form': KaContainerType
      'KapixTeleport': KapixTeleportType
      'kapix-teleport': KapixTeleportType
      'KapixDidacticiel': DefineComponent
      'kapix-didacticiel': DefineComponent
      'KapixTooltipsContainer': DefineComponent
      'kapix-tooltips-container': DefineComponent
    }
  }
  
  const KapixComponentsPlugin: KapixComponentsPluginType
  export default KapixComponentsPlugin
}
