package vui

import (
	"netease_control_center/globals"
	"netease_control_center/interfaces/log"
	"sync"
	"time"
	"netease_control_center/nembd/controller/adau1761"
)

var (
	lastIconInsert = IconLed_DoNothing
	lastIconStatus = IconLed_DoNothing

	justlastIcon = IconLed_DoNothing

	DoShowIcon func(icon IconLedDesc)

	iconlock sync.Mutex

	iconTimer *time.Timer
)

func GetLastStatusIcon() IconLedDesc {
	return lastIconStatus
}

func GetLastIcon() IconLedDesc {
	return justlastIcon
}

func init() {
	globals.IconLedSwitch.RegisterCb(func(e interface{}, cbType globals.CallCbType) {
		if val, ok := e.(int); ok && val == 0 {
			iconlock.Lock()
			DoShowIcon(IconLed_Clear)
			iconlock.Unlock()
		}

		if val, ok := e.(int); ok && val == 1 {
			bakicon := lastIconStatus
			lastIconStatus = IconLed_Clear
			justlastIcon = IconLed_DoNothing

			bakicon.Show()
		}
	})
}

func RestoreLastIcon() {
	iconlock.Lock()
	defer iconlock.Unlock()
	log.Println(log.DebugLog, "Restore last icon:", lastIconStatus.Name)
	DoShowIcon(lastIconStatus)
}

func ClearIcon(icon IconLedDesc) {
	iconlock.Lock()
	defer iconlock.Unlock()

	if icon.Equal(justlastIcon, lastIconStatus) {
		log.Println(log.DebugLog, "Clear icon:", justlastIcon)

		if icon.Equal(justlastIcon) || iconTimer == nil {
			if iconTimer != nil {
				iconTimer.Stop()
				iconTimer = nil
			}
			DoShowIcon(IconLed_Clear)
			justlastIcon = IconLed_Clear
		}

		if icon.IsStatusIcon() {
			lastIconStatus = IconLed_Clear
		} else if icon.IsInsertIcon() {
			lastIconInsert = IconLed_Clear
		}
	} else {
		log.Println(log.DebugLog, "Icon not eq, do not clear:", icon, justlastIcon, lastIconStatus)
	}
}

func ShowIcon(icon IconLedDesc) {
	//log.Printf(log.DebugLog, "Begin to show icon: %+v\n", icon)
	if len(icon.Name) == 0 {
		return
	}

	iconlock.Lock()
	defer func() {
		justlastIcon = icon
		if justlastIcon.OnHold > 0 || justlastIcon.Name == IconLed_ShowVolume.Name {
			lastIconInsert = icon
		} else {
			lastIconStatus = icon
		}
		iconlock.Unlock()

		if err := recover(); err != nil {
			log.Println(log.ErrorLog, err)
		}
	}()

	if val := globals.IconLedSwitch.GetCfgListVui(); val == 0 && icon.CanNotOff == false {
		if icon.Equal(justlastIcon) == false {
			log.Println(log.DebugLog, "Icon show is off, do not show:", icon.Name)
		}
		return
	}

	if icon.Equal(justlastIcon) == true {
		if icon.OnHold > 0 {
			if iconTimer != nil {
				iconTimer.Reset(icon.OnHold)
			}
		}
		//log.Println(log.DebugLog, "Icon equal last, do not show:", icon.Name)
		return
	}
	log.Printf(log.DebugLog, "Begin to show icon: %+v\n", icon)

	//music icon can not interrupt time show icon of none music show
	if icon.IsMusicShow == true {
		//music icon need wait the icon show finish
		if iconTimer == nil || lastIconInsert.IsMusicShow == true {
			if iconTimer != nil {
				iconTimer.Stop()
				iconTimer = nil
			}

			DoShowIcon(icon)
			if icon.OnHold > 0 {
				var mytimer *time.Timer
				iconTimer = time.AfterFunc(icon.OnHold, func() {
					iconlock.Lock()
					defer iconlock.Unlock()
					log.Println(log.DebugLog, "Icon timer out!!!")
					if iconTimer == nil || mytimer != iconTimer {
						log.Println(log.DebugLog, " timer change, just exit, iconTimer == nil || mytimer != iconTimer, return!")
						return
					}
					iconTimer = nil
					if val := globals.IconLedSwitch.GetCfgListVui(); val == 0 {
						DoShowIcon(IconLed_Clear)
						return
					}

					if icon.Equal(justlastIcon) {
						justlastIcon = IconLed_DoNothing
					}
					DoShowIcon(lastIconStatus)
				})
				mytimer = iconTimer
			}
		}
	} else {
		if iconTimer != nil {
			iconTimer.Stop()
			iconTimer = nil
		}
		DoShowIcon(icon)
		if icon.OnHold > 0 {
			var mytimer *time.Timer
			iconTimer = time.AfterFunc(icon.OnHold, func() {
				iconlock.Lock()
				defer iconlock.Unlock()
				log.Println(log.DebugLog, "Icon timer out!!!")
				if iconTimer == nil || mytimer != iconTimer {
					log.Println(log.DebugLog, " timer change, just exit, iconTimer == nil || mytimer != iconTimer, return!")
					return
				}
				iconTimer = nil
				if val := globals.IconLedSwitch.GetCfgListVui(); val == 0 {
					DoShowIcon(IconLed_Clear)
					return
				}

				if icon.Equal(justlastIcon) {
					justlastIcon = IconLed_DoNothing
				}
				DoShowIcon(lastIconStatus)
			})
			mytimer = iconTimer
		}
	}
	//log.Printf(log.DebugLog, "icon cmd:%+v\n", icon)
}

func ShowIconMusic() {
	//don't show icon for natural sound
	if globals.PlayListSrcRec.BizType == globals.BIZ_TYPE_NATURAL_SOUND || globals.PlayListSrcRec.BizType == globals.BIZ_TYPE_RADIO_STATION {
		ClearIconMusic()
		return
	}
	tp := globals.IconLedMusicPlayMode.GetCfgListVui()
	switch tp {
	case 1:
		IconLed_iconMusic001.Arg,_ = adau1761.GetVol()
		IconLed_iconMusic001.Show()
	case 2:
		IconLed_iconMusic002.Arg,_ = adau1761.GetVol()
		IconLed_iconMusic002.Show()
	case 3:
		IconLed_iconMusic003.Arg,_ = adau1761.GetVol()
		IconLed_iconMusic003.Show()
	}
}

func ClearIconMusic() {
	iconlock.Lock()
	defer iconlock.Unlock()

	if justlastIcon.Equal(IconLed_iconMusic001, IconLed_iconMusic002, IconLed_iconMusic003) {
		DoShowIcon(IconLed_Clear)
		justlastIcon = IconLed_Clear
		lastIconStatus = IconLed_Clear
	}

	if lastIconStatus.Equal(IconLed_iconMusic001, IconLed_iconMusic002, IconLed_iconMusic003) {
		lastIconStatus = IconLed_Clear
	}
}
