import { IconDefinition, IconLookup, IconName, IconPrefix } from '@fortawesome/fontawesome-svg-core'
import { DefineComponent, FunctionalComponent, AllowedComponentProps, VNodeProps } from 'vue'

type IconProp = IconDefinition | IconLookup | [IconPrefix, IconName] | IconName | (string & {}) | object

interface GradientStop {
  offset: string | number
  color: string
  opacity?: number
}

interface LinearGradientFill {
  type: 'linear'
  id: string
  x1?: string | number
  y1?: string | number
  x2?: string | number
  y2?: string | number
  stops: GradientStop[]
}

interface RadialGradientFill {
  type: 'radial'
  id: string
  cx?: string | number
  cy?: string | number
  r?: string | number
  fx?: string | number
  fy?: string | number
  stops: GradientStop[]
}

interface FontAwesomeIconProps {
  border?: boolean
  fixedWidth?: boolean
  flip?: 'horizontal' | 'vertical' | 'both' | boolean
  icon: IconProp
  mask?: IconProp
  maskId?: string
  listItem?: boolean
  pull?: 'right' | 'left'
  pulse?: boolean
  rotation?: 90 | 180 | 270 | '90' | '180' | '270'
  rotateBy?: boolean
  swapOpacity?: boolean
  size?: '2xs' | 'xs' | 'sm' | 'lg' | 'xl' | '2xl' | '1x' | '2x' | '3x' | '4x' | '5x' | '6x' | '7x' | '8x' | '9x' | '10x'
  spin?: boolean
  transform?: object | string
  symbol?: boolean | string
  title?: string
  titleId?: string
  inverse?: boolean
  bounce?: boolean
  shake?: boolean
  beat?: boolean
  fade?: boolean
  beatFade?: boolean
  flash?: boolean
  spinPulse?: boolean
  spinReverse?: boolean
  widthAuto?: boolean
  canvasSquare?: boolean
  canvasRoomy?: boolean
  gradientFill?: LinearGradientFill | RadialGradientFill
  flip360?: boolean
  buzz?: boolean
  float?: boolean
  jello?: boolean
  spinSnap?: boolean
  spinSnap4?: boolean
  spinSnap8?: boolean
  swing?: boolean
  wag?: boolean
}

interface FontAwesomeLayersProps {
  fixedWidth?: boolean
}

interface FontAwesomeLayersTextProps {
  value: string | number
  transform?: object | string
  counter?: boolean
  position?: 'bottom-left' | 'bottom-right' | 'top-left' | 'top-right'
}

declare const FontAwesomeIcon: FunctionalComponent<FontAwesomeIconProps & AllowedComponentProps & VNodeProps>
declare const FontAwesomeLayers: DefineComponent<FontAwesomeLayersProps>
declare const FontAwesomeLayersText: DefineComponent<FontAwesomeLayersTextProps>

export {
  FontAwesomeIcon,
  FontAwesomeIconProps,
  FontAwesomeLayers,
  FontAwesomeLayersProps,
  FontAwesomeLayersText,
  FontAwesomeLayersTextProps,
  GradientStop,
  LinearGradientFill,
  RadialGradientFill,
  IconProp
}
