This commit is contained in:
Adam D. Ruppe 2020-04-02 15:03:57 -04:00
parent 1c119753b3
commit 738148b861
2 changed files with 73 additions and 12 deletions

View File

@ -1109,7 +1109,15 @@ struct Terminal {
nw.show();
});
tew = window.tew;
window.loop();
//try
window.loop();
/*
catch(Throwable t) {
import std.stdio;
stdout.writeln(t);
stdout.flush();
}
*/
});
guiThread.start();
guiThread.priority = Thread.PRIORITY_MAX; // gui thread needs responsiveness
@ -1813,10 +1821,13 @@ struct Terminal {
}
+/
void writePrintableString(in char[] s, ForceOption force = ForceOption.automatic) {
void writePrintableString(const(char)[] s, ForceOption force = ForceOption.automatic) {
// an escape character is going to mess things up. Actually any non-printable character could, but meh
// assert(s.indexOf("\033") == -1);
if(s.length == 0)
return;
// tracking cursor position
// FIXME: by grapheme?
foreach(dchar ch; s) {
@ -1852,7 +1863,26 @@ struct Terminal {
+/
}
writeStringRaw(s);
version(TerminalDirectToEmulator) {
// this breaks up extremely long output a little as an aid to the
// gui thread; by breaking it up, it helps to avoid monopolizing the
// event loop. Easier to do here than in the thread itself because
// this one doesn't have escape sequences to break up so it avoids work.
while(s.length) {
auto len = s.length;
if(len > 1024 * 32) {
len = 1024 * 32;
// get to the start of a utf-8 sequence. kidna sorta.
while(len && (s[len] & 0x1000_0000))
len--;
}
auto next = s[0 .. len];
s = s[len .. $];
writeStringRaw(next);
}
} else {
writeStringRaw(s);
}
}
/* private */ bool _wrapAround = true;
@ -1864,6 +1894,8 @@ struct Terminal {
// you really, really shouldn't use this unless you know what you are doing
/*private*/ void writeStringRaw(in char[] s) {
writeBuffer ~= s; // buffer it to do everything at once in flush() calls
if(writeBuffer.length > 1024 * 32)
flush();
}
/// Clears the screen.
@ -6214,13 +6246,18 @@ version(TerminalDirectToEmulator) {
}
protected override void demandAttention() {
//window.requestAttention();
if(widget && widget.parentWindow)
widget.parentWindow.win.requestAttention();
}
protected override void copyToClipboard(string text) {
setClipboardText(widget.parentWindow.win, text);
}
override int maxScrollbackLength() const {
return int.max; // no scrollback limit for custom programs
}
protected override void pasteFromClipboard(void delegate(in char[]) dg) {
static if(UsingSimpledisplayX11)
getPrimarySelection(widget.parentWindow.win, dg);

View File

@ -362,6 +362,9 @@ class TerminalEmulator {
start = idx;
end = selectionEnd;
}
if(start < 0 || end >= ((alternateScreenActive ? alternateScreen.length : normalScreen.length)))
return false;
foreach(ref cell; (alternateScreenActive ? alternateScreen : normalScreen)[start .. end]) {
cell.invalidated = true;
cell.selected = false;
@ -1477,10 +1480,12 @@ class TerminalEmulator {
bool overflowed;
foreach(cell; line) {
cell.invalidated = true;
if(overflowed)
if(overflowed) {
screen[cursorY * screenWidth + cursorX] = overflowCell;
else
break;
} else {
screen[cursorY * screenWidth + cursorX] = cell;
}
if(cursorX == screenWidth-1) {
if(scrollbackReflow) {
@ -1665,8 +1670,12 @@ class TerminalEmulator {
void clear() {
start = 0;
length_ = 0;
backing = null;
}
// FIXME: if scrollback hits limits the scroll bar needs
// to understand the circular buffer
void opOpAssign(string op : "~")(TerminalCell[] line) {
if(length_ < maxScrollback) {
backing.assumeSafeAppend();
@ -1900,26 +1909,41 @@ class TerminalEmulator {
}
}
private int recalculationThreshold = 0;
public void addScrollbackLine(TerminalCell[] line) {
scrollbackBuffer ~= line;
if(!scrollbackReflow && line.length > scrollbackWidth_)
scrollbackWidth_ = cast(int) line.length;
scrollbackLength = cast(int) (scrollbackLength + 1 + (scrollbackBuffer[cast(int) scrollbackBuffer.length - 1].length) / screenWidth);
notifyScrollbackAdded();
if(scrollbackBuffer.length_ == ScrollbackBuffer.maxScrollback) {
recalculationThreshold++;
if(recalculationThreshold > 100) {
recalculateScrollbackLength();
notifyScrollbackAdded();
recalculationThreshold = 0;
}
} else {
if(!scrollbackReflow && line.length > scrollbackWidth_)
scrollbackWidth_ = cast(int) line.length;
scrollbackLength = cast(int) (scrollbackLength + 1 + (scrollbackBuffer[cast(int) scrollbackBuffer.length - 1].length) / screenWidth);
notifyScrollbackAdded();
}
if(!alternateScreenActive)
notifyScrollbarPosition(0, int.max);
}
protected int maxScrollbackLength() pure const @nogc nothrow {
return 1024;
}
bool insertMode = false;
void newLine(bool commitScrollback) {
if(!alternateScreenActive && commitScrollback) {
// I am limiting this because obscenely long lines are kinda useless anyway and
// i don't want it to eat excessive memory when i spam some thing accidentally
if(currentScrollbackLine.length < 1024)
if(currentScrollbackLine.length < maxScrollbackLength())
addScrollbackLine(currentScrollbackLine.sliceTrailingWhitespace);
else
addScrollbackLine(currentScrollbackLine[0 .. 1024].sliceTrailingWhitespace);
addScrollbackLine(currentScrollbackLine[0 .. maxScrollbackLength()].sliceTrailingWhitespace);
currentScrollbackLine = null;
currentScrollbackLine.reserve(64);