<template>
  <div class="section-card">
    <!-- Main Headline -->
    <div class="text-center mb-6" v-if="hasData">
      <div class="text-3xl font-mono font-bold text-black dark:text-white mb-2">
        {{ mainHeadline }}
      </div>
      <div class="text-lg font-mono text-neutral-600 dark:text-neutral-400 mb-4">
        {{ subHeadline }}
      </div>
      
      <!-- Coverage Text -->
      <div class="text-base font-mono text-neutral-700 dark:text-neutral-300 mb-4" v-if="coverageText">
        {{ coverageText }}
      </div>
    </div>




    <!-- Toggles (Experiments) -->
    <div class="mb-6 space-y-3" v-if="hasData">
      <label class="flex items-center space-x-2 cursor-pointer">
        <input 
          v-model="includePlannedRevenue" 
          type="checkbox" 
          class="bitmap-checkbox"
        >
        <span class="text-sm font-mono font-bold text-black dark:text-white">Count planned income</span>
      </label>
      <label class="flex items-center space-x-2 cursor-pointer">
        <input 
          v-model="imagineNoIncome" 
          type="checkbox" 
          class="bitmap-checkbox"
        >
        <span class="text-sm font-mono font-bold text-black dark:text-white">Imagine no income</span>
      </label>
    </div>


    <!-- Chart Container -->
    <div class="mb-6">
      <div class="h-48 relative bg-white dark:bg-neutral-950 border border-black dark:border-white">
        <canvas 
          ref="chartCanvas" 
          class="w-full h-full"
          width="400" 
          height="192"
        ></canvas>
      </div>
    </div>

    <!-- Chart Caption -->
    <div class="text-center text-sm font-mono text-neutral-600 dark:text-neutral-400 mb-4" v-if="hasData">
      This shows how your coop's money might hold up over a year.
    </div>

    <!-- Guidance Sentence -->
    <div class="text-center mb-4" v-if="hasData">
      <div class="text-base font-mono text-neutral-700 dark:text-neutral-300">
        {{ guidanceText }}
      </div>
    </div>
    
    <!-- Diversification Risk -->
    <div v-if="diversificationGuidance" class="text-center text-sm font-mono text-neutral-600 dark:text-neutral-400 mb-4">
      {{ diversificationGuidance }}
    </div>
    
    <!-- Empty State -->
    <div v-else class="text-center py-8">
      <div class="text-neutral-400 mb-4">
        <svg class="mx-auto h-12 w-12" fill="none" viewBox="0 0 24 24" stroke="currentColor">
          <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 19v-6a2 2 0 00-2-2H5a2 2 0 00-2 2v6a2 2 0 002 2h2a2 2 0 002-2zm0 0V9a2 2 0 012-2h2a2 2 0 012 2v10m-6 0a2 2 0 002 2h2a2 2 0 002-2m0 0V5a2 2 0 012-2h2a2 2 0 012 2v14a2 2 0 01-2 2h-2a2 2 0 01-2-2z"/>
        </svg>
      </div>
      <p class="font-mono text-neutral-500 dark:text-neutral-500 text-sm">
        Complete the Setup Wizard to see your runway projection
      </p>
    </div>
  </div>
</template>

<script setup lang="ts">
interface Props {
  startingCash?: number
  revenuePlanned?: number[]
  expensePlanned?: number[]
  members?: Array<{ name: string, needs: number, targetPay: number, payRelationship: string }>
  diversificationGuidance?: string
}

const props = withDefaults(defineProps<Props>(), {
  startingCash: 0,
  revenuePlanned: () => [],
  expensePlanned: () => [],
  members: () => [],
  diversificationGuidance: ''
})

const includePlannedRevenue = ref(true)
const imagineNoIncome = ref(false)
const chartCanvas = ref<HTMLCanvasElement | null>(null)

const months = [...Array(12).keys()] // 0..11
const monthNames = ['Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec']
const targetMonths = 6
const horizon = 6

const toNum = (v:any) => Number.isFinite(+v) ? +v : 0

const monthlyCosts = computed(() => {
  if (!Array.isArray(props.expensePlanned)) return 0
  const sum = props.expensePlanned.reduce((a, b) => toNum(a) + toNum(b), 0)
  return sum / 12
})

// Keep the old name for compatibility
const monthlyBurn = monthlyCosts

const fmtCurrency = (v:number) => Number.isFinite(v) ? new Intl.NumberFormat(undefined,{style:'currency',currency:'USD',maximumFractionDigits:0}).format(v) : ''
const fmtShort = (v:number) => {
  if (!Number.isFinite(v)) return ''
  if (Math.abs(v) >= 1000) return `${(v/1000).toFixed(0)}k`
  return `${Math.round(v)}`
}

function outOfCashMonth(balances: number[]): number {
  return balances.findIndex(b => b < 0) // -1 if none
}

// Pay coverage calculations
const memberCoverage = computed(() => {
  if (!Array.isArray(props.members) || props.members.length === 0) return []
  
  return props.members.map(member => {
    const coverage = member.needs > 0 ? ((member.targetPay || 0) / member.needs) * 100 : 0
    return {
      name: member.name,
      coverage: Math.min(coverage, 200) // Cap at 200%
    }
  })
})

const coverageText = computed(() => {
  if (memberCoverage.value.length === 0) return ''
  
  const coverages = memberCoverage.value.map(m => m.coverage)
  const min = Math.min(...coverages)
  const max = Math.max(...coverages)
  
  if (min >= 80) {
    return "Most members' needs are nearly covered."
  } else if (min < 50) {
    return "Some members' needs are far from covered — consider adjusting pay relationships."
  } else {
    return `On this plan, coverage ranges from ${Math.round(min)}% to ${Math.round(max)}% of members' needs.`
  }
})


function project(includeRevenue: boolean, forceNoIncome = false) {
  const balances: number[] = []
  let bal = toNum(props.startingCash)
  
  // Pad arrays to 12 elements if shorter
  const revenuePadded = Array.isArray(props.revenuePlanned) ? 
    [...props.revenuePlanned, ...Array(12 - props.revenuePlanned.length).fill(0)].slice(0, 12) :
    Array(12).fill(0)
  const expensesPadded = Array.isArray(props.expensePlanned) ? 
    [...props.expensePlanned, ...Array(12 - props.expensePlanned.length).fill(0)].slice(0, 12) :
    Array(12).fill(0)
  
  for (let i = 0; i < 12; i++) {
    const inflow = (includeRevenue && !forceNoIncome) ? toNum(revenuePadded[i]) : 0
    const outflow = toNum(expensesPadded[i])
    bal = bal + inflow - outflow
    balances.push(bal)
  }
  return balances
}

const withRev = computed(() => project(true, imagineNoIncome.value))
const noRev = computed(() => project(false, true))

function runwayFrom(balances: number[]) {
  // find first month index where balance < 0
  const i = balances.findIndex(b => b < 0)
  if (i === -1) return 12 // survived 12+ months
  // linear interpolation within month i
  const prev = i === 0 ? toNum(props.startingCash) : toNum(balances[i-1])
  const delta = toNum(balances[i]) - prev
  const frac = delta === 0 ? 0 : (0 - prev) / delta // 0..1
  return Math.max(0, (i-1) + frac + 1) // months from now
}

// Check if we have meaningful data
const hasData = computed(() => {
  return props.startingCash > 0 || 
         (Array.isArray(props.revenuePlanned) && props.revenuePlanned.some(v => v > 0)) || 
         (Array.isArray(props.expensePlanned) && props.expensePlanned.some(v => v > 0))
})

const runwayMonths = computed(() => {
  if (!hasData.value) return 0
  if (monthlyCosts.value <= 0) return 12
  
  if (imagineNoIncome.value) {
    return runwayFrom(noRev.value)
  } else {
    return includePlannedRevenue.value ? runwayFrom(withRev.value) : runwayFrom(noRev.value)
  }
})

const mainHeadline = computed(() => {
  const months = runwayMonths.value >= 12 ? '12+' : runwayMonths.value.toFixed(1)
  return `You could keep going for about ${months} months.`
})

const subHeadline = computed(() => {
  return `That's with monthly costs of ${fmtCurrency(monthlyCosts.value)} and the income ideas you entered.`
})

const guidanceText = computed(() => {
  const months = runwayMonths.value
  if (months < 3) {
    return "This sketch shows less than 3 months covered — that's risky."
  } else if (months <= 6) {
    return "This sketch shows about 3–6 months — that's a common minimum target."
  } else {
    return "This sketch shows more than 6 months — a safer position."
  }
})


const bufferFlagText = computed(() => {
  return guidanceText.value
})


// Out-of-money month computations  
const oocWith = computed(() => outOfCashMonth(withRev.value))
const oocNo = computed(() => outOfCashMonth(noRev.value))

// Path to Safe Buffer calculation

// Break-even Month calculation





const projectionData = computed(() => {
  const monthIndices = [...Array(13).keys()] // 0..12 for chart display
  const withIncome = []
  const withoutIncome = []
  
  // Pad arrays to 12 elements if shorter
  const revenuePadded = Array.isArray(props.revenuePlanned) ? 
    [...props.revenuePlanned, ...Array(12 - props.revenuePlanned.length).fill(0)].slice(0, 12) :
    Array(12).fill(0)
  const expensesPadded = Array.isArray(props.expensePlanned) ? 
    [...props.expensePlanned, ...Array(12 - props.expensePlanned.length).fill(0)].slice(0, 12) :
    Array(12).fill(0)
  
  // Start with initial balance
  withIncome.push(toNum(props.startingCash))
  withoutIncome.push(toNum(props.startingCash))
  
  // Project forward month by month
  for (let i = 0; i < 12; i++) {
    const lastWithIncome = withIncome[withIncome.length - 1]
    const lastWithoutIncome = withoutIncome[withoutIncome.length - 1]
    
    // Safe access to array values using toNum helper
    const revenueAmount = toNum(revenuePadded[i])
    const expenseAmount = toNum(expensesPadded[i])
    
    // Line A: with income ideas
    const withIncomeBalance = lastWithIncome + revenueAmount - expenseAmount
    withIncome.push(withIncomeBalance)
    
    // Line B: no income
    const withoutIncomeBalance = lastWithoutIncome - expenseAmount
    withoutIncome.push(withoutIncomeBalance)
  }
  
  return { months: monthIndices, withIncome, withoutIncome }
})

const drawChart = () => {
  if (!chartCanvas.value) return
  
  const canvas = chartCanvas.value
  const ctx = canvas.getContext('2d')
  if (!ctx) return
  
  // Clear canvas
  ctx.clearRect(0, 0, canvas.width, canvas.height)
  
  if (!hasData.value) {
    // Draw empty state in chart
    ctx.fillStyle = '#6b7280'
    ctx.font = '14px monospace'
    ctx.textAlign = 'center'
    ctx.fillText('No data available', canvas.width / 2, canvas.height / 2)
    return
  }
  
  const { months, withIncome, withoutIncome } = projectionData.value
  
  const padding = 40
  const chartWidth = canvas.width - padding * 2
  const chartHeight = canvas.height - padding * 2
  
  // Calculate scale - ensure all values are finite numbers
  const allValues = [...withIncome, ...withoutIncome].map(v => toNum(v))
  const maxValue = Math.max(...allValues, toNum(props.startingCash))
  const minValue = Math.min(...allValues, 0)
  const valueRange = Math.max(maxValue - minValue, 1000) // ensure minimum range
  
  const scaleX = chartWidth / 12
  const scaleY = chartHeight / valueRange
  
  // Helper function to get canvas coordinates
  const getX = (month: number) => padding + (month * scaleX)
  const getY = (value: number) => padding + chartHeight - ((value - minValue) * scaleY)
  
  // Fill background red where balance < 0
  ctx.fillStyle = 'rgba(239, 68, 68, 0.1)'
  const zeroY = getY(0)
  ctx.fillRect(padding, zeroY, chartWidth, canvas.height - zeroY - padding)
  
  // Draw grid lines
  ctx.strokeStyle = '#e5e7eb'
  ctx.lineWidth = 1
  
  // Horizontal grid lines
  for (let i = 0; i <= 4; i++) {
    const y = padding + (chartHeight / 4) * i
    ctx.beginPath()
    ctx.moveTo(padding, y)
    ctx.lineTo(padding + chartWidth, y)
    ctx.stroke()
  }
  
  // Vertical grid lines
  for (let i = 0; i <= 12; i += 3) {
    const x = getX(i)
    ctx.beginPath()
    ctx.moveTo(x, padding)
    ctx.lineTo(x, padding + chartHeight)
    ctx.stroke()
  }
  
  // Draw zero line
  ctx.strokeStyle = '#6b7280'
  ctx.lineWidth = 2
  ctx.beginPath()
  ctx.moveTo(padding, zeroY)
  ctx.lineTo(padding + chartWidth, zeroY)
  ctx.stroke()
  
  // Draw vertical reference lines at out-of-cash points
  ctx.strokeStyle = '#ef4444'
  ctx.lineWidth = 1
  ctx.setLineDash([5, 5])
  
  if (oocWith.value !== -1) {
    const x = getX(oocWith.value)
    ctx.beginPath()
    ctx.moveTo(x, padding)
    ctx.lineTo(x, padding + chartHeight)
    ctx.stroke()
    
    // Label
    ctx.fillStyle = '#ef4444'
    ctx.font = '10px monospace'
    ctx.textAlign = 'center'
    ctx.fillText('OOC', x, padding - 5)
  }
  
  if (oocNo.value !== -1 && oocNo.value !== oocWith.value) {
    const x = getX(oocNo.value)
    ctx.beginPath()
    ctx.moveTo(x, padding)
    ctx.lineTo(x, padding + chartHeight)
    ctx.stroke()
    
    // Label
    ctx.fillStyle = '#ef4444'
    ctx.font = '10px monospace'
    ctx.textAlign = 'center'
    ctx.fillText('OOC', x, padding - 5)
  }
  
  ctx.setLineDash([])
  
  // Draw Line A (with income) - always show, bold if selected
  ctx.strokeStyle = '#22c55e'
  ctx.lineWidth = (includePlannedRevenue.value && !imagineNoIncome.value) ? 3 : 2
  ctx.globalAlpha = (includePlannedRevenue.value && !imagineNoIncome.value) ? 1 : 0.6
  ctx.beginPath()
  withIncome.forEach((value, index) => {
    const x = getX(index)
    const y = getY(toNum(value))
    if (index === 0) {
      ctx.moveTo(x, y)
    } else {
      ctx.lineTo(x, y)
    }
  })
  ctx.stroke()
  
  // Add point annotation where active scenario crosses y=0
  if (includePlannedRevenue.value && !imagineNoIncome.value) {
    const crossingIdx = withIncome.findIndex((value, idx) => {
      if (idx === 0) return false
      const prev = toNum(withIncome[idx - 1])
      const curr = toNum(value)
      return prev >= 0 && curr < 0
    })
    
    if (crossingIdx !== -1) {
      const x = getX(crossingIdx)
      const y = getY(0)
      ctx.fillStyle = '#22c55e'
      ctx.beginPath()
      ctx.arc(x, y, 4, 0, 2 * Math.PI)
      ctx.fill()
      
      // Add label
      ctx.fillStyle = '#22c55e'
      ctx.font = '10px monospace'
      ctx.textAlign = 'center'
      ctx.fillText('Out of money', x, y - 10)
    }
  }
  
  // Draw Line B (no income) - always show, bold if selected
  ctx.strokeStyle = '#ef4444'
  ctx.lineWidth = (!includePlannedRevenue.value || imagineNoIncome.value) ? 3 : 2
  ctx.globalAlpha = (!includePlannedRevenue.value || imagineNoIncome.value) ? 1 : 0.6
  ctx.beginPath()
  withoutIncome.forEach((value, index) => {
    const x = getX(index)
    const y = getY(toNum(value))
    if (index === 0) {
      ctx.moveTo(x, y)
    } else {
      ctx.lineTo(x, y)
    }
  })
  ctx.stroke()
  
  // Add point annotation where active scenario crosses y=0
  if (!includePlannedRevenue.value || imagineNoIncome.value) {
    const crossingIdx = withoutIncome.findIndex((value, idx) => {
      if (idx === 0) return false
      const prev = toNum(withoutIncome[idx - 1])
      const curr = toNum(value)
      return prev >= 0 && curr < 0
    })
    
    if (crossingIdx !== -1) {
      const x = getX(crossingIdx)
      const y = getY(0)
      ctx.fillStyle = '#ef4444'
      ctx.beginPath()
      ctx.arc(x, y, 4, 0, 2 * Math.PI)
      ctx.fill()
      
      // Add label
      ctx.fillStyle = '#ef4444'
      ctx.font = '10px monospace'
      ctx.textAlign = 'center'
      ctx.fillText('Out of money', x, y - 10)
    }
  }
  
  ctx.globalAlpha = 1
  
  // Draw axis labels
  ctx.fillStyle = '#6b7280'
  ctx.font = '12px monospace'
  ctx.textAlign = 'center'
  
  // X-axis labels (months)
  for (let i = 0; i <= 12; i += 3) {
    const x = getX(i)
    ctx.fillText(i.toString(), x, canvas.height - 10)
  }
  
  // Y-axis labels (balance) - guarded formatting
  ctx.textAlign = 'right'
  for (let i = 0; i <= 4; i++) {
    const value = minValue + (valueRange / 4) * (4 - i)
    const y = padding + (chartHeight / 4) * i + 4
    const formattedValue = Number.isFinite(value) ? fmtShort(value) : '0'
    ctx.fillText(formattedValue, padding - 10, y)
  }
}

// Watch for changes that should trigger chart redraw
watch([includePlannedRevenue, imagineNoIncome, projectionData], () => {
  nextTick(() => drawChart())
}, { deep: true })

onMounted(() => {
  nextTick(() => drawChart())
})
</script>