1use std::{
2 borrow::Cow,
3 collections::{HashMap, HashSet},
4 fmt::Debug,
5};
6
7use bevy_ecs::{prelude::*, world::CommandQueue};
8use derive_more::{AsMut, AsRef, Deref, DerefMut};
9use futures::channel::mpsc::{UnboundedReceiver, UnboundedSender};
10use lsp_types::Position;
11
12use crate::{
13 lang::{Lang, LangHelper},
14 prelude::*,
15 systems::TypeId,
16};
17
18#[derive(Component, Default, Debug, Clone, Eq, Hash, PartialEq, PartialOrd, Ord)]
19pub struct CurrentType(pub Vec<TypeId>);
20
21#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
23pub struct Element<L: Lang>(pub Spanned<L::Element>);
24
25#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
27pub struct Wrapped<E>(pub E);
28
29#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
31pub struct Errors<E>(pub Vec<E>);
32
33#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
35pub struct Source(pub String);
36
37#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
39pub struct RopeC(pub ropey::Rope);
40
41#[derive(Component, Debug, AsRef, Deref)]
44pub struct DynLang(pub Box<dyn LangHelper + 'static + Send + Sync>);
45
46#[derive(Component, Debug)]
50pub struct Open;
51
52#[derive(Component, Debug)]
58pub struct Dirty;
59
60#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
62pub struct Label(pub lsp_types::Url);
63
64#[derive(Resource, AsRef, Deref, AsMut, DerefMut, Debug)]
66pub struct CommandReceiver(pub UnboundedReceiver<CommandQueue>);
67
68#[derive(Resource, AsRef, Deref, AsMut, DerefMut, Debug, Clone)]
70pub struct CommandSender(pub UnboundedSender<CommandQueue>);
71
72#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug, Clone)]
77pub struct DocumentLinks(pub Vec<(lsp_types::Url, &'static str)>);
78
79#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
85pub struct PositionComponent(pub Position);
86
87#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
89pub struct KeyWords(pub Vec<&'static str>);
90
91#[derive(Component, AsRef, Deref, AsMut, DerefMut, Debug)]
93pub struct Types(pub HashMap<Cow<'static, str>, Vec<TypeId>>);
94
95#[derive(Resource, Debug, Default)]
113pub struct TypeHierarchy<'a> {
114 numbers: HashMap<Cow<'a, str>, TypeId>,
115 nodes: Vec<Cow<'a, str>>,
116 subclass: Vec<HashSet<TypeId>>,
117 superclass: Vec<HashSet<TypeId>>,
118}
119
120impl<'a> TypeHierarchy<'a> {
121 pub fn get_id(&mut self, class: &str) -> TypeId {
122 if let Some(id) = self.numbers.get(class) {
123 *id
124 } else {
125 let new_id = TypeId(self.nodes.len());
126 let class_cow: Cow<'a, str> = Cow::Owned(class.to_string());
127 self.nodes.push(class_cow.clone());
128 self.numbers.insert(class_cow, new_id);
129 self.subclass.push(HashSet::new());
130 self.superclass.push(HashSet::new());
131 new_id
132 }
133 }
134
135 pub fn get_id_ref(&self, class: &str) -> Option<TypeId> {
136 self.numbers.get(class).copied()
137 }
138
139 pub fn set_subclass_of(&mut self, class: TypeId, to: TypeId) {
140 self.subclass[class.0].insert(to);
141 self.superclass[to.0].insert(class);
142 }
143
144 pub fn iter_subclass<'b>(&'b self, id: TypeId) -> impl Iterator<Item = Cow<'a, str>> + 'b {
145 let mut stack = std::collections::VecDeque::new();
146 stack.push_back(id);
147 let mut done = HashSet::new();
148 std::iter::from_fn(move || {
149 while let Some(id) = stack.pop_front() {
150 if done.contains(&id) {
151 continue;
152 }
153 done.insert(id);
154
155 self.subclass[id.0].iter().for_each(|i| stack.push_back(*i));
156 return Some(self.nodes[id.0].clone());
157 }
158
159 None
160 })
161 }
162
163 pub fn type_name(&self, id: TypeId) -> Cow<'a, str> {
164 self.nodes[id.0].clone()
165 }
166
167 pub fn iter_superclass<'b>(&'b self, id: TypeId) -> impl Iterator<Item = Cow<'a, str>> + 'b {
168 let mut stack = std::collections::VecDeque::new();
169 stack.push_back(id);
170 let mut done = HashSet::new();
171 std::iter::from_fn(move || {
172 while let Some(id) = stack.pop_front() {
173 if done.contains(&id) {
174 continue;
175 }
176 done.insert(id);
177
178 self.superclass[id.0]
179 .iter()
180 .for_each(|i| stack.push_back(*i));
181 return Some(self.nodes[id.0].clone());
182 }
183
184 None
185 })
186 }
187}