use std::cmp::max;
use std::cmp::min;
fn sanitize_selection(selection: isize, count: usize) -> usize {
if count == 0 {
0
} else {
max(0, min(count as isize - 1, selection)) as usize
}
}
pub trait Selectable {
fn selection_index(&self) -> isize;
fn set_selection_index(&mut self, selection: isize);
fn count(&self) -> usize;
fn selection(&self, add: isize) -> usize {
let count = self.count();
let index = self.selection_index();
let selection = sanitize_selection(index, count);
debug_assert!(add >= 0 || selection as isize >= add);
(selection as isize + add) as usize
}
fn select(&mut self, selection: isize) -> bool {
let count = self.count();
let index = self.selection_index();
let old_selection = sanitize_selection(index, count);
let new_selection = sanitize_selection(selection, count);
self.set_selection_index(selection);
new_selection != old_selection
}
fn change_selection(&mut self, change: isize) -> bool {
let count = self.count();
let index = self.selection_index();
let selection = sanitize_selection(index, count);
let new_selection = selection as isize + change;
self.select(new_selection)
}
}