1 | use std::rc::Rc; |
2 | |
3 | use crate::sources::EventDispatcher; |
4 | use crate::token::TokenInner; |
5 | |
6 | pub(crate) struct SourceEntry<'l, Data> { |
7 | pub(crate) token: TokenInner, |
8 | pub(crate) source: Option<Rc<dyn EventDispatcher<Data> + 'l>>, |
9 | } |
10 | |
11 | pub(crate) struct SourceList<'l, Data> { |
12 | sources: Vec<SourceEntry<'l, Data>>, |
13 | } |
14 | |
15 | impl<'l, Data> SourceList<'l, Data> { |
16 | pub(crate) fn new() -> Self { |
17 | SourceList { |
18 | sources: Vec::new(), |
19 | } |
20 | } |
21 | |
22 | pub(crate) fn vacant_entry(&mut self) -> &mut SourceEntry<'l, Data> { |
23 | let opt_id = self.sources.iter().position(|slot| slot.source.is_none()); |
24 | match opt_id { |
25 | Some(id) => { |
26 | // we are reusing a slot |
27 | let slot = &mut self.sources[id]; |
28 | // increment the slot version |
29 | slot.token = slot.token.increment_version(); |
30 | slot |
31 | } |
32 | None => { |
33 | // we are inserting a new slot |
34 | let next_id = self.sources.len(); |
35 | self.sources.push(SourceEntry { |
36 | token: TokenInner::new(self.sources.len()) |
37 | .expect("Trying to insert too many sources in an event loop." ), |
38 | source: None, |
39 | }); |
40 | &mut self.sources[next_id] |
41 | } |
42 | } |
43 | } |
44 | |
45 | pub(crate) fn get(&self, token: TokenInner) -> crate::Result<&SourceEntry<'l, Data>> { |
46 | let entry = self |
47 | .sources |
48 | .get(token.get_id()) |
49 | .ok_or(crate::Error::InvalidToken)?; |
50 | if entry.token.same_source_as(token) { |
51 | Ok(entry) |
52 | } else { |
53 | Err(crate::Error::InvalidToken) |
54 | } |
55 | } |
56 | |
57 | pub(crate) fn get_mut( |
58 | &mut self, |
59 | token: TokenInner, |
60 | ) -> crate::Result<&mut SourceEntry<'l, Data>> { |
61 | let entry = self |
62 | .sources |
63 | .get_mut(token.get_id()) |
64 | .ok_or(crate::Error::InvalidToken)?; |
65 | if entry.token.same_source_as(token) { |
66 | Ok(entry) |
67 | } else { |
68 | Err(crate::Error::InvalidToken) |
69 | } |
70 | } |
71 | } |
72 | |