<template>
  <rung-builder :name="prices.length>1?'Ladder':'Limit'" :order="order" :builder="builder"
                v-model:value-a="priceA" v-model:value-b="priceB" :mode="0" :shape="HLine"
                :get-model-value="getModelValue" :set-model-value="setModelValue"
                :set-values="setPrices" :set-weights="setWeights"
                :std-width="stdWidth" :build-tranches="buildTranches">
    <table>
      <tbody>
      <template v-if="prices.length>1">
        <tr>
          <td>
            <v-text-field type="number" v-model="higherPrice" min="0"
                          density="compact" hide-details class="mx-1 my-2" variant="outlined"
                          label="Price"
                          :color="color" :base-color="color"
                          style="flex: 6em"
            />
          </td>
          <td class="weight">{{ allocationText(weights[higherIndex]) }}</td>
        </tr>
        <tr v-for="i in innerIndexes" class="ml-5">
          <td class="pl-5">{{ prices[i] }}</td>
          <td class="weight">{{ allocationText(weights[i]) }}</td>
        </tr>
      </template>
      <tr>
        <td>
          <v-text-field type="number" v-model="lowerPrice" min="0"
                        density="compact" hide-details class="mx-1 my-2" variant="outlined"
                        label="Price"
                        :color="color" :base-color="color"
                        style="flex: 6em"
          />
        </td>
        <td class="weight">{{ weights.length ? allocationText(weights[lowerIndex]) : '' }}</td>
      </tr>
      </tbody>
    </table>
  </rung-builder>
</template>

<script setup>
import {applyLine2, builderDefaults, useChartOrderStore} from "@/orderbuild.js";
import {sideColor} from "@/misc.js";
import {useTheme} from "vuetify";
import {useOrderStore, useStore} from "@/store/store.js";
import {MAX_FRACTION, newTranche} from "@/blockchain/orderlib.js";
import RungBuilder from "@/components/chart/RungBuilder.vue";
import {computed, ref, watchEffect} from "vue";
import {chart} from "@/charts/chart.js";
import {HLine} from "@/charts/shape.js";

const s = useStore()
const os = useOrderStore()
const co = useChartOrderStore()
const theme = useTheme().current
const props = defineProps(['order', 'builder'])

function computeDefaultColor() {
  const index = props.order.builders.indexOf(props.builder)
  return sideColor(props.order.buy, index)
}

const defaultColor = computeDefaultColor()

// Fields must be defined in order to be reactive
builderDefaults(props.builder, {
  start: null, // todo
  end: null, // todo
  priceA: null,
  priceB: null,
  rungs: 1,
  skew: 0,
  color: defaultColor,
})

function buildTranches() {
  const order = props.order
  const builder = props.builder
  const tranches = []

  console.log('buildTranches', builder, order, tranches)
  const ps = prices.value
  const ws = weights.value
  for(let i=0; i<ps.length; i++) {
    const p = ps[i]
    const w = ws[i]
    const t = newTranche({
      // todo start/end
      fraction: w * MAX_FRACTION,
    })
    const symbol = co.selectedSymbol
    console.log('symbol', symbol)
    applyLine2(t, !order.buy, p, 0, symbol.decimals, symbol.inverted)
    tranches.push(t)
  }
  return tranches
}


const priceA = computed({
  get() { return props.builder.priceA },
  set(v) {
    props.builder.priceA = v===null ? v : Number(v)
  }
})

const priceB = computed({
  get() { return props.builder.priceB },
  set(v) {
    props.builder.priceB = v===null ? v : Number(v)
  }
})

const flipped = computed(()=>{
  const a = props.builder.priceA
  const b = props.builder.priceB
  return a !== null && b !== null && a > b
})

const higherPrice = computed({
  get() { return flipped.value ? priceA.value : priceB.value },
  set(v) {
    if (flipped.value)
      priceA.value = v
    else
      priceB.value = v
  }
})

const higherIndex = computed(()=>flipped.value ? 0 : weights.value.length-1)
const lowerIndex = computed(()=>!flipped.value ? 0 : weights.value.length-1)
const innerIndexes = computed(()=>{
  const result = []
  const n = prices.value.length
  const f = flipped.value
  for (let i=1; i<n-1; i++)
    result.push(f?i:n-1-i)
  return result
})

const lowerPrice = computed({
  get() {
    return !flipped.value ? priceA.value : priceB.value
  },
  set(v) {
    if (!flipped.value)
      priceA.value = v
    else
      priceB.value = v
  }
})

const start = computed({
  get() {return props.builder.start || 0},
  set(v) {props.builder.start=v; },
})

const end = computed({
  get() {return props.builder.end || 0},
  set(v) {props.builder.end=v; },
})


const prices = ref([])
const weights = ref([])
function setPrices(ps) {prices.value = ps}
function setWeights(ws) { weights.value = ws }


const color = computed(()=>props.builder.color ? props.builder.color : defaultColor)

function computeRange() {
  let range = 0
  const series = chart.getSeries()
  const bars = series.data().bars();
  const final = Math.max(bars.size() - 50, 0)
  let count = 0
  for (let barIndex = bars.size() - 1; barIndex >= final; barIndex--) {
    count++
    const [_time, _open, high, low, _close, _volume, _ms] = bars.valueAt(barIndex)
    range += (high - low)
  }
  if (count > 0)
    range /= count
  else
    range = 1
  return range
}

const stdWidth = 2*computeRange() // todo make reactive


const amountSymbol = computed(()=>props.order.amountIsTokenA ? co.selectedSymbol.base.s : co.selectedSymbol.quote.s )


// todo move into misc and use in shape as well
function allocationText(weight) {
  const alloc = props.builder.allocation
  if (alloc===null) return ''
  const w = weight * alloc
  // console.log('weight', weight, alloc, props.amount)
  const a = props.order.amount * w
  return `${(w*100).toFixed(1)}% = ${a.toLocaleString('fullwide')} ${amountSymbol.value}`
}

function getModelValue(model) {
  if(!model)
    return null
  return model.price
}

function setModelValue(model, value) {
  // console.log('setModelValue->', {...model}, value)
  if (model.price !== value)
    model.price = value
}


</script>

<style scoped lang="scss">
:deep(.v-slider.v-input--vertical > .v-input__control) {
  min-height: 5em !important;
}
:deep(.v-slider.no-slider-bg .v-slider-track__fill) {
  background-color: inherit !important;
}
td.weight {
  padding-left: 0.5em;
  padding-right: 0.5em;
  text-align: right;
}
</style>

