60 lines
1.3 KiB
Rust

use std::path::PathBuf;
use std::sync::Arc;
pub struct SourceFile {
pub id: usize,
pub path: PathBuf,
pub source: Arc<str>,
}
pub struct FileManager {
files: Vec<SourceFile>,
}
impl FileManager {
pub fn new() -> Self {
Self { files: Vec::new() }
}
pub fn add(&mut self, path: PathBuf, source: String) -> usize {
let id = self.files.len();
self.files.push(SourceFile {
id,
path,
source: Arc::from(source),
});
id
}
pub fn get_file(&self, id: usize) -> Option<&SourceFile> {
self.files.get(id)
}
pub fn get_path(&self, id: usize) -> Option<PathBuf> {
self.files.get(id).map(|f| f.path.clone())
}
pub fn lookup_pos(&self, file_id: usize, pos: u32) -> (usize, usize) {
let file = if let Some(f) = self.files.get(file_id) {
f
} else {
return (0, 0);
};
let mut line = 1;
let mut col = 1;
for (i, c) in file.source.char_indices() {
if i as u32 == pos {
break;
}
if c == '\n' {
line += 1;
col = 1;
} else {
col += 1;
}
}
(line, col)
}
}