-
Notifications
You must be signed in to change notification settings - Fork 3
Editor refactoring mode #11
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
base: master
Are you sure you want to change the base?
Changes from all commits
ebb1779
75ac660
0534da2
11ff361
a8ff17c
b723321
7ac8ec7
11a93a0
c37dc6f
c94a7fb
f37482b
68b1ca5
efb9201
177e172
d692242
dcacf71
bf9fda4
331026d
f3421b0
0d131f0
afd80fc
75f9103
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -341,6 +341,7 @@ function EditorController:_handle_submit(go) | |
| local ok, res = inter:evaluate() | ||
| local _, chunks = buf.chunker(pretty, true) | ||
| if ok then | ||
| local newlines_injection_needed = (#chunks > 1) | ||
| if #chunks < #raw_chunks then | ||
| local rc = raw_chunks | ||
| if rc[1].tag == 'empty' then | ||
|
|
@@ -351,6 +352,17 @@ function EditorController:_handle_submit(go) | |
| table.insert(chunks, Empty(li + 1)) | ||
| end | ||
| end | ||
| if newlines_injection_needed then | ||
| for i = #chunks, 2, -1 do | ||
| local ch=chunks | ||
| local this_nonempty = ch[i].tag ~= 'empty' | ||
| local prev_nonempty = ch[i-1].tag ~= 'empty' | ||
| if this_nonempty and prev_nonempty then | ||
| local prev_pos = ch[i-1].pos.fin | ||
| table.insert(ch, i, Empty(prev_pos+1)) | ||
| end | ||
| end | ||
| end | ||
| go(chunks) | ||
| else | ||
| local eval_err = res | ||
|
|
@@ -589,42 +601,95 @@ function EditorController:_normal_mode_keys(k) | |
| --- handlers | ||
| local function submit() | ||
| local bufv = self.view:get_current_buffer() | ||
| local is_lua = bufv.content_type == 'lua' | ||
| local size_limit = bufv:get_size() | ||
| local is_oversized_chunk = function(v) | ||
| return (v and v.pos and v.pos:len() > size_limit) | ||
| end | ||
| local first_oversized_chunk = function(chunks) | ||
| if is_lua then | ||
| return table.find_by(chunks, is_oversized_chunk) | ||
|
hleb-rubanau marked this conversation as resolved.
|
||
| end | ||
| end | ||
| local to_lines = function(x) return x.lines end | ||
|
Owner
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We could also add this as a helper in |
||
| local analyze_input = function(newtext) | ||
| local oversized = first_oversized_chunk(newtext) | ||
| if not oversized then | ||
| return newtext, false | ||
| end | ||
| if oversized == 1 then | ||
| return false | ||
| end | ||
| local approved = table.slice(newtext, 1, oversized-1) | ||
| local rejected = table.slice(newtext, oversized) | ||
| local rejected_lines = table.map(rejected, to_lines) | ||
| local rejected_raw = table.flatten(rejected_lines) | ||
| return approved, rejected_raw | ||
| end | ||
|
|
||
| local function replace(newtext) | ||
| if bufv:is_selection_visible() then | ||
| if buf:loaded_is_sel(true) then | ||
| local _, n = buf:replace_content(newtext) | ||
| buf:clear_loaded() | ||
| self:save(buf) | ||
| input:clear() | ||
| self.view:refresh() | ||
| self:_move_sel('down', n) | ||
| load_selection() | ||
| self:update_status() | ||
| else | ||
| buf:select_loaded() | ||
| bufv:follow_selection() | ||
| end | ||
| else | ||
| if not bufv:is_selection_visible(true) then | ||
| return bufv:follow_selection() | ||
| end | ||
|
|
||
| if not buf:loaded_is_sel(true) then | ||
| buf:select_loaded() | ||
| bufv:follow_selection() | ||
| return | ||
| end | ||
|
|
||
| local approved, rejected = analyze_input(newtext) | ||
| if not approved then return end | ||
| if rejected then | ||
| local _, n = buf:insert_content(approved) | ||
| self:save(buf) | ||
| self.view:refresh() | ||
| self:_move_sel('down', n) | ||
| buf:set_loaded() -- still editing that piece | ||
| input:set_text(rejected) | ||
| input:jump_home() | ||
| else | ||
| local _, n = buf:replace_content(approved) | ||
| self:save(buf) | ||
| self.view:refresh() | ||
| self:_move_sel('down', n) | ||
| buf:clear_loaded() | ||
| input:clear() | ||
| load_selection() | ||
| end | ||
|
|
||
| self:update_status() | ||
| end | ||
|
|
||
| if Key.ctrl() | ||
| and not Key.shift() | ||
| and not Key.alt() | ||
| and Key.is_enter(k) then | ||
| local function add(newtext) | ||
| if bufv:is_selection_visible() then | ||
| local sel = buf:get_selection() | ||
| local _, n = buf:insert_content(newtext, sel) | ||
| self:save(buf) | ||
| self.view:refresh() | ||
| self:_move_sel('down', n) | ||
| buf:clear_loaded() | ||
| self:update_status() | ||
| if not bufv:is_selection_visible() then | ||
| return bufv:follow_selection() | ||
| end | ||
|
|
||
| local approved, rejected = newtext, false | ||
| if is_lua then | ||
| approved, rejected = analyze_input(newtext) | ||
| end | ||
| if not approved then return end | ||
|
|
||
| local sel = buf:get_selection() | ||
| local _, n = buf:insert_content(approved, sel) | ||
| self:save(buf) | ||
| self.view:refresh() | ||
| self:_move_sel('down', n) | ||
| if rejected then | ||
| buf:set_loaded() -- still editing that piece | ||
| input:set_text(rejected) | ||
| input:jump_home() | ||
| else | ||
| bufv:follow_selection() | ||
| buf:clear_loaded() | ||
| -- input not cleared/reset, is it ok? | ||
| end | ||
| self:update_status() | ||
| end | ||
|
|
||
| self:_handle_submit(add) | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -120,6 +120,11 @@ function BufferView:get_state() | |
| } | ||
| end | ||
|
|
||
| --- @return integer | ||
| function BufferView:get_size() | ||
|
Owner
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is not quite correct conceptually, I probably should have named the field better. |
||
| return self.LINES | ||
| end | ||
|
|
||
| --- @param moved integer? | ||
| function BufferView:refresh(moved) | ||
| if not self.content then | ||
|
|
@@ -211,7 +216,7 @@ end | |
| --- @return boolean | ||
| --- @return VerticalDir? | ||
| --- @return number? diff | ||
| function BufferView:is_selection_visible() | ||
| function BufferView:is_selection_visible(tolerate_oversize) | ||
| local sel = self.buffer:get_selection() | ||
|
|
||
| local s_w | ||
|
|
@@ -227,6 +232,13 @@ function BufferView:is_selection_visible() | |
| local r = self.content:get_range() | ||
| if r:inc(sel_s) and r:inc(sel_e) then return true end | ||
|
|
||
| -- handle monster blocks | ||
| if tolerate_oversize then | ||
| if (sel_s == r.start) and (sel_e > r.fin) then | ||
| return true | ||
| end | ||
| end | ||
|
|
||
| local dir = (function() | ||
| if r.start > sel_s then return 'up' end | ||
| if r.fin < sel_e then return 'down' end | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.