From 49ab2791b861884d01488de68f63bdd49d71c1b2 Mon Sep 17 00:00:00 2001 From: Brian Cully Date: Sun, 24 Aug 2025 09:16:11 -0400 Subject: pass annotations to js so we can highlight program text --- src/lib.rs | 60 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 59 insertions(+), 1 deletion(-) (limited to 'src/lib.rs') diff --git a/src/lib.rs b/src/lib.rs index 850070a..71f7b7d 100755 --- a/src/lib.rs +++ b/src/lib.rs @@ -50,15 +50,55 @@ impl ExportedByteCode { } } +// ibid. +#[wasm_bindgen] +#[derive(Clone)] +pub struct ExportedAnnotation { + pub start: usize, + pub end: usize, +} + +impl From<(usize, usize)> for ExportedAnnotation { + fn from(v: (usize, usize)) -> Self { + Self { + start: v.0, + end: v.1, + } + } +} + +// ibid. +#[wasm_bindgen] +#[derive(Clone)] +pub struct ExportedWordAnnotations(Vec); + +impl ExportedWordAnnotations { + pub fn from_word_annotations(annos: &Vec) -> Self { + ExportedWordAnnotations(annos.iter().map(|anno| anno.loc.into()).collect()) + } +} + +#[wasm_bindgen] +impl ExportedWordAnnotations { + pub fn len(&self) -> usize { + self.0.len() + } + + pub fn at(&self, offset: usize) -> ExportedAnnotation { + self.0[offset].clone() + } +} + #[wasm_bindgen] pub struct ExportedInterp { + annos: Vec, i: Option, } #[wasm_bindgen] impl ExportedInterp { fn new() -> Self { - Self { i: None } + Self { annos: vec![], i: None } } pub fn compile(&mut self, text: &str) -> bool { @@ -67,6 +107,16 @@ impl ExportedInterp { error!("couldn't parse program text: {:?}", e); return false } + self.annos = p.annotations.iter() + .map(|word_anno| -> ExportedWordAnnotations { + let v = word_anno.into_iter() + .map(|anno| -> ExportedAnnotation { + anno.loc.into() + }) + .collect(); + ExportedWordAnnotations(v) + }) + .collect(); let interp = forth::interp::Interp::new(p.wordlist); let _ = self.i.insert(interp); true @@ -105,6 +155,14 @@ impl ExportedInterp { interp.wordlist.iter().map(|bc| ExportedByteCode::from_bc(bc)).collect() } + pub fn annotations(&self) -> Vec { + self.annos.clone() + } + + pub fn annotation_at(&self, ip: &ExportedInstructionPointer) -> ExportedAnnotation { + self.annos[ip.word].0[ip.offset].clone() + } + pub fn callstack(&self) -> Vec { let Some(interp) = &self.i else { return vec![] -- cgit v1.3