@@ -412,23 +412,22 @@ function edit_move_down(s)
412
412
changed
413
413
end
414
414
415
- function memmove (dst:: IOBuffer , idst:: Int , src:: IOBuffer , isrc:: Int , num:: Int )
416
- num == 0 && return
417
- @assert 0 < num
418
- @assert 0 < idst <= length (dst. data) - num + 1
419
- @assert 0 < isrc <= length (src. data) - num + 1
420
- pdst = pointer (dst. data, idst)
421
- psrc = pointer (src. data, isrc)
422
- ccall (:memmove , Void, (Ptr{Void},Ptr{Void},Csize_t), pdst, psrc, num)
415
+ # splice! for IOBuffer: convert from 0-indexed positions, update the size,
416
+ # and keep the cursor position stable with the text
417
+ function splice_buffer! {T<:Integer} (buf:: IOBuffer , r:: UnitRange{T} , ins:: String = " " )
418
+ pos = position (buf)
419
+ if ! isempty (r) && pos in r
420
+ seek (buf, first (r))
421
+ elseif pos > last (r)
422
+ seek (buf, pos - length (r))
423
+ end
424
+ splice! (buf. data, r .+ 1 , ins. data) # position(), etc, are 0-indexed
425
+ buf. size = buf. size + sizeof (ins) - length (r)
426
+ seek (buf, position (buf) + sizeof (ins))
423
427
end
424
428
425
429
function edit_replace (s, from, to, str)
426
- room = length (str. data) - (to - from)
427
- ensureroom (s. input_buffer, s. input_buffer. size + room)
428
- memmove (s. input_buffer, to+ room+ 1 , s. input_buffer, to+ 1 , s. input_buffer. size- to)
429
- s. input_buffer. size += room
430
- seek (s. input_buffer, from)
431
- write (s. input_buffer, str)
430
+ splice_buffer! (buffer (s), from: to- 1 , str)
432
431
end
433
432
434
433
function edit_insert (s:: PromptState , c)
@@ -443,17 +442,11 @@ function edit_insert(s::PromptState, c)
443
442
end
444
443
end
445
444
446
- # TODO : Don't use memmove
447
445
function edit_insert (buf:: IOBuffer , c)
448
446
if eof (buf)
449
447
write (buf, c)
450
448
else
451
- s = string (c)
452
- ensureroom (buf, buf. size- position (buf)+ sizeof (s))
453
- oldpos = position (buf)
454
- memmove (buf, position (buf)+ 1 + sizeof (s), buf, position (buf)+ 1 , buf. size- position (buf))
455
- buf. size += sizeof (s)
456
- write (buf, c)
449
+ splice_buffer! (buf, position (buf): position (buf)- 1 , string (c))
457
450
end
458
451
end
459
452
@@ -468,8 +461,7 @@ function edit_backspace(buf::IOBuffer)
468
461
if position (buf) > 0 && buf. size > 0
469
462
oldpos = position (buf)
470
463
char_move_left (buf)
471
- memmove (buf, position (buf)+ 1 , buf, oldpos+ 1 , buf. size- oldpos)
472
- buf. size -= oldpos- position (buf)
464
+ splice_buffer! (buf, position (buf): oldpos- 1 )
473
465
return true
474
466
else
475
467
return false
@@ -478,26 +470,19 @@ end
478
470
479
471
edit_delete (s) = edit_delete (buffer (s)) ? refresh_line (s) : beep (LineEdit. terminal (s))
480
472
function edit_delete (buf:: IOBuffer )
481
- # (buf.size == 0 || eof(buf)) && return false
482
- if buf. size > 0 && position (buf) < buf. size
483
- oldpos = position (buf)
484
- char_move_right (buf)
485
- memmove (buf, oldpos+ 1 , buf, position (buf)+ 1 , buf. size- position (buf))
486
- buf. size -= position (buf) - oldpos
487
- seek (buf, oldpos)
488
- return true
489
- else
490
- return false
491
- end
473
+ eof (buf) && return false
474
+ oldpos = position (buf)
475
+ char_move_right (buf)
476
+ splice_buffer! (buf, oldpos: position (buf)- 1 )
477
+ true
492
478
end
493
479
494
480
function edit_werase (buf:: IOBuffer )
495
481
pos1 = position (buf)
496
482
char_move_word_left (buf,isspace)
497
483
pos0 = position (buf)
498
484
pos0 < pos1 || return false
499
- memmove (buf, pos0+ 1 , buf, pos1+ 1 , buf. size- pos1)
500
- buf. size -= pos1 - pos0
485
+ splice_buffer! (buf, pos0: pos1- 1 )
501
486
true
502
487
end
503
488
function edit_werase (s)
@@ -509,8 +494,7 @@ function edit_delete_prev_word(buf::IOBuffer)
509
494
char_move_word_left (buf)
510
495
pos0 = position (buf)
511
496
pos0 < pos1 || return false
512
- memmove (buf, pos0+ 1 , buf, pos1+ 1 , buf. size- pos1)
513
- buf. size -= pos1 - pos0
497
+ splice_buffer! (buf, pos0: pos1- 1 )
514
498
true
515
499
end
516
500
function edit_delete_prev_word (s)
@@ -522,9 +506,7 @@ function edit_delete_next_word(buf::IOBuffer)
522
506
char_move_word_right (buf)
523
507
pos1 = position (buf)
524
508
pos0 < pos1 || return false
525
- seek (buf,pos0)
526
- memmove (buf, pos0+ 1 , buf, pos1+ 1 , buf. size- pos1)
527
- buf. size -= pos1 - pos0
509
+ splice_buffer! (buf, pos0: pos1- 1 )
528
510
true
529
511
end
530
512
function edit_delete_next_word (s)
@@ -537,16 +519,14 @@ function edit_yank(s::MIState)
537
519
end
538
520
539
521
function edit_kill_line (s:: MIState )
540
- pos = position (buffer (s))
541
- s. kill_buffer = readline (buffer (s))
542
- rest = readall (buffer (s))
543
- truncate (buffer (s), pos)
544
- if ! isempty (s. kill_buffer) && s. kill_buffer[end ] == ' \n '
522
+ buf = buffer (s)
523
+ pos = position (buf)
524
+ s. kill_buffer = readline (buf)
525
+ if length (s. kill_buffer) > 1 && s. kill_buffer[end ] == ' \n '
545
526
s. kill_buffer = s. kill_buffer[1 : end - 1 ]
546
- isempty (s . kill_buffer) || print ( buffer (s), ' \n ' )
527
+ char_move_left (buf )
547
528
end
548
- print (buffer (s), rest)
549
- seek (buffer (s), pos)
529
+ splice_buffer! (buf, pos: position (buf)- 1 )
550
530
refresh_line (s)
551
531
end
552
532
0 commit comments