function Command({
  id = "",
  protocol = "",
  commandNumber = -1,
  device = -1,
  commandType = "",
  title = "",
} = {}) {
  if (typeof commandNumber !== "number")
    throw new Error("Command number must be a number");
  if (typeof device !== "number") throw new Error("Device must be a number");
  let _id = id;
  let _protocol = protocol;
  let _commandNumber = commandNumber;
  let _device = device;
  let _commandType = commandType;
  let _title = title;

  function getId() {
    return _id;
  }

  function setId(id) {
    _id = id;
  }

  function getProtocol() {
    return _protocol;
  }

  function setProtocol(protocol) {
    _protocol = protocol;
  }

  function getCommandNumber() {
    return _commandNumber;
  }

  function setCommandNumber(commandNumber) {
    if (typeof commandNumber !== "number")
      throw new Error("Command number must be a number");
    _commandNumber = commandNumber;
  }

  function getDevice() {
    return _device;
  }

  function setDevice(device) {
    if (typeof device !== "number") throw new Error("Device must be a number");
    _device = device;
  }

  function getCommandType() {
    return _commandType;
  }

  function setCommandType(commandType) {
    _commandType = commandType;
  }

  function getTitle() {
    if (_title) return _title;
    return `${Command.getTypeString(_commandType)} (${Command.getProtocolString(_protocol)})`;
  }

  function setTitle(title) {
    _title = title;
  }

  return {
    getId,
    setId,
    getProtocol,
    setProtocol,
    getCommandNumber,
    setCommandNumber,
    getDevice,
    setDevice,
    getCommandType,
    setCommandType,
    getTitle,
    setTitle,
  };
}

Command.PROTOCOLS = {
  SAMSUNG: "samsung",
  NEC: "nec",
  ONKYO: "onkyo",
  APPLE: "apple",
  DENON: "denon",
  SHARP: "sharp",
  PANASONIC: "panasonic",
  KASEIKYO: "kaseikyo",
  JVC: "jvc",
  LG: "lg",
  SONY: "sony",
  RC5: "rc5",
  RC6: "rc6",
  UNIVERSAL_PULSE_DISTANCE: "universal_pulse_distance",
  UNIVERSAL_PULSE_WIDTH: "universal_pulse_width",
  UNIVERSAL_PULSE_DISTANCE_WIDTH: "universal_pulse_distance_width",
  HASH: "hash",
  PRONTO: "pronto",
  BOSE_WAVE: "bose_wave",
  BANG_OLUFSEN: "bang_olufsen",
  LEGO: "lego",
  FAST: "fast",
  WHYNTER: "whynter",
  MAGIQUEST: "magiquest",
}

Command.getProtocolString = (protocol) => {
  let mapping = {
    [Command.PROTOCOLS.SAMSUNG]: "Samsung",
    [Command.PROTOCOLS.NEC]: "NEC",
    [Command.PROTOCOLS.ONKYO]: "Onkyo",
    [Command.PROTOCOLS.APPLE]: "Apple",
    [Command.PROTOCOLS.DENON]: "Denon",
    [Command.PROTOCOLS.SHARP]: "Sharp",
    [Command.PROTOCOLS.PANASONIC]: "Panasonic",
    [Command.PROTOCOLS.KASEIKYO]: "Kaseikyo",
    [Command.PROTOCOLS.JVC]: "JVC",
    [Command.PROTOCOLS.LG]: "LG",
    [Command.PROTOCOLS.SONY]: "Sony",
    [Command.PROTOCOLS.RC5]: "RC5",
    [Command.PROTOCOLS.RC6]: "RC6",
    [Command.PROTOCOLS.UNIVERSAL_PULSE_DISTANCE]: "Universal Pulse Distance",
    [Command.PROTOCOLS.UNIVERSAL_PULSE_WIDTH]: "Universal Pulse Width",
    [Command.PROTOCOLS.UNIVERSAL_PULSE_DISTANCE_WIDTH]: "Universal Pulse Distance Width",
    [Command.PROTOCOLS.HASH]: "Hash",
    [Command.PROTOCOLS.PRONTO]: "Pronto",
    [Command.PROTOCOLS.BOSE_WAVE]: "BoseWave",
    [Command.PROTOCOLS.BANG_OLUFSEN]: "Bang & Olufsen",
    [Command.PROTOCOLS.LEGO]: "Lego",
    [Command.PROTOCOLS.FAST]: "FAST",
    [Command.PROTOCOLS.WHYNTER]: "Whynter",
    [Command.PROTOCOLS.MAGIQUEST]: "MagiQuest",
  }
  return mapping[protocol]
}

Command.TYPES = {
  POWER: "power",
  INPUT: "input",
  ONE: "one",
  TWO: "two",
  THREE: "three",
  FOUR: "four",
  FIVE: "five",
  SIX: "six",
  SEVEN: "seven",
  EIGHT: "eight",
  NINE: "nine",
  ZERO: "zero",
  VOLUME_UP: "volume_up",
  VOLUME_DOWN: "volume_down",
  MUTE: "mute",
  CHANNEL_UP: "channel_up",
  CHANNEL_DOWN: "channel_down",
  MENU: "menu",
  HOME: "home",
  SETTINGS: "settings",
  OPTIONS: "options",
  UP: "up",
  DOWN: "down",
  LEFT: "left",
  RIGHT: "right",
  ENTER: "enter",
  INFO: "info",
  RETURN: "return",
  EXIT: "exit",
  RED: "red",
  GREEN: "green",
  YELLOW: "yellow",
  BLUE: "blue",
  REWIND: "rewind",
  PLAY: "play",
  PAUSE: "pause",
  STOP: "stop",
  FORWARD: "forward",
  OTHER: "other",
}

Command.getTypeString = (type) => {
  let mapping = {
    [Command.TYPES.POWER]: "Power",
    [Command.TYPES.INPUT]: "Input",
    [Command.TYPES.ONE]: "1",
    [Command.TYPES.TWO]: "2",
    [Command.TYPES.THREE]: "3",
    [Command.TYPES.FOUR]: "4",
    [Command.TYPES.FIVE]: "5",
    [Command.TYPES.SIX]: "6",
    [Command.TYPES.SEVEN]: "7",
    [Command.TYPES.EIGHT]: "8",
    [Command.TYPES.NINE]: "9",
    [Command.TYPES.ZERO]: "0",
    [Command.TYPES.VOLUME_UP]: "Volume Up",
    [Command.TYPES.VOLUME_DOWN]: "Volume Down",
    [Command.TYPES.MUTE]: "Mute",
    [Command.TYPES.CHANNEL_UP]: "Channel Up",
    [Command.TYPES.CHANNEL_DOWN]: "Channel Down",
    [Command.TYPES.MENU]: "Menu",
    [Command.TYPES.HOME]: "Home",
    [Command.TYPES.SETTINGS]: "Settings",
    [Command.TYPES.OPTIONS]: "Options",
    [Command.TYPES.UP]: "Up",
    [Command.TYPES.DOWN]: "Down",
    [Command.TYPES.LEFT]: "Left",
    [Command.TYPES.RIGHT]: "Right",
    [Command.TYPES.ENTER]: "Enter",
    [Command.TYPES.INFO]: "Info",
    [Command.TYPES.RETURN]: "Return",
    [Command.TYPES.EXIT]: "Exit",
    [Command.TYPES.RED]: "Red",
    [Command.TYPES.GREEN]: "Green",
    [Command.TYPES.YELLOW]: "Yellow",
    [Command.TYPES.BLUE]: "Blue",
    [Command.TYPES.REWIND]: "Rewind",
    [Command.TYPES.PLAY]: "Play",
    [Command.TYPES.PAUSE]: "Pause",
    [Command.TYPES.STOP]: "Stop",
    [Command.TYPES.FORWARD]: "Forward",
    [Command.TYPES.OTHER]: "Other",
  }
  return mapping[type]
}

export default Command;
