/**
 * Scenic Background — Skandinavische Landschaftsanimation
 *
 * Erzeugt eine sanfte, minimalistische Hintergrundszene mit:
 * - Sanften Hügeln / Fjord-Silhouette
 * - Segelboot das langsam vorbeifährt
 * - Wolken die ziehen
 * - Vögel die fliegen
 * - Subtile Wellenbewegung
 *
 * Alles in gedeckten Naturfarben, leicht und beruhigend.
 */

interface ScenicElement {
  x: number
  y: number
  speed: number
  size: number
  opacity: number
}

interface Cloud extends ScenicElement {
  width: number
}

interface Bird extends ScenicElement {
  wingPhase: number
  wingSpeed: number
}

interface Boat extends ScenicElement {
  bobPhase: number
}

interface Wave {
  offset: number
  amplitude: number
  frequency: number
  speed: number
}

export class ScenicBackground {
  private canvas: HTMLCanvasElement
  private ctx: CanvasRenderingContext2D
  private width = 0
  private height = 0
  private time = 0
  private animId = 0

  private clouds: Cloud[] = []
  private birds: Bird[] = []
  private boat: Boat
  private waves: Wave[] = []

  // Farben — skandinavisch gedeckt
  private colors = {
    sky:        '#e8ebe6',
    skyBottom:  '#d4ddd6',
    water:      '#9ab5b8',
    waterDeep:  '#7a9ea2',
    mountain:   '#8a9a8c',
    mountainFar:'#b0bab2',
    land:       '#a4b09a',
    cloud:      '#ffffff',
    boat:       '#c07a6b',
    boatSail:   '#f0eeea',
    bird:       '#5a5a5a',
  }

  constructor(container: HTMLElement) {
    this.canvas = document.createElement('canvas')
    this.canvas.style.cssText = 'position:absolute;top:0;left:0;width:100%;height:100%;pointer-events:none;z-index:0;'
    container.style.position = 'relative'
    container.prepend(this.canvas)

    const ctx = this.canvas.getContext('2d')
    if (!ctx) throw new Error('Canvas 2D not supported')
    this.ctx = ctx

    this.boat = { x: -100, y: 0, speed: 0.3, size: 1, opacity: 0.7, bobPhase: 0 }

    this.resize()
    this.initElements()
    window.addEventListener('resize', () => this.resize())
  }

  private resize(): void {
    const rect = this.canvas.parentElement!.getBoundingClientRect()
    const dpr = window.devicePixelRatio || 1
    this.width = rect.width
    this.height = rect.height
    this.canvas.width = this.width * dpr
    this.canvas.height = this.height * dpr
    this.ctx.scale(dpr, dpr)
  }

  private initElements(): void {
    // Wolken
    this.clouds = Array.from({ length: 5 }, () => ({
      x: Math.random() * this.width * 1.5,
      y: this.height * (0.05 + Math.random() * 0.15),
      speed: 0.1 + Math.random() * 0.2,
      size: 0.6 + Math.random() * 0.6,
      opacity: 0.3 + Math.random() * 0.4,
      width: 60 + Math.random() * 80,
    }))

    // Vögel
    this.birds = Array.from({ length: 3 }, () => ({
      x: Math.random() * this.width,
      y: this.height * (0.1 + Math.random() * 0.2),
      speed: 0.4 + Math.random() * 0.3,
      size: 4 + Math.random() * 4,
      opacity: 0.3 + Math.random() * 0.2,
      wingPhase: Math.random() * Math.PI * 2,
      wingSpeed: 3 + Math.random() * 2,
    }))

    // Wellen
    this.waves = Array.from({ length: 3 }, (_, i) => ({
      offset: 0,
      amplitude: 2 + i * 1.5,
      frequency: 0.008 + i * 0.003,
      speed: 0.3 + i * 0.15,
    }))
  }

  start(): void {
    const animate = () => {
      this.time += 0.016
      this.update()
      this.draw()
      this.animId = requestAnimationFrame(animate)
    }
    animate()
  }

  stop(): void {
    cancelAnimationFrame(this.animId)
  }

  private update(): void {
    // Wolken bewegen
    for (const c of this.clouds) {
      c.x += c.speed
      if (c.x > this.width + c.width) {
        c.x = -c.width * 2
        c.y = this.height * (0.05 + Math.random() * 0.15)
      }
    }

    // Vögel bewegen
    for (const b of this.birds) {
      b.x += b.speed
      b.wingPhase += b.wingSpeed * 0.016
      b.y += Math.sin(this.time * 0.5 + b.wingPhase) * 0.15
      if (b.x > this.width + 50) {
        b.x = -50
        b.y = this.height * (0.1 + Math.random() * 0.2)
      }
    }

    // Boot bewegen
    this.boat.x += this.boat.speed
    this.boat.bobPhase += 0.02
    if (this.boat.x > this.width + 100) {
      this.boat.x = -100
    }

    // Wellen
    for (const w of this.waves) {
      w.offset += w.speed
    }
  }

  private draw(): void {
    const { ctx, width: w, height: h } = this
    const waterLine = h * 0.55

    ctx.clearRect(0, 0, w, h)

    // Himmel — sanfter Gradient
    const skyGrad = ctx.createLinearGradient(0, 0, 0, waterLine)
    skyGrad.addColorStop(0, this.colors.sky)
    skyGrad.addColorStop(1, this.colors.skyBottom)
    ctx.fillStyle = skyGrad
    ctx.fillRect(0, 0, w, waterLine)

    // Ferne Berge
    this.drawMountains(ctx, w, waterLine, this.colors.mountainFar, 0.35, 0.08)
    this.drawMountains(ctx, w, waterLine, this.colors.mountain, 0.45, 0.12)

    // Wolken
    for (const c of this.clouds) {
      this.drawCloud(ctx, c)
    }

    // Vögel
    for (const b of this.birds) {
      this.drawBird(ctx, b)
    }

    // Wasser
    const waterGrad = ctx.createLinearGradient(0, waterLine, 0, h)
    waterGrad.addColorStop(0, this.colors.water)
    waterGrad.addColorStop(1, this.colors.waterDeep)
    ctx.fillStyle = waterGrad
    ctx.fillRect(0, waterLine, w, h - waterLine)

    // Wellen auf dem Wasser
    for (const wave of this.waves) {
      ctx.beginPath()
      ctx.moveTo(0, waterLine)
      for (let x = 0; x <= w; x += 3) {
        const y = waterLine + Math.sin(x * wave.frequency + wave.offset * 0.01) * wave.amplitude
        ctx.lineTo(x, y)
      }
      ctx.lineTo(w, h)
      ctx.lineTo(0, h)
      ctx.closePath()
      ctx.fillStyle = `rgba(255,255,255,0.04)`
      ctx.fill()
    }

    // Boot
    const boatY = waterLine - 8 + Math.sin(this.boat.bobPhase) * 2.5
    this.drawBoat(ctx, this.boat.x, boatY)

    // Sanfter Fade nach unten (damit Text darüber lesbar bleibt)
    const fadeGrad = ctx.createLinearGradient(0, h * 0.7, 0, h)
    fadeGrad.addColorStop(0, 'rgba(250,250,248,0)')
    fadeGrad.addColorStop(1, 'rgba(250,250,248,1)')
    ctx.fillStyle = fadeGrad
    ctx.fillRect(0, h * 0.7, w, h * 0.3)
  }

  private drawMountains(ctx: CanvasRenderingContext2D, w: number, baseline: number, color: string, heightFactor: number, roughness: number): void {
    ctx.beginPath()
    ctx.moveTo(0, baseline)

    const segments = 8
    const segW = w / segments
    for (let i = 0; i <= segments; i++) {
      const x = i * segW
      const peakH = baseline * heightFactor * (0.5 + Math.sin(i * 1.3 + 0.5) * 0.5)
      const y = baseline - peakH + Math.sin(i * 2.7) * baseline * roughness
      if (i === 0) {
        ctx.lineTo(x, y)
      } else {
        const cpx = x - segW * 0.5
        const cpy = y - baseline * roughness * 0.3
        ctx.quadraticCurveTo(cpx, cpy, x, y)
      }
    }

    ctx.lineTo(w, baseline)
    ctx.closePath()
    ctx.fillStyle = color
    ctx.fill()
  }

  private drawCloud(ctx: CanvasRenderingContext2D, c: Cloud): void {
    ctx.globalAlpha = c.opacity
    ctx.fillStyle = this.colors.cloud

    const cx = c.x
    const cy = c.y
    const s = c.size

    // Wolke aus überlappenden Ellipsen
    ctx.beginPath()
    ctx.ellipse(cx, cy, 30 * s, 12 * s, 0, 0, Math.PI * 2)
    ctx.fill()
    ctx.beginPath()
    ctx.ellipse(cx - 18 * s, cy + 2 * s, 20 * s, 10 * s, 0, 0, Math.PI * 2)
    ctx.fill()
    ctx.beginPath()
    ctx.ellipse(cx + 20 * s, cy + 3 * s, 22 * s, 9 * s, 0, 0, Math.PI * 2)
    ctx.fill()

    ctx.globalAlpha = 1
  }

  private drawBird(ctx: CanvasRenderingContext2D, b: Bird): void {
    const wingAngle = Math.sin(b.wingPhase) * 0.4
    ctx.globalAlpha = b.opacity
    ctx.strokeStyle = this.colors.bird
    ctx.lineWidth = 1.5
    ctx.lineCap = 'round'

    ctx.beginPath()
    ctx.moveTo(b.x - b.size, b.y - wingAngle * b.size)
    ctx.quadraticCurveTo(b.x, b.y + 1, b.x + b.size, b.y - wingAngle * b.size)
    ctx.stroke()

    ctx.globalAlpha = 1
  }

  private drawBoat(ctx: CanvasRenderingContext2D, x: number, y: number): void {
    ctx.globalAlpha = this.boat.opacity
    const s = 0.8

    // Rumpf
    ctx.fillStyle = this.colors.boat
    ctx.beginPath()
    ctx.moveTo(x - 20 * s, y)
    ctx.lineTo(x - 16 * s, y + 8 * s)
    ctx.lineTo(x + 16 * s, y + 8 * s)
    ctx.lineTo(x + 20 * s, y)
    ctx.closePath()
    ctx.fill()

    // Mast
    ctx.strokeStyle = '#5a5a5a'
    ctx.lineWidth = 1.5
    ctx.beginPath()
    ctx.moveTo(x, y)
    ctx.lineTo(x, y - 22 * s)
    ctx.stroke()

    // Segel
    ctx.fillStyle = this.colors.boatSail
    ctx.beginPath()
    ctx.moveTo(x + 1, y - 20 * s)
    ctx.lineTo(x + 14 * s, y - 4 * s)
    ctx.lineTo(x + 1, y - 2 * s)
    ctx.closePath()
    ctx.fill()

    ctx.globalAlpha = 1
  }
}
