wip rework to be range based
This commit is contained in:
parent
d5e288f727
commit
ae0f10b48c
|
@ -4,6 +4,7 @@ use crate::{
|
||||||
};
|
};
|
||||||
use ::bitvec::{order::Msb0, prelude::BitSlice, slice::IterMut};
|
use ::bitvec::{order::Msb0, prelude::BitSlice, slice::IterMut};
|
||||||
use inherent::inherent;
|
use inherent::inherent;
|
||||||
|
use std::ops::{Index, Range};
|
||||||
|
|
||||||
/// A fixed-size 2D grid of booleans.
|
/// A fixed-size 2D grid of booleans.
|
||||||
///
|
///
|
||||||
|
@ -183,12 +184,10 @@ impl Bitmap {
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn window(
|
pub fn window(
|
||||||
&self,
|
&self,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<Window<bool, Self>> {
|
) -> Option<Window<bool, Self>> {
|
||||||
Window::new(self, x, y, width, height)
|
Window::new(self, xs, ys)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Creates a mutable window into the bitmap.
|
/// Creates a mutable window into the bitmap.
|
||||||
|
@ -196,12 +195,10 @@ impl Bitmap {
|
||||||
/// Returns None in case the window does not fit.
|
/// Returns None in case the window does not fit.
|
||||||
pub fn window_mut(
|
pub fn window_mut(
|
||||||
&mut self,
|
&mut self,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<WindowMut<bool, Self>> {
|
) -> Option<WindowMut<bool, Self>> {
|
||||||
WindowMut::new(self, x, y, width, height)
|
WindowMut::new(self, xs, ys)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,10 @@
|
||||||
use crate::{DataRef, Grid, GridMut, Window, WindowMut};
|
use crate::{DataRef, Grid, GridMut, Window, WindowMut};
|
||||||
use inherent::inherent;
|
use inherent::inherent;
|
||||||
use std::fmt::Debug;
|
use std::{
|
||||||
use std::slice::{Iter, IterMut};
|
fmt::Debug,
|
||||||
|
ops::Range,
|
||||||
|
slice::{Iter, IterMut},
|
||||||
|
};
|
||||||
|
|
||||||
/// A type that can be stored in a [`ValueGrid`], e.g. [char], [u8].
|
/// A type that can be stored in a [`ValueGrid`], e.g. [char], [u8].
|
||||||
pub trait Value: Sized + Default + Copy + Clone + Debug {}
|
pub trait Value: Sized + Default + Copy + Clone + Debug {}
|
||||||
|
@ -317,12 +320,10 @@ impl<T: Value> ValueGrid<T> {
|
||||||
/// Returns None in case the window does not fit.
|
/// Returns None in case the window does not fit.
|
||||||
pub fn window(
|
pub fn window(
|
||||||
&self,
|
&self,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<Window<T, Self>> {
|
) -> Option<Window<T, Self>> {
|
||||||
Window::new(self, x, y, width, height)
|
Window::new(self, xs, ys)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Creates a mutable window into the grid.
|
/// Creates a mutable window into the grid.
|
||||||
|
@ -330,12 +331,10 @@ impl<T: Value> ValueGrid<T> {
|
||||||
/// Returns None in case the window does not fit.
|
/// Returns None in case the window does not fit.
|
||||||
pub fn window_mut(
|
pub fn window_mut(
|
||||||
&mut self,
|
&mut self,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<WindowMut<T, Self>> {
|
) -> Option<WindowMut<T, Self>> {
|
||||||
WindowMut::new(self, x, y, width, height)
|
WindowMut::new(self, xs, ys)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@ use crate::{
|
||||||
containers::char_grid::{CharGridExt, CharGridMutExt},
|
containers::char_grid::{CharGridExt, CharGridMutExt},
|
||||||
Grid, GridMut,
|
Grid, GridMut,
|
||||||
};
|
};
|
||||||
use std::marker::PhantomData;
|
use std::{marker::PhantomData, ops::Range};
|
||||||
|
|
||||||
macro_rules! define_window {
|
macro_rules! define_window {
|
||||||
($name:ident, $grid:ty) => {
|
($name:ident, $grid:ty) => {
|
||||||
|
@ -13,10 +13,8 @@ macro_rules! define_window {
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct $name<'t, TElement: Copy, TGrid: Grid<TElement>> {
|
pub struct $name<'t, TElement: Copy, TGrid: Grid<TElement>> {
|
||||||
grid: $grid,
|
grid: $grid,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
phantom: PhantomData<TElement>,
|
phantom: PhantomData<TElement>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -28,22 +26,18 @@ macro_rules! define_window {
|
||||||
#[allow(unused, reason = "False positive because of #[inherent]")]
|
#[allow(unused, reason = "False positive because of #[inherent]")]
|
||||||
pub fn new(
|
pub fn new(
|
||||||
grid: $grid,
|
grid: $grid,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<Self> {
|
) -> Option<Self> {
|
||||||
if !grid.is_in_bounds(x + width - 1, y + height - 1) {
|
if !grid.is_in_bounds(xs.end - 1, ys.end - 1) {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
|
|
||||||
Some(Self {
|
Some(Self {
|
||||||
grid,
|
grid,
|
||||||
x,
|
xs,
|
||||||
y,
|
ys,
|
||||||
width,
|
phantom: PhantomData::default(),
|
||||||
height,
|
|
||||||
phantom: PhantomData,
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -53,15 +47,18 @@ macro_rules! define_window {
|
||||||
/// Returns None in case the window does not fit.
|
/// Returns None in case the window does not fit.
|
||||||
pub fn window(
|
pub fn window(
|
||||||
&self,
|
&self,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<Window<TElement, TGrid>> {
|
) -> Option<Window<TElement, TGrid>> {
|
||||||
if x + width >= self.width || y + height >= self.height {
|
if !self.is_in_bounds(xs.end - 1, ys.end - 1) {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
Window::new(self.grid, self.x + x, self.y + y, width, height)
|
Window::new(
|
||||||
|
self.grid,
|
||||||
|
// TODO off by one
|
||||||
|
(self.xs.start + xs.start)..(self.xs.end + xs.end),
|
||||||
|
(self.ys.start + ys.start)..(self.ys.end + ys.end),
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
#[must_use]
|
#[must_use]
|
||||||
|
@ -72,20 +69,14 @@ macro_rules! define_window {
|
||||||
Window<'t, TElement, TGrid>,
|
Window<'t, TElement, TGrid>,
|
||||||
Window<'t, TElement, TGrid>,
|
Window<'t, TElement, TGrid>,
|
||||||
)> {
|
)> {
|
||||||
|
let middle_abs = self.xs.start + left_width;
|
||||||
let left = Window::new(
|
let left = Window::new(
|
||||||
self.grid,
|
self.grid,
|
||||||
self.x,
|
self.xs.start..middle_abs,
|
||||||
self.y,
|
self.ys.clone(),
|
||||||
left_width,
|
|
||||||
self.height,
|
|
||||||
)?;
|
|
||||||
let right = Window::new(
|
|
||||||
self.grid,
|
|
||||||
self.x + left_width,
|
|
||||||
self.y,
|
|
||||||
self.width - left_width,
|
|
||||||
self.height,
|
|
||||||
)?;
|
)?;
|
||||||
|
let right =
|
||||||
|
Window::new(self.grid, middle_abs..self.xs.end, self.ys)?;
|
||||||
Some((left, right))
|
Some((left, right))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -97,16 +88,14 @@ macro_rules! define_window {
|
||||||
Window<'t, TElement, TGrid>,
|
Window<'t, TElement, TGrid>,
|
||||||
Window<'t, TElement, TGrid>,
|
Window<'t, TElement, TGrid>,
|
||||||
)> {
|
)> {
|
||||||
|
let middle_abs = self.ys.start + top_height;
|
||||||
let top = Window::new(
|
let top = Window::new(
|
||||||
self.grid, self.x, self.y, self.width, top_height,
|
|
||||||
)?;
|
|
||||||
let bottom = Window::new(
|
|
||||||
self.grid,
|
self.grid,
|
||||||
self.x,
|
self.xs.clone(),
|
||||||
self.y + top_height,
|
self.ys.start..middle_abs,
|
||||||
self.width,
|
|
||||||
self.height - top_height,
|
|
||||||
)?;
|
)?;
|
||||||
|
let bottom =
|
||||||
|
Window::new(self.grid, self.xs, middle_abs..self.ys.end)?;
|
||||||
Some((top, bottom))
|
Some((top, bottom))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -118,19 +107,19 @@ macro_rules! define_window {
|
||||||
#[must_use]
|
#[must_use]
|
||||||
#[allow(unused, reason = "False positive because of #[inherent]")]
|
#[allow(unused, reason = "False positive because of #[inherent]")]
|
||||||
pub fn get(&self, x: usize, y: usize) -> TElement {
|
pub fn get(&self, x: usize, y: usize) -> TElement {
|
||||||
self.grid.get(x + self.x, y + self.y)
|
self.grid.get(self.xs.start + x, self.ys.start + y)
|
||||||
}
|
}
|
||||||
|
|
||||||
#[must_use]
|
#[must_use]
|
||||||
#[allow(unused, reason = "False positive because of #[inherent]")]
|
#[allow(unused, reason = "False positive because of #[inherent]")]
|
||||||
pub fn width(&self) -> usize {
|
pub fn width(&self) -> usize {
|
||||||
self.width
|
self.xs.len()
|
||||||
}
|
}
|
||||||
|
|
||||||
#[must_use]
|
#[must_use]
|
||||||
#[allow(unused, reason = "False positive because of #[inherent]")]
|
#[allow(unused, reason = "False positive because of #[inherent]")]
|
||||||
pub fn height(&self) -> usize {
|
pub fn height(&self) -> usize {
|
||||||
self.height
|
self.ys.len()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -148,13 +137,13 @@ impl<TElement: Copy, TGrid: GridMut<TElement>> GridMut<TElement>
|
||||||
{
|
{
|
||||||
#[allow(unused, reason = "False positive because of #[inherent]")]
|
#[allow(unused, reason = "False positive because of #[inherent]")]
|
||||||
pub fn set(&mut self, x: usize, y: usize, value: TElement) {
|
pub fn set(&mut self, x: usize, y: usize, value: TElement) {
|
||||||
self.grid.set(x + self.x, y + self.y, value);
|
self.grid.set(self.xs.start + x, self.ys.start + y, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(unused, reason = "False positive because of #[inherent]")]
|
#[allow(unused, reason = "False positive because of #[inherent]")]
|
||||||
pub fn fill(&mut self, value: TElement) {
|
pub fn fill(&mut self, value: TElement) {
|
||||||
for y in self.y..(self.y + self.height) {
|
for y in self.ys.clone() {
|
||||||
for x in self.x..(self.x + self.width) {
|
for x in self.xs.clone() {
|
||||||
self.grid.set(x, y, value);
|
self.grid.set(x, y, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -170,22 +159,25 @@ impl<TElement: Copy, TGrid: GridMut<TElement>> WindowMut<'_, TElement, TGrid> {
|
||||||
/// Returns None in case the window does not fit.
|
/// Returns None in case the window does not fit.
|
||||||
pub fn window_mut(
|
pub fn window_mut(
|
||||||
&mut self,
|
&mut self,
|
||||||
x: usize,
|
xs: Range<usize>,
|
||||||
y: usize,
|
ys: Range<usize>,
|
||||||
width: usize,
|
|
||||||
height: usize,
|
|
||||||
) -> Option<WindowMut<TElement, TGrid>> {
|
) -> Option<WindowMut<TElement, TGrid>> {
|
||||||
if x + width > self.width || y + height > self.height {
|
if self.is_in_bounds(xs.end - 1, ys.end - 1) {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
WindowMut::new(self.grid, self.x + x, self.y + y, width, height)
|
|
||||||
|
WindowMut::new(
|
||||||
|
self.grid,
|
||||||
|
(self.xs.start + xs.start)..(self.xs.end + xs.end),
|
||||||
|
(self.ys.start + ys.start)..(self.ys.end + ys.end),
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn deref_assign<O: Grid<TElement>>(&mut self, other: &O) {
|
pub fn deref_assign<O: Grid<TElement>>(&mut self, other: &O) {
|
||||||
assert!(self.width() == other.width());
|
assert_eq!(self.width(), other.width());
|
||||||
assert!(self.height() == other.height());
|
assert_eq!(self.height(), other.height());
|
||||||
for y in 0..self.height {
|
for y in self.ys.clone() {
|
||||||
for x in 0..self.width {
|
for x in self.xs.clone() {
|
||||||
self.set(x, y, other.get(x, y));
|
self.set(x, y, other.get(x, y));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -197,34 +189,20 @@ impl<TElement: Copy, TGrid: GridMut<TElement>> WindowMut<'_, TElement, TGrid> {
|
||||||
left_width: usize,
|
left_width: usize,
|
||||||
) -> Option<(Self, Self)> {
|
) -> Option<(Self, Self)> {
|
||||||
let (grid1, grid2) = unsafe { Self::duplicate_mutable_ref(self.grid) };
|
let (grid1, grid2) = unsafe { Self::duplicate_mutable_ref(self.grid) };
|
||||||
|
let middle_abs = self.xs.start + left_width;
|
||||||
let left =
|
let left =
|
||||||
WindowMut::new(grid1, self.x, self.y, left_width, self.height)?;
|
WindowMut::new(grid1, self.xs.start..middle_abs, self.ys.clone())?;
|
||||||
let right = WindowMut::new(
|
let right = WindowMut::new(grid2, middle_abs..self.xs.end, self.ys)?;
|
||||||
grid2,
|
|
||||||
self.x + left_width,
|
|
||||||
self.y,
|
|
||||||
self.width - left_width,
|
|
||||||
self.height,
|
|
||||||
)?;
|
|
||||||
Some((left, right))
|
Some((left, right))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn split_vertical_mut(self, top_height: usize) -> Option<(Self, Self)> {
|
pub fn split_vertical_mut(self, top_height: usize) -> Option<(Self, Self)> {
|
||||||
let (grid1, grid2) = unsafe { Self::duplicate_mutable_ref(self.grid) };
|
let (grid1, grid2) = unsafe { Self::duplicate_mutable_ref(self.grid) };
|
||||||
|
let middle_abs = self.ys.start + top_height;
|
||||||
let top =
|
let top =
|
||||||
WindowMut::new(grid1, self.x, self.y, self.width, top_height)?;
|
WindowMut::new(grid1, self.xs.clone(), self.ys.start..middle_abs)?;
|
||||||
let bottom = WindowMut::new(
|
let bottom = WindowMut::new(grid2, self.xs, middle_abs..self.ys.end)?;
|
||||||
grid2,
|
|
||||||
self.x,
|
|
||||||
self.y + top_height,
|
|
||||||
self.width,
|
|
||||||
self.height - top_height,
|
|
||||||
)?;
|
|
||||||
|
|
||||||
let foo = &mut [..];
|
|
||||||
*foo = [..];
|
|
||||||
|
|
||||||
Some((top, bottom))
|
Some((top, bottom))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -247,7 +225,7 @@ mod tests {
|
||||||
let mut bitmap = Bitmap::new(8, 4).unwrap();
|
let mut bitmap = Bitmap::new(8, 4).unwrap();
|
||||||
|
|
||||||
// non-byte-aligned views work
|
// non-byte-aligned views work
|
||||||
let mut view = bitmap.window_mut(3, 1, 4, 2).unwrap();
|
let mut view = bitmap.window_mut(3..7, 1..3).unwrap();
|
||||||
view.fill(true);
|
view.fill(true);
|
||||||
|
|
||||||
assert_eq!(bitmap.data_ref(), &[0, 30, 30, 0]);
|
assert_eq!(bitmap.data_ref(), &[0, 30, 30, 0]);
|
||||||
|
@ -255,17 +233,17 @@ mod tests {
|
||||||
assert_eq!(bitmap.set_optional(99, 99, false), false);
|
assert_eq!(bitmap.set_optional(99, 99, false), false);
|
||||||
|
|
||||||
// full size view works
|
// full size view works
|
||||||
bitmap.window(0, 0, 8, 4).unwrap();
|
bitmap.window(0..8, 0..4).unwrap();
|
||||||
|
|
||||||
// zero size view works
|
// zero size view works
|
||||||
assert!(Window::new(&mut bitmap, 1, 2, 3, 0).is_some());
|
assert!(Window::new(&mut bitmap, 1..4, 2..2).is_some());
|
||||||
assert!(WindowMut::new(&mut bitmap, 1, 2, 0, 1)
|
assert!(WindowMut::new(&mut bitmap, 1..1, 2..3)
|
||||||
.is_some_and(|w| w.get_optional(0, 0).is_none()));
|
.is_some_and(|w| w.get_optional(0, 0).is_none()));
|
||||||
|
|
||||||
// oob does not work
|
// oob does not work
|
||||||
assert!(Window::new(&mut bitmap, 30, 43, 3, 1).is_none());
|
assert!(Window::new(&mut bitmap, 30..33, 43..44).is_none());
|
||||||
assert!(WindowMut::new(&mut bitmap, 0, 0, 9, 1).is_none());
|
assert!(WindowMut::new(&mut bitmap, 0..9, 0..1).is_none());
|
||||||
assert!(Window::new(&mut bitmap, 0, 0, 1, 5).is_none());
|
assert!(Window::new(&mut bitmap, 0..1, 0..5).is_none());
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
|
@ -273,7 +251,7 @@ mod tests {
|
||||||
let mut grid = CharGrid::new(3, 4);
|
let mut grid = CharGrid::new(3, 4);
|
||||||
grid.fill(' ');
|
grid.fill(' ');
|
||||||
|
|
||||||
let mut view = grid.window_mut(1, 1, 1, 3).unwrap();
|
let mut view = grid.window_mut(1..2, 1..4).unwrap();
|
||||||
view.fill('#');
|
view.fill('#');
|
||||||
view.set(0, 0, '!');
|
view.set(0, 0, '!');
|
||||||
|
|
||||||
|
@ -283,30 +261,30 @@ mod tests {
|
||||||
);
|
);
|
||||||
|
|
||||||
// full size view works
|
// full size view works
|
||||||
_ = grid.window(0, 0, 3, 4).unwrap();
|
_ = grid.window(0..3, 0..4).unwrap();
|
||||||
|
|
||||||
// zero size view works
|
// zero size view works
|
||||||
assert!(grid
|
assert!(grid
|
||||||
.window(1, 2, 2, 0)
|
.window(1..3, 2..2)
|
||||||
.is_some_and(|w| w.get_optional(0, 0).is_none()));
|
.is_some_and(|w| w.get_optional(0, 0).is_none()));
|
||||||
assert!(grid.window(1, 2, 0, 1).is_some());
|
assert!(grid.window(1..1, 2..3).is_some());
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn round_trip_bitmap() {
|
fn round_trip_bitmap() {
|
||||||
let bitmap = Bitmap::new(8, 4).unwrap();
|
let bitmap = Bitmap::new(8, 4).unwrap();
|
||||||
|
|
||||||
let non_aligned = bitmap.window(3, 1, 4, 2).unwrap();
|
let non_aligned = bitmap.window(3..7, 1..3).unwrap();
|
||||||
assert_eq!(Bitmap::try_from(&non_aligned), Err(()));
|
assert_eq!(Bitmap::try_from(&non_aligned), Err(()));
|
||||||
|
|
||||||
let aligned = bitmap.window(0, 1, 8, 2).unwrap();
|
let aligned = bitmap.window(0..8, 1..3).unwrap();
|
||||||
assert!(matches!(Bitmap::try_from(&aligned), Ok(_)));
|
assert!(matches!(Bitmap::try_from(&aligned), Ok(_)));
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn split_vertical() {
|
fn split_vertical() {
|
||||||
let grid = ByteGrid::new(5, 4);
|
let grid = ByteGrid::new(5, 4);
|
||||||
let window = grid.window(0, 0, grid.width(), grid.height()).unwrap();
|
let window = grid.window(0..grid.width(), 0..grid.height()).unwrap();
|
||||||
|
|
||||||
let (left, right) = window.split_vertical(3).unwrap();
|
let (left, right) = window.split_vertical(3).unwrap();
|
||||||
assert_eq!(3, left.height());
|
assert_eq!(3, left.height());
|
||||||
|
@ -318,7 +296,7 @@ mod tests {
|
||||||
#[test]
|
#[test]
|
||||||
fn split_horizontal() {
|
fn split_horizontal() {
|
||||||
let grid = ByteGrid::new(4, 5);
|
let grid = ByteGrid::new(4, 5);
|
||||||
let window = grid.window(0, 0, grid.width(), grid.height()).unwrap();
|
let window = grid.window(0..grid.width(), 0..grid.height()).unwrap();
|
||||||
|
|
||||||
let (top, bottom) = window.split_horizontal(3).unwrap();
|
let (top, bottom) = window.split_horizontal(3).unwrap();
|
||||||
assert_eq!(3, top.width());
|
assert_eq!(3, top.width());
|
||||||
|
@ -326,4 +304,65 @@ mod tests {
|
||||||
assert_eq!(5, top.height());
|
assert_eq!(5, top.height());
|
||||||
assert_eq!(5, bottom.height())
|
assert_eq!(5, bottom.height())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn window_in_window() {
|
||||||
|
let mut grid = ByteGrid::new(6, 7);
|
||||||
|
grid.fill(1);
|
||||||
|
|
||||||
|
let mut w1 = grid
|
||||||
|
.window_mut(1..grid.width() - 2, 1..grid.height() - 2)
|
||||||
|
.unwrap();
|
||||||
|
w1.fill(2);
|
||||||
|
|
||||||
|
let w1_1 = w1.window(0..w1.width(), 0..w1.height()).unwrap();
|
||||||
|
assert_eq!(w1_1.get(0, 0), 2);
|
||||||
|
|
||||||
|
assert!(matches!(w1.window(0..w1.width(), 1..w1.height()), None));
|
||||||
|
|
||||||
|
let mut w2 = w1
|
||||||
|
.window_mut(1..w1.width() - 2, 1..w1.height() - 2)
|
||||||
|
.unwrap();
|
||||||
|
w2.fill(3);
|
||||||
|
|
||||||
|
// zero-sized
|
||||||
|
let mut w3 = w2
|
||||||
|
.window_mut(1..w2.width() - 2, 1..w2.height() - 2)
|
||||||
|
.unwrap();
|
||||||
|
w3.fill(4);
|
||||||
|
|
||||||
|
#[rustfmt::skip]
|
||||||
|
assert_eq!(
|
||||||
|
grid.data_ref(),
|
||||||
|
&[
|
||||||
|
1, 1, 1, 1, 1, 1,
|
||||||
|
1, 2, 2, 2, 2, 1,
|
||||||
|
1, 2, 3, 3, 2, 1,
|
||||||
|
1, 2, 3, 3, 2, 1,
|
||||||
|
1, 2, 3, 3, 2, 1,
|
||||||
|
1, 2, 2, 2, 2, 1,
|
||||||
|
1, 1, 1, 1, 1, 1
|
||||||
|
]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn width_height() {
|
||||||
|
let grid = ByteGrid::new(4, 4);
|
||||||
|
let w1 = grid.window(0..grid.width(), 0..grid.height()).unwrap();
|
||||||
|
assert_eq!(grid.width(), w1.width());
|
||||||
|
assert_eq!(grid.height(), w1.height());
|
||||||
|
let w2 = w1.window(0..w1.width(), 0..w1.height()).unwrap();
|
||||||
|
assert_eq!(grid.width(), w2.width());
|
||||||
|
assert_eq!(grid.height(), w2.height());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn split_mut() {
|
||||||
|
let mut grid = ByteGrid::new(5, 5);
|
||||||
|
grid.fill(1);
|
||||||
|
|
||||||
|
assert_eq!((0..5).len(), 5);
|
||||||
|
//let mut w1 = grid
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue