diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/ide/complete.rs | 34 | ||||
| -rw-r--r-- | src/model/cast.rs | 2 | ||||
| -rw-r--r-- | src/model/eval.rs | 2 | ||||
| -rw-r--r-- | src/model/func.rs | 17 | ||||
| -rw-r--r-- | src/model/library.rs | 4 | ||||
| -rw-r--r-- | src/syntax/ast.rs | 15 |
6 files changed, 50 insertions, 24 deletions
diff --git a/src/ide/complete.rs b/src/ide/complete.rs index d4e72b3d..153a9ccb 100644 --- a/src/ide/complete.rs +++ b/src/ide/complete.rs @@ -1,3 +1,5 @@ +use std::collections::HashSet; + use if_chain::if_chain; use super::summarize_font_family; @@ -141,7 +143,7 @@ fn complete_params(ctx: &mut CompletionContext) -> bool { SyntaxKind::Colon | SyntaxKind::Space { .. } => ctx.cursor, _ => ctx.leaf.offset(), }; - ctx.param_value_completions(&callee, ¶m); + ctx.named_param_value_completions(&callee, ¶m); return true; } } @@ -360,6 +362,7 @@ struct CompletionContext<'a> { explicit: bool, from: usize, completions: Vec<Completion>, + seen_casts: HashSet<u128>, } impl<'a> CompletionContext<'a> { @@ -382,6 +385,7 @@ impl<'a> CompletionContext<'a> { explicit, from: cursor, completions: vec![], + seen_casts: HashSet::new(), }) } @@ -440,14 +444,16 @@ impl<'a> CompletionContext<'a> { continue; } - self.completions.push(Completion { - kind: CompletionKind::Param, - label: param.name.into(), - apply: Some(format_eco!("{}: ${{}}", param.name)), - detail: Some(param.docs.into()), - }); + if param.named { + self.completions.push(Completion { + kind: CompletionKind::Param, + label: param.name.into(), + apply: Some(format_eco!("{}: ${{}}", param.name)), + detail: Some(param.docs.into()), + }); + } - if param.shorthand { + if param.positional { self.cast_completions(¶m.cast); } } @@ -458,11 +464,12 @@ impl<'a> CompletionContext<'a> { } /// Add completions for the values of a function parameter. - fn param_value_completions(&mut self, callee: &ast::Ident, name: &str) { + fn named_param_value_completions(&mut self, callee: &ast::Ident, name: &str) { let param = if_chain! { if let Some(Value::Func(func)) = self.scope.get(callee); if let Some(info) = func.info(); if let Some(param) = info.param(name); + if param.named; then { param } else { return; } }; @@ -475,7 +482,12 @@ impl<'a> CompletionContext<'a> { } /// Add completions for a castable. - fn cast_completions(&mut self, cast: &CastInfo) { + fn cast_completions(&mut self, cast: &'a CastInfo) { + // Prevent duplicate completions from appearing. + if !self.seen_casts.insert(crate::util::hash128(cast)) { + return; + } + match cast { CastInfo::Any => {} CastInfo::Value(value, docs) => { @@ -485,7 +497,7 @@ impl<'a> CompletionContext<'a> { self.snippet_completion("none", "none", "Nonexistent.") } CastInfo::Type("auto") => { - self.snippet_completion("auto", "auto", "A smart default"); + self.snippet_completion("auto", "auto", "A smart default."); } CastInfo::Type("boolean") => { self.snippet_completion("false", "false", "Yes / Enabled."); diff --git a/src/model/cast.rs b/src/model/cast.rs index 833b9e9e..5c95fe4b 100644 --- a/src/model/cast.rs +++ b/src/model/cast.rs @@ -33,7 +33,7 @@ pub trait Cast<V = Value>: Sized { } /// Describes a possible value for a cast. -#[derive(Debug, Clone)] +#[derive(Debug, Clone, Hash)] pub enum CastInfo { /// Any value is okay. Any, diff --git a/src/model/eval.rs b/src/model/eval.rs index d54acf0a..a9fa2e14 100644 --- a/src/model/eval.rs +++ b/src/model/eval.rs @@ -411,7 +411,7 @@ impl Eval for ast::Math { self.children() .map(|node| node.eval(vm)) .collect::<SourceResult<_>>()?, - self.display(), + self.block(), )) } } diff --git a/src/model/func.rs b/src/model/func.rs index 5b38b700..46befd77 100644 --- a/src/model/func.rs +++ b/src/model/func.rs @@ -232,12 +232,21 @@ pub struct ParamInfo { pub name: &'static str, /// Documentation for the parameter. pub docs: &'static str, - /// Is the parameter settable with a set rule? - pub settable: bool, - /// Can the name be omitted? - pub shorthand: bool, /// Valid values for the parameter. pub cast: CastInfo, + /// Is the parameter positional? + pub positional: bool, + /// Is the parameter named? + /// + /// Can be true even if `positional` is true if the parameter can be given + /// in both variants. + pub named: bool, + /// Is the parameter required? + pub required: bool, + /// Can the parameter be given any number of times? + pub variadic: bool, + /// Is the parameter settable with a set rule? + pub settable: bool, } /// A user-defined closure. diff --git a/src/model/library.rs b/src/model/library.rs index 02eb9179..83310610 100644 --- a/src/model/library.rs +++ b/src/model/library.rs @@ -66,7 +66,7 @@ pub struct LangItems { /// An item in a description list: `/ Term: Details`. pub desc_item: fn(term: Content, body: Content) -> Content, /// A mathematical formula: `$x$`, `$ x^2 $`. - pub math: fn(children: Vec<Content>, display: bool) -> Content, + pub math: fn(children: Vec<Content>, block: bool) -> Content, /// An atom in a formula: `x`, `+`, `12`. pub math_atom: fn(atom: EcoString) -> Content, /// A base with optional sub- and superscripts in a formula: `a_1^2`. @@ -75,7 +75,7 @@ pub struct LangItems { /// A fraction in a formula: `x/2`. pub math_frac: fn(num: Content, denom: Content) -> Content, /// An alignment point in a formula: `&`, `&&`. - pub math_align_point: fn(count: usize) -> Content, + pub math_align_point: fn(count: NonZeroUsize) -> Content, } impl Debug for LangItems { diff --git a/src/syntax/ast.rs b/src/syntax/ast.rs index 56d4415e..abbca5ec 100644 --- a/src/syntax/ast.rs +++ b/src/syntax/ast.rs @@ -295,7 +295,7 @@ impl Raw { self.get().lang.as_ref() } - /// Whether the raw block is block-level. + /// Whether the raw text should be displayed in a separate block. pub fn block(&self) -> bool { self.get().block } @@ -425,8 +425,8 @@ impl Math { self.0.children().filter_map(SyntaxNode::cast) } - /// Whether this is a display-level math formula. - pub fn display(&self) -> bool { + /// Whether the formula should be displayed as a separate block. + pub fn block(&self) -> bool { matches!(self.children().next(), Some(MathNode::Space(_))) && matches!(self.children().last(), Some(MathNode::Space(_))) } @@ -564,8 +564,13 @@ node! { impl AlignPoint { /// The number of ampersands. - pub fn count(&self) -> usize { - self.0.children().filter(|n| n.kind() == &SyntaxKind::Amp).count() + pub fn count(&self) -> NonZeroUsize { + self.0 + .children() + .filter(|n| n.kind() == &SyntaxKind::Amp) + .count() + .try_into() + .expect("alignment point is missing ampersand sign") } } |
