tidalcycles / vscode-tidalcycles

Support for TidalCycles in VSCode
GNU General Public License v3.0
35 stars 11 forks source link

[WIP] evaluate selected range using shift-enter and ctrl-enter #8

Open lopho opened 5 years ago

lopho commented 5 years ago
lopho commented 5 years ago

fixes #7

lopho commented 5 years ago

If I find the time in the next few days, I would also take a look at ctrl+enter selection evaluation for multiple single line statements. As shift+enter evaluation only works with "single" line statements broken in multiple lines.

Works using selection shift-enter (single statement multiple lines):

d1 $ s "hh*8"    -- selected
  # up "1 2 3 4" -- selected

Does not (multiple statements multiple lines), but hopefully with a selection-type ctrl-enter:

d1 $ s "hh*8" -- selected
d2 $ s "bd*4" -- selected

This would really improve usability, at least for me. Selecting entire sections to execute, maybe even giving the do block idiom for sync a run for it's money.

lopho commented 5 years ago

Functionality is implemented.

The mocking system of the unit tests irritate me a bit. I don't have the time to dive into those right now. Using manual testing everything seems to work as intended.

My problems with the mocks:

I'm not sure if I can take this on right now. Aside from that, everythings seems to work.

shift+enter evaluates single line statements: the line with the caret if nothing is selected, or all lines being at least partially selected. ctrl+enter evaluates multi-line statements: the statement with the caret if nothing is selected, or all lines being at least partially selected. This keeps the old behavior of evaluating entire do blocks as long as nothing is selected (well, it evaluates everything until it encounters an empty line on the way up the document).

For multiple single line statements, I prefix the statements with a do. This way single line and multi line statements can be evaluated together, as the :{ operator expects multi line statements (like do).

lopho commented 5 years ago

Welp. I done goof'd. The do block wrapping was a stupid idea, as it made evaluating single line non-expressions, like let a = 0 impossible and it messed up scoping. Now I've implemented a more involved method, keeping track of the current and next indentation level.

Using this method everything is evaluatable. Function definitions like:

f :: a -> a
f a
    | a < 0 = 0
    | otherwise = a

with ctrl+enter (because of the missing indentation on the second line)

Single statements over multiple lines:

d1 $ s "hh*8"
    # up "1 2 3 4"

with shift+enter

let do where case blocks with indentation with shift+enter, otherwise with ctrl+enter. Anything mixed like statements, blocks, etc. with shift+enter, again, as long as indentation makes sense.

I really hope I got everything right this time. But I've got a good feeling about it.

kindohm commented 5 years ago

@lopho are the tests broken in this PR or should they run successfully?

lopho commented 5 years ago

Yes, they are broken. But I'm fairly certain that the mocking system is at fault here.

I tried to fix it, but the values returned by the editor mock objects are absurd when selecting.

https://github.com/tidalcycles/vscode-tidalcycles/pull/8#issuecomment-462853626

The mocking system of the unit tests irritate me a bit. I don't have the time to dive into those right now. Using manual testing everything seems to work as intended.

My problems with the mocks:

  • selection in mock editor is unreliable

    • returns loads of [object Objects] in empty and non empty lines

    • skips lines altogether

    • see Multi-line expression from split selection and Multi-line expression retrieved before selection (those two test still expect the old behaviour, but still, selection is weird)

    • the mock repl in Single-line expression evaluated in .tidal file does not seem to correctly count invocations on single line statements, always counting 0

If you have the time, could you please take a look at those tests, especially the behavior of tests when checking the content of expressions. There seems to be some concurrency issues as well, as lines get returned in mixed order and such (in the tests/mocking objects, not the real thing).

yaxu commented 5 years ago

Did you get evaluating multiple statements in one go working in the end? e.g.

d1 $ s "hh*8"
d2 $ s "bd*4"
  # vowel "a e"

I'm not a vscode user but am interested because we tried (and failed) to get this working in emacs

lopho commented 5 years ago

@yaxu Yes, your example works (using shift+enter). As long as your code follows some (hierarchical) indentation, it should evaluate correctly.