const {
  getFaultText
} = require('./calculation-context.js')
const {
  parseHexInteger
} = require('../../utils/base-utils.js')
const {
  calculateStatusValue,
  formatFixedValue
} = require('./conversions.js')
const {
  getByteRegisterValue
} = require('./registers.js')

const statusWordValues = {}

const statusRawValues = {}

const SYS_STATE_TEXT = {
  0: '就绪状态',
  1: '初始化',
  2: '检测偏置电压',
  3: '预充电',
  4: '风向检测',
  5: '初始位置检测',
  6: '预定位',
  7: '电机启动',
  8: '电机运行',
  9: '电机停止',
  10: '刹车',
  11: '故障'
}

const FORMULA_STATUS_NAMES = [
  '母线电压',
  '模拟输入电压',
  '母线电流',
  'NTC 温度',
  '估算速度',
  '估算功率',
  '频率',
  '占空比'
]

function formatStatusRegister(item) {
  const rawValue = item.type === 'uint8_t' && item.bytePosition && statusWordValues[item.address] !== undefined
    ? getByteRegisterValue(item, statusWordValues[item.address])
    : statusRawValues[item.name]
  const hasFormula = FORMULA_STATUS_NAMES.includes(item.name)
  let displayValue = rawValue === undefined ? '--' : String(rawValue)

  if (item.name === '故障码' && rawValue !== undefined) {
    displayValue = getFaultText(rawValue)
  }

  if (item.name === '状态机' && rawValue !== undefined) {
    displayValue = SYS_STATE_TEXT[rawValue] || `未知状态 ${rawValue}`
  }

  if (hasFormula && rawValue !== undefined) {
    const calculatedValue = calculateStatusValue(item.name, rawValue)
    displayValue = item.name === '频率' || item.name === '占空比'
      ? formatFixedValue(calculatedValue, 1)
      : formatFixedValue(calculatedValue, 2)
  }

  return {
    ...item,
    rawValue: rawValue === undefined ? '--' : rawValue,
    displayUnit: displayValue === '--' ? '' : item.displayUnit || item.unit || '',
    displayValue
  }
}

function formatStatusRegisters(registers) {
  return registers.map(formatStatusRegister)
}

function toSigned16(value) {
  const wordValue = Number(value) & 0xFFFF

  return wordValue > 0x7FFF ? wordValue - 0x10000 : wordValue
}

function updateStatusRegisterWords(registers, startAddress, words) {
  const start = Number(startAddress)

  registers.forEach((item) => {
    const offset = parseHexInteger(item.address) - start
    if (offset < 0 || offset >= words.length) return

    const wordValue = Number(words[offset]) & 0xFFFF
    statusWordValues[item.address] = wordValue

    if (item.type === 'uint8_t' && item.bytePosition) {
      statusRawValues[item.name] = getByteRegisterValue(item, wordValue)
      return
    }

    statusRawValues[item.name] = item.type === 'int16_t' ? toSigned16(wordValue) : wordValue
  })

  return formatStatusRegisters(registers)
}

module.exports = {
  formatStatusRegisters,
  updateStatusRegisterWords
}
