~ruther/CTU-FEE-B0B35APO-Semestral-project

6615fb42ecfa0deef95bea0eeac1297e869f2ab9 — František Boháček 4 years ago 5942716
feat: add better navigation
M file-browser/src/gui_list_commands.c => file-browser/src/gui_list_commands.c +54 -0
@@ 54,11 54,65 @@ static void command_handler_move_up(void *state, int amount) {
  command_handler_move(state, UP, amount);
}

static void command_handler_home(void *state, int amount) {
  gui_list_command_state_t *click_state = (gui_list_command_state_t *)state;
  if (click_state->window == click_state->gui->active_window) {
    gui_list_set_selected_index(click_state->container, 0);
  }
}

static void command_handler_end(void *state, int amount) {
  gui_list_command_state_t *click_state = (gui_list_command_state_t *)state;
  if (click_state->window == click_state->gui->active_window) {
    gui_list_set_selected_index(click_state->container, gui_list_get_items_count(click_state->container));
  }
}

static void command_handler_page_down(void *state, int amount) {
  gui_list_command_state_t *click_state = (gui_list_command_state_t *)state;
  if (click_state->window == click_state->gui->active_window) {
    uint32_t selected_index = gui_list_get_selected_index(click_state->container);
    gui_list_set_selected_index(
        click_state->container,
        selected_index +
            gui_list_get_visible_items_count(click_state->container));
  }
}

static void command_handler_page_up(void *state, int amount) {
  gui_list_command_state_t *click_state = (gui_list_command_state_t *)state;
  if (click_state->window == click_state->gui->active_window) {
    uint32_t selected_index =
        gui_list_get_selected_index(click_state->container);
    uint32_t visible_items = gui_list_get_visible_items_count(click_state->container);

    if (selected_index < visible_items) {
      selected_index = 0;
    } else {
      selected_index -= visible_items;
    }

    gui_list_set_selected_index(
        click_state->container,
        selected_index);
  }
}

void gui_list_commands_register(commands_t *commands, gui_list_command_state_t *state) {
  commands_register(commands, IN_KEYBOARD, 13, command_handler_gui_list_clicked, state);
  commands_register(commands, IN_KEYBOARD, 'v', command_handler_gui_list_clicked,
                    state);

  commands_register(commands, IN_KEYBOARD, KEYBOARD_HOME, command_handler_home,
                    state);
  commands_register(commands, IN_KEYBOARD, KEYBOARD_END, command_handler_end,
                    state);

  commands_register(commands, IN_KEYBOARD, KEYBOARD_PAGE_DOWN,
                    command_handler_page_down, state);
  commands_register(commands, IN_KEYBOARD, KEYBOARD_PAGE_UP,
                    command_handler_page_up, state);

  commands_register(commands, IN_KEYBOARD, KEYBOARD_DOWN,
                    command_handler_move_down, state);
  commands_register(commands, IN_KEYBOARD, KEYBOARD_UP, command_handler_move_up,

M file-browser/src/window_browser.c => file-browser/src/window_browser.c +49 -1
@@ 14,6 14,7 @@
#include "logger.h"
#include "path.h"
#include "renderer.h"
#include "keyboard_const.h"
#include <stdio.h>
#include <time.h>
#include <unistd.h>


@@ 114,6 115,45 @@ static void command_handler_exit(void *state, int amount) {
  }
}

static void command_handler_jump_right(void *state, int amount) {
  browser_window_state_t *bstate = (browser_window_state_t *)state;
  if (bstate->gui->active_window == bstate->browser_window) {
    uint32_t scroll_x = bstate->list_container->inner.list.scroll_x;
    uint32_t current_x = 0;

    int i;
    for (i = 0; i < COLUMNS_COUNT - 1; i++) {
      current_x += bstate->column_widths[i];
      if (scroll_x < current_x) {
        break;
      }
    }

    if (amount < 0) {
      i --;
    } else {
      i++;
    }

    if (i < 0) {
      i = 0;
    } else if (i > COLUMNS_COUNT - 1) {
      i = COLUMNS_COUNT - 1;
    }

    scroll_x = 0;
    for (int j = 0; j < i; j++) {
      scroll_x += bstate->column_widths[j];
    }

    bstate->list_container->inner.list.scroll_x = scroll_x;
  }
}

static void command_handler_jump_left(void *state, int amount) {
  command_handler_jump_right(state, -amount);
}

static void *browser_window_construct(window_t *window, void *state) {
  browser_window_state_t *bstate = (browser_window_state_t *)state;
  logger_t *logger = bstate->gui->logger;


@@ 137,7 177,7 @@ static void *browser_window_construct(window_t *window, void *state) {
  // group components init
  component_t path_text = gui_text_create(&bstate->text_state, 3, 3, bstate->gui->size.x, 0);
  component_t line_component = gui_line_create(&WHITE_PIXEL, 0, path_text.height + path_text.y + 3, 1000, 1);
  

  gui_group_container_add_component(&window->containers[1], path_text);
  bstate->line_component =
      gui_group_container_add_component(&window->containers[1], line_component);


@@ 153,6 193,10 @@ static void *browser_window_construct(window_t *window, void *state) {
  gui_list_commands_register(bstate->gui->commands, &bstate->click_state);
  commands_register(bstate->gui->commands, IN_KEYBOARD, 'e',
                    command_handler_exit, state);
  commands_register(bstate->gui->commands, IN_KEYBOARD, KEYBOARD_JUMP_RIGHT,
                    command_handler_jump_right, state);
  commands_register(bstate->gui->commands, IN_KEYBOARD, KEYBOARD_JUMP_LEFT,
                    command_handler_jump_left, state);

  return state;
}


@@ 161,6 205,10 @@ static void browser_window_item_clicked(container_t *container, void *state,
                                        uint32_t selected_index) {

  browser_window_state_t *bstate = (browser_window_state_t *)state;
  if (bstate->gui->active_window != bstate->browser_window) {
    return;
  }

  logger_t *logger = bstate->gui->logger;

  file_t current_file = bstate->current_directory->files[selected_index];

M lib-gui/include/gui.h => lib-gui/include/gui.h +4 -0
@@ 353,6 353,8 @@ container_t gui_list_container_create(void *state, uint32_t items_count,
 */
uint32_t gui_list_get_selected_index(container_t *container);

void gui_list_set_selected_index(container_t *container, uint32_t index);

/**
 * @brief Scroll list container by x, y
 * @details Increase scroll coordinates by x, y so different view arrea is shown


@@ 389,5 391,7 @@ bool gui_list_container_set_render_function(container_t *container,

void gui_list_container_render(gui_t *gui, container_t *container);
void gui_list_container_update(gui_t *gui, container_t *container);
uint32_t gui_list_get_visible_items_count(container_t *container);
uint32_t gui_list_get_items_count(container_t *container);

#endif // __GUI_H__

M lib-gui/include/keyboard_const.h => lib-gui/include/keyboard_const.h +9 -0
@@ 4,3 4,12 @@
#define KEYBOARD_UP 'k'
#define KEYBOARD_ZOOM_IN 'z'
#define KEYBOARD_ZOOM_OUT 'x'

#define KEYBOARD_HOME 'n'
#define KEYBOARD_END 'm'

#define KEYBOARD_PAGE_UP 'u'
#define KEYBOARD_PAGE_DOWN 'i'

#define KEYBOARD_JUMP_LEFT 'y'
#define KEYBOARD_JUMP_RIGHT 'o'

M lib-gui/src/gui_list_container.c => lib-gui/src/gui_list_container.c +26 -9
@@ 123,6 123,31 @@ uint32_t gui_list_get_selected_index(container_t *container) {
  return container->inner.list.selected_index;
}

void gui_list_set_selected_index(container_t *container, uint32_t index) {
  if (index >= container->inner.list.items_count) {
    index = container->inner.list.items_count - 1;
  }

  container->inner.list.selected_index = index;
}

uint32_t gui_list_get_items_count(container_t *container) {
  return container->inner.list.items_count;
}

uint32_t gui_list_get_visible_items_count(container_t *container) {
  list_container_t list = container->inner.list;
  uint16_t item_full_height = list.item_height + list.item_padding * 2;
  uint32_t container_height = container->height;

  bool header = list.render_header_fn != NULL;
  if (header) {
    container_height -= item_full_height;
  }

  return (double)(container_height) / item_full_height - 1;
}

void gui_list_container_update(gui_t *gui, container_t *container) {
  list_container_t list = container->inner.list;



@@ 138,16 163,8 @@ void gui_list_container_update(gui_t *gui, container_t *container) {
    first_visible_index = 0;
  }

  uint32_t container_height = container->height;

  bool header = list.render_header_fn != NULL;
  if (header) {
    container_height -= item_full_height;
  }

  uint32_t items_count = (double)(container_height) / item_full_height - 1;
  uint32_t items_count = gui_list_get_visible_items_count(container);
  uint32_t last_visible_index = first_visible_index + items_count;

  uint32_t selected_index = list.selected_index;

  if (selected_index < first_visible_index) {