@@ -2,7 +2,7 @@ use std::fmt;
22use std:: ops:: Range ;
33use std:: rc:: Rc ;
44
5- use super :: { AsRangedCoord , Ranged } ;
5+ use super :: { AsRangedCoord , DiscreteRanged , Ranged } ;
66
77/// The category coordinate
88pub struct Category < T : PartialEq > {
@@ -22,10 +22,33 @@ impl<T: PartialEq> Clone for Category<T> {
2222 }
2323}
2424
25+ impl < T : PartialEq > std:: cmp:: PartialEq for Category < T > {
26+ fn eq ( & self , other : & Self ) -> bool {
27+ self . name == other. name && self . elements == other. elements && self . idx == other. idx
28+ }
29+ }
30+
31+ impl < T : std:: hash:: Hash + Eq > std:: hash:: Hash for Category < T > {
32+ fn hash < H > ( & self , state : & mut H )
33+ where
34+ H : std:: hash:: Hasher ,
35+ {
36+ self . name . hash ( state) ;
37+ self . idx . hash ( state) ;
38+ self . elements . iter ( ) . for_each ( |ele| ele. hash ( state) ) ;
39+ }
40+ }
41+
42+ impl < T : Eq > std:: cmp:: Eq for Category < T > { }
43+
2544impl < T : PartialEq + fmt:: Display > fmt:: Debug for Category < T > {
2645 fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
27- let element = & self . elements [ self . idx as usize ] ;
28- write ! ( f, "{}" , element)
46+ if self . idx < 0 {
47+ write ! ( f, "{}" , "NO VALUE" )
48+ } else {
49+ let element = & self . elements [ self . idx as usize ] ;
50+ write ! ( f, "{}" , element)
51+ }
2952 }
3053}
3154
@@ -172,6 +195,37 @@ impl<T: PartialEq> Ranged for Category<T> {
172195 }
173196}
174197
198+ impl < T : PartialEq > DiscreteRanged for Category < T > {
199+ type RangeParameter = ( ) ;
200+
201+ fn get_range_parameter ( & self ) { }
202+
203+ /// Get the smallest value that is larger than the `this` value
204+ fn next_value ( this : & Self :: ValueType , _param : & ( ) ) -> Self :: ValueType {
205+ let mut out = this. clone ( ) ;
206+ out. idx = match out. idx {
207+ // Any negative number (ie. -1) should return 0 (the start)
208+ idx if idx < 0 => 0 ,
209+ // If we've hit the end of the range, start again
210+ idx if idx as usize >= out. elements . len ( ) => 0 ,
211+ // Otherwise just increase idx
212+ idx => idx + 1 ,
213+ } ;
214+ out
215+ }
216+
217+ /// Get the largest value that is smaller than `this` value
218+ fn previous_value ( this : & Self :: ValueType , _param : & ( ) ) -> Self :: ValueType {
219+ let mut out = this. clone ( ) ;
220+ out. idx -= 1 ;
221+ if out. idx < 0 {
222+ // If we need to wrap around
223+ out. idx = ( out. elements . len ( ) - 1 ) as i32 ;
224+ }
225+ out
226+ }
227+ }
228+
175229impl < T : PartialEq > AsRangedCoord for Category < T > {
176230 type CoordDescType = Self ;
177231 type Value = Category < T > ;
0 commit comments