xref: /haiku/src/apps/terminal/TerminalLine.h (revision a127b88ecbfab58f64944c98aa47722a18e363b2)
1 /*
2  * Copyright 2013, Haiku, Inc. All rights reserved.
3  * Copyright 2008, Ingo Weinhold, ingo_weinhold@gmx.de.
4  * Distributed under the terms of the MIT License.
5  *
6  * Authors:
7  *		Ingo Weinhold, ingo_weinhold@gmx.de
8  *		Siarzhuk Zharski, zharik@gmx.li
9  */
10 #ifndef TERMINAL_LINE_H
11 #define TERMINAL_LINE_H
12 
13 #include <GraphicsDefs.h>
14 #include <SupportDefs.h>
15 
16 #include "TermConst.h"
17 
18 #include "UTF8Char.h"
19 
20 
21 struct Attributes {
22 	uint32 state;
23 	uint32 foreground;
24 	uint32 background;
25 
26 	Attributes() : state(0), foreground(0), background(0) {}
27 
28 	inline void Reset() { state = 0; foreground = 0; background = 0; }
29 
30 	inline bool IsWidth() const { return (state & A_WIDTH) == A_WIDTH; }
31 	inline bool IsBold() const { return (state & BOLD) == BOLD; }
32 	inline bool IsUnder() const { return (state & UNDERLINE) == UNDERLINE; }
33 	inline bool IsInverse() const { return (state & INVERSE) == INVERSE; }
34 	inline bool IsMouse() const { return (state & MOUSE) == MOUSE; }
35 	inline bool IsForeSet() const { return (state & FORESET) == FORESET; }
36 	inline bool IsBackSet() const { return (state & BACKSET) == BACKSET; }
37 	inline bool IsFont() const { return (state & FONT) == FONT; }
38 	inline bool IsCR() const { return (state & DUMPCR) == DUMPCR; }
39 
40 	inline void SetDirectForeground(uint8 red, uint8 green, uint8 blue)
41 	{
42 		foreground = 0x80000000 | (red << 16) | (green << 8) | blue;
43 		state &= ~FORECOLOR;
44 		state |= FORESET;
45 	}
46 
47 	inline void SetDirectBackground(uint8 red, uint8 green, uint8 blue)
48 	{
49 		background = 0x80000000 | (red << 16) | (green << 8) | blue;
50 		state &= ~BACKCOLOR;
51 		state |= BACKSET;
52 	}
53 
54 	inline void SetIndexedForeground(uint32 index)
55 	{
56 		state &= ~FORECOLOR;
57 		state |= FORESET;
58 		state |= FORECOLORED(index);
59 		foreground = 0;
60 	}
61 
62 	inline void SetIndexedBackground(uint32 index)
63 	{
64 		state &= ~BACKCOLOR;
65 		state |= BACKSET;
66 		state |= BACKCOLORED(index);
67 		background = 0;
68 	}
69 
70 	inline void UnsetForeground()
71 	{
72 		state &= ~FORESET;
73 		foreground = 0;
74 	}
75 
76 	inline void UnsetBackground()
77 	{
78 		state &= ~BACKSET;
79 		background = 0;
80 	}
81 
82 	inline rgb_color
83 	ForegroundColor(const rgb_color* indexedColors) const
84 	{
85 		if ((foreground & 0x80000000) != 0)
86 			return make_color((foreground >> 16) & 0xFF,
87 				(foreground >> 8) & 0xFF,
88 				foreground & 0xFF);
89 		else
90 			return indexedColors[(state & FORECOLOR) >> 16];
91 	}
92 
93 	inline rgb_color
94 	BackgroundColor(const rgb_color* indexedColors) const
95 	{
96 		if ((background & 0x80000000) != 0)
97 			return make_color((background >> 16) & 0xFF,
98 				(background >> 8) & 0xFF,
99 				background & 0xFF);
100 		else
101 			return indexedColors[(state & BACKCOLOR) >> 24];
102 	}
103 
104 	inline Attributes&
105 	operator&=(uint32 value) { state &= value; return *this; }
106 
107 	inline Attributes&
108 	operator|=(uint32 value) { state |= value; return *this; }
109 
110 	inline uint32
111 	operator|(uint32 value) { return state | value; }
112 
113 	inline uint32
114 	operator&(uint32 value) { return state & value; }
115 
116 	inline bool
117 	operator==(const Attributes& other) const
118 	{
119 		return state == other.state
120 			&& foreground == other.foreground
121 			&& background == other.background;
122 	}
123 
124 	inline bool
125 	operator!=(const Attributes& other) const
126 	{
127 		return state != other.state
128 			|| foreground != other.foreground
129 			|| background != other.background;
130 	}
131 };
132 
133 
134 struct TerminalCell {
135 	UTF8Char			character;
136 	Attributes			attributes;
137 
138 	inline bool
139 	operator!=(const Attributes& other) const
140 	{
141 		return (attributes.state & CHAR_ATTRIBUTES)
142 				!= (other.state & CHAR_ATTRIBUTES)
143 			|| attributes.foreground != other.foreground
144 			|| attributes.background != other.background;
145 	}
146 };
147 
148 
149 struct TerminalLine {
150 	uint16			length;
151 	bool			softBreak;	// soft line break
152 	Attributes		attributes;
153 	TerminalCell	cells[1];
154 
155 	inline void Clear()
156 	{
157 		Clear(Attributes());
158 	}
159 
160 	inline void Clear(size_t count)
161 	{
162 		Clear(Attributes(), count);
163 	}
164 
165 	inline void Clear(Attributes attr, size_t count = 0)
166 	{
167 		length = 0;
168 		attributes = attr;
169 		softBreak = false;
170 		for (size_t i = 0; i < count; i++)
171 			cells[i].attributes = attr;
172 	}
173 };
174 
175 
176 struct AttributesRun {
177 	Attributes	attributes;
178 	uint16	offset;			// character offset
179 	uint16	length;			// length of the run in characters
180 };
181 
182 
183 struct HistoryLine {
184 	AttributesRun*	attributesRuns;
185 	uint16			attributesRunCount;	// number of attribute runs
186 	uint16			byteLength : 15;	// number of bytes in the line
187 	bool			softBreak : 1;		// soft line break;
188 	Attributes		attributes;
189 
190 	AttributesRun* AttributesRuns() const
191 	{
192 		return attributesRuns;
193 	}
194 
195 	char* Chars() const
196 	{
197 		return (char*)(attributesRuns + attributesRunCount);
198 	}
199 
200 	int32 BufferSize() const
201 	{
202 		return attributesRunCount * sizeof(AttributesRun) + byteLength;
203 	}
204 };
205 
206 
207 #endif	// TERMINAL_LINE_H
208