/**
 * Copyright (c) 2021 Dominic Masters
 * 
 * This software is released under the MIT License.
 * https://opensource.org/licenses/MIT
 */

#include "menu.h"

void menuInit(menu_t *menu) {
  menu->itemCount = 0;
  menu->selected = 0;
  menu->cursorX = 0;
  menu->cursorY = 0;
  menu->user = NULL;
  menu->onSelect = NULL;
}

void menuUpdate(menu_t *menu, engine_t *engine) {
  menuitem_t *current;
  menuitem_t *item;
  uint8_t x, y, i, j;

  current = menu->items + menu->selected;

  if(inputIsPressed(&engine->input, INPUT_ACCEPT)) {
    if(menu->onSelect != NULL) {
      menu->onSelect(menu->user, menu->selected);
    }
    return;
  }

  // Handle press binds.
  if(inputIsPressed(&engine->input, INPUT_DOWN)) {
    x = 0;
    y = 1;
  } else if(inputIsPressed(&engine->input, INPUT_UP)) {
    x = 0;
    y = -1;
  } else if(inputIsPressed(&engine->input, INPUT_LEFT)) {
    x = -1;
    y = 0;
  } else if(inputIsPressed(&engine->input, INPUT_RIGHT)) {
    x = 1;
    y = 0;
  } else {
    x = 0;
    y = 0;
  }

  // Update cursor positions
  if(x != 0 || y != 0) {
    if(x > 0) {
      menu->cursorX = (current->x + current->width - 1) + x;
    } else if(x < 0) {
      menu->cursorX = current->x + x;
    }

    if(y > 0) {
      menu->cursorY = (current->y + current->height - 1) + y;
    } else if(y < 0) {
      menu->cursorY = current->y + y;
    }
    
    // Get the item selected
    j = MENU_ITEMS_MAX;
    for(i = 0; i < menu->itemCount; i++) {
      if(i == menu->selected) continue;
      item = menu->items + i;

      if(
        item->x > menu->cursorX || (item->x+item->width-1) < menu->cursorX ||
        item->y > menu->cursorY || (item->y+item->height-1) < menu->cursorY
      ) continue;

      j = i;
      break;
    }

    // Was a target found?
    if(j == MENU_ITEMS_MAX) return;
    menu->selected = j;
  }
}

menuitem_t * menuAdd(menu_t *menu) {
  menuitem_t *item = menu->items + menu->itemCount;

  item->x = 0;
  item->y = 0;
  item->width = 1;
  item->height = 1;

  menu->itemCount++;
  return item;
}