mirror of
https://github.com/FliegendeWurst/cursive.git
synced 2024-11-23 17:35:00 +00:00
Fix desperate LinearLayout
This commit is contained in:
parent
be977c705f
commit
810dc6a591
@ -63,7 +63,6 @@ impl<'a> Iterator for LinesIterator<'a> {
|
|||||||
|
|
||||||
fn next(&mut self) -> Option<Row> {
|
fn next(&mut self) -> Option<Row> {
|
||||||
let row = self.iter.next()?;
|
let row = self.iter.next()?;
|
||||||
// println!("Got a row: {:?}", row);
|
|
||||||
|
|
||||||
let start = row.segments.first()?.start;
|
let start = row.segments.first()?.start;
|
||||||
let end = row.segments.last()?.end;
|
let end = row.segments.last()?.end;
|
||||||
|
@ -78,7 +78,7 @@ impl<'a, T: Deref<Target = Child>, I: Iterator<Item = T>> Iterator
|
|||||||
// Save the current offset.
|
// Save the current offset.
|
||||||
let offset = self.offset;
|
let offset = self.offset;
|
||||||
|
|
||||||
// eprintln!("Available: {}", self.available);
|
// debug!("Available: {}", self.available);
|
||||||
|
|
||||||
let length =
|
let length =
|
||||||
min(self.available, *child.size.get(self.orientation));
|
min(self.available, *child.size.get(self.orientation));
|
||||||
@ -336,16 +336,16 @@ fn try_focus(
|
|||||||
impl View for LinearLayout {
|
impl View for LinearLayout {
|
||||||
fn draw(&self, printer: &Printer) {
|
fn draw(&self, printer: &Printer) {
|
||||||
// Use pre-computed sizes
|
// Use pre-computed sizes
|
||||||
// eprintln!("Pre loop!");
|
// debug!("Pre loop!");
|
||||||
for (i, item) in ChildIterator::new(
|
for (i, item) in ChildIterator::new(
|
||||||
self.children.iter(),
|
self.children.iter(),
|
||||||
self.orientation,
|
self.orientation,
|
||||||
*printer.size.get(self.orientation),
|
*printer.size.get(self.orientation),
|
||||||
).enumerate()
|
).enumerate()
|
||||||
{
|
{
|
||||||
// eprintln!("Printer size: {:?}", printer.size);
|
// debug!("Printer size: {:?}", printer.size);
|
||||||
// eprintln!("Child size: {:?}", item.child.size);
|
// debug!("Child size: {:?}", item.child.size);
|
||||||
// eprintln!("Offset: {:?}", item.offset);
|
// debug!("Offset: {:?}", item.offset);
|
||||||
let printer = &printer
|
let printer = &printer
|
||||||
.offset(self.orientation.make_vec(item.offset, 0))
|
.offset(self.orientation.make_vec(item.offset, 0))
|
||||||
.cropped(item.child.size)
|
.cropped(item.child.size)
|
||||||
@ -364,7 +364,7 @@ impl View for LinearLayout {
|
|||||||
|
|
||||||
fn layout(&mut self, size: Vec2) {
|
fn layout(&mut self, size: Vec2) {
|
||||||
// If we can get away without breaking a sweat, you can bet we will.
|
// If we can get away without breaking a sweat, you can bet we will.
|
||||||
// eprintln!("Laying out with {:?}", size);
|
// debug!("Laying out with {:?}", size);
|
||||||
if self.get_cache(size).is_none() {
|
if self.get_cache(size).is_none() {
|
||||||
self.required_size(size);
|
self.required_size(size);
|
||||||
}
|
}
|
||||||
@ -387,6 +387,7 @@ impl View for LinearLayout {
|
|||||||
if let Some(size) = self.get_cache(req) {
|
if let Some(size) = self.get_cache(req) {
|
||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
|
debug!("Req: {:?}", req);
|
||||||
|
|
||||||
// First, make a naive scenario: everything will work fine.
|
// First, make a naive scenario: everything will work fine.
|
||||||
let ideal_sizes: Vec<Vec2> = self
|
let ideal_sizes: Vec<Vec2> = self
|
||||||
@ -425,7 +426,7 @@ impl View for LinearLayout {
|
|||||||
|
|
||||||
// This is the lowest we'll ever go. It better fit at least.
|
// This is the lowest we'll ever go. It better fit at least.
|
||||||
let orientation = self.orientation;
|
let orientation = self.orientation;
|
||||||
if !desperate.fits_in(req) {
|
if desperate.get(orientation) > req.get(orientation) {
|
||||||
// Just give up...
|
// Just give up...
|
||||||
// TODO: hard-cut
|
// TODO: hard-cut
|
||||||
cap(
|
cap(
|
||||||
@ -447,7 +448,8 @@ impl View for LinearLayout {
|
|||||||
|
|
||||||
// This here is how much we're generously offered
|
// This here is how much we're generously offered
|
||||||
// (We just checked that req >= desperate, so the subtraction is safe
|
// (We just checked that req >= desperate, so the subtraction is safe
|
||||||
let mut available = self.orientation.get(&(req - desperate));
|
let mut available =
|
||||||
|
self.orientation.get(&(req.saturating_sub(desperate)));
|
||||||
debug!("Available: {:?}", available);
|
debug!("Available: {:?}", available);
|
||||||
|
|
||||||
// Here, we have to make a compromise between the ideal
|
// Here, we have to make a compromise between the ideal
|
||||||
|
@ -56,9 +56,11 @@ impl Placement {
|
|||||||
enum ChildWrapper<T: View> {
|
enum ChildWrapper<T: View> {
|
||||||
// Some views include a shadow around.
|
// Some views include a shadow around.
|
||||||
Shadow(ShadowView<Layer<T>>),
|
Shadow(ShadowView<Layer<T>>),
|
||||||
// Some include a background.
|
|
||||||
|
// Some include only include a background.
|
||||||
Backfilled(Layer<T>),
|
Backfilled(Layer<T>),
|
||||||
// Some views don't (fullscreen views mostly)
|
|
||||||
|
// Some views don't even have a background (they'll be transparent).
|
||||||
Plain(T),
|
Plain(T),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -18,7 +18,10 @@ use {Printer, With, XY};
|
|||||||
pub struct TextArea {
|
pub struct TextArea {
|
||||||
// TODO: use a smarter data structure (rope?)
|
// TODO: use a smarter data structure (rope?)
|
||||||
content: String,
|
content: String,
|
||||||
|
|
||||||
/// Byte offsets within `content` representing text rows
|
/// Byte offsets within `content` representing text rows
|
||||||
|
///
|
||||||
|
/// Invariant: never empty.
|
||||||
rows: Vec<Row>,
|
rows: Vec<Row>,
|
||||||
|
|
||||||
/// When `false`, we don't take any input.
|
/// When `false`, we don't take any input.
|
||||||
@ -36,6 +39,8 @@ pub struct TextArea {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn make_rows(text: &str, width: usize) -> Vec<Row> {
|
fn make_rows(text: &str, width: usize) -> Vec<Row> {
|
||||||
|
// We can't make rows with width=0, so force at least width=1.
|
||||||
|
let width = usize::max(width, 1);
|
||||||
LinesIterator::new(text, width).show_spaces().collect()
|
LinesIterator::new(text, width).show_spaces().collect()
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -142,6 +147,10 @@ impl TextArea {
|
|||||||
/// Finds the row containing the grapheme at the given offset
|
/// Finds the row containing the grapheme at the given offset
|
||||||
fn row_at(&self, offset: usize) -> usize {
|
fn row_at(&self, offset: usize) -> usize {
|
||||||
debug!("Offset: {}", offset);
|
debug!("Offset: {}", offset);
|
||||||
|
|
||||||
|
assert!(!self.rows.is_empty());
|
||||||
|
assert!(offset >= self.rows[0].start);
|
||||||
|
|
||||||
self.rows
|
self.rows
|
||||||
.iter()
|
.iter()
|
||||||
.enumerate()
|
.enumerate()
|
||||||
@ -160,6 +169,7 @@ impl TextArea {
|
|||||||
|
|
||||||
/// Finds the row containing the cursor
|
/// Finds the row containing the cursor
|
||||||
fn selected_row(&self) -> usize {
|
fn selected_row(&self) -> usize {
|
||||||
|
assert!(!self.rows.is_empty(), "Rows should never be empty.");
|
||||||
self.row_at(self.cursor)
|
self.row_at(self.cursor)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user