chore(ppu): reimplement the object buffer struct

This commit is contained in:
Rekai Nyangadzayi Musuka 2021-04-23 23:42:47 -05:00
parent 4ab59007f9
commit 98af1865ee
1 changed files with 10 additions and 29 deletions

View File

@ -177,7 +177,7 @@ impl Ppu {
if attr.x > 0 if attr.x > 0
&& line_y >= attr.y && line_y >= attr.y
&& line_y < (attr.y + sprite_height) && line_y < (attr.y + sprite_height)
&& !self.obj_buffer.full() && !self.obj_buffer.is_full()
{ {
self.obj_buffer.add(attr); self.obj_buffer.add(attr);
} }
@ -286,8 +286,6 @@ impl Ppu {
self.fetcher.bg.resume(); self.fetcher.bg.resume();
self.fifo.resume(); self.fifo.resume();
self.obj_buffer.remove(&attr);
} }
} else if self.fetcher.obj.fifo_count == 2 { } else if self.fetcher.obj.fifo_count == 2 {
self.fetcher.obj.reset(); self.fetcher.obj.reset();
@ -1008,56 +1006,39 @@ impl From<ObjectPaletteId> for u8 {
#[derive(Debug, Clone, Copy)] #[derive(Debug, Clone, Copy)]
struct ObjectBuffer { struct ObjectBuffer {
buf: [Option<ObjectAttribute>; 10], buf: [Option<ObjectAttribute>; OBJECT_LIMIT],
len: usize,
} }
impl ObjectBuffer { impl ObjectBuffer {
pub fn full(&self) -> bool { pub fn is_full(&self) -> bool {
!self.buf.iter().any(|maybe_attr| maybe_attr.is_none()) self.len == OBJECT_LIMIT
} }
pub fn clear(&mut self) { pub fn clear(&mut self) {
self.buf = [Default::default(); 10]; self.buf = [Default::default(); 10];
self.len = 0;
} }
pub fn add(&mut self, attr: ObjectAttribute) { pub fn add(&mut self, attr: ObjectAttribute) {
// TODO: Maybe this doesn't need to be O(n)? self.buf[self.len] = Some(attr);
for maybe_attr in self.buf.iter_mut() { self.len += 1;
if maybe_attr.is_none() {
*maybe_attr = Some(attr);
}
}
} }
pub fn len(&self) -> usize { pub fn len(&self) -> usize {
self.buf self.len
.iter()
.filter(|maybe_attr| maybe_attr.is_some())
.count()
} }
pub fn get(&self, index: usize) -> Option<&ObjectAttribute> { pub fn get(&self, index: usize) -> Option<&ObjectAttribute> {
self.buf[index].as_ref() self.buf[index].as_ref()
} }
pub fn position(&self, attr: &ObjectAttribute) -> Option<usize> {
self.buf.iter().position(|maybe_attr| match maybe_attr {
Some(other_attr) => attr == other_attr,
None => false,
})
}
pub fn remove(&mut self, attr: &ObjectAttribute) {
if let Some(i) = self.position(attr) {
self.buf[i] = None;
}
}
} }
impl Default for ObjectBuffer { impl Default for ObjectBuffer {
fn default() -> Self { fn default() -> Self {
Self { Self {
buf: [Default::default(); OBJECT_LIMIT], buf: [Default::default(); OBJECT_LIMIT],
len: Default::default(),
} }
} }
} }