metaborg / nabl

Spoofax' Name Binding Language
Apache License 2.0
7 stars 12 forks source link

Outline for Statix spec #69

Open MeAmAnUsername opened 3 years ago

MeAmAnUsername commented 3 years ago

Short description Show strategies in the outline.

Problem description. I want to go to a function in a file somewhere. Pretty much all my files are hundreds of lines long, so scrolling takes a while and requires looking where I am approximately.

Describe the solution you'd like Show an outline of the Statix file in the outline view. Ideally it has nodes for every section, with only the rules section expanded. The rules section shows predicates / functions, and merges consecutive rules of the same function/predicate, for example:

imports
  signatures/Common
  statics/whatever

signature
  sorts Foo constructors
    Foo1 : Foo
    Foo2 : Foo

  sorts BOOLEAN FuncKind
  constructors
    FALSE : BOOLEAN
    ForeignJavaKind : FuncKind
    TRUE : BOOLEAN
    PieFuncKind : FuncKind

rules
  someFunc : Foo -> string
  someFunc(..) = .. :- ..
  someFunc(..) = .. :- ..

  anotherFunc : int
  anotherFunc(0).
  anotherFunc(1) :- ...

  someFunc(..) = .. :- ..

Would produce the outline

|- imports // no subnodes, I see no reason why you want to see them 
|             in the outline, just click on the imports section.
|             Maybe add subnodes if there are multiple imports sections in the file?
|- signature // this section is collapsed by default
|  |- sort Foo with constructors // use text like this if only one sort declared and following
|  |  |                             constructor section declares only constructors of this sort
|  |  |- Foo1
|  |  \- Foo2
|  |- sorts
|  |  |- BOOLEAN
|  |  \- FuncKind
|  \- constructors
|     |- FALSE
|     |- ForeignJavaKind
|     |- TRUE
|     \- PieFuncKind
\- rules
   |- someFunc // merges definition and the rules. Refers to the first node, i.e. the definition
   |- anotherFunc
   \- someFunc // last rule was not grouped with other `someFunc` rules, gets its own node.

Describe alternatives you've considered I could use CTRL-F, use global search, or keep scrolling. Searching gets false positives in the form of references to that function, and scrolling costs time and requires checking where in the file you are.

Additional context Explanation of how to create an outline: https://www.spoofax.dev/references/editor-services/outline/ The PIE DSL source has the following definition, which seems like it would work decently:

  editor-outline:
    (_, _, ast, path, project-path) -> outline
    where
      outline := <simple-label-outline(to-outline-label)> ast

  to-outline-label = fail

Which has the following documentation:

  /**
   * Creates an outline given a strategy s1 that rewrites AST nodes to outline labels.
   * Only AST nodes for which s1 succeed end up in the outline.
   *
   * Example:
   *   outline = simple-label-outline(to-outline-label)
   *   to-outline-label: Entity(name, _) -> name
   *   to-outline-label: Property(name, _) -> name
   */

This is not a massive improvement, but it is a nice QOL improvement and probably not much work.

AZWN commented 3 years ago

Thanks for submitting this detailed/well-worked out issue. I agree with your final assessment, so put it on the backlog. Most challenging part will perhaps be finding proper icons.

AZWN commented 3 years ago

It turns out that Statix had an outline, but apparently it made the editor very slow: https://github.com/metaborg/nabl/commit/fcd1b64deacbd9d236c21ad96ef9e59d2822a018

MeAmAnUsername commented 3 years ago

Hmm. If it slows down the editor a lot then it's probably best to leave it disabled. Best case scenario it would update the outline after updating the editor instead of as part of updating the editor, but that likely requires redoing some of the Spoofax/Eclipse internals.