aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--common.h4
-rw-r--r--fish_tests.cpp14
-rw-r--r--pager.cpp26
-rw-r--r--reader.cpp29
4 files changed, 62 insertions, 11 deletions
diff --git a/common.h b/common.h
index 4eb17bf0..a4bee08f 100644
--- a/common.h
+++ b/common.h
@@ -98,6 +98,8 @@ enum selection_direction_t
direction_east,
direction_south,
direction_west,
+ direction_page_north,
+ direction_page_south,
/* logical directions */
direction_next,
@@ -112,7 +114,9 @@ inline bool selection_direction_is_cardinal(selection_direction_t dir)
switch (dir)
{
case direction_north:
+ case direction_page_north:
case direction_east:
+ case direction_page_south:
case direction_south:
case direction_west:
return true;
diff --git a/fish_tests.cpp b/fish_tests.cpp
index 6cab5a66..c51ea8ab 100644
--- a/fish_tests.cpp
+++ b/fish_tests.cpp
@@ -1664,7 +1664,19 @@ static void test_pager_navigation()
{direction_north, 18},
{direction_west, 14},
{direction_south, 15},
- {direction_north, 14}
+ {direction_north, 14},
+
+ /* pages */
+ {direction_page_north, 12},
+ {direction_page_south, 15},
+ {direction_page_north, 12},
+ {direction_east, 16},
+ {direction_page_south, 18},
+ {direction_east, 3},
+ {direction_north, 2},
+ {direction_page_north, 0},
+ {direction_page_south, 3},
+
};
for (size_t i=0; i < sizeof cmds / sizeof *cmds; i++)
{
diff --git a/pager.cpp b/pager.cpp
index 002479bc..b2a4e4da 100644
--- a/pager.cpp
+++ b/pager.cpp
@@ -684,6 +684,7 @@ bool pager_t::select_next_completion_in_direction(selection_direction_t directio
{
/* These directions do something sane */
case direction_south:
+ case direction_page_south:
case direction_next:
case direction_prev:
if (direction == direction_prev)
@@ -698,6 +699,7 @@ bool pager_t::select_next_completion_in_direction(selection_direction_t directio
/* These do nothing */
case direction_north:
+ case direction_page_north:
case direction_east:
case direction_west:
case direction_deselect:
@@ -744,9 +746,18 @@ bool pager_t::select_next_completion_in_direction(selection_direction_t directio
/* Cardinal directions. We have a completion index; we wish to compute its row and column. */
size_t current_row = this->get_selected_row(rendering);
size_t current_col = this->get_selected_column(rendering);
+ size_t page_height = maxi(rendering.term_height - 1, 1);
switch (direction)
{
+ case direction_page_north:
+ {
+ if (current_row > page_height)
+ current_row = current_row - page_height;
+ else
+ current_row = 0;
+ break;
+ }
case direction_north:
{
/* Go up a whole row. If we cycle, go to the previous column. */
@@ -763,6 +774,21 @@ bool pager_t::select_next_completion_in_direction(selection_direction_t directio
break;
}
+ case direction_page_south:
+ {
+ if (current_row + page_height < rendering.rows)
+ {
+ current_row += page_height;
+ }
+ else
+ {
+ current_row = rendering.rows - 1;
+ if (current_col * rendering.rows + current_row >= completion_infos.size()) {
+ current_row = (completion_infos.size() - 1) % rendering.rows;
+ }
+ }
+ break;
+ }
case direction_south:
{
/* Go down, unless we are in the last row. Note that this means that we may set selected_completion_idx to an out-of-bounds value if the last row is incomplete; this is a feature (it allows "last column memory"). */
diff --git a/reader.cpp b/reader.cpp
index b946bbcb..13937f11 100644
--- a/reader.cpp
+++ b/reader.cpp
@@ -1142,8 +1142,6 @@ static bool command_ends_paging(wchar_t c, bool focused_on_search_field)
/* These commands always end paging */
case R_HISTORY_SEARCH_BACKWARD:
case R_HISTORY_SEARCH_FORWARD:
- case R_BEGINNING_OF_HISTORY:
- case R_END_OF_HISTORY:
case R_HISTORY_TOKEN_SEARCH_BACKWARD:
case R_HISTORY_TOKEN_SEARCH_FORWARD:
case R_ACCEPT_AUTOSUGGESTION:
@@ -1160,6 +1158,8 @@ static bool command_ends_paging(wchar_t c, bool focused_on_search_field)
case R_NULL:
case R_REPAINT:
case R_SUPPRESS_AUTOSUGGESTION:
+ case R_BEGINNING_OF_HISTORY:
+ case R_END_OF_HISTORY:
default:
return false;
@@ -3780,21 +3780,30 @@ const wchar_t *reader_readline(int nchars)
case R_BEGINNING_OF_HISTORY:
{
- const editable_line_t *el = &data->command_line;
- data->history_search = history_search_t(*data->history, el->text, HISTORY_SEARCH_TYPE_PREFIX);
- data->history_search.go_to_beginning();
- if (! data->history_search.is_at_end())
+ if (data->is_navigating_pager_contents())
{
- wcstring new_text = data->history_search.current_string();
- set_command_line_and_position(&data->command_line, new_text, new_text.size());
+ select_completion_in_direction(direction_page_north);
+ } else {
+ const editable_line_t *el = &data->command_line;
+ data->history_search = history_search_t(*data->history, el->text, HISTORY_SEARCH_TYPE_PREFIX);
+ data->history_search.go_to_beginning();
+ if (! data->history_search.is_at_end())
+ {
+ wcstring new_text = data->history_search.current_string();
+ set_command_line_and_position(&data->command_line, new_text, new_text.size());
+ }
}
-
break;
}
case R_END_OF_HISTORY:
{
- data->history_search.go_to_end();
+ if (data->is_navigating_pager_contents())
+ {
+ select_completion_in_direction(direction_page_south);
+ } else {
+ data->history_search.go_to_end();
+ }
break;
}