Add page up/down bindings to the Markdown preview (#33403)
First time contributor here. 😊 I settled on markdown::MovePageUp and markdown::MovePageDown to match the names the editor uses for the same functionality. Closes #30246 Release Notes: - Support PgUp/PgDown in Markdown previews
This commit is contained in:
parent
123a25c58c
commit
f000dfebd2
5 changed files with 119 additions and 4 deletions
|
@ -291,6 +291,31 @@ impl ListState {
|
|||
self.0.borrow().logical_scroll_top()
|
||||
}
|
||||
|
||||
/// Scroll the list by the given offset
|
||||
pub fn scroll_by(&self, distance: Pixels) {
|
||||
if distance == px(0.) {
|
||||
return;
|
||||
}
|
||||
|
||||
let current_offset = self.logical_scroll_top();
|
||||
let state = &mut *self.0.borrow_mut();
|
||||
let mut cursor = state.items.cursor::<ListItemSummary>(&());
|
||||
cursor.seek(&Count(current_offset.item_ix), Bias::Right, &());
|
||||
|
||||
let start_pixel_offset = cursor.start().height + current_offset.offset_in_item;
|
||||
let new_pixel_offset = (start_pixel_offset + distance).max(px(0.));
|
||||
if new_pixel_offset > start_pixel_offset {
|
||||
cursor.seek_forward(&Height(new_pixel_offset), Bias::Right, &());
|
||||
} else {
|
||||
cursor.seek(&Height(new_pixel_offset), Bias::Right, &());
|
||||
}
|
||||
|
||||
state.logical_scroll_top = Some(ListOffset {
|
||||
item_ix: cursor.start().count,
|
||||
offset_in_item: new_pixel_offset - cursor.start().height,
|
||||
});
|
||||
}
|
||||
|
||||
/// Scroll the list to the given offset
|
||||
pub fn scroll_to(&self, mut scroll_top: ListOffset) {
|
||||
let state = &mut *self.0.borrow_mut();
|
||||
|
@ -1119,4 +1144,52 @@ mod test {
|
|||
assert_eq!(state.logical_scroll_top().item_ix, 0);
|
||||
assert_eq!(state.logical_scroll_top().offset_in_item, px(0.));
|
||||
}
|
||||
|
||||
#[gpui::test]
|
||||
fn test_scroll_by_positive_and_negative_distance(cx: &mut TestAppContext) {
|
||||
use crate::{
|
||||
AppContext, Context, Element, IntoElement, ListState, Render, Styled, Window, div,
|
||||
list, point, px, size,
|
||||
};
|
||||
|
||||
let cx = cx.add_empty_window();
|
||||
|
||||
let state = ListState::new(5, crate::ListAlignment::Top, px(10.), |_, _, _| {
|
||||
div().h(px(20.)).w_full().into_any()
|
||||
});
|
||||
|
||||
struct TestView(ListState);
|
||||
impl Render for TestView {
|
||||
fn render(&mut self, _: &mut Window, _: &mut Context<Self>) -> impl IntoElement {
|
||||
list(self.0.clone()).w_full().h_full()
|
||||
}
|
||||
}
|
||||
|
||||
// Paint
|
||||
cx.draw(point(px(0.), px(0.)), size(px(100.), px(100.)), |_, cx| {
|
||||
cx.new(|_| TestView(state.clone()))
|
||||
});
|
||||
|
||||
// Test positive distance: start at item 1, move down 30px
|
||||
state.scroll_by(px(30.));
|
||||
|
||||
// Should move to item 2
|
||||
let offset = state.logical_scroll_top();
|
||||
assert_eq!(offset.item_ix, 1);
|
||||
assert_eq!(offset.offset_in_item, px(10.));
|
||||
|
||||
// Test negative distance: start at item 2, move up 30px
|
||||
state.scroll_by(px(-30.));
|
||||
|
||||
// Should move back to item 1
|
||||
let offset = state.logical_scroll_top();
|
||||
assert_eq!(offset.item_ix, 0);
|
||||
assert_eq!(offset.offset_in_item, px(0.));
|
||||
|
||||
// Test zero distance
|
||||
state.scroll_by(px(0.));
|
||||
let offset = state.logical_scroll_top();
|
||||
assert_eq!(offset.item_ix, 0);
|
||||
assert_eq!(offset.offset_in_item, px(0.));
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue