Adding in UpdateAt for ListChange
This commit is contained in:
parent
9bb627ae20
commit
e34fc50ad0
|
@ -2,7 +2,7 @@ use futures::Async;
|
|||
//use std::iter::Iterator;
|
||||
|
||||
|
||||
fn update_indexes<A: Copy, F: FnMut(A) -> A>(indexes: &mut [Option<A>], mut f: F) -> Option<A> {
|
||||
fn increment_indexes(indexes: &mut [Option<usize>]) -> Option<usize> {
|
||||
let mut first = None;
|
||||
|
||||
for index in indexes.into_iter() {
|
||||
|
@ -11,13 +11,21 @@ fn update_indexes<A: Copy, F: FnMut(A) -> A>(indexes: &mut [Option<A>], mut f: F
|
|||
first = Some(i);
|
||||
}
|
||||
|
||||
*index = Some(f(i));
|
||||
*index = Some(i + 1);
|
||||
}
|
||||
}
|
||||
|
||||
first
|
||||
}
|
||||
|
||||
fn decrement_indexes(indexes: &mut [Option<usize>]) {
|
||||
for index in indexes {
|
||||
if let Some(i) = *index {
|
||||
*index = Some(i - 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub enum ListChange<A> {
|
||||
|
@ -30,6 +38,11 @@ pub enum ListChange<A> {
|
|||
value: A,
|
||||
},
|
||||
|
||||
UpdateAt {
|
||||
index: usize,
|
||||
value: A,
|
||||
},
|
||||
|
||||
RemoveAt {
|
||||
index: usize,
|
||||
},
|
||||
|
@ -56,6 +69,7 @@ impl<A> ListChange<A> {
|
|||
// TODO figure out a more efficient way of implementing this
|
||||
ListChange::Replace { values } => ListChange::Replace { values: values.into_iter().map(callback).collect() },
|
||||
ListChange::InsertAt { index, value } => ListChange::InsertAt { index, value: callback(value) },
|
||||
ListChange::UpdateAt { index, value } => ListChange::UpdateAt { index, value: callback(value) },
|
||||
ListChange::RemoveAt { index } => ListChange::RemoveAt { index },
|
||||
ListChange::Push { value } => ListChange::Push { value: callback(value) },
|
||||
ListChange::Pop {} => ListChange::Pop {},
|
||||
|
@ -162,7 +176,7 @@ impl<A, B, F> SignalList for FilterMap<A, F>
|
|||
ListChange::InsertAt { index, value } => {
|
||||
match (self.callback)(value) {
|
||||
Some(value) => {
|
||||
let new_index = update_indexes(&mut self.indexes[index..], |index| index + 1).unwrap_or(self.length);
|
||||
let new_index = increment_indexes(&mut self.indexes[index..]).unwrap_or(self.length);
|
||||
|
||||
self.indexes.insert(index, Some(new_index));
|
||||
self.length += 1;
|
||||
|
@ -176,14 +190,46 @@ impl<A, B, F> SignalList for FilterMap<A, F>
|
|||
}
|
||||
},
|
||||
|
||||
ListChange::UpdateAt { index, value } => {
|
||||
match (self.callback)(value) {
|
||||
Some(value) => {
|
||||
match self.indexes[index] {
|
||||
Some(old_index) => {
|
||||
Async::Ready(Some(ListChange::UpdateAt { index: old_index, value }))
|
||||
},
|
||||
None => {
|
||||
let new_index = increment_indexes(&mut self.indexes[(index + 1)..]).unwrap_or(self.length);
|
||||
|
||||
self.indexes[index] = Some(new_index);
|
||||
self.length += 1;
|
||||
|
||||
Async::Ready(Some(ListChange::InsertAt { index: new_index, value }))
|
||||
},
|
||||
}
|
||||
},
|
||||
None => {
|
||||
match self.indexes[index] {
|
||||
Some(old_index) => {
|
||||
self.indexes[index] = None;
|
||||
|
||||
decrement_indexes(&mut self.indexes[(index + 1)..]);
|
||||
self.length -= 1;
|
||||
|
||||
Async::Ready(Some(ListChange::RemoveAt { index: old_index }))
|
||||
},
|
||||
None => {
|
||||
continue;
|
||||
},
|
||||
}
|
||||
},
|
||||
}
|
||||
},
|
||||
|
||||
ListChange::RemoveAt { index } => {
|
||||
match self.indexes.remove(index) {
|
||||
Some(old_index) => {
|
||||
for index in &mut self.indexes[index..] {
|
||||
if let Some(i) = *index {
|
||||
*index = Some(i - 1);
|
||||
}
|
||||
}
|
||||
decrement_indexes(&mut self.indexes[index..]);
|
||||
self.length -= 1;
|
||||
|
||||
Async::Ready(Some(ListChange::RemoveAt { index: old_index }))
|
||||
},
|
||||
|
@ -209,7 +255,7 @@ impl<A, B, F> SignalList for FilterMap<A, F>
|
|||
|
||||
ListChange::Pop {} => {
|
||||
match self.indexes.pop().expect("Cannot pop from empty vec") {
|
||||
Some(index) => {
|
||||
Some(_) => {
|
||||
Async::Ready(Some(ListChange::Pop {}))
|
||||
},
|
||||
None => {
|
||||
|
|
Loading…
Reference in New Issue