export type ElementStatus =
  | 'pending'
  | 'idle'
  | 'error'
  | 'success'
  | 'redrawing'
  | 'readonly'

export type ElementType =
  | 'text'
  | 'group'
  | 'artboard'
  | 'image'
  | 'shape'
  | 'placeholder'

export interface Rect {
  x: number
  y: number
  width: number
  height: number
}

export interface ElementUIState {
  status: ElementStatus
  statusText?: string
  [key: string]: unknown
}

export type ResizeType = 'none' | 'both' | 'horizontal' | 'vertical'

export interface BaseElement extends Rect {
  id: string
  type: ElementType
  rotation: number
  originalWidth: number
  originalHeight: number
  parentId?: string
  hideMetadata?: boolean
  lockAspectRatio?: boolean
  resize?: ResizeType
  rotatable?: boolean
  scalable?: boolean
  selectable?: boolean
  draggable?: boolean
  data?: {
    [key: string]: unknown
  }
}

export interface ArtboardElement extends BaseElement {
  type: 'artboard'
  name?: string
  childrenIds: string[]
  background?: string
}

export interface GroupElement extends BaseElement {
  type: 'group'
  childrenIds: string[]
}

export interface ImageElement extends BaseElement {
  type: 'image'
  src: string
  fileName: string
  data?: {
    path?: string
    size?: number
    [key: string]: unknown
  }
}

export interface TextStyle {
  fontSize?: number
  fontWeight?: string | number
  color?: string
  fontFamily?: string
  lineHeight?: number
  textAlign?: 'left' | 'center' | 'right'
  fontStyle?: 'normal' | 'italic'
}

export interface TextElement extends BaseElement, TextStyle {
  type: 'text'
  content: string
}

export interface PlaceholderElement extends BaseElement {
  type: 'placeholder'
  label?: string
}

/**
 * 暂时没有这种类型
 */
export interface ShapeElement extends BaseElement {
  type: 'shape'
  shapeType: 'rect' | 'ellipse' | 'polygon'
  fill?: string
  stroke?: string
  strokeWidth?: number
}

export type SceneElement =
  | ArtboardElement
  | GroupElement
  | ImageElement
  | TextElement
  | ShapeElement
  | PlaceholderElement

export interface Viewport {
  x: number
  y: number
  scale: number
}

export interface SnapLine {
  type: 'x' | 'y'
  value: number
}

export interface Snapshot {
  elements: Record<string, SceneElement>
  elementOrder: string[]
}

export interface Padding {
  top?: number
  right?: number
  bottom?: number
  left?: number
}

export type ScrollAlignment = 'start' | 'center' | 'end' | 'nearest'

export interface ScrollIntoViewOptions {
  /**
   * 避开 UI 的内边距
   */
  padding?: Partial<Padding>
  /**
   * 垂直方向对齐方式
   * @default 'nearest'
   */
  block?: ScrollAlignment
  /**
   * 水平方向对齐方式
   * @default 'nearest'
   */
  inline?: ScrollAlignment
  /**
   * 是否强制平移（即使已在范围内）
   */
  force?: boolean
  /**
   * 缩放级别，如果不提供则使用当前缩放
   */
  scale?: number
}

export interface DominoState {
  elements: Record<string, SceneElement>
  placeholders: Record<string, PlaceholderElement>
  elementUIStates: Record<string, ElementUIState>
  elementOrder: string[] // Top-level elements ordering
  selectedIds: string[]
  focusedElementId: string | null
  hoveredElementId: string | null
  selectionBox: { x: number; y: number; width: number; height: number } | null
  mode: 'select' | 'pan'
  viewport: Viewport
  snapLines: SnapLine[] | null
  readOnly: boolean
  // Metadata for persistence
  metadata?: {
    createdAt?: number
    updatedAt?: number
  }
  padding: Padding
  // History
  past: Snapshot[]
  future: Snapshot[]
}

export interface DominoCanvasData {
  elements: Record<string, SceneElement>
  elementOrder: string[]
  viewport?: Viewport
  createdAt: number
  updatedAt: number
}

export interface DominoActions {
  setViewport: (viewport: Partial<Viewport>) => void
  setElementsData: (
    elements: Record<string, SceneElement>,
    order: string[],
  ) => void
  setFocusedElementId: (id: string | null) => void
  setHoveredElementId: (id: string | null) => void
  updateElementSize: (
    id: string,
    width: number,
    height: number,
    x?: number,
    y?: number,
  ) => void

  // History Actions
  undo: () => void
  redo: () => void
  takeSnapshot: () => void
  resetHistory: () => void
  setReadOnly: (readOnly: boolean) => void
}

export interface DominoEvents {
  onClick?: (e: React.MouseEvent | React.PointerEvent, id?: string) => void
  onSelect?: (ids: string[]) => void
  onElementClick?: (id: string, element: SceneElement) => void
  onTransformEnd?: (ids: string[]) => void
  onViewportChange?: (viewport: Viewport) => void
  onContextMenu?: (e: React.MouseEvent, id?: string) => void
  onHoverChange?: (id: string | null) => void
  onBeforeRemove?: (ids: string[]) => Promise<boolean> | boolean
  onElementsRemove?: (ids: string[]) => void
}

export interface DominoCanvasProps extends DominoEvents {
  className?: string
  style?: React.CSSProperties
  minScale?: number
  maxScale?: number
  initViewport?: Partial<Viewport>
  padding?: Partial<Padding>
  readOnly?: boolean
  children?: React.ReactNode

  // Controlled data
  elements?: Record<string, SceneElement>
  elementOrder?: string[]

  // Render hooks
  renderElement?: (props: {
    element: SceneElement
    defaultRender: React.ReactNode
  }) => React.ReactNode
  renderElementMetadata?: (props: { element: SceneElement }) => React.ReactNode
}
