BufferView: add scroll_view_{up,down}()
This commit is contained in:
parent
84759d0a36
commit
70aba6e2d4
@ -192,6 +192,46 @@ bool BufferView::cursor_move(CursorMovement which, bool allow_eol)
|
||||
return moved;
|
||||
}
|
||||
|
||||
void BufferView::scroll_view_up(int n_lines, bool allow_eol)
|
||||
{
|
||||
int so = effective_scroll_offset();
|
||||
int rows_to_move_cursor = (so + n_lines) - (m_height - m_cursor_screen_row - 1);
|
||||
rows_to_move_cursor = std::min(calculate_rows_above_screen(rows_to_move_cursor), rows_to_move_cursor);
|
||||
int actual_lines_moved = 0;
|
||||
while (rows_to_move_cursor-- > 0)
|
||||
{
|
||||
if (move_cursor_screen_row_up(allow_eol))
|
||||
{
|
||||
actual_lines_moved++;
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
m_cursor_screen_row += (n_lines - actual_lines_moved);
|
||||
}
|
||||
|
||||
void BufferView::scroll_view_down(int n_lines, bool allow_eol)
|
||||
{
|
||||
int so = effective_scroll_offset();
|
||||
int rows_to_move_cursor = (so + n_lines) - m_cursor_screen_row;
|
||||
rows_to_move_cursor = std::min(calculate_rows_below_screen(rows_to_move_cursor), rows_to_move_cursor);
|
||||
int actual_lines_moved = 0;
|
||||
while (rows_to_move_cursor-- > 0)
|
||||
{
|
||||
if (move_cursor_screen_row_down(allow_eol))
|
||||
{
|
||||
actual_lines_moved++;
|
||||
}
|
||||
else
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
m_cursor_screen_row -= (n_lines - actual_lines_moved);
|
||||
}
|
||||
|
||||
/**************************************************************************
|
||||
* Internal functions
|
||||
*************************************************************************/
|
||||
@ -374,3 +414,35 @@ void BufferView::move_forward_to_screen_position(
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int BufferView::calculate_rows_above_screen(int stop_at)
|
||||
{
|
||||
if (m_lines.empty())
|
||||
return 0;
|
||||
const LineDescriptor & first_line = *m_lines.begin();
|
||||
auto iterator = std::make_shared<Buffer::Iterator>(*first_line.line);
|
||||
int lines = std::max(0, -first_line.row_offset);
|
||||
while (lines < stop_at)
|
||||
{
|
||||
if (!iterator->go_previous_line())
|
||||
break;
|
||||
lines += calculate_rows_in_line(iterator);
|
||||
}
|
||||
return lines;
|
||||
}
|
||||
|
||||
int BufferView::calculate_rows_below_screen(int stop_at)
|
||||
{
|
||||
if (m_lines.empty())
|
||||
return 0;
|
||||
const LineDescriptor & last_line = *m_lines.rbegin();
|
||||
auto iterator = std::make_shared<Buffer::Iterator>(*last_line.line);
|
||||
int lines = std::max(0, last_line.row_offset + last_line.n_rows - m_height);
|
||||
while (lines < stop_at)
|
||||
{
|
||||
if (!iterator->go_next_line())
|
||||
break;
|
||||
lines += calculate_rows_in_line(iterator);
|
||||
}
|
||||
return lines;
|
||||
}
|
||||
|
@ -84,6 +84,8 @@ public:
|
||||
{
|
||||
m_cursor_screen_row = cursor_screen_row;
|
||||
}
|
||||
void scroll_view_up(int n_lines, bool allow_eol);
|
||||
void scroll_view_down(int n_lines, bool allow_eol);
|
||||
|
||||
protected:
|
||||
struct LineDescriptor
|
||||
@ -126,6 +128,8 @@ protected:
|
||||
void move_forward_to_screen_position(
|
||||
std::shared_ptr<Buffer::Iterator> line, int target_row_offset,
|
||||
bool allow_eol);
|
||||
int calculate_rows_above_screen(int stop_at);
|
||||
int calculate_rows_below_screen(int stop_at);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -520,3 +520,116 @@ TEST(BufferViewTest, cursor_move_screen_row_up_and_down_returns_false_at_top_and
|
||||
}
|
||||
EXPECT_FALSE(bv.cursor_move(BufferView::CursorMovement::SCREEN_ROW_DOWN, false));
|
||||
}
|
||||
|
||||
TEST(BufferViewTest, scrolls_the_view_up_and_down)
|
||||
{
|
||||
auto b = buffer1();
|
||||
auto iterator = b->add_iterator();
|
||||
BufferView bv(b, iterator, Cwd);
|
||||
bv.resize(40, 6);
|
||||
bv.update();
|
||||
EXPECT_EQ(0, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(1, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(5, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(6, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(7, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(7, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(3, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(7, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(7, LineNumber(iterator));
|
||||
EXPECT_EQ(1, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(4, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(7, LineNumber(iterator));
|
||||
EXPECT_EQ(5, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(6, LineNumber(iterator));
|
||||
EXPECT_EQ(5, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(5, LineNumber(iterator));
|
||||
EXPECT_EQ(5, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(5, LineNumber(iterator));
|
||||
EXPECT_EQ(5, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(3, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(5, LineNumber(iterator));
|
||||
EXPECT_EQ(5, bv.cursor_screen_row());
|
||||
}
|
||||
|
||||
TEST(BufferViewTest, scrolls_the_view_up_and_down_with_nonzero_scroll_offset)
|
||||
{
|
||||
auto b = buffer1();
|
||||
auto iterator = b->add_iterator();
|
||||
BufferView bv(b, iterator, Cwd);
|
||||
bv.resize(40, 6);
|
||||
bv.set_scroll_offset(2);
|
||||
bv.update();
|
||||
EXPECT_EQ(0, LineNumber(iterator));
|
||||
EXPECT_EQ(0, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(3, LineNumber(iterator));
|
||||
EXPECT_EQ(2, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(5, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(8, LineNumber(iterator));
|
||||
EXPECT_EQ(2, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(9, LineNumber(iterator));
|
||||
EXPECT_EQ(2, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(9, LineNumber(iterator));
|
||||
EXPECT_EQ(2, bv.cursor_screen_row());
|
||||
bv.scroll_view_down(3, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(9, LineNumber(iterator));
|
||||
EXPECT_EQ(2, bv.cursor_screen_row());
|
||||
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(9, LineNumber(iterator));
|
||||
EXPECT_EQ(3, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(4, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(5, LineNumber(iterator));
|
||||
EXPECT_EQ(3, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(4, LineNumber(iterator));
|
||||
EXPECT_EQ(3, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(3, LineNumber(iterator));
|
||||
EXPECT_EQ(3, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(1, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(3, LineNumber(iterator));
|
||||
EXPECT_EQ(3, bv.cursor_screen_row());
|
||||
bv.scroll_view_up(3, false);
|
||||
bv.update();
|
||||
EXPECT_EQ(3, LineNumber(iterator));
|
||||
EXPECT_EQ(3, bv.cursor_screen_row());
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user