Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

editor: Improve Evy web editor to use smarter indentation #455

Merged
merged 1 commit into from
Nov 19, 2024
Merged

Conversation

juliaogris
Copy link
Member

@juliaogris juliaogris commented Nov 19, 2024

Use smarter indentation in Evy web editor.

Whenever a new line is inserted, the editor will automatically:

  • preserves indent of current line by default (we already had this).
  • increases the indent after block opening keywords
    func on if else while for (new).
  • updates the current line indent for end and else keywords:
    decreasing the indent if needed (new).

There are many edge cases. This is a best effort improvement. Current
line updating only happens if no selection is active - selection start
and end index are equal.

Fixes: evylang/todo#115


The main challenge of this PR is to a bunch of tedious manual testing of the editor.

I will try and write a longer Evy program in the web editor before merging.

@juliaogris juliaogris added this to the 🚸 Learn v0.2.0 milestone Nov 19, 2024
Copy link
Member

@camh- camh- left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've managed to golf this down a little. I've put else in the second group in the regex (removed it from the end):

const matches = /^(\s+)?((func|on|if|else|while|for)\b)?(end\b)?/.exec(currentLine)

and have this code:

  event.preventDefault()
  let indent = matches[1] || ""
  let before = value.substring(0, selectionStart)
  const after = value.substring(selectionEnd)

  // Matches block-closing keywords, 'end' 'else'
  if (matches[4] !== undefined || matches[2] === "else") {
    // Decrease indent of current line, if indent of current and previous line equal.
    if (shouldDedent(indent, lines, currentLineNumber)) {
      const beforeCurrentLine = before.substring(0, before.length - currentLine.length)
      const dedentedCurrentLine = currentLine.substring(4)
      before = beforeCurrentLine + dedentedCurrentLine
      // Decrease indent
      indent = indent.substring(4)
    }
  }

  // Matches block-opening keywords, 'func' 'on' 'if' 'else' 'while' 'for'.
  if (matches[2] !== undefined) {
    // Increase indent.
    indent += "    "
  }

  const newValue = before + "\n" + indent + after
  const newIdx = newValue.length - after.length

I've test that and it seems to work locally.

frontend/module/editor.js Outdated Show resolved Hide resolved
frontend/module/editor.js Outdated Show resolved Hide resolved
frontend/module/editor.js Outdated Show resolved Hide resolved
frontend/module/editor.js Outdated Show resolved Hide resolved
Use smarter indentation in Evy web editor.

Whenever a new line is inserted, the editor will automatically:

- preserves indent of current line by default (we already had this).
- increases the indent after block opening keywords
  'func' 'on' 'if' 'else' while' 'for' (new).
- updates the current line indent for 'end' and 'else' keywords:
  decreasing the indent if needed (new).

There are many edge cases. This is a best effort improvement. Current
line updating only happens if no selection is active - selection start
and end index are equal.
Copy link
Member

@camh- camh- left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🍏

@juliaogris juliaogris merged commit caeed5c into main Nov 19, 2024
4 checks passed
@juliaogris juliaogris deleted the indents branch November 19, 2024 23:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Smart indent Evy web editor
2 participants