package onelead

import (
	"image/color"
	"math"
	"odoki-firmware/constants"
	"odoki-firmware/ecg"
	"odoki-firmware/utils"

	"tinygo.org/x/drivers/st7789"
	"tinygo.org/x/tinyfont"
	"tinygo.org/x/tinyfont/freemono"
)

var SelectedLead = 1
var LeadNames = []string{"I", "II", "III"}
var LastDrawnIndex int16

var DisplayBufferMinMaxes [constants.ChannelCount][2]int32

const PlotHeight = (constants.DisplayHeight - constants.LineHeight*2 - constants.Padding*2)

func DrawPair(display st7789.Device, x, start, end int16) {
	min := min(start, end)
	max := max(start, end)
	display.FillRectangle(constants.Padding+x, constants.Padding+constants.LineHeight*2, 1, PlotHeight, color.RGBA{0, 0, 0, 255})
	display.FillRectangle(constants.Padding+x, constants.Padding+constants.LineHeight*2+PlotHeight-max, 1, max-min+1, color.RGBA{255, 255, 255, 255})
}

func IndexToY(index int16) int16 {
	if DisplayBufferMinMaxes[SelectedLead][0] == DisplayBufferMinMaxes[SelectedLead][1] {
		return int16(math.Round(0.5 * float64(PlotHeight-1)))
	}
	return int16(float64(PlotHeight-1) * utils.RemapInt32FromRange(int(DisplayBufferMinMaxes[SelectedLead][0]), int(DisplayBufferMinMaxes[SelectedLead][1]), ecg.DisplayBuffers[SelectedLead][index]))
}

func Draw(VoidDisplayed bool, display st7789.Device) bool {
	if VoidDisplayed {
		display.FillScreen(color.RGBA{0, 0, 0, 255})
		tinyfont.WriteLine(&display, &freemono.Bold9pt7b, constants.Padding, constants.Padding+constants.LineHeight, "ECG "+LeadNames[SelectedLead], color.RGBA{255, 255, 255, 255})
		display.FillRectangle(constants.Padding, constants.Padding+constants.LineHeight*2, constants.DisplayECGBufferSize, PlotHeight, color.RGBA{0, 0, 0, 255})
		DrawPair(display, constants.Padding, IndexToY(constants.DisplayECGBufferSize-2), IndexToY(constants.DisplayECGBufferSize-1))
		DrawPair(display, constants.Padding+1, IndexToY(constants.DisplayECGBufferSize-1), IndexToY(0))
		for i := 2; i < int(constants.DisplayECGBufferSize); i++ {
			DrawPair(display, int16(i)+constants.Padding, IndexToY(int16(i)-2), IndexToY(int16(i)-1))
		}
	}
	if LastDrawnIndex != ecg.DisplayBufferIndex {
		DisplayBufferMinMaxes[SelectedLead][0], DisplayBufferMinMaxes[SelectedLead][1] = utils.MinMaxInt32(ecg.DisplayBuffers[SelectedLead][:])
		lastDisplayBufferIndex := (ecg.DisplayBufferIndex - 1)
		if lastDisplayBufferIndex == -1 {
			lastDisplayBufferIndex = constants.DisplayECGBufferSize - 1
		}
		beforeLastDisplayBufferIndex := (ecg.DisplayBufferIndex - 2)
		if beforeLastDisplayBufferIndex < 0 {
			beforeLastDisplayBufferIndex = constants.DisplayECGBufferSize + beforeLastDisplayBufferIndex
		}
		DrawPair(display, ecg.DisplayBufferIndex, IndexToY(beforeLastDisplayBufferIndex), IndexToY(lastDisplayBufferIndex))
		LastDrawnIndex = ecg.DisplayBufferIndex
	}

	return false
}
