mirror of
https://github.com/paradoxxxzero/butterfly.git
synced 2026-05-26 07:08:08 +00:00
Add horizontal wrap (expandable no wrapping lines) on decset 77
This commit is contained in:
@@ -29,6 +29,34 @@ body
|
||||
.line.active
|
||||
background-color: $active-bg
|
||||
|
||||
.line.extended
|
||||
overflow-x: auto
|
||||
overflow-x: overlay
|
||||
cursor: zoom-in
|
||||
background-image: linear-gradient(90deg, rgba(darken($bg, 3%), 0), 95%, darken($bg, 3%))
|
||||
|
||||
&:not(.expanded):hover
|
||||
background-color: lighten($bg, 2%)
|
||||
|
||||
&.expanded
|
||||
cursor: zoom-out
|
||||
background-color: darken($bg, 3%)
|
||||
|
||||
.extra
|
||||
display: block
|
||||
white-space: pre-line
|
||||
word-break: break-all
|
||||
|
||||
&::-webkit-scrollbar
|
||||
background: rgba($scroll-bg, .1)
|
||||
height: 0
|
||||
|
||||
&::-webkit-scrollbar-thumb
|
||||
background: rgba($scroll-fg, .1)
|
||||
|
||||
&::-webkit-scrollbar-thumb:hover
|
||||
background: rgba($scroll-fg-hover, .1)
|
||||
|
||||
&::-webkit-scrollbar
|
||||
background: $scroll-bg
|
||||
width: $scroll-width
|
||||
|
||||
@@ -156,6 +156,29 @@
|
||||
}
|
||||
});
|
||||
|
||||
Terminal.on('change', function(lines) {
|
||||
var j, len1, line, results;
|
||||
results = [];
|
||||
for (j = 0, len1 = lines.length; j < len1; j++) {
|
||||
line = lines[j];
|
||||
if (indexOf.call(line.classList, 'extended') >= 0) {
|
||||
results.push(line.addEventListener('click', (function(line) {
|
||||
return function() {
|
||||
if (indexOf.call(line.classList, 'expanded') >= 0) {
|
||||
return line.classList.remove('expanded');
|
||||
} else {
|
||||
line.classList.add('expanded');
|
||||
return butterfly.nativeScrollTo();
|
||||
}
|
||||
};
|
||||
})(line)));
|
||||
} else {
|
||||
results.push(void 0);
|
||||
}
|
||||
}
|
||||
return results;
|
||||
});
|
||||
|
||||
walk = function(node, callback) {
|
||||
var child, j, len1, ref, results;
|
||||
ref = node.childNodes;
|
||||
|
||||
@@ -2816,6 +2816,27 @@ body {
|
||||
/* Pop ups */ }
|
||||
body .line.active {
|
||||
background-color: transparent; }
|
||||
body .line.extended {
|
||||
overflow-x: auto;
|
||||
overflow-x: overlay;
|
||||
cursor: zoom-in;
|
||||
background-image: linear-gradient(90deg, rgba(9, 8, 10, 0), 95%, #09080a); }
|
||||
body .line.extended:not(.expanded):hover {
|
||||
background-color: #161419; }
|
||||
body .line.extended.expanded {
|
||||
cursor: zoom-out;
|
||||
background-color: #09080a; }
|
||||
body .line.extended.expanded .extra {
|
||||
display: block;
|
||||
white-space: pre-line;
|
||||
word-break: break-all; }
|
||||
body .line.extended::-webkit-scrollbar {
|
||||
background: rgba(17, 15, 19, 0.1);
|
||||
height: 0; }
|
||||
body .line.extended::-webkit-scrollbar-thumb {
|
||||
background: rgba(244, 234, 213, 0.1); }
|
||||
body .line.extended::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(244, 234, 213, 0.1); }
|
||||
body::-webkit-scrollbar {
|
||||
background: #110f13;
|
||||
width: 0.75em; }
|
||||
|
||||
@@ -282,6 +282,7 @@
|
||||
this.applicationCursor = false;
|
||||
this.originMode = false;
|
||||
this.autowrap = true;
|
||||
this.horizontalWrap = false;
|
||||
this.normal = null;
|
||||
this.charset = null;
|
||||
this.gcharset = null;
|
||||
@@ -535,7 +536,7 @@
|
||||
};
|
||||
|
||||
Terminal.prototype.refresh = function(force) {
|
||||
var active, attr, ch, classes, cursor, data, fg, group, i, j, k, len, len1, len2, len3, len4, line, lines, m, modified, newOut, o, out, q, ref, ref1, ref2, ref3, ref4, ref5, skipnext, styles, u, v, x;
|
||||
var active, attr, ch, classes, cls, cursor, data, fg, group, i, j, k, len, len1, len2, len3, len4, line, lines, m, modified, newOut, o, out, q, ref, ref1, ref2, ref3, ref4, ref5, skipnext, styles, u, v, x;
|
||||
if (force == null) {
|
||||
force = false;
|
||||
}
|
||||
@@ -678,14 +679,27 @@
|
||||
if (line.wrap) {
|
||||
out += '\u23CE';
|
||||
}
|
||||
if (line.extra) {
|
||||
out += '<span class="extra">' + line.extra + '</span>';
|
||||
}
|
||||
if (this.children[j]) {
|
||||
this.children[j].innerHTML = out;
|
||||
modified.push(this.children[j]);
|
||||
if (x !== -Infinity) {
|
||||
this.children[j].classList.add('active');
|
||||
}
|
||||
if (line.extra) {
|
||||
this.children[j].classList.add('extended');
|
||||
}
|
||||
} else {
|
||||
newOut += "<div class=\"line" + (x !== -Infinity && ' active' || '') + "\">" + out + "</div>";
|
||||
cls = ['line'];
|
||||
if (x !== -Infinity) {
|
||||
cls.push('active');
|
||||
}
|
||||
if (line.extra) {
|
||||
cls.push('extended');
|
||||
}
|
||||
newOut += "<div class=\"" + (cls.join(' ')) + "\">" + out + "</div>";
|
||||
}
|
||||
this.screen[j].dirty = false;
|
||||
}
|
||||
@@ -831,11 +845,17 @@
|
||||
case "\n":
|
||||
case "\x0b":
|
||||
case "\x0c":
|
||||
this.screen[this.y + this.shift].dirty = true;
|
||||
this.nextLine();
|
||||
if (this.horizontalWrap) {
|
||||
this.screen[this.y + this.shift].extra += ch;
|
||||
} else {
|
||||
this.screen[this.y + this.shift].dirty = true;
|
||||
this.nextLine();
|
||||
}
|
||||
break;
|
||||
case "\r":
|
||||
this.x = 0;
|
||||
if (!this.horizontalWrap) {
|
||||
this.x = 0;
|
||||
}
|
||||
break;
|
||||
case "\b":
|
||||
if (this.x >= this.cols) {
|
||||
@@ -877,11 +897,15 @@
|
||||
ch = this.charset[ch];
|
||||
}
|
||||
if (this.x >= this.cols) {
|
||||
if (this.autowrap) {
|
||||
this.screen[this.y + this.shift].wrap = true;
|
||||
this.nextLine();
|
||||
if (this.horizontalWrap) {
|
||||
this.screen[this.y + this.shift].extra += ch;
|
||||
} else {
|
||||
if (this.autowrap) {
|
||||
this.screen[this.y + this.shift].wrap = true;
|
||||
this.nextLine();
|
||||
}
|
||||
this.x = 0;
|
||||
}
|
||||
this.x = 0;
|
||||
}
|
||||
this.putChar(ch);
|
||||
this.x++;
|
||||
@@ -1291,8 +1315,7 @@
|
||||
attr = this.cloneAttr(this.curAttr);
|
||||
attr.html = "<div class=\"inline-html\">" + safe + "</div>";
|
||||
this.screen[this.y + this.shift].chars[this.x] = attr;
|
||||
this.screen[this.y + this.shift].dirty = true;
|
||||
this.screen[this.y + this.shift].wrap = false;
|
||||
this.resetLine(this.screen[this.y + this.shift]);
|
||||
this.nextLine();
|
||||
break;
|
||||
case "IMAGE":
|
||||
@@ -1307,8 +1330,7 @@
|
||||
attr = this.cloneAttr(this.curAttr);
|
||||
attr.html = "<img class=\"inline-image\" src=\"data:" + mime + ";base64," + b64 + "\" />";
|
||||
this.screen[this.y + this.shift].chars[this.x] = attr;
|
||||
this.screen[this.y + this.shift].dirty = true;
|
||||
this.screen[this.y + this.shift].wrap = false;
|
||||
this.resetLine(this.screen[this.y + this.shift]);
|
||||
break;
|
||||
case "PROMPT":
|
||||
this.send(content);
|
||||
@@ -1865,8 +1887,7 @@
|
||||
line[x] = this.eraseAttr();
|
||||
x++;
|
||||
}
|
||||
this.screen[y + this.shift].dirty = true;
|
||||
return this.screen[y + this.shift].wrap = false;
|
||||
return this.resetLine(this.screen[y + this.shift]);
|
||||
};
|
||||
|
||||
Terminal.prototype.eraseLeft = function(x, y) {
|
||||
@@ -1874,14 +1895,19 @@
|
||||
while (x--) {
|
||||
this.screen[y + this.shift].chars[x] = this.eraseAttr();
|
||||
}
|
||||
this.screen[y + this.shift].dirty = true;
|
||||
return this.screen[y + this.shift].wrap = false;
|
||||
return this.resetLine(this.screen[y + this.shift]);
|
||||
};
|
||||
|
||||
Terminal.prototype.eraseLine = function(y) {
|
||||
return this.eraseRight(0, y);
|
||||
};
|
||||
|
||||
Terminal.prototype.resetLine = function(l) {
|
||||
l.dirty = true;
|
||||
l.wrap = false;
|
||||
return l.extra = '';
|
||||
};
|
||||
|
||||
Terminal.prototype.blankLine = function(cur, dirty) {
|
||||
var attr, i, line;
|
||||
if (cur == null) {
|
||||
@@ -1900,7 +1926,8 @@
|
||||
return {
|
||||
chars: line,
|
||||
dirty: dirty,
|
||||
wrap: false
|
||||
wrap: false,
|
||||
extra: ''
|
||||
};
|
||||
};
|
||||
|
||||
@@ -2304,8 +2331,7 @@
|
||||
this.screen[this.y + this.shift].chars.splice(this.x, 1);
|
||||
this.screen[this.y + this.shift].chars.push(this.eraseAttr());
|
||||
}
|
||||
this.screen[this.y + this.shift].dirty = true;
|
||||
return this.screen[this.y + this.shift].wrap = false;
|
||||
return this.resetLine(this.screen[this.y + this.shift]);
|
||||
};
|
||||
|
||||
Terminal.prototype.eraseChars = function(params) {
|
||||
@@ -2318,8 +2344,7 @@
|
||||
while (param-- && j < this.cols) {
|
||||
this.screen[this.y + this.shift].chars[j++] = this.eraseAttr();
|
||||
}
|
||||
this.screen[this.y + this.shift].dirty = true;
|
||||
return this.screen[this.y + this.shift].wrap = false;
|
||||
return this.resetLine(this.screen[this.y + this.shift]);
|
||||
};
|
||||
|
||||
Terminal.prototype.charPosAbsolute = function(params) {
|
||||
@@ -2455,6 +2480,8 @@
|
||||
return this.autowrap = true;
|
||||
case 66:
|
||||
return this.applicationKeypad = true;
|
||||
case 77:
|
||||
return this.horizontalWrap = true;
|
||||
case 9:
|
||||
case 1000:
|
||||
case 1002:
|
||||
@@ -2534,6 +2561,8 @@
|
||||
return this.autowrap = false;
|
||||
case 66:
|
||||
return this.applicationKeypad = false;
|
||||
case 77:
|
||||
return this.horizontalWrap = false;
|
||||
case 9:
|
||||
case 1000:
|
||||
case 1002:
|
||||
@@ -2834,8 +2863,7 @@
|
||||
while (i < l) {
|
||||
this.screen[i].chars.splice(this.x, 1);
|
||||
this.screen[i].chars.push(this.eraseAttr());
|
||||
this.screen[i].dirty = true;
|
||||
this.screen[i].wrap = false;
|
||||
this.resetLine(this.screen[i].dirty);
|
||||
results1.push(i++);
|
||||
}
|
||||
return results1;
|
||||
|
||||
9
coffees/ext/expand_extended.coffee
Normal file
9
coffees/ext/expand_extended.coffee
Normal file
@@ -0,0 +1,9 @@
|
||||
Terminal.on 'change', (lines) ->
|
||||
for line in lines
|
||||
if 'extended' in line.classList
|
||||
line.addEventListener 'click', do (line) -> ->
|
||||
if 'expanded' in line.classList
|
||||
line.classList.remove 'expanded'
|
||||
else
|
||||
line.classList.add 'expanded'
|
||||
butterfly.nativeScrollTo()
|
||||
@@ -168,6 +168,7 @@ class Terminal
|
||||
@applicationCursor = false
|
||||
@originMode = false
|
||||
@autowrap = true
|
||||
@horizontalWrap = false
|
||||
@normal = null
|
||||
|
||||
# charset
|
||||
@@ -421,6 +422,8 @@ class Terminal
|
||||
@document.createTextNode(cursor.textContent), cursor)
|
||||
for active in @body.querySelectorAll(".line.active")
|
||||
active.classList.remove('active')
|
||||
# for active in @body.querySelectorAll(".line.extended")
|
||||
# active.classList.remove('extended')
|
||||
|
||||
newOut = ''
|
||||
modified = []
|
||||
@@ -526,14 +529,22 @@ class Terminal
|
||||
attr = data
|
||||
out += "</span>" unless @equalAttr attr, @defAttr
|
||||
out += '\u23CE' if line.wrap
|
||||
if line.extra
|
||||
out += '<span class="extra">' + line.extra + '</span>'
|
||||
if @children[j]
|
||||
@children[j].innerHTML = out
|
||||
modified.push @children[j]
|
||||
if x isnt -Infinity
|
||||
@children[j].classList.add 'active'
|
||||
if line.extra
|
||||
@children[j].classList.add 'extended'
|
||||
else
|
||||
newOut += "<div class=\"line#{
|
||||
x isnt -Infinity and ' active' or ''}\">#{out}</div>"
|
||||
cls = ['line']
|
||||
if x isnt -Infinity
|
||||
cls.push 'active'
|
||||
if line.extra
|
||||
cls.push 'extended'
|
||||
newOut += "<div class=\"#{cls.join(' ')}\">#{out}</div>"
|
||||
@screen[j].dirty = false
|
||||
|
||||
if newOut isnt ''
|
||||
@@ -644,12 +655,16 @@ class Terminal
|
||||
# '\n', '\v', '\f'
|
||||
when "\n", "\x0b", "\x0c"
|
||||
# @x = 0 if @convertEol
|
||||
@screen[@y + @shift].dirty = true
|
||||
@nextLine()
|
||||
if @horizontalWrap
|
||||
@screen[@y + @shift].extra += ch
|
||||
else
|
||||
@screen[@y + @shift].dirty = true
|
||||
@nextLine()
|
||||
|
||||
# '\r'
|
||||
when "\r"
|
||||
@x = 0
|
||||
unless @horizontalWrap
|
||||
@x = 0
|
||||
|
||||
# '\b'
|
||||
when "\b"
|
||||
@@ -697,11 +712,13 @@ class Terminal
|
||||
if ch >= " "
|
||||
ch = @charset[ch] if @charset?[ch]
|
||||
if @x >= @cols
|
||||
if @autowrap
|
||||
@screen[@y + @shift].wrap = true
|
||||
@nextLine()
|
||||
@x = 0
|
||||
|
||||
if @horizontalWrap
|
||||
@screen[@y + @shift].extra += ch
|
||||
else
|
||||
if @autowrap
|
||||
@screen[@y + @shift].wrap = true
|
||||
@nextLine()
|
||||
@x = 0
|
||||
@putChar ch
|
||||
@x++
|
||||
if @forceWidth and "\uff00" < ch < "\uffef"
|
||||
@@ -1150,8 +1167,6 @@ class Terminal
|
||||
switch @prefix
|
||||
# User-Defined Keys (DECUDK).
|
||||
when ""
|
||||
# Disabling this for now as we need a good script
|
||||
# striper to avoid malicious script injection
|
||||
pt = @currentParam
|
||||
unless pt[0] is ';'
|
||||
console.error "Unknown DECUDK: #{pt}"
|
||||
@@ -1171,8 +1186,7 @@ class Terminal
|
||||
attr.html = (
|
||||
"<div class=\"inline-html\">#{safe}</div>")
|
||||
@screen[@y + @shift].chars[@x] = attr
|
||||
@screen[@y + @shift].dirty = true
|
||||
@screen[@y + @shift].wrap = false
|
||||
@resetLine @screen[@y + @shift]
|
||||
@nextLine()
|
||||
|
||||
when "IMAGE"
|
||||
@@ -1190,8 +1204,7 @@ class Terminal
|
||||
"<img class=\"inline-image\" src=\"data:#{mime};base64,#{
|
||||
b64}\" />")
|
||||
@screen[@y + @shift].chars[@x] = attr
|
||||
@screen[@y + @shift].dirty = true
|
||||
@screen[@y + @shift].wrap = false
|
||||
@resetLine @screen[@y + @shift]
|
||||
|
||||
when "PROMPT"
|
||||
@send content
|
||||
@@ -1690,18 +1703,21 @@ class Terminal
|
||||
while x < @cols
|
||||
line[x] = @eraseAttr()
|
||||
x++
|
||||
@screen[y + @shift].dirty = true
|
||||
@screen[y + @shift].wrap = false
|
||||
@resetLine @screen[y + @shift]
|
||||
|
||||
eraseLeft: (x, y) ->
|
||||
x++
|
||||
@screen[y + @shift].chars[x] = @eraseAttr() while x--
|
||||
@screen[y + @shift].dirty = true
|
||||
@screen[y + @shift].wrap = false
|
||||
@resetLine @screen[y + @shift]
|
||||
|
||||
eraseLine: (y) ->
|
||||
@eraseRight 0, y
|
||||
|
||||
resetLine: (l) ->
|
||||
l.dirty = true
|
||||
l.wrap = false
|
||||
l.extra = ''
|
||||
|
||||
blankLine: (cur=false, dirty=true) ->
|
||||
attr = (if cur then @eraseAttr() else @defAttr)
|
||||
line = []
|
||||
@@ -1713,6 +1729,7 @@ class Terminal
|
||||
chars: line
|
||||
dirty: dirty
|
||||
wrap: false
|
||||
extra: ''
|
||||
|
||||
ch: (cur) ->
|
||||
if cur then @eraseAttr() else @defAttr
|
||||
@@ -2193,8 +2210,7 @@ class Terminal
|
||||
while param--
|
||||
@screen[@y + @shift].chars.splice @x, 1
|
||||
@screen[@y + @shift].chars.push @eraseAttr()
|
||||
@screen[@y + @shift].dirty = true
|
||||
@screen[@y + @shift].wrap = false
|
||||
@resetLine @screen[@y + @shift]
|
||||
|
||||
# CSI Ps X
|
||||
# Erase Ps Character(s) (default = 1) (ECH).
|
||||
@@ -2204,8 +2220,7 @@ class Terminal
|
||||
j = @x
|
||||
# xterm
|
||||
@screen[@y + @shift].chars[j++] = @eraseAttr() while param-- and j < @cols
|
||||
@screen[@y + @shift].dirty = true
|
||||
@screen[@y + @shift].wrap = false
|
||||
@resetLine @screen[@y + @shift]
|
||||
|
||||
# CSI Pm ` Character Position Absolute
|
||||
# [column] (default = [row,1]) (HPA).
|
||||
@@ -2434,6 +2449,8 @@ class Terminal
|
||||
@autowrap = true
|
||||
when 66
|
||||
@applicationKeypad = true
|
||||
when 77
|
||||
@horizontalWrap = true
|
||||
# X10 Mouse
|
||||
# no release, no motion, no wheel, no modifiers.
|
||||
when 9, 1000, 1002, 1003 # any event mouse
|
||||
@@ -2595,6 +2612,8 @@ class Terminal
|
||||
@autowrap = false
|
||||
when 66
|
||||
@applicationKeypad = false
|
||||
when 77
|
||||
@horizontalWrap = false
|
||||
when 9, 1000, 1002 , 1003 # any event mouse
|
||||
@x10Mouse = false
|
||||
@vt200Mouse = false
|
||||
@@ -3175,8 +3194,7 @@ class Terminal
|
||||
while i < l
|
||||
@screen[i].chars.splice @x, 1
|
||||
@screen[i].chars.push @eraseAttr()
|
||||
@screen[i].dirty = true
|
||||
@screen[i].wrap = false
|
||||
@resetLine @screen[i].dirty
|
||||
i++
|
||||
|
||||
# DEC Special Character and Line Drawing Set.
|
||||
|
||||
Reference in New Issue
Block a user