-
Notifications
You must be signed in to change notification settings - Fork 14
/
Copy pathterminal.h
239 lines (193 loc) · 7.52 KB
/
terminal.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
/*
Copyright 2011-2012 Heikki Holstila <heikki.holstila@gmail.com>
This work is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.
This work is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this work. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef TERMINAL_H
#define TERMINAL_H
#include <QObject>
#include <QRect>
#include <QRgb>
#include <QVector>
#include "ptyiface.h"
struct TermChar
{
// TODO: Replace with the version in Parser.
enum TextAttributes
{
NoAttributes = 0x00,
BoldAttribute = 0x01,
ItalicAttribute = 0x02,
UnderlineAttribute = 0x04,
NegativeAttribute = 0x08,
BlinkAttribute = 0x10
};
QChar c;
QRgb fgColor;
QRgb bgColor;
TextAttributes attrib;
};
inline TermChar::TextAttributes operator~(TermChar::TextAttributes a) { return (TermChar::TextAttributes) ~(int)a; }
inline TermChar::TextAttributes operator|(TermChar::TextAttributes a, TermChar::TextAttributes b) { return (TermChar::TextAttributes)((int)a | (int)b); }
inline TermChar::TextAttributes operator&(TermChar::TextAttributes a, TermChar::TextAttributes b) { return (TermChar::TextAttributes)((int)a & (int)b); }
inline TermChar::TextAttributes operator^(TermChar::TextAttributes a, TermChar::TextAttributes b) { return (TermChar::TextAttributes)((int)a ^ (int)b); }
inline TermChar::TextAttributes& operator|=(TermChar::TextAttributes& a, TermChar::TextAttributes b) { return (TermChar::TextAttributes&)((int&)a |= (int)b); }
inline TermChar::TextAttributes& operator&=(TermChar::TextAttributes& a, TermChar::TextAttributes b) { return (TermChar::TextAttributes&)((int&)a &= (int)b); }
inline TermChar::TextAttributes& operator^=(TermChar::TextAttributes& a, TermChar::TextAttributes b) { return (TermChar::TextAttributes&)((int&)a ^= (int)b); }
const QByteArray multiCharEscapes("().*+-/%#");
struct TermAttribs
{
QPoint cursorPos;
bool wrapAroundMode;
bool originMode;
QRgb currentFgColor;
QRgb currentBgColor;
TermChar::TextAttributes currentAttrib;
};
class TerminalLine
{
public:
int size() const { return m_contents.size(); }
void append(const TermChar& tc) { m_contents.append(tc); }
void insert(int pos, const TermChar& tc) { m_contents.insert(pos, tc); }
void removeAt(int pos) { m_contents.removeAt(pos); }
void clear() { m_contents.clear(); }
TermChar& operator[](int pos) { return m_contents[pos]; }
const TermChar& operator[](int pos) const { return m_contents[pos]; }
const TermChar& at(int pos) const { return m_contents.at(pos); }
private:
QVector<TermChar> m_contents;
};
class TerminalBuffer
{
public:
int size() const { return m_buffer.size(); }
void append(const TerminalLine& l) { m_buffer.append(l); }
void insert(int pos, const TerminalLine& l) { m_buffer.insert(pos, l); }
void removeAt(int pos) { m_buffer.removeAt(pos); }
TerminalLine takeAt(int pos) { return m_buffer.takeAt(pos); }
void clear() { m_buffer.clear(); }
TerminalLine& operator[](int pos) { return m_buffer[pos]; }
const TerminalLine& operator[](int pos) const { return m_buffer[pos]; }
const TerminalLine& at(int pos) const { return m_buffer.at(pos); }
private:
QVector<TerminalLine> m_buffer;
};
class Terminal : public QObject
{
Q_OBJECT
public:
explicit Terminal(QObject* parent = 0);
virtual ~Terminal() { }
void init();
QPoint cursorPos();
void setCursorPos(QPoint pos);
bool showCursor();
QSize termSize() const { return iTermSize; }
void setTermSize(QSize size);
TerminalBuffer& buffer();
const TerminalBuffer& buffer() const;
TerminalBuffer& backBuffer() { return iBackBuffer; }
const TerminalBuffer& backBuffer() const { return iBackBuffer; }
TerminalLine& currentLine();
bool inverseVideoMode() const { return m_inverseVideoMode; }
void keyPress(int key, int modifiers, const QString& text = "");
const QStringList printableLinesFromCursor(int lines);
void putString(QString str);
void paste(const QString& text);
const QStringList grabURLsFromBuffer();
void scrollBackBufferFwd(int lines);
void scrollBackBufferBack(int lines);
int backBufferScrollPos() const { return iBackBufferScrollPos; }
void resetBackBufferScrollPos();
QString selectedText() const;
void setSelection(QPoint start, QPoint end, bool selectionOngoing);
QRect selection() const;
void clearSelection();
int rows() const;
int columns() const;
bool useAltScreenBuffer() const { return iUseAltScreenBuffer; }
TermChar zeroChar;
signals:
void cursorPosChanged(QPoint newPos);
void termSizeChanged(int rows, int columns);
void displayBufferChanged();
void selectionChanged();
void scrollBackBufferAdjusted(bool reset);
void selectionFinished();
void visualBell();
void windowTitleChanged(const QString& windowTitle);
void workingDirectoryChanged(const QString& workingDirectory);
void hangupReceived();
protected:
void timerEvent(QTimerEvent*) override;
void insertInBuffer(const QString& chars);
private slots:
void onDataAvailable();
private:
Q_DISABLE_COPY(Terminal)
void insertAtCursor(QChar c, bool overwriteMode = true, bool advanceCursor = true);
void eraseLineAtCursor(int from = -1, int to = -1);
void clearAll(bool wholeBuffer = false);
void ansiSequence(const QString& seq);
void handleMode(int mode, bool set, const QString& extra);
bool handleIL(const QList<int>& params, const QString& extra);
bool handleDL(const QList<int>& params, const QString& extra);
bool handleDCH(const QList<int>& params, const QString& extra);
bool handleICH(const QList<int>& params, const QString& extra);
bool handleDECSED(const QList<int>& params, const QString& extra);
bool handleEL(const QList<int>& params, const QString& extra);
bool handleECH(const QList<int>& params, const QString& extra);
void oscSequence(const QString& seq);
void escControlChar(const QString& seq);
void trimBackBuffer();
void scrollBack(int lines, int insertAt = -1);
void scrollFwd(int lines, int removeAt = -1);
enum class ResetMode
{
Soft,
Hard,
};
void resetTerminal(ResetMode);
void resetTabs();
void adjustSelectionPosition(int lines);
void forwardTab();
void backwardTab();
// ### consider making this not a pointer
PtyIFace* m_pty;
TerminalBuffer iBuffer;
TerminalBuffer iAltBuffer;
TerminalBuffer iBackBuffer;
QVector<QVector<int>> iTabStops;
QSize iTermSize;
bool iEmitCursorChangeSignal;
bool iShowCursor;
bool iUseAltScreenBuffer;
bool iAppCursorKeys;
bool iReplaceMode;
bool iNewLineMode;
bool m_inverseVideoMode;
bool m_bracketedPasteMode;
int iMarginTop;
int iMarginBottom;
int iBackBufferScrollPos;
TermAttribs iTermAttribs;
TermAttribs iTermAttribs_saved;
TermAttribs iTermAttribs_saved_alt;
QString escSeq;
QString oscSeq;
int escape;
QRect iSelection;
QVector<QRgb> iColorTable;
int m_dispatch_timer;
friend class TextRender;
};
#endif // TERMINAL_H