aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp
diff options
context:
space:
mode:
authorDavid Walter Seikel2013-01-13 18:54:10 +1000
committerDavid Walter Seikel2013-01-13 18:54:10 +1000
commit959831f4ef5a3e797f576c3de08cd65032c997ad (patch)
treee7351908be5995f0b325b2ebeaa02d5a34b82583 /libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp
parentAdd info about changes to Irrlicht. (diff)
downloadSledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.zip
SledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.tar.gz
SledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.tar.bz2
SledjHamr-959831f4ef5a3e797f576c3de08cd65032c997ad.tar.xz
Remove damned ancient DOS line endings from Irrlicht. Hopefully I did not go overboard.
Diffstat (limited to 'libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp')
-rw-r--r--libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp3110
1 files changed, 1555 insertions, 1555 deletions
diff --git a/libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp b/libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp
index a937cc2..7b6842d 100644
--- a/libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp
+++ b/libraries/irrlicht-1.8/source/Irrlicht/CGUIEditBox.cpp
@@ -1,1555 +1,1555 @@
1// Copyright (C) 2002-2012 Nikolaus Gebhardt 1// Copyright (C) 2002-2012 Nikolaus Gebhardt
2// This file is part of the "Irrlicht Engine". 2// This file is part of the "Irrlicht Engine".
3// For conditions of distribution and use, see copyright notice in irrlicht.h 3// For conditions of distribution and use, see copyright notice in irrlicht.h
4 4
5#include "CGUIEditBox.h" 5#include "CGUIEditBox.h"
6#ifdef _IRR_COMPILE_WITH_GUI_ 6#ifdef _IRR_COMPILE_WITH_GUI_
7 7
8#include "IGUISkin.h" 8#include "IGUISkin.h"
9#include "IGUIEnvironment.h" 9#include "IGUIEnvironment.h"
10#include "IGUIFont.h" 10#include "IGUIFont.h"
11#include "IVideoDriver.h" 11#include "IVideoDriver.h"
12#include "rect.h" 12#include "rect.h"
13#include "os.h" 13#include "os.h"
14#include "Keycodes.h" 14#include "Keycodes.h"
15 15
16/* 16/*
17 todo: 17 todo:
18 optional scrollbars 18 optional scrollbars
19 ctrl+left/right to select word 19 ctrl+left/right to select word
20 double click/ctrl click: word select + drag to select whole words, triple click to select line 20 double click/ctrl click: word select + drag to select whole words, triple click to select line
21 optional? dragging selected text 21 optional? dragging selected text
22 numerical 22 numerical
23*/ 23*/
24 24
25namespace irr 25namespace irr
26{ 26{
27namespace gui 27namespace gui
28{ 28{
29 29
30//! constructor 30//! constructor
31CGUIEditBox::CGUIEditBox(const wchar_t* text, bool border, 31CGUIEditBox::CGUIEditBox(const wchar_t* text, bool border,
32 IGUIEnvironment* environment, IGUIElement* parent, s32 id, 32 IGUIEnvironment* environment, IGUIElement* parent, s32 id,
33 const core::rect<s32>& rectangle) 33 const core::rect<s32>& rectangle)
34 : IGUIEditBox(environment, parent, id, rectangle), MouseMarking(false), 34 : IGUIEditBox(environment, parent, id, rectangle), MouseMarking(false),
35 Border(border), Background(true), OverrideColorEnabled(false), MarkBegin(0), MarkEnd(0), 35 Border(border), Background(true), OverrideColorEnabled(false), MarkBegin(0), MarkEnd(0),
36 OverrideColor(video::SColor(101,255,255,255)), OverrideFont(0), LastBreakFont(0), 36 OverrideColor(video::SColor(101,255,255,255)), OverrideFont(0), LastBreakFont(0),
37 Operator(0), BlinkStartTime(0), CursorPos(0), HScrollPos(0), VScrollPos(0), Max(0), 37 Operator(0), BlinkStartTime(0), CursorPos(0), HScrollPos(0), VScrollPos(0), Max(0),
38 WordWrap(false), MultiLine(false), AutoScroll(true), PasswordBox(false), 38 WordWrap(false), MultiLine(false), AutoScroll(true), PasswordBox(false),
39 PasswordChar(L'*'), HAlign(EGUIA_UPPERLEFT), VAlign(EGUIA_CENTER), 39 PasswordChar(L'*'), HAlign(EGUIA_UPPERLEFT), VAlign(EGUIA_CENTER),
40 CurrentTextRect(0,0,1,1), FrameRect(rectangle) 40 CurrentTextRect(0,0,1,1), FrameRect(rectangle)
41{ 41{
42 #ifdef _DEBUG 42 #ifdef _DEBUG
43 setDebugName("CGUIEditBox"); 43 setDebugName("CGUIEditBox");
44 #endif 44 #endif
45 45
46 Text = text; 46 Text = text;
47 47
48 if (Environment) 48 if (Environment)
49 Operator = Environment->getOSOperator(); 49 Operator = Environment->getOSOperator();
50 50
51 if (Operator) 51 if (Operator)
52 Operator->grab(); 52 Operator->grab();
53 53
54 // this element can be tabbed to 54 // this element can be tabbed to
55 setTabStop(true); 55 setTabStop(true);
56 setTabOrder(-1); 56 setTabOrder(-1);
57 57
58 calculateFrameRect(); 58 calculateFrameRect();
59 breakText(); 59 breakText();
60 60
61 calculateScrollPos(); 61 calculateScrollPos();
62} 62}
63 63
64 64
65//! destructor 65//! destructor
66CGUIEditBox::~CGUIEditBox() 66CGUIEditBox::~CGUIEditBox()
67{ 67{
68 if (OverrideFont) 68 if (OverrideFont)
69 OverrideFont->drop(); 69 OverrideFont->drop();
70 70
71 if (Operator) 71 if (Operator)
72 Operator->drop(); 72 Operator->drop();
73} 73}
74 74
75 75
76//! Sets another skin independent font. 76//! Sets another skin independent font.
77void CGUIEditBox::setOverrideFont(IGUIFont* font) 77void CGUIEditBox::setOverrideFont(IGUIFont* font)
78{ 78{
79 if (OverrideFont == font) 79 if (OverrideFont == font)
80 return; 80 return;
81 81
82 if (OverrideFont) 82 if (OverrideFont)
83 OverrideFont->drop(); 83 OverrideFont->drop();
84 84
85 OverrideFont = font; 85 OverrideFont = font;
86 86
87 if (OverrideFont) 87 if (OverrideFont)
88 OverrideFont->grab(); 88 OverrideFont->grab();
89 89
90 breakText(); 90 breakText();
91} 91}
92 92
93//! Gets the override font (if any) 93//! Gets the override font (if any)
94IGUIFont * CGUIEditBox::getOverrideFont() const 94IGUIFont * CGUIEditBox::getOverrideFont() const
95{ 95{
96 return OverrideFont; 96 return OverrideFont;
97} 97}
98 98
99//! Get the font which is used right now for drawing 99//! Get the font which is used right now for drawing
100IGUIFont* CGUIEditBox::getActiveFont() const 100IGUIFont* CGUIEditBox::getActiveFont() const
101{ 101{
102 if ( OverrideFont ) 102 if ( OverrideFont )
103 return OverrideFont; 103 return OverrideFont;
104 IGUISkin* skin = Environment->getSkin(); 104 IGUISkin* skin = Environment->getSkin();
105 if (skin) 105 if (skin)
106 return skin->getFont(); 106 return skin->getFont();
107 return 0; 107 return 0;
108} 108}
109 109
110//! Sets another color for the text. 110//! Sets another color for the text.
111void CGUIEditBox::setOverrideColor(video::SColor color) 111void CGUIEditBox::setOverrideColor(video::SColor color)
112{ 112{
113 OverrideColor = color; 113 OverrideColor = color;
114 OverrideColorEnabled = true; 114 OverrideColorEnabled = true;
115} 115}
116 116
117 117
118video::SColor CGUIEditBox::getOverrideColor() const 118video::SColor CGUIEditBox::getOverrideColor() const
119{ 119{
120 return OverrideColor; 120 return OverrideColor;
121} 121}
122 122
123 123
124//! Turns the border on or off 124//! Turns the border on or off
125void CGUIEditBox::setDrawBorder(bool border) 125void CGUIEditBox::setDrawBorder(bool border)
126{ 126{
127 Border = border; 127 Border = border;
128} 128}
129 129
130//! Sets whether to draw the background 130//! Sets whether to draw the background
131void CGUIEditBox::setDrawBackground(bool draw) 131void CGUIEditBox::setDrawBackground(bool draw)
132{ 132{
133 Background = draw; 133 Background = draw;
134} 134}
135 135
136//! Sets if the text should use the overide color or the color in the gui skin. 136//! Sets if the text should use the overide color or the color in the gui skin.
137void CGUIEditBox::enableOverrideColor(bool enable) 137void CGUIEditBox::enableOverrideColor(bool enable)
138{ 138{
139 OverrideColorEnabled = enable; 139 OverrideColorEnabled = enable;
140} 140}
141 141
142bool CGUIEditBox::isOverrideColorEnabled() const 142bool CGUIEditBox::isOverrideColorEnabled() const
143{ 143{
144 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX; 144 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX;
145 return OverrideColorEnabled; 145 return OverrideColorEnabled;
146} 146}
147 147
148//! Enables or disables word wrap 148//! Enables or disables word wrap
149void CGUIEditBox::setWordWrap(bool enable) 149void CGUIEditBox::setWordWrap(bool enable)
150{ 150{
151 WordWrap = enable; 151 WordWrap = enable;
152 breakText(); 152 breakText();
153} 153}
154 154
155 155
156void CGUIEditBox::updateAbsolutePosition() 156void CGUIEditBox::updateAbsolutePosition()
157{ 157{
158 core::rect<s32> oldAbsoluteRect(AbsoluteRect); 158 core::rect<s32> oldAbsoluteRect(AbsoluteRect);
159 IGUIElement::updateAbsolutePosition(); 159 IGUIElement::updateAbsolutePosition();
160 if ( oldAbsoluteRect != AbsoluteRect ) 160 if ( oldAbsoluteRect != AbsoluteRect )
161 { 161 {
162 calculateFrameRect(); 162 calculateFrameRect();
163 breakText(); 163 breakText();
164 calculateScrollPos(); 164 calculateScrollPos();
165 } 165 }
166} 166}
167 167
168 168
169//! Checks if word wrap is enabled 169//! Checks if word wrap is enabled
170bool CGUIEditBox::isWordWrapEnabled() const 170bool CGUIEditBox::isWordWrapEnabled() const
171{ 171{
172 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX; 172 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX;
173 return WordWrap; 173 return WordWrap;
174} 174}
175 175
176 176
177//! Enables or disables newlines. 177//! Enables or disables newlines.
178void CGUIEditBox::setMultiLine(bool enable) 178void CGUIEditBox::setMultiLine(bool enable)
179{ 179{
180 MultiLine = enable; 180 MultiLine = enable;
181} 181}
182 182
183 183
184//! Checks if multi line editing is enabled 184//! Checks if multi line editing is enabled
185bool CGUIEditBox::isMultiLineEnabled() const 185bool CGUIEditBox::isMultiLineEnabled() const
186{ 186{
187 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX; 187 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX;
188 return MultiLine; 188 return MultiLine;
189} 189}
190 190
191 191
192void CGUIEditBox::setPasswordBox(bool passwordBox, wchar_t passwordChar) 192void CGUIEditBox::setPasswordBox(bool passwordBox, wchar_t passwordChar)
193{ 193{
194 PasswordBox = passwordBox; 194 PasswordBox = passwordBox;
195 if (PasswordBox) 195 if (PasswordBox)
196 { 196 {
197 PasswordChar = passwordChar; 197 PasswordChar = passwordChar;
198 setMultiLine(false); 198 setMultiLine(false);
199 setWordWrap(false); 199 setWordWrap(false);
200 BrokenText.clear(); 200 BrokenText.clear();
201 } 201 }
202} 202}
203 203
204 204
205bool CGUIEditBox::isPasswordBox() const 205bool CGUIEditBox::isPasswordBox() const
206{ 206{
207 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX; 207 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX;
208 return PasswordBox; 208 return PasswordBox;
209} 209}
210 210
211 211
212//! Sets text justification 212//! Sets text justification
213void CGUIEditBox::setTextAlignment(EGUI_ALIGNMENT horizontal, EGUI_ALIGNMENT vertical) 213void CGUIEditBox::setTextAlignment(EGUI_ALIGNMENT horizontal, EGUI_ALIGNMENT vertical)
214{ 214{
215 HAlign = horizontal; 215 HAlign = horizontal;
216 VAlign = vertical; 216 VAlign = vertical;
217} 217}
218 218
219 219
220//! called if an event happened. 220//! called if an event happened.
221bool CGUIEditBox::OnEvent(const SEvent& event) 221bool CGUIEditBox::OnEvent(const SEvent& event)
222{ 222{
223 if (isEnabled()) 223 if (isEnabled())
224 { 224 {
225 225
226 switch(event.EventType) 226 switch(event.EventType)
227 { 227 {
228 case EET_GUI_EVENT: 228 case EET_GUI_EVENT:
229 if (event.GUIEvent.EventType == EGET_ELEMENT_FOCUS_LOST) 229 if (event.GUIEvent.EventType == EGET_ELEMENT_FOCUS_LOST)
230 { 230 {
231 if (event.GUIEvent.Caller == this) 231 if (event.GUIEvent.Caller == this)
232 { 232 {
233 MouseMarking = false; 233 MouseMarking = false;
234 setTextMarkers(0,0); 234 setTextMarkers(0,0);
235 } 235 }
236 } 236 }
237 break; 237 break;
238 case EET_KEY_INPUT_EVENT: 238 case EET_KEY_INPUT_EVENT:
239 if (processKey(event)) 239 if (processKey(event))
240 return true; 240 return true;
241 break; 241 break;
242 case EET_MOUSE_INPUT_EVENT: 242 case EET_MOUSE_INPUT_EVENT:
243 if (processMouse(event)) 243 if (processMouse(event))
244 return true; 244 return true;
245 break; 245 break;
246 default: 246 default:
247 break; 247 break;
248 } 248 }
249 } 249 }
250 250
251 return IGUIElement::OnEvent(event); 251 return IGUIElement::OnEvent(event);
252} 252}
253 253
254 254
255bool CGUIEditBox::processKey(const SEvent& event) 255bool CGUIEditBox::processKey(const SEvent& event)
256{ 256{
257 if (!event.KeyInput.PressedDown) 257 if (!event.KeyInput.PressedDown)
258 return false; 258 return false;
259 259
260 bool textChanged = false; 260 bool textChanged = false;
261 s32 newMarkBegin = MarkBegin; 261 s32 newMarkBegin = MarkBegin;
262 s32 newMarkEnd = MarkEnd; 262 s32 newMarkEnd = MarkEnd;
263 263
264 // control shortcut handling 264 // control shortcut handling
265 265
266 if (event.KeyInput.Control) 266 if (event.KeyInput.Control)
267 { 267 {
268 // german backlash '\' entered with control + '?' 268 // german backlash '\' entered with control + '?'
269 if ( event.KeyInput.Char == '\\' ) 269 if ( event.KeyInput.Char == '\\' )
270 { 270 {
271 inputChar(event.KeyInput.Char); 271 inputChar(event.KeyInput.Char);
272 return true; 272 return true;
273 } 273 }
274 274
275 switch(event.KeyInput.Key) 275 switch(event.KeyInput.Key)
276 { 276 {
277 case KEY_KEY_A: 277 case KEY_KEY_A:
278 // select all 278 // select all
279 newMarkBegin = 0; 279 newMarkBegin = 0;
280 newMarkEnd = Text.size(); 280 newMarkEnd = Text.size();
281 break; 281 break;
282 case KEY_KEY_C: 282 case KEY_KEY_C:
283 // copy to clipboard 283 // copy to clipboard
284 if (!PasswordBox && Operator && MarkBegin != MarkEnd) 284 if (!PasswordBox && Operator && MarkBegin != MarkEnd)
285 { 285 {
286 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 286 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
287 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 287 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
288 288
289 core::stringc s; 289 core::stringc s;
290 s = Text.subString(realmbgn, realmend - realmbgn).c_str(); 290 s = Text.subString(realmbgn, realmend - realmbgn).c_str();
291 Operator->copyToClipboard(s.c_str()); 291 Operator->copyToClipboard(s.c_str());
292 } 292 }
293 break; 293 break;
294 case KEY_KEY_X: 294 case KEY_KEY_X:
295 // cut to the clipboard 295 // cut to the clipboard
296 if (!PasswordBox && Operator && MarkBegin != MarkEnd) 296 if (!PasswordBox && Operator && MarkBegin != MarkEnd)
297 { 297 {
298 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 298 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
299 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 299 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
300 300
301 // copy 301 // copy
302 core::stringc sc; 302 core::stringc sc;
303 sc = Text.subString(realmbgn, realmend - realmbgn).c_str(); 303 sc = Text.subString(realmbgn, realmend - realmbgn).c_str();
304 Operator->copyToClipboard(sc.c_str()); 304 Operator->copyToClipboard(sc.c_str());
305 305
306 if (isEnabled()) 306 if (isEnabled())
307 { 307 {
308 // delete 308 // delete
309 core::stringw s; 309 core::stringw s;
310 s = Text.subString(0, realmbgn); 310 s = Text.subString(0, realmbgn);
311 s.append( Text.subString(realmend, Text.size()-realmend) ); 311 s.append( Text.subString(realmend, Text.size()-realmend) );
312 Text = s; 312 Text = s;
313 313
314 CursorPos = realmbgn; 314 CursorPos = realmbgn;
315 newMarkBegin = 0; 315 newMarkBegin = 0;
316 newMarkEnd = 0; 316 newMarkEnd = 0;
317 textChanged = true; 317 textChanged = true;
318 } 318 }
319 } 319 }
320 break; 320 break;
321 case KEY_KEY_V: 321 case KEY_KEY_V:
322 if ( !isEnabled() ) 322 if ( !isEnabled() )
323 break; 323 break;
324 324
325 // paste from the clipboard 325 // paste from the clipboard
326 if (Operator) 326 if (Operator)
327 { 327 {
328 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 328 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
329 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 329 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
330 330
331 // add new character 331 // add new character
332 const c8* p = Operator->getTextFromClipboard(); 332 const c8* p = Operator->getTextFromClipboard();
333 if (p) 333 if (p)
334 { 334 {
335 if (MarkBegin == MarkEnd) 335 if (MarkBegin == MarkEnd)
336 { 336 {
337 // insert text 337 // insert text
338 core::stringw s = Text.subString(0, CursorPos); 338 core::stringw s = Text.subString(0, CursorPos);
339 s.append(p); 339 s.append(p);
340 s.append( Text.subString(CursorPos, Text.size()-CursorPos) ); 340 s.append( Text.subString(CursorPos, Text.size()-CursorPos) );
341 341
342 if (!Max || s.size()<=Max) // thx to Fish FH for fix 342 if (!Max || s.size()<=Max) // thx to Fish FH for fix
343 { 343 {
344 Text = s; 344 Text = s;
345 s = p; 345 s = p;
346 CursorPos += s.size(); 346 CursorPos += s.size();
347 } 347 }
348 } 348 }
349 else 349 else
350 { 350 {
351 // replace text 351 // replace text
352 352
353 core::stringw s = Text.subString(0, realmbgn); 353 core::stringw s = Text.subString(0, realmbgn);
354 s.append(p); 354 s.append(p);
355 s.append( Text.subString(realmend, Text.size()-realmend) ); 355 s.append( Text.subString(realmend, Text.size()-realmend) );
356 356
357 if (!Max || s.size()<=Max) // thx to Fish FH for fix 357 if (!Max || s.size()<=Max) // thx to Fish FH for fix
358 { 358 {
359 Text = s; 359 Text = s;
360 s = p; 360 s = p;
361 CursorPos = realmbgn + s.size(); 361 CursorPos = realmbgn + s.size();
362 } 362 }
363 } 363 }
364 } 364 }
365 365
366 newMarkBegin = 0; 366 newMarkBegin = 0;
367 newMarkEnd = 0; 367 newMarkEnd = 0;
368 textChanged = true; 368 textChanged = true;
369 } 369 }
370 break; 370 break;
371 case KEY_HOME: 371 case KEY_HOME:
372 // move/highlight to start of text 372 // move/highlight to start of text
373 if (event.KeyInput.Shift) 373 if (event.KeyInput.Shift)
374 { 374 {
375 newMarkEnd = CursorPos; 375 newMarkEnd = CursorPos;
376 newMarkBegin = 0; 376 newMarkBegin = 0;
377 CursorPos = 0; 377 CursorPos = 0;
378 } 378 }
379 else 379 else
380 { 380 {
381 CursorPos = 0; 381 CursorPos = 0;
382 newMarkBegin = 0; 382 newMarkBegin = 0;
383 newMarkEnd = 0; 383 newMarkEnd = 0;
384 } 384 }
385 break; 385 break;
386 case KEY_END: 386 case KEY_END:
387 // move/highlight to end of text 387 // move/highlight to end of text
388 if (event.KeyInput.Shift) 388 if (event.KeyInput.Shift)
389 { 389 {
390 newMarkBegin = CursorPos; 390 newMarkBegin = CursorPos;
391 newMarkEnd = Text.size(); 391 newMarkEnd = Text.size();
392 CursorPos = 0; 392 CursorPos = 0;
393 } 393 }
394 else 394 else
395 { 395 {
396 CursorPos = Text.size(); 396 CursorPos = Text.size();
397 newMarkBegin = 0; 397 newMarkBegin = 0;
398 newMarkEnd = 0; 398 newMarkEnd = 0;
399 } 399 }
400 break; 400 break;
401 default: 401 default:
402 return false; 402 return false;
403 } 403 }
404 } 404 }
405 // default keyboard handling 405 // default keyboard handling
406 else 406 else
407 switch(event.KeyInput.Key) 407 switch(event.KeyInput.Key)
408 { 408 {
409 case KEY_END: 409 case KEY_END:
410 { 410 {
411 s32 p = Text.size(); 411 s32 p = Text.size();
412 if (WordWrap || MultiLine) 412 if (WordWrap || MultiLine)
413 { 413 {
414 p = getLineFromPos(CursorPos); 414 p = getLineFromPos(CursorPos);
415 p = BrokenTextPositions[p] + (s32)BrokenText[p].size(); 415 p = BrokenTextPositions[p] + (s32)BrokenText[p].size();
416 if (p > 0 && (Text[p-1] == L'\r' || Text[p-1] == L'\n' )) 416 if (p > 0 && (Text[p-1] == L'\r' || Text[p-1] == L'\n' ))
417 p-=1; 417 p-=1;
418 } 418 }
419 419
420 if (event.KeyInput.Shift) 420 if (event.KeyInput.Shift)
421 { 421 {
422 if (MarkBegin == MarkEnd) 422 if (MarkBegin == MarkEnd)
423 newMarkBegin = CursorPos; 423 newMarkBegin = CursorPos;
424 424
425 newMarkEnd = p; 425 newMarkEnd = p;
426 } 426 }
427 else 427 else
428 { 428 {
429 newMarkBegin = 0; 429 newMarkBegin = 0;
430 newMarkEnd = 0; 430 newMarkEnd = 0;
431 } 431 }
432 CursorPos = p; 432 CursorPos = p;
433 BlinkStartTime = os::Timer::getTime(); 433 BlinkStartTime = os::Timer::getTime();
434 } 434 }
435 break; 435 break;
436 case KEY_HOME: 436 case KEY_HOME:
437 { 437 {
438 438
439 s32 p = 0; 439 s32 p = 0;
440 if (WordWrap || MultiLine) 440 if (WordWrap || MultiLine)
441 { 441 {
442 p = getLineFromPos(CursorPos); 442 p = getLineFromPos(CursorPos);
443 p = BrokenTextPositions[p]; 443 p = BrokenTextPositions[p];
444 } 444 }
445 445
446 if (event.KeyInput.Shift) 446 if (event.KeyInput.Shift)
447 { 447 {
448 if (MarkBegin == MarkEnd) 448 if (MarkBegin == MarkEnd)
449 newMarkBegin = CursorPos; 449 newMarkBegin = CursorPos;
450 newMarkEnd = p; 450 newMarkEnd = p;
451 } 451 }
452 else 452 else
453 { 453 {
454 newMarkBegin = 0; 454 newMarkBegin = 0;
455 newMarkEnd = 0; 455 newMarkEnd = 0;
456 } 456 }
457 CursorPos = p; 457 CursorPos = p;
458 BlinkStartTime = os::Timer::getTime(); 458 BlinkStartTime = os::Timer::getTime();
459 } 459 }
460 break; 460 break;
461 case KEY_RETURN: 461 case KEY_RETURN:
462 if (MultiLine) 462 if (MultiLine)
463 { 463 {
464 inputChar(L'\n'); 464 inputChar(L'\n');
465 } 465 }
466 else 466 else
467 { 467 {
468 calculateScrollPos(); 468 calculateScrollPos();
469 sendGuiEvent( EGET_EDITBOX_ENTER ); 469 sendGuiEvent( EGET_EDITBOX_ENTER );
470 } 470 }
471 return true; 471 return true;
472 case KEY_LEFT: 472 case KEY_LEFT:
473 473
474 if (event.KeyInput.Shift) 474 if (event.KeyInput.Shift)
475 { 475 {
476 if (CursorPos > 0) 476 if (CursorPos > 0)
477 { 477 {
478 if (MarkBegin == MarkEnd) 478 if (MarkBegin == MarkEnd)
479 newMarkBegin = CursorPos; 479 newMarkBegin = CursorPos;
480 480
481 newMarkEnd = CursorPos-1; 481 newMarkEnd = CursorPos-1;
482 } 482 }
483 } 483 }
484 else 484 else
485 { 485 {
486 newMarkBegin = 0; 486 newMarkBegin = 0;
487 newMarkEnd = 0; 487 newMarkEnd = 0;
488 } 488 }
489 489
490 if (CursorPos > 0) CursorPos--; 490 if (CursorPos > 0) CursorPos--;
491 BlinkStartTime = os::Timer::getTime(); 491 BlinkStartTime = os::Timer::getTime();
492 break; 492 break;
493 493
494 case KEY_RIGHT: 494 case KEY_RIGHT:
495 if (event.KeyInput.Shift) 495 if (event.KeyInput.Shift)
496 { 496 {
497 if (Text.size() > (u32)CursorPos) 497 if (Text.size() > (u32)CursorPos)
498 { 498 {
499 if (MarkBegin == MarkEnd) 499 if (MarkBegin == MarkEnd)
500 newMarkBegin = CursorPos; 500 newMarkBegin = CursorPos;
501 501
502 newMarkEnd = CursorPos+1; 502 newMarkEnd = CursorPos+1;
503 } 503 }
504 } 504 }
505 else 505 else
506 { 506 {
507 newMarkBegin = 0; 507 newMarkBegin = 0;
508 newMarkEnd = 0; 508 newMarkEnd = 0;
509 } 509 }
510 510
511 if (Text.size() > (u32)CursorPos) CursorPos++; 511 if (Text.size() > (u32)CursorPos) CursorPos++;
512 BlinkStartTime = os::Timer::getTime(); 512 BlinkStartTime = os::Timer::getTime();
513 break; 513 break;
514 case KEY_UP: 514 case KEY_UP:
515 if (MultiLine || (WordWrap && BrokenText.size() > 1) ) 515 if (MultiLine || (WordWrap && BrokenText.size() > 1) )
516 { 516 {
517 s32 lineNo = getLineFromPos(CursorPos); 517 s32 lineNo = getLineFromPos(CursorPos);
518 s32 mb = (MarkBegin == MarkEnd) ? CursorPos : (MarkBegin > MarkEnd ? MarkBegin : MarkEnd); 518 s32 mb = (MarkBegin == MarkEnd) ? CursorPos : (MarkBegin > MarkEnd ? MarkBegin : MarkEnd);
519 if (lineNo > 0) 519 if (lineNo > 0)
520 { 520 {
521 s32 cp = CursorPos - BrokenTextPositions[lineNo]; 521 s32 cp = CursorPos - BrokenTextPositions[lineNo];
522 if ((s32)BrokenText[lineNo-1].size() < cp) 522 if ((s32)BrokenText[lineNo-1].size() < cp)
523 CursorPos = BrokenTextPositions[lineNo-1] + core::max_((u32)1, BrokenText[lineNo-1].size())-1; 523 CursorPos = BrokenTextPositions[lineNo-1] + core::max_((u32)1, BrokenText[lineNo-1].size())-1;
524 else 524 else
525 CursorPos = BrokenTextPositions[lineNo-1] + cp; 525 CursorPos = BrokenTextPositions[lineNo-1] + cp;
526 } 526 }
527 527
528 if (event.KeyInput.Shift) 528 if (event.KeyInput.Shift)
529 { 529 {
530 newMarkBegin = mb; 530 newMarkBegin = mb;
531 newMarkEnd = CursorPos; 531 newMarkEnd = CursorPos;
532 } 532 }
533 else 533 else
534 { 534 {
535 newMarkBegin = 0; 535 newMarkBegin = 0;
536 newMarkEnd = 0; 536 newMarkEnd = 0;
537 } 537 }
538 538
539 } 539 }
540 else 540 else
541 { 541 {
542 return false; 542 return false;
543 } 543 }
544 break; 544 break;
545 case KEY_DOWN: 545 case KEY_DOWN:
546 if (MultiLine || (WordWrap && BrokenText.size() > 1) ) 546 if (MultiLine || (WordWrap && BrokenText.size() > 1) )
547 { 547 {
548 s32 lineNo = getLineFromPos(CursorPos); 548 s32 lineNo = getLineFromPos(CursorPos);
549 s32 mb = (MarkBegin == MarkEnd) ? CursorPos : (MarkBegin < MarkEnd ? MarkBegin : MarkEnd); 549 s32 mb = (MarkBegin == MarkEnd) ? CursorPos : (MarkBegin < MarkEnd ? MarkBegin : MarkEnd);
550 if (lineNo < (s32)BrokenText.size()-1) 550 if (lineNo < (s32)BrokenText.size()-1)
551 { 551 {
552 s32 cp = CursorPos - BrokenTextPositions[lineNo]; 552 s32 cp = CursorPos - BrokenTextPositions[lineNo];
553 if ((s32)BrokenText[lineNo+1].size() < cp) 553 if ((s32)BrokenText[lineNo+1].size() < cp)
554 CursorPos = BrokenTextPositions[lineNo+1] + core::max_((u32)1, BrokenText[lineNo+1].size())-1; 554 CursorPos = BrokenTextPositions[lineNo+1] + core::max_((u32)1, BrokenText[lineNo+1].size())-1;
555 else 555 else
556 CursorPos = BrokenTextPositions[lineNo+1] + cp; 556 CursorPos = BrokenTextPositions[lineNo+1] + cp;
557 } 557 }
558 558
559 if (event.KeyInput.Shift) 559 if (event.KeyInput.Shift)
560 { 560 {
561 newMarkBegin = mb; 561 newMarkBegin = mb;
562 newMarkEnd = CursorPos; 562 newMarkEnd = CursorPos;
563 } 563 }
564 else 564 else
565 { 565 {
566 newMarkBegin = 0; 566 newMarkBegin = 0;
567 newMarkEnd = 0; 567 newMarkEnd = 0;
568 } 568 }
569 569
570 } 570 }
571 else 571 else
572 { 572 {
573 return false; 573 return false;
574 } 574 }
575 break; 575 break;
576 576
577 case KEY_BACK: 577 case KEY_BACK:
578 if ( !isEnabled() ) 578 if ( !isEnabled() )
579 break; 579 break;
580 580
581 if (Text.size()) 581 if (Text.size())
582 { 582 {
583 core::stringw s; 583 core::stringw s;
584 584
585 if (MarkBegin != MarkEnd) 585 if (MarkBegin != MarkEnd)
586 { 586 {
587 // delete marked text 587 // delete marked text
588 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 588 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
589 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 589 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
590 590
591 s = Text.subString(0, realmbgn); 591 s = Text.subString(0, realmbgn);
592 s.append( Text.subString(realmend, Text.size()-realmend) ); 592 s.append( Text.subString(realmend, Text.size()-realmend) );
593 Text = s; 593 Text = s;
594 594
595 CursorPos = realmbgn; 595 CursorPos = realmbgn;
596 } 596 }
597 else 597 else
598 { 598 {
599 // delete text behind cursor 599 // delete text behind cursor
600 if (CursorPos>0) 600 if (CursorPos>0)
601 s = Text.subString(0, CursorPos-1); 601 s = Text.subString(0, CursorPos-1);
602 else 602 else
603 s = L""; 603 s = L"";
604 s.append( Text.subString(CursorPos, Text.size()-CursorPos) ); 604 s.append( Text.subString(CursorPos, Text.size()-CursorPos) );
605 Text = s; 605 Text = s;
606 --CursorPos; 606 --CursorPos;
607 } 607 }
608 608
609 if (CursorPos < 0) 609 if (CursorPos < 0)
610 CursorPos = 0; 610 CursorPos = 0;
611 BlinkStartTime = os::Timer::getTime(); 611 BlinkStartTime = os::Timer::getTime();
612 newMarkBegin = 0; 612 newMarkBegin = 0;
613 newMarkEnd = 0; 613 newMarkEnd = 0;
614 textChanged = true; 614 textChanged = true;
615 } 615 }
616 break; 616 break;
617 case KEY_DELETE: 617 case KEY_DELETE:
618 if ( !isEnabled() ) 618 if ( !isEnabled() )
619 break; 619 break;
620 620
621 if (Text.size() != 0) 621 if (Text.size() != 0)
622 { 622 {
623 core::stringw s; 623 core::stringw s;
624 624
625 if (MarkBegin != MarkEnd) 625 if (MarkBegin != MarkEnd)
626 { 626 {
627 // delete marked text 627 // delete marked text
628 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 628 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
629 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 629 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
630 630
631 s = Text.subString(0, realmbgn); 631 s = Text.subString(0, realmbgn);
632 s.append( Text.subString(realmend, Text.size()-realmend) ); 632 s.append( Text.subString(realmend, Text.size()-realmend) );
633 Text = s; 633 Text = s;
634 634
635 CursorPos = realmbgn; 635 CursorPos = realmbgn;
636 } 636 }
637 else 637 else
638 { 638 {
639 // delete text before cursor 639 // delete text before cursor
640 s = Text.subString(0, CursorPos); 640 s = Text.subString(0, CursorPos);
641 s.append( Text.subString(CursorPos+1, Text.size()-CursorPos-1) ); 641 s.append( Text.subString(CursorPos+1, Text.size()-CursorPos-1) );
642 Text = s; 642 Text = s;
643 } 643 }
644 644
645 if (CursorPos > (s32)Text.size()) 645 if (CursorPos > (s32)Text.size())
646 CursorPos = (s32)Text.size(); 646 CursorPos = (s32)Text.size();
647 647
648 BlinkStartTime = os::Timer::getTime(); 648 BlinkStartTime = os::Timer::getTime();
649 newMarkBegin = 0; 649 newMarkBegin = 0;
650 newMarkEnd = 0; 650 newMarkEnd = 0;
651 textChanged = true; 651 textChanged = true;
652 } 652 }
653 break; 653 break;
654 654
655 case KEY_ESCAPE: 655 case KEY_ESCAPE:
656 case KEY_TAB: 656 case KEY_TAB:
657 case KEY_SHIFT: 657 case KEY_SHIFT:
658 case KEY_F1: 658 case KEY_F1:
659 case KEY_F2: 659 case KEY_F2:
660 case KEY_F3: 660 case KEY_F3:
661 case KEY_F4: 661 case KEY_F4:
662 case KEY_F5: 662 case KEY_F5:
663 case KEY_F6: 663 case KEY_F6:
664 case KEY_F7: 664 case KEY_F7:
665 case KEY_F8: 665 case KEY_F8:
666 case KEY_F9: 666 case KEY_F9:
667 case KEY_F10: 667 case KEY_F10:
668 case KEY_F11: 668 case KEY_F11:
669 case KEY_F12: 669 case KEY_F12:
670 case KEY_F13: 670 case KEY_F13:
671 case KEY_F14: 671 case KEY_F14:
672 case KEY_F15: 672 case KEY_F15:
673 case KEY_F16: 673 case KEY_F16:
674 case KEY_F17: 674 case KEY_F17:
675 case KEY_F18: 675 case KEY_F18:
676 case KEY_F19: 676 case KEY_F19:
677 case KEY_F20: 677 case KEY_F20:
678 case KEY_F21: 678 case KEY_F21:
679 case KEY_F22: 679 case KEY_F22:
680 case KEY_F23: 680 case KEY_F23:
681 case KEY_F24: 681 case KEY_F24:
682 // ignore these keys 682 // ignore these keys
683 return false; 683 return false;
684 684
685 default: 685 default:
686 inputChar(event.KeyInput.Char); 686 inputChar(event.KeyInput.Char);
687 return true; 687 return true;
688 } 688 }
689 689
690 // Set new text markers 690 // Set new text markers
691 setTextMarkers( newMarkBegin, newMarkEnd ); 691 setTextMarkers( newMarkBegin, newMarkEnd );
692 692
693 // break the text if it has changed 693 // break the text if it has changed
694 if (textChanged) 694 if (textChanged)
695 { 695 {
696 breakText(); 696 breakText();
697 calculateScrollPos(); 697 calculateScrollPos();
698 sendGuiEvent(EGET_EDITBOX_CHANGED); 698 sendGuiEvent(EGET_EDITBOX_CHANGED);
699 } 699 }
700 else 700 else
701 { 701 {
702 calculateScrollPos(); 702 calculateScrollPos();
703 } 703 }
704 704
705 return true; 705 return true;
706} 706}
707 707
708 708
709//! draws the element and its children 709//! draws the element and its children
710void CGUIEditBox::draw() 710void CGUIEditBox::draw()
711{ 711{
712 if (!IsVisible) 712 if (!IsVisible)
713 return; 713 return;
714 714
715 const bool focus = Environment->hasFocus(this); 715 const bool focus = Environment->hasFocus(this);
716 716
717 IGUISkin* skin = Environment->getSkin(); 717 IGUISkin* skin = Environment->getSkin();
718 if (!skin) 718 if (!skin)
719 return; 719 return;
720 720
721 EGUI_DEFAULT_COLOR bgCol = EGDC_GRAY_EDITABLE; 721 EGUI_DEFAULT_COLOR bgCol = EGDC_GRAY_EDITABLE;
722 if ( isEnabled() ) 722 if ( isEnabled() )
723 bgCol = focus ? EGDC_FOCUSED_EDITABLE : EGDC_EDITABLE; 723 bgCol = focus ? EGDC_FOCUSED_EDITABLE : EGDC_EDITABLE;
724 724
725 if (!Border && Background) 725 if (!Border && Background)
726 { 726 {
727 skin->draw2DRectangle(this, skin->getColor(bgCol), AbsoluteRect, &AbsoluteClippingRect); 727 skin->draw2DRectangle(this, skin->getColor(bgCol), AbsoluteRect, &AbsoluteClippingRect);
728 } 728 }
729 729
730 if (Border) 730 if (Border)
731 { 731 {
732 // draw the border 732 // draw the border
733 skin->draw3DSunkenPane(this, skin->getColor(bgCol), false, Background, AbsoluteRect, &AbsoluteClippingRect); 733 skin->draw3DSunkenPane(this, skin->getColor(bgCol), false, Background, AbsoluteRect, &AbsoluteClippingRect);
734 734
735 calculateFrameRect(); 735 calculateFrameRect();
736 } 736 }
737 737
738 core::rect<s32> localClipRect = FrameRect; 738 core::rect<s32> localClipRect = FrameRect;
739 localClipRect.clipAgainst(AbsoluteClippingRect); 739 localClipRect.clipAgainst(AbsoluteClippingRect);
740 740
741 // draw the text 741 // draw the text
742 742
743 IGUIFont* font = getActiveFont(); 743 IGUIFont* font = getActiveFont();
744 744
745 s32 cursorLine = 0; 745 s32 cursorLine = 0;
746 s32 charcursorpos = 0; 746 s32 charcursorpos = 0;
747 747
748 if (font) 748 if (font)
749 { 749 {
750 if (LastBreakFont != font) 750 if (LastBreakFont != font)
751 { 751 {
752 breakText(); 752 breakText();
753 } 753 }
754 754
755 // calculate cursor pos 755 // calculate cursor pos
756 756
757 core::stringw *txtLine = &Text; 757 core::stringw *txtLine = &Text;
758 s32 startPos = 0; 758 s32 startPos = 0;
759 759
760 core::stringw s, s2; 760 core::stringw s, s2;
761 761
762 // get mark position 762 // get mark position
763 const bool ml = (!PasswordBox && (WordWrap || MultiLine)); 763 const bool ml = (!PasswordBox && (WordWrap || MultiLine));
764 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 764 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
765 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 765 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
766 const s32 hlineStart = ml ? getLineFromPos(realmbgn) : 0; 766 const s32 hlineStart = ml ? getLineFromPos(realmbgn) : 0;
767 const s32 hlineCount = ml ? getLineFromPos(realmend) - hlineStart + 1 : 1; 767 const s32 hlineCount = ml ? getLineFromPos(realmend) - hlineStart + 1 : 1;
768 const s32 lineCount = ml ? BrokenText.size() : 1; 768 const s32 lineCount = ml ? BrokenText.size() : 1;
769 769
770 // Save the override color information. 770 // Save the override color information.
771 // Then, alter it if the edit box is disabled. 771 // Then, alter it if the edit box is disabled.
772 const bool prevOver = OverrideColorEnabled; 772 const bool prevOver = OverrideColorEnabled;
773 const video::SColor prevColor = OverrideColor; 773 const video::SColor prevColor = OverrideColor;
774 774
775 if (Text.size()) 775 if (Text.size())
776 { 776 {
777 if (!isEnabled() && !OverrideColorEnabled) 777 if (!isEnabled() && !OverrideColorEnabled)
778 { 778 {
779 OverrideColorEnabled = true; 779 OverrideColorEnabled = true;
780 OverrideColor = skin->getColor(EGDC_GRAY_TEXT); 780 OverrideColor = skin->getColor(EGDC_GRAY_TEXT);
781 } 781 }
782 782
783 for (s32 i=0; i < lineCount; ++i) 783 for (s32 i=0; i < lineCount; ++i)
784 { 784 {
785 setTextRect(i); 785 setTextRect(i);
786 786
787 // clipping test - don't draw anything outside the visible area 787 // clipping test - don't draw anything outside the visible area
788 core::rect<s32> c = localClipRect; 788 core::rect<s32> c = localClipRect;
789 c.clipAgainst(CurrentTextRect); 789 c.clipAgainst(CurrentTextRect);
790 if (!c.isValid()) 790 if (!c.isValid())
791 continue; 791 continue;
792 792
793 // get current line 793 // get current line
794 if (PasswordBox) 794 if (PasswordBox)
795 { 795 {
796 if (BrokenText.size() != 1) 796 if (BrokenText.size() != 1)
797 { 797 {
798 BrokenText.clear(); 798 BrokenText.clear();
799 BrokenText.push_back(core::stringw()); 799 BrokenText.push_back(core::stringw());
800 } 800 }
801 if (BrokenText[0].size() != Text.size()) 801 if (BrokenText[0].size() != Text.size())
802 { 802 {
803 BrokenText[0] = Text; 803 BrokenText[0] = Text;
804 for (u32 q = 0; q < Text.size(); ++q) 804 for (u32 q = 0; q < Text.size(); ++q)
805 { 805 {
806 BrokenText[0] [q] = PasswordChar; 806 BrokenText[0] [q] = PasswordChar;
807 } 807 }
808 } 808 }
809 txtLine = &BrokenText[0]; 809 txtLine = &BrokenText[0];
810 startPos = 0; 810 startPos = 0;
811 } 811 }
812 else 812 else
813 { 813 {
814 txtLine = ml ? &BrokenText[i] : &Text; 814 txtLine = ml ? &BrokenText[i] : &Text;
815 startPos = ml ? BrokenTextPositions[i] : 0; 815 startPos = ml ? BrokenTextPositions[i] : 0;
816 } 816 }
817 817
818 818
819 // draw normal text 819 // draw normal text
820 font->draw(txtLine->c_str(), CurrentTextRect, 820 font->draw(txtLine->c_str(), CurrentTextRect,
821 OverrideColorEnabled ? OverrideColor : skin->getColor(EGDC_BUTTON_TEXT), 821 OverrideColorEnabled ? OverrideColor : skin->getColor(EGDC_BUTTON_TEXT),
822 false, true, &localClipRect); 822 false, true, &localClipRect);
823 823
824 // draw mark and marked text 824 // draw mark and marked text
825 if (focus && MarkBegin != MarkEnd && i >= hlineStart && i < hlineStart + hlineCount) 825 if (focus && MarkBegin != MarkEnd && i >= hlineStart && i < hlineStart + hlineCount)
826 { 826 {
827 827
828 s32 mbegin = 0, mend = 0; 828 s32 mbegin = 0, mend = 0;
829 s32 lineStartPos = 0, lineEndPos = txtLine->size(); 829 s32 lineStartPos = 0, lineEndPos = txtLine->size();
830 830
831 if (i == hlineStart) 831 if (i == hlineStart)
832 { 832 {
833 // highlight start is on this line 833 // highlight start is on this line
834 s = txtLine->subString(0, realmbgn - startPos); 834 s = txtLine->subString(0, realmbgn - startPos);
835 mbegin = font->getDimension(s.c_str()).Width; 835 mbegin = font->getDimension(s.c_str()).Width;
836 836
837 // deal with kerning 837 // deal with kerning
838 mbegin += font->getKerningWidth( 838 mbegin += font->getKerningWidth(
839 &((*txtLine)[realmbgn - startPos]), 839 &((*txtLine)[realmbgn - startPos]),
840 realmbgn - startPos > 0 ? &((*txtLine)[realmbgn - startPos - 1]) : 0); 840 realmbgn - startPos > 0 ? &((*txtLine)[realmbgn - startPos - 1]) : 0);
841 841
842 lineStartPos = realmbgn - startPos; 842 lineStartPos = realmbgn - startPos;
843 } 843 }
844 if (i == hlineStart + hlineCount - 1) 844 if (i == hlineStart + hlineCount - 1)
845 { 845 {
846 // highlight end is on this line 846 // highlight end is on this line
847 s2 = txtLine->subString(0, realmend - startPos); 847 s2 = txtLine->subString(0, realmend - startPos);
848 mend = font->getDimension(s2.c_str()).Width; 848 mend = font->getDimension(s2.c_str()).Width;
849 lineEndPos = (s32)s2.size(); 849 lineEndPos = (s32)s2.size();
850 } 850 }
851 else 851 else
852 mend = font->getDimension(txtLine->c_str()).Width; 852 mend = font->getDimension(txtLine->c_str()).Width;
853 853
854 CurrentTextRect.UpperLeftCorner.X += mbegin; 854 CurrentTextRect.UpperLeftCorner.X += mbegin;
855 CurrentTextRect.LowerRightCorner.X = CurrentTextRect.UpperLeftCorner.X + mend - mbegin; 855 CurrentTextRect.LowerRightCorner.X = CurrentTextRect.UpperLeftCorner.X + mend - mbegin;
856 856
857 // draw mark 857 // draw mark
858 skin->draw2DRectangle(this, skin->getColor(EGDC_HIGH_LIGHT), CurrentTextRect, &localClipRect); 858 skin->draw2DRectangle(this, skin->getColor(EGDC_HIGH_LIGHT), CurrentTextRect, &localClipRect);
859 859
860 // draw marked text 860 // draw marked text
861 s = txtLine->subString(lineStartPos, lineEndPos - lineStartPos); 861 s = txtLine->subString(lineStartPos, lineEndPos - lineStartPos);
862 862
863 if (s.size()) 863 if (s.size())
864 font->draw(s.c_str(), CurrentTextRect, 864 font->draw(s.c_str(), CurrentTextRect,
865 OverrideColorEnabled ? OverrideColor : skin->getColor(EGDC_HIGH_LIGHT_TEXT), 865 OverrideColorEnabled ? OverrideColor : skin->getColor(EGDC_HIGH_LIGHT_TEXT),
866 false, true, &localClipRect); 866 false, true, &localClipRect);
867 867
868 } 868 }
869 } 869 }
870 870
871 // Return the override color information to its previous settings. 871 // Return the override color information to its previous settings.
872 OverrideColorEnabled = prevOver; 872 OverrideColorEnabled = prevOver;
873 OverrideColor = prevColor; 873 OverrideColor = prevColor;
874 } 874 }
875 875
876 // draw cursor 876 // draw cursor
877 if ( IsEnabled ) 877 if ( IsEnabled )
878 { 878 {
879 if (WordWrap || MultiLine) 879 if (WordWrap || MultiLine)
880 { 880 {
881 cursorLine = getLineFromPos(CursorPos); 881 cursorLine = getLineFromPos(CursorPos);
882 txtLine = &BrokenText[cursorLine]; 882 txtLine = &BrokenText[cursorLine];
883 startPos = BrokenTextPositions[cursorLine]; 883 startPos = BrokenTextPositions[cursorLine];
884 } 884 }
885 s = txtLine->subString(0,CursorPos-startPos); 885 s = txtLine->subString(0,CursorPos-startPos);
886 charcursorpos = font->getDimension(s.c_str()).Width + 886 charcursorpos = font->getDimension(s.c_str()).Width +
887 font->getKerningWidth(L"_", CursorPos-startPos > 0 ? &((*txtLine)[CursorPos-startPos-1]) : 0); 887 font->getKerningWidth(L"_", CursorPos-startPos > 0 ? &((*txtLine)[CursorPos-startPos-1]) : 0);
888 888
889 if (focus && (os::Timer::getTime() - BlinkStartTime) % 700 < 350) 889 if (focus && (os::Timer::getTime() - BlinkStartTime) % 700 < 350)
890 { 890 {
891 setTextRect(cursorLine); 891 setTextRect(cursorLine);
892 CurrentTextRect.UpperLeftCorner.X += charcursorpos; 892 CurrentTextRect.UpperLeftCorner.X += charcursorpos;
893 893
894 font->draw(L"_", CurrentTextRect, 894 font->draw(L"_", CurrentTextRect,
895 OverrideColorEnabled ? OverrideColor : skin->getColor(EGDC_BUTTON_TEXT), 895 OverrideColorEnabled ? OverrideColor : skin->getColor(EGDC_BUTTON_TEXT),
896 false, true, &localClipRect); 896 false, true, &localClipRect);
897 } 897 }
898 } 898 }
899 } 899 }
900 900
901 // draw children 901 // draw children
902 IGUIElement::draw(); 902 IGUIElement::draw();
903} 903}
904 904
905 905
906//! Sets the new caption of this element. 906//! Sets the new caption of this element.
907void CGUIEditBox::setText(const wchar_t* text) 907void CGUIEditBox::setText(const wchar_t* text)
908{ 908{
909 Text = text; 909 Text = text;
910 if (u32(CursorPos) > Text.size()) 910 if (u32(CursorPos) > Text.size())
911 CursorPos = Text.size(); 911 CursorPos = Text.size();
912 HScrollPos = 0; 912 HScrollPos = 0;
913 breakText(); 913 breakText();
914} 914}
915 915
916 916
917//! Enables or disables automatic scrolling with cursor position 917//! Enables or disables automatic scrolling with cursor position
918//! \param enable: If set to true, the text will move around with the cursor position 918//! \param enable: If set to true, the text will move around with the cursor position
919void CGUIEditBox::setAutoScroll(bool enable) 919void CGUIEditBox::setAutoScroll(bool enable)
920{ 920{
921 AutoScroll = enable; 921 AutoScroll = enable;
922} 922}
923 923
924 924
925//! Checks to see if automatic scrolling is enabled 925//! Checks to see if automatic scrolling is enabled
926//! \return true if automatic scrolling is enabled, false if not 926//! \return true if automatic scrolling is enabled, false if not
927bool CGUIEditBox::isAutoScrollEnabled() const 927bool CGUIEditBox::isAutoScrollEnabled() const
928{ 928{
929 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX; 929 _IRR_IMPLEMENT_MANAGED_MARSHALLING_BUGFIX;
930 return AutoScroll; 930 return AutoScroll;
931} 931}
932 932
933 933
934//! Gets the area of the text in the edit box 934//! Gets the area of the text in the edit box
935//! \return Returns the size in pixels of the text 935//! \return Returns the size in pixels of the text
936core::dimension2du CGUIEditBox::getTextDimension() 936core::dimension2du CGUIEditBox::getTextDimension()
937{ 937{
938 core::rect<s32> ret; 938 core::rect<s32> ret;
939 939
940 setTextRect(0); 940 setTextRect(0);
941 ret = CurrentTextRect; 941 ret = CurrentTextRect;
942 942
943 for (u32 i=1; i < BrokenText.size(); ++i) 943 for (u32 i=1; i < BrokenText.size(); ++i)
944 { 944 {
945 setTextRect(i); 945 setTextRect(i);
946 ret.addInternalPoint(CurrentTextRect.UpperLeftCorner); 946 ret.addInternalPoint(CurrentTextRect.UpperLeftCorner);
947 ret.addInternalPoint(CurrentTextRect.LowerRightCorner); 947 ret.addInternalPoint(CurrentTextRect.LowerRightCorner);
948 } 948 }
949 949
950 return core::dimension2du(ret.getSize()); 950 return core::dimension2du(ret.getSize());
951} 951}
952 952
953 953
954//! Sets the maximum amount of characters which may be entered in the box. 954//! Sets the maximum amount of characters which may be entered in the box.
955//! \param max: Maximum amount of characters. If 0, the character amount is 955//! \param max: Maximum amount of characters. If 0, the character amount is
956//! infinity. 956//! infinity.
957void CGUIEditBox::setMax(u32 max) 957void CGUIEditBox::setMax(u32 max)
958{ 958{
959 Max = max; 959 Max = max;
960 960
961 if (Text.size() > Max && Max != 0) 961 if (Text.size() > Max && Max != 0)
962 Text = Text.subString(0, Max); 962 Text = Text.subString(0, Max);
963} 963}
964 964
965 965
966//! Returns maximum amount of characters, previously set by setMax(); 966//! Returns maximum amount of characters, previously set by setMax();
967u32 CGUIEditBox::getMax() const 967u32 CGUIEditBox::getMax() const
968{ 968{
969 return Max; 969 return Max;
970} 970}
971 971
972 972
973bool CGUIEditBox::processMouse(const SEvent& event) 973bool CGUIEditBox::processMouse(const SEvent& event)
974{ 974{
975 switch(event.MouseInput.Event) 975 switch(event.MouseInput.Event)
976 { 976 {
977 case irr::EMIE_LMOUSE_LEFT_UP: 977 case irr::EMIE_LMOUSE_LEFT_UP:
978 if (Environment->hasFocus(this)) 978 if (Environment->hasFocus(this))
979 { 979 {
980 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y); 980 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y);
981 if (MouseMarking) 981 if (MouseMarking)
982 { 982 {
983 setTextMarkers( MarkBegin, CursorPos ); 983 setTextMarkers( MarkBegin, CursorPos );
984 } 984 }
985 MouseMarking = false; 985 MouseMarking = false;
986 calculateScrollPos(); 986 calculateScrollPos();
987 return true; 987 return true;
988 } 988 }
989 break; 989 break;
990 case irr::EMIE_MOUSE_MOVED: 990 case irr::EMIE_MOUSE_MOVED:
991 { 991 {
992 if (MouseMarking) 992 if (MouseMarking)
993 { 993 {
994 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y); 994 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y);
995 setTextMarkers( MarkBegin, CursorPos ); 995 setTextMarkers( MarkBegin, CursorPos );
996 calculateScrollPos(); 996 calculateScrollPos();
997 return true; 997 return true;
998 } 998 }
999 } 999 }
1000 break; 1000 break;
1001 case EMIE_LMOUSE_PRESSED_DOWN: 1001 case EMIE_LMOUSE_PRESSED_DOWN:
1002 if (!Environment->hasFocus(this)) 1002 if (!Environment->hasFocus(this))
1003 { 1003 {
1004 BlinkStartTime = os::Timer::getTime(); 1004 BlinkStartTime = os::Timer::getTime();
1005 MouseMarking = true; 1005 MouseMarking = true;
1006 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y); 1006 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y);
1007 setTextMarkers(CursorPos, CursorPos ); 1007 setTextMarkers(CursorPos, CursorPos );
1008 calculateScrollPos(); 1008 calculateScrollPos();
1009 return true; 1009 return true;
1010 } 1010 }
1011 else 1011 else
1012 { 1012 {
1013 if (!AbsoluteClippingRect.isPointInside( 1013 if (!AbsoluteClippingRect.isPointInside(
1014 core::position2d<s32>(event.MouseInput.X, event.MouseInput.Y))) 1014 core::position2d<s32>(event.MouseInput.X, event.MouseInput.Y)))
1015 { 1015 {
1016 return false; 1016 return false;
1017 } 1017 }
1018 else 1018 else
1019 { 1019 {
1020 // move cursor 1020 // move cursor
1021 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y); 1021 CursorPos = getCursorPos(event.MouseInput.X, event.MouseInput.Y);
1022 1022
1023 s32 newMarkBegin = MarkBegin; 1023 s32 newMarkBegin = MarkBegin;
1024 if (!MouseMarking) 1024 if (!MouseMarking)
1025 newMarkBegin = CursorPos; 1025 newMarkBegin = CursorPos;
1026 1026
1027 MouseMarking = true; 1027 MouseMarking = true;
1028 setTextMarkers( newMarkBegin, CursorPos); 1028 setTextMarkers( newMarkBegin, CursorPos);
1029 calculateScrollPos(); 1029 calculateScrollPos();
1030 return true; 1030 return true;
1031 } 1031 }
1032 } 1032 }
1033 default: 1033 default:
1034 break; 1034 break;
1035 } 1035 }
1036 1036
1037 return false; 1037 return false;
1038} 1038}
1039 1039
1040 1040
1041s32 CGUIEditBox::getCursorPos(s32 x, s32 y) 1041s32 CGUIEditBox::getCursorPos(s32 x, s32 y)
1042{ 1042{
1043 IGUIFont* font = getActiveFont(); 1043 IGUIFont* font = getActiveFont();
1044 1044
1045 const u32 lineCount = (WordWrap || MultiLine) ? BrokenText.size() : 1; 1045 const u32 lineCount = (WordWrap || MultiLine) ? BrokenText.size() : 1;
1046 1046
1047 core::stringw *txtLine=0; 1047 core::stringw *txtLine=0;
1048 s32 startPos=0; 1048 s32 startPos=0;
1049 x+=3; 1049 x+=3;
1050 1050
1051 for (u32 i=0; i < lineCount; ++i) 1051 for (u32 i=0; i < lineCount; ++i)
1052 { 1052 {
1053 setTextRect(i); 1053 setTextRect(i);
1054 if (i == 0 && y < CurrentTextRect.UpperLeftCorner.Y) 1054 if (i == 0 && y < CurrentTextRect.UpperLeftCorner.Y)
1055 y = CurrentTextRect.UpperLeftCorner.Y; 1055 y = CurrentTextRect.UpperLeftCorner.Y;
1056 if (i == lineCount - 1 && y > CurrentTextRect.LowerRightCorner.Y ) 1056 if (i == lineCount - 1 && y > CurrentTextRect.LowerRightCorner.Y )
1057 y = CurrentTextRect.LowerRightCorner.Y; 1057 y = CurrentTextRect.LowerRightCorner.Y;
1058 1058
1059 // is it inside this region? 1059 // is it inside this region?
1060 if (y >= CurrentTextRect.UpperLeftCorner.Y && y <= CurrentTextRect.LowerRightCorner.Y) 1060 if (y >= CurrentTextRect.UpperLeftCorner.Y && y <= CurrentTextRect.LowerRightCorner.Y)
1061 { 1061 {
1062 // we've found the clicked line 1062 // we've found the clicked line
1063 txtLine = (WordWrap || MultiLine) ? &BrokenText[i] : &Text; 1063 txtLine = (WordWrap || MultiLine) ? &BrokenText[i] : &Text;
1064 startPos = (WordWrap || MultiLine) ? BrokenTextPositions[i] : 0; 1064 startPos = (WordWrap || MultiLine) ? BrokenTextPositions[i] : 0;
1065 break; 1065 break;
1066 } 1066 }
1067 } 1067 }
1068 1068
1069 if (x < CurrentTextRect.UpperLeftCorner.X) 1069 if (x < CurrentTextRect.UpperLeftCorner.X)
1070 x = CurrentTextRect.UpperLeftCorner.X; 1070 x = CurrentTextRect.UpperLeftCorner.X;
1071 1071
1072 if ( !txtLine ) 1072 if ( !txtLine )
1073 return 0; 1073 return 0;
1074 1074
1075 s32 idx = font->getCharacterFromPos(txtLine->c_str(), x - CurrentTextRect.UpperLeftCorner.X); 1075 s32 idx = font->getCharacterFromPos(txtLine->c_str(), x - CurrentTextRect.UpperLeftCorner.X);
1076 1076
1077 // click was on or left of the line 1077 // click was on or left of the line
1078 if (idx != -1) 1078 if (idx != -1)
1079 return idx + startPos; 1079 return idx + startPos;
1080 1080
1081 // click was off the right edge of the line, go to end. 1081 // click was off the right edge of the line, go to end.
1082 return txtLine->size() + startPos; 1082 return txtLine->size() + startPos;
1083} 1083}
1084 1084
1085 1085
1086//! Breaks the single text line. 1086//! Breaks the single text line.
1087void CGUIEditBox::breakText() 1087void CGUIEditBox::breakText()
1088{ 1088{
1089 if ((!WordWrap && !MultiLine)) 1089 if ((!WordWrap && !MultiLine))
1090 return; 1090 return;
1091 1091
1092 BrokenText.clear(); // need to reallocate :/ 1092 BrokenText.clear(); // need to reallocate :/
1093 BrokenTextPositions.set_used(0); 1093 BrokenTextPositions.set_used(0);
1094 1094
1095 IGUIFont* font = getActiveFont(); 1095 IGUIFont* font = getActiveFont();
1096 if (!font) 1096 if (!font)
1097 return; 1097 return;
1098 1098
1099 LastBreakFont = font; 1099 LastBreakFont = font;
1100 1100
1101 core::stringw line; 1101 core::stringw line;
1102 core::stringw word; 1102 core::stringw word;
1103 core::stringw whitespace; 1103 core::stringw whitespace;
1104 s32 lastLineStart = 0; 1104 s32 lastLineStart = 0;
1105 s32 size = Text.size(); 1105 s32 size = Text.size();
1106 s32 length = 0; 1106 s32 length = 0;
1107 s32 elWidth = RelativeRect.getWidth() - 6; 1107 s32 elWidth = RelativeRect.getWidth() - 6;
1108 wchar_t c; 1108 wchar_t c;
1109 1109
1110 for (s32 i=0; i<size; ++i) 1110 for (s32 i=0; i<size; ++i)
1111 { 1111 {
1112 c = Text[i]; 1112 c = Text[i];
1113 bool lineBreak = false; 1113 bool lineBreak = false;
1114 1114
1115 if (c == L'\r') // Mac or Windows breaks 1115 if (c == L'\r') // Mac or Windows breaks
1116 { 1116 {
1117 lineBreak = true; 1117 lineBreak = true;
1118 c = 0; 1118 c = 0;
1119 if (Text[i+1] == L'\n') // Windows breaks 1119 if (Text[i+1] == L'\n') // Windows breaks
1120 { 1120 {
1121 // TODO: I (Michael) think that we shouldn't change the text given by the user for whatever reason. 1121 // TODO: I (Michael) think that we shouldn't change the text given by the user for whatever reason.
1122 // Instead rework the cursor positioning to be able to handle this (but not in stable release 1122 // Instead rework the cursor positioning to be able to handle this (but not in stable release
1123 // branch as users might already expect this behavior). 1123 // branch as users might already expect this behavior).
1124 Text.erase(i+1); 1124 Text.erase(i+1);
1125 --size; 1125 --size;
1126 if ( CursorPos > i ) 1126 if ( CursorPos > i )
1127 --CursorPos; 1127 --CursorPos;
1128 } 1128 }
1129 } 1129 }
1130 else if (c == L'\n') // Unix breaks 1130 else if (c == L'\n') // Unix breaks
1131 { 1131 {
1132 lineBreak = true; 1132 lineBreak = true;
1133 c = 0; 1133 c = 0;
1134 } 1134 }
1135 1135
1136 // don't break if we're not a multi-line edit box 1136 // don't break if we're not a multi-line edit box
1137 if (!MultiLine) 1137 if (!MultiLine)
1138 lineBreak = false; 1138 lineBreak = false;
1139 1139
1140 if (c == L' ' || c == 0 || i == (size-1)) 1140 if (c == L' ' || c == 0 || i == (size-1))
1141 { 1141 {
1142 // here comes the next whitespace, look if 1142 // here comes the next whitespace, look if
1143 // we can break the last word to the next line 1143 // we can break the last word to the next line
1144 // We also break whitespace, otherwise cursor would vanish beside the right border. 1144 // We also break whitespace, otherwise cursor would vanish beside the right border.
1145 s32 whitelgth = font->getDimension(whitespace.c_str()).Width; 1145 s32 whitelgth = font->getDimension(whitespace.c_str()).Width;
1146 s32 worldlgth = font->getDimension(word.c_str()).Width; 1146 s32 worldlgth = font->getDimension(word.c_str()).Width;
1147 1147
1148 if (WordWrap && length + worldlgth + whitelgth > elWidth && line.size() > 0) 1148 if (WordWrap && length + worldlgth + whitelgth > elWidth && line.size() > 0)
1149 { 1149 {
1150 // break to next line 1150 // break to next line
1151 length = worldlgth; 1151 length = worldlgth;
1152 BrokenText.push_back(line); 1152 BrokenText.push_back(line);
1153 BrokenTextPositions.push_back(lastLineStart); 1153 BrokenTextPositions.push_back(lastLineStart);
1154 lastLineStart = i - (s32)word.size(); 1154 lastLineStart = i - (s32)word.size();
1155 line = word; 1155 line = word;
1156 } 1156 }
1157 else 1157 else
1158 { 1158 {
1159 // add word to line 1159 // add word to line
1160 line += whitespace; 1160 line += whitespace;
1161 line += word; 1161 line += word;
1162 length += whitelgth + worldlgth; 1162 length += whitelgth + worldlgth;
1163 } 1163 }
1164 1164
1165 word = L""; 1165 word = L"";
1166 whitespace = L""; 1166 whitespace = L"";
1167 1167
1168 1168
1169 if ( c ) 1169 if ( c )
1170 whitespace += c; 1170 whitespace += c;
1171 1171
1172 // compute line break 1172 // compute line break
1173 if (lineBreak) 1173 if (lineBreak)
1174 { 1174 {
1175 line += whitespace; 1175 line += whitespace;
1176 line += word; 1176 line += word;
1177 BrokenText.push_back(line); 1177 BrokenText.push_back(line);
1178 BrokenTextPositions.push_back(lastLineStart); 1178 BrokenTextPositions.push_back(lastLineStart);
1179 lastLineStart = i+1; 1179 lastLineStart = i+1;
1180 line = L""; 1180 line = L"";
1181 word = L""; 1181 word = L"";
1182 whitespace = L""; 1182 whitespace = L"";
1183 length = 0; 1183 length = 0;
1184 } 1184 }
1185 } 1185 }
1186 else 1186 else
1187 { 1187 {
1188 // yippee this is a word.. 1188 // yippee this is a word..
1189 word += c; 1189 word += c;
1190 } 1190 }
1191 } 1191 }
1192 1192
1193 line += whitespace; 1193 line += whitespace;
1194 line += word; 1194 line += word;
1195 BrokenText.push_back(line); 1195 BrokenText.push_back(line);
1196 BrokenTextPositions.push_back(lastLineStart); 1196 BrokenTextPositions.push_back(lastLineStart);
1197} 1197}
1198 1198
1199// TODO: that function does interpret VAlign according to line-index (indexed line is placed on top-center-bottom) 1199// TODO: that function does interpret VAlign according to line-index (indexed line is placed on top-center-bottom)
1200// but HAlign according to line-width (pixels) and not by row. 1200// but HAlign according to line-width (pixels) and not by row.
1201// Intuitively I suppose HAlign handling is better as VScrollPos should handle the line-scrolling. 1201// Intuitively I suppose HAlign handling is better as VScrollPos should handle the line-scrolling.
1202// But please no one change this without also rewriting (and this time fucking testing!!!) autoscrolling (I noticed this when fixing the old autoscrolling). 1202// But please no one change this without also rewriting (and this time fucking testing!!!) autoscrolling (I noticed this when fixing the old autoscrolling).
1203void CGUIEditBox::setTextRect(s32 line) 1203void CGUIEditBox::setTextRect(s32 line)
1204{ 1204{
1205 if ( line < 0 ) 1205 if ( line < 0 )
1206 return; 1206 return;
1207 1207
1208 IGUIFont* font = getActiveFont(); 1208 IGUIFont* font = getActiveFont();
1209 if (!font) 1209 if (!font)
1210 return; 1210 return;
1211 1211
1212 core::dimension2du d; 1212 core::dimension2du d;
1213 1213
1214 // get text dimension 1214 // get text dimension
1215 const u32 lineCount = (WordWrap || MultiLine) ? BrokenText.size() : 1; 1215 const u32 lineCount = (WordWrap || MultiLine) ? BrokenText.size() : 1;
1216 if (WordWrap || MultiLine) 1216 if (WordWrap || MultiLine)
1217 { 1217 {
1218 d = font->getDimension(BrokenText[line].c_str()); 1218 d = font->getDimension(BrokenText[line].c_str());
1219 } 1219 }
1220 else 1220 else
1221 { 1221 {
1222 d = font->getDimension(Text.c_str()); 1222 d = font->getDimension(Text.c_str());
1223 d.Height = AbsoluteRect.getHeight(); 1223 d.Height = AbsoluteRect.getHeight();
1224 } 1224 }
1225 d.Height += font->getKerningHeight(); 1225 d.Height += font->getKerningHeight();
1226 1226
1227 // justification 1227 // justification
1228 switch (HAlign) 1228 switch (HAlign)
1229 { 1229 {
1230 case EGUIA_CENTER: 1230 case EGUIA_CENTER:
1231 // align to h centre 1231 // align to h centre
1232 CurrentTextRect.UpperLeftCorner.X = (FrameRect.getWidth()/2) - (d.Width/2); 1232 CurrentTextRect.UpperLeftCorner.X = (FrameRect.getWidth()/2) - (d.Width/2);
1233 CurrentTextRect.LowerRightCorner.X = (FrameRect.getWidth()/2) + (d.Width/2); 1233 CurrentTextRect.LowerRightCorner.X = (FrameRect.getWidth()/2) + (d.Width/2);
1234 break; 1234 break;
1235 case EGUIA_LOWERRIGHT: 1235 case EGUIA_LOWERRIGHT:
1236 // align to right edge 1236 // align to right edge
1237 CurrentTextRect.UpperLeftCorner.X = FrameRect.getWidth() - d.Width; 1237 CurrentTextRect.UpperLeftCorner.X = FrameRect.getWidth() - d.Width;
1238 CurrentTextRect.LowerRightCorner.X = FrameRect.getWidth(); 1238 CurrentTextRect.LowerRightCorner.X = FrameRect.getWidth();
1239 break; 1239 break;
1240 default: 1240 default:
1241 // align to left edge 1241 // align to left edge
1242 CurrentTextRect.UpperLeftCorner.X = 0; 1242 CurrentTextRect.UpperLeftCorner.X = 0;
1243 CurrentTextRect.LowerRightCorner.X = d.Width; 1243 CurrentTextRect.LowerRightCorner.X = d.Width;
1244 1244
1245 } 1245 }
1246 1246
1247 switch (VAlign) 1247 switch (VAlign)
1248 { 1248 {
1249 case EGUIA_CENTER: 1249 case EGUIA_CENTER:
1250 // align to v centre 1250 // align to v centre
1251 CurrentTextRect.UpperLeftCorner.Y = 1251 CurrentTextRect.UpperLeftCorner.Y =
1252 (FrameRect.getHeight()/2) - (lineCount*d.Height)/2 + d.Height*line; 1252 (FrameRect.getHeight()/2) - (lineCount*d.Height)/2 + d.Height*line;
1253 break; 1253 break;
1254 case EGUIA_LOWERRIGHT: 1254 case EGUIA_LOWERRIGHT:
1255 // align to bottom edge 1255 // align to bottom edge
1256 CurrentTextRect.UpperLeftCorner.Y = 1256 CurrentTextRect.UpperLeftCorner.Y =
1257 FrameRect.getHeight() - lineCount*d.Height + d.Height*line; 1257 FrameRect.getHeight() - lineCount*d.Height + d.Height*line;
1258 break; 1258 break;
1259 default: 1259 default:
1260 // align to top edge 1260 // align to top edge
1261 CurrentTextRect.UpperLeftCorner.Y = d.Height*line; 1261 CurrentTextRect.UpperLeftCorner.Y = d.Height*line;
1262 break; 1262 break;
1263 } 1263 }
1264 1264
1265 CurrentTextRect.UpperLeftCorner.X -= HScrollPos; 1265 CurrentTextRect.UpperLeftCorner.X -= HScrollPos;
1266 CurrentTextRect.LowerRightCorner.X -= HScrollPos; 1266 CurrentTextRect.LowerRightCorner.X -= HScrollPos;
1267 CurrentTextRect.UpperLeftCorner.Y -= VScrollPos; 1267 CurrentTextRect.UpperLeftCorner.Y -= VScrollPos;
1268 CurrentTextRect.LowerRightCorner.Y = CurrentTextRect.UpperLeftCorner.Y + d.Height; 1268 CurrentTextRect.LowerRightCorner.Y = CurrentTextRect.UpperLeftCorner.Y + d.Height;
1269 1269
1270 CurrentTextRect += FrameRect.UpperLeftCorner; 1270 CurrentTextRect += FrameRect.UpperLeftCorner;
1271 1271
1272} 1272}
1273 1273
1274 1274
1275s32 CGUIEditBox::getLineFromPos(s32 pos) 1275s32 CGUIEditBox::getLineFromPos(s32 pos)
1276{ 1276{
1277 if (!WordWrap && !MultiLine) 1277 if (!WordWrap && !MultiLine)
1278 return 0; 1278 return 0;
1279 1279
1280 s32 i=0; 1280 s32 i=0;
1281 while (i < (s32)BrokenTextPositions.size()) 1281 while (i < (s32)BrokenTextPositions.size())
1282 { 1282 {
1283 if (BrokenTextPositions[i] > pos) 1283 if (BrokenTextPositions[i] > pos)
1284 return i-1; 1284 return i-1;
1285 ++i; 1285 ++i;
1286 } 1286 }
1287 return (s32)BrokenTextPositions.size() - 1; 1287 return (s32)BrokenTextPositions.size() - 1;
1288} 1288}
1289 1289
1290 1290
1291void CGUIEditBox::inputChar(wchar_t c) 1291void CGUIEditBox::inputChar(wchar_t c)
1292{ 1292{
1293 if (!isEnabled()) 1293 if (!isEnabled())
1294 return; 1294 return;
1295 1295
1296 if (c != 0) 1296 if (c != 0)
1297 { 1297 {
1298 if (Text.size() < Max || Max == 0) 1298 if (Text.size() < Max || Max == 0)
1299 { 1299 {
1300 core::stringw s; 1300 core::stringw s;
1301 1301
1302 if (MarkBegin != MarkEnd) 1302 if (MarkBegin != MarkEnd)
1303 { 1303 {
1304 // replace marked text 1304 // replace marked text
1305 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd; 1305 const s32 realmbgn = MarkBegin < MarkEnd ? MarkBegin : MarkEnd;
1306 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin; 1306 const s32 realmend = MarkBegin < MarkEnd ? MarkEnd : MarkBegin;
1307 1307
1308 s = Text.subString(0, realmbgn); 1308 s = Text.subString(0, realmbgn);
1309 s.append(c); 1309 s.append(c);
1310 s.append( Text.subString(realmend, Text.size()-realmend) ); 1310 s.append( Text.subString(realmend, Text.size()-realmend) );
1311 Text = s; 1311 Text = s;
1312 CursorPos = realmbgn+1; 1312 CursorPos = realmbgn+1;
1313 } 1313 }
1314 else 1314 else
1315 { 1315 {
1316 // add new character 1316 // add new character
1317 s = Text.subString(0, CursorPos); 1317 s = Text.subString(0, CursorPos);
1318 s.append(c); 1318 s.append(c);
1319 s.append( Text.subString(CursorPos, Text.size()-CursorPos) ); 1319 s.append( Text.subString(CursorPos, Text.size()-CursorPos) );
1320 Text = s; 1320 Text = s;
1321 ++CursorPos; 1321 ++CursorPos;
1322 } 1322 }
1323 1323
1324 BlinkStartTime = os::Timer::getTime(); 1324 BlinkStartTime = os::Timer::getTime();
1325 setTextMarkers(0, 0); 1325 setTextMarkers(0, 0);
1326 } 1326 }
1327 } 1327 }
1328 breakText(); 1328 breakText();
1329 calculateScrollPos(); 1329 calculateScrollPos();
1330 sendGuiEvent(EGET_EDITBOX_CHANGED); 1330 sendGuiEvent(EGET_EDITBOX_CHANGED);
1331} 1331}
1332 1332
1333// calculate autoscroll 1333// calculate autoscroll
1334void CGUIEditBox::calculateScrollPos() 1334void CGUIEditBox::calculateScrollPos()
1335{ 1335{
1336 if (!AutoScroll) 1336 if (!AutoScroll)
1337 return; 1337 return;
1338 1338
1339 IGUISkin* skin = Environment->getSkin(); 1339 IGUISkin* skin = Environment->getSkin();
1340 if (!skin) 1340 if (!skin)
1341 return; 1341 return;
1342 IGUIFont* font = OverrideFont ? OverrideFont : skin->getFont(); 1342 IGUIFont* font = OverrideFont ? OverrideFont : skin->getFont();
1343 if (!font) 1343 if (!font)
1344 return; 1344 return;
1345 1345
1346 s32 cursLine = getLineFromPos(CursorPos); 1346 s32 cursLine = getLineFromPos(CursorPos);
1347 if ( cursLine < 0 ) 1347 if ( cursLine < 0 )
1348 return; 1348 return;
1349 setTextRect(cursLine); 1349 setTextRect(cursLine);
1350 const bool hasBrokenText = MultiLine || WordWrap; 1350 const bool hasBrokenText = MultiLine || WordWrap;
1351 1351
1352 // Check horizonal scrolling 1352 // Check horizonal scrolling
1353 // NOTE: Calculations different to vertical scrolling because setTextRect interprets VAlign relative to line but HAlign not relative to row 1353 // NOTE: Calculations different to vertical scrolling because setTextRect interprets VAlign relative to line but HAlign not relative to row
1354 { 1354 {
1355 // get cursor position 1355 // get cursor position
1356 IGUIFont* font = getActiveFont(); 1356 IGUIFont* font = getActiveFont();
1357 if (!font) 1357 if (!font)
1358 return; 1358 return;
1359 1359
1360 // get cursor area 1360 // get cursor area
1361 irr::u32 cursorWidth = font->getDimension(L"_").Width; 1361 irr::u32 cursorWidth = font->getDimension(L"_").Width;
1362 core::stringw *txtLine = hasBrokenText ? &BrokenText[cursLine] : &Text; 1362 core::stringw *txtLine = hasBrokenText ? &BrokenText[cursLine] : &Text;
1363 s32 cPos = hasBrokenText ? CursorPos - BrokenTextPositions[cursLine] : CursorPos; // column 1363 s32 cPos = hasBrokenText ? CursorPos - BrokenTextPositions[cursLine] : CursorPos; // column
1364 s32 cStart = font->getDimension(txtLine->subString(0, cPos).c_str()).Width; // pixels from text-start 1364 s32 cStart = font->getDimension(txtLine->subString(0, cPos).c_str()).Width; // pixels from text-start
1365 s32 cEnd = cStart + cursorWidth; 1365 s32 cEnd = cStart + cursorWidth;
1366 s32 txtWidth = font->getDimension(txtLine->c_str()).Width; 1366 s32 txtWidth = font->getDimension(txtLine->c_str()).Width;
1367 1367
1368 if ( txtWidth < FrameRect.getWidth() ) 1368 if ( txtWidth < FrameRect.getWidth() )
1369 { 1369 {
1370 // TODO: Needs a clean left and right gap removal depending on HAlign, similar to vertical scrolling tests for top/bottom. 1370 // TODO: Needs a clean left and right gap removal depending on HAlign, similar to vertical scrolling tests for top/bottom.
1371 // This check just fixes the case where it was most noticable (text smaller than clipping area). 1371 // This check just fixes the case where it was most noticable (text smaller than clipping area).
1372 1372
1373 HScrollPos = 0; 1373 HScrollPos = 0;
1374 setTextRect(cursLine); 1374 setTextRect(cursLine);
1375 } 1375 }
1376 1376
1377 if ( CurrentTextRect.UpperLeftCorner.X+cStart < FrameRect.UpperLeftCorner.X ) 1377 if ( CurrentTextRect.UpperLeftCorner.X+cStart < FrameRect.UpperLeftCorner.X )
1378 { 1378 {
1379 // cursor to the left of the clipping area 1379 // cursor to the left of the clipping area
1380 HScrollPos -= FrameRect.UpperLeftCorner.X-(CurrentTextRect.UpperLeftCorner.X+cStart); 1380 HScrollPos -= FrameRect.UpperLeftCorner.X-(CurrentTextRect.UpperLeftCorner.X+cStart);
1381 setTextRect(cursLine); 1381 setTextRect(cursLine);
1382 1382
1383 // TODO: should show more characters to the left when we're scrolling left 1383 // TODO: should show more characters to the left when we're scrolling left
1384 // and the cursor reaches the border. 1384 // and the cursor reaches the border.
1385 } 1385 }
1386 else if ( CurrentTextRect.UpperLeftCorner.X+cEnd > FrameRect.LowerRightCorner.X) 1386 else if ( CurrentTextRect.UpperLeftCorner.X+cEnd > FrameRect.LowerRightCorner.X)
1387 { 1387 {
1388 // cursor to the right of the clipping area 1388 // cursor to the right of the clipping area
1389 HScrollPos += (CurrentTextRect.UpperLeftCorner.X+cEnd)-FrameRect.LowerRightCorner.X; 1389 HScrollPos += (CurrentTextRect.UpperLeftCorner.X+cEnd)-FrameRect.LowerRightCorner.X;
1390 setTextRect(cursLine); 1390 setTextRect(cursLine);
1391 } 1391 }
1392 } 1392 }
1393 1393
1394 // calculate vertical scrolling 1394 // calculate vertical scrolling
1395 if (hasBrokenText) 1395 if (hasBrokenText)
1396 { 1396 {
1397 irr::u32 lineHeight = font->getDimension(L"A").Height + font->getKerningHeight(); 1397 irr::u32 lineHeight = font->getDimension(L"A").Height + font->getKerningHeight();
1398 // only up to 1 line fits? 1398 // only up to 1 line fits?
1399 if ( lineHeight >= (irr::u32)FrameRect.getHeight() ) 1399 if ( lineHeight >= (irr::u32)FrameRect.getHeight() )
1400 { 1400 {
1401 VScrollPos = 0; 1401 VScrollPos = 0;
1402 setTextRect(cursLine); 1402 setTextRect(cursLine);
1403 s32 unscrolledPos = CurrentTextRect.UpperLeftCorner.Y; 1403 s32 unscrolledPos = CurrentTextRect.UpperLeftCorner.Y;
1404 s32 pivot = FrameRect.UpperLeftCorner.Y; 1404 s32 pivot = FrameRect.UpperLeftCorner.Y;
1405 switch (VAlign) 1405 switch (VAlign)
1406 { 1406 {
1407 case EGUIA_CENTER: 1407 case EGUIA_CENTER:
1408 pivot += FrameRect.getHeight()/2; 1408 pivot += FrameRect.getHeight()/2;
1409 unscrolledPos += lineHeight/2; 1409 unscrolledPos += lineHeight/2;
1410 break; 1410 break;
1411 case EGUIA_LOWERRIGHT: 1411 case EGUIA_LOWERRIGHT:
1412 pivot += FrameRect.getHeight(); 1412 pivot += FrameRect.getHeight();
1413 unscrolledPos += lineHeight; 1413 unscrolledPos += lineHeight;
1414 break; 1414 break;
1415 default: 1415 default:
1416 break; 1416 break;
1417 } 1417 }
1418 VScrollPos = unscrolledPos-pivot; 1418 VScrollPos = unscrolledPos-pivot;
1419 setTextRect(cursLine); 1419 setTextRect(cursLine);
1420 } 1420 }
1421 else 1421 else
1422 { 1422 {
1423 // First 2 checks are necessary when people delete lines 1423 // First 2 checks are necessary when people delete lines
1424 setTextRect(0); 1424 setTextRect(0);
1425 if ( CurrentTextRect.UpperLeftCorner.Y > FrameRect.UpperLeftCorner.Y && VAlign != EGUIA_LOWERRIGHT) 1425 if ( CurrentTextRect.UpperLeftCorner.Y > FrameRect.UpperLeftCorner.Y && VAlign != EGUIA_LOWERRIGHT)
1426 { 1426 {
1427 // first line is leaving a gap on top 1427 // first line is leaving a gap on top
1428 VScrollPos = 0; 1428 VScrollPos = 0;
1429 } 1429 }
1430 else if (VAlign != EGUIA_UPPERLEFT) 1430 else if (VAlign != EGUIA_UPPERLEFT)
1431 { 1431 {
1432 u32 lastLine = BrokenTextPositions.empty() ? 0 : BrokenTextPositions.size()-1; 1432 u32 lastLine = BrokenTextPositions.empty() ? 0 : BrokenTextPositions.size()-1;
1433 setTextRect(lastLine); 1433 setTextRect(lastLine);
1434 if ( CurrentTextRect.LowerRightCorner.Y < FrameRect.LowerRightCorner.Y) 1434 if ( CurrentTextRect.LowerRightCorner.Y < FrameRect.LowerRightCorner.Y)
1435 { 1435 {
1436 // last line is leaving a gap on bottom 1436 // last line is leaving a gap on bottom
1437 VScrollPos -= FrameRect.LowerRightCorner.Y-CurrentTextRect.LowerRightCorner.Y; 1437 VScrollPos -= FrameRect.LowerRightCorner.Y-CurrentTextRect.LowerRightCorner.Y;
1438 } 1438 }
1439 } 1439 }
1440 1440
1441 setTextRect(cursLine); 1441 setTextRect(cursLine);
1442 if ( CurrentTextRect.UpperLeftCorner.Y < FrameRect.UpperLeftCorner.Y ) 1442 if ( CurrentTextRect.UpperLeftCorner.Y < FrameRect.UpperLeftCorner.Y )
1443 { 1443 {
1444 // text above valid area 1444 // text above valid area
1445 VScrollPos -= FrameRect.UpperLeftCorner.Y-CurrentTextRect.UpperLeftCorner.Y; 1445 VScrollPos -= FrameRect.UpperLeftCorner.Y-CurrentTextRect.UpperLeftCorner.Y;
1446 setTextRect(cursLine); 1446 setTextRect(cursLine);
1447 } 1447 }
1448 else if ( CurrentTextRect.LowerRightCorner.Y > FrameRect.LowerRightCorner.Y) 1448 else if ( CurrentTextRect.LowerRightCorner.Y > FrameRect.LowerRightCorner.Y)
1449 { 1449 {
1450 // text below valid area 1450 // text below valid area
1451 VScrollPos += CurrentTextRect.LowerRightCorner.Y-FrameRect.LowerRightCorner.Y; 1451 VScrollPos += CurrentTextRect.LowerRightCorner.Y-FrameRect.LowerRightCorner.Y;
1452 setTextRect(cursLine); 1452 setTextRect(cursLine);
1453 } 1453 }
1454 } 1454 }
1455 } 1455 }
1456} 1456}
1457 1457
1458void CGUIEditBox::calculateFrameRect() 1458void CGUIEditBox::calculateFrameRect()
1459{ 1459{
1460 FrameRect = AbsoluteRect; 1460 FrameRect = AbsoluteRect;
1461 IGUISkin *skin = 0; 1461 IGUISkin *skin = 0;
1462 if (Environment) 1462 if (Environment)
1463 skin = Environment->getSkin(); 1463 skin = Environment->getSkin();
1464 if (Border && skin) 1464 if (Border && skin)
1465 { 1465 {
1466 FrameRect.UpperLeftCorner.X += skin->getSize(EGDS_TEXT_DISTANCE_X)+1; 1466 FrameRect.UpperLeftCorner.X += skin->getSize(EGDS_TEXT_DISTANCE_X)+1;
1467 FrameRect.UpperLeftCorner.Y += skin->getSize(EGDS_TEXT_DISTANCE_Y)+1; 1467 FrameRect.UpperLeftCorner.Y += skin->getSize(EGDS_TEXT_DISTANCE_Y)+1;
1468 FrameRect.LowerRightCorner.X -= skin->getSize(EGDS_TEXT_DISTANCE_X)+1; 1468 FrameRect.LowerRightCorner.X -= skin->getSize(EGDS_TEXT_DISTANCE_X)+1;
1469 FrameRect.LowerRightCorner.Y -= skin->getSize(EGDS_TEXT_DISTANCE_Y)+1; 1469 FrameRect.LowerRightCorner.Y -= skin->getSize(EGDS_TEXT_DISTANCE_Y)+1;
1470 } 1470 }
1471} 1471}
1472 1472
1473//! set text markers 1473//! set text markers
1474void CGUIEditBox::setTextMarkers(s32 begin, s32 end) 1474void CGUIEditBox::setTextMarkers(s32 begin, s32 end)
1475{ 1475{
1476 if ( begin != MarkBegin || end != MarkEnd ) 1476 if ( begin != MarkBegin || end != MarkEnd )
1477 { 1477 {
1478 MarkBegin = begin; 1478 MarkBegin = begin;
1479 MarkEnd = end; 1479 MarkEnd = end;
1480 sendGuiEvent(EGET_EDITBOX_MARKING_CHANGED); 1480 sendGuiEvent(EGET_EDITBOX_MARKING_CHANGED);
1481 } 1481 }
1482} 1482}
1483 1483
1484//! send some gui event to parent 1484//! send some gui event to parent
1485void CGUIEditBox::sendGuiEvent(EGUI_EVENT_TYPE type) 1485void CGUIEditBox::sendGuiEvent(EGUI_EVENT_TYPE type)
1486{ 1486{
1487 if ( Parent ) 1487 if ( Parent )
1488 { 1488 {
1489 SEvent e; 1489 SEvent e;
1490 e.EventType = EET_GUI_EVENT; 1490 e.EventType = EET_GUI_EVENT;
1491 e.GUIEvent.Caller = this; 1491 e.GUIEvent.Caller = this;
1492 e.GUIEvent.Element = 0; 1492 e.GUIEvent.Element = 0;
1493 e.GUIEvent.EventType = type; 1493 e.GUIEvent.EventType = type;
1494 1494
1495 Parent->OnEvent(e); 1495 Parent->OnEvent(e);
1496 } 1496 }
1497} 1497}
1498 1498
1499//! Writes attributes of the element. 1499//! Writes attributes of the element.
1500void CGUIEditBox::serializeAttributes(io::IAttributes* out, io::SAttributeReadWriteOptions* options=0) const 1500void CGUIEditBox::serializeAttributes(io::IAttributes* out, io::SAttributeReadWriteOptions* options=0) const
1501{ 1501{
1502 // IGUIEditBox::serializeAttributes(out,options); 1502 // IGUIEditBox::serializeAttributes(out,options);
1503 1503
1504 out->addBool ("Border", Border); 1504 out->addBool ("Border", Border);
1505 out->addBool ("Background", Background); 1505 out->addBool ("Background", Background);
1506 out->addBool ("OverrideColorEnabled", OverrideColorEnabled ); 1506 out->addBool ("OverrideColorEnabled", OverrideColorEnabled );
1507 out->addColor ("OverrideColor", OverrideColor); 1507 out->addColor ("OverrideColor", OverrideColor);
1508 // out->addFont("OverrideFont", OverrideFont); 1508 // out->addFont("OverrideFont", OverrideFont);
1509 out->addInt ("MaxChars", Max); 1509 out->addInt ("MaxChars", Max);
1510 out->addBool ("WordWrap", WordWrap); 1510 out->addBool ("WordWrap", WordWrap);
1511 out->addBool ("MultiLine", MultiLine); 1511 out->addBool ("MultiLine", MultiLine);
1512 out->addBool ("AutoScroll", AutoScroll); 1512 out->addBool ("AutoScroll", AutoScroll);
1513 out->addBool ("PasswordBox", PasswordBox); 1513 out->addBool ("PasswordBox", PasswordBox);
1514 core::stringw ch = L" "; 1514 core::stringw ch = L" ";
1515 ch[0] = PasswordChar; 1515 ch[0] = PasswordChar;
1516 out->addString("PasswordChar", ch.c_str()); 1516 out->addString("PasswordChar", ch.c_str());
1517 out->addEnum ("HTextAlign", HAlign, GUIAlignmentNames); 1517 out->addEnum ("HTextAlign", HAlign, GUIAlignmentNames);
1518 out->addEnum ("VTextAlign", VAlign, GUIAlignmentNames); 1518 out->addEnum ("VTextAlign", VAlign, GUIAlignmentNames);
1519 1519
1520 IGUIEditBox::serializeAttributes(out,options); 1520 IGUIEditBox::serializeAttributes(out,options);
1521} 1521}
1522 1522
1523 1523
1524//! Reads attributes of the element 1524//! Reads attributes of the element
1525void CGUIEditBox::deserializeAttributes(io::IAttributes* in, io::SAttributeReadWriteOptions* options=0) 1525void CGUIEditBox::deserializeAttributes(io::IAttributes* in, io::SAttributeReadWriteOptions* options=0)
1526{ 1526{
1527 IGUIEditBox::deserializeAttributes(in,options); 1527 IGUIEditBox::deserializeAttributes(in,options);
1528 1528
1529 setDrawBorder( in->getAttributeAsBool("Border") ); 1529 setDrawBorder( in->getAttributeAsBool("Border") );
1530 setDrawBackground( in->getAttributeAsBool("Background") ); 1530 setDrawBackground( in->getAttributeAsBool("Background") );
1531 setOverrideColor(in->getAttributeAsColor("OverrideColor")); 1531 setOverrideColor(in->getAttributeAsColor("OverrideColor"));
1532 enableOverrideColor(in->getAttributeAsBool("OverrideColorEnabled")); 1532 enableOverrideColor(in->getAttributeAsBool("OverrideColorEnabled"));
1533 setMax(in->getAttributeAsInt("MaxChars")); 1533 setMax(in->getAttributeAsInt("MaxChars"));
1534 setWordWrap(in->getAttributeAsBool("WordWrap")); 1534 setWordWrap(in->getAttributeAsBool("WordWrap"));
1535 setMultiLine(in->getAttributeAsBool("MultiLine")); 1535 setMultiLine(in->getAttributeAsBool("MultiLine"));
1536 setAutoScroll(in->getAttributeAsBool("AutoScroll")); 1536 setAutoScroll(in->getAttributeAsBool("AutoScroll"));
1537 core::stringw ch = in->getAttributeAsStringW("PasswordChar"); 1537 core::stringw ch = in->getAttributeAsStringW("PasswordChar");
1538 1538
1539 if (!ch.size()) 1539 if (!ch.size())
1540 setPasswordBox(in->getAttributeAsBool("PasswordBox")); 1540 setPasswordBox(in->getAttributeAsBool("PasswordBox"));
1541 else 1541 else
1542 setPasswordBox(in->getAttributeAsBool("PasswordBox"), ch[0]); 1542 setPasswordBox(in->getAttributeAsBool("PasswordBox"), ch[0]);
1543 1543
1544 setTextAlignment( (EGUI_ALIGNMENT) in->getAttributeAsEnumeration("HTextAlign", GUIAlignmentNames), 1544 setTextAlignment( (EGUI_ALIGNMENT) in->getAttributeAsEnumeration("HTextAlign", GUIAlignmentNames),
1545 (EGUI_ALIGNMENT) in->getAttributeAsEnumeration("VTextAlign", GUIAlignmentNames)); 1545 (EGUI_ALIGNMENT) in->getAttributeAsEnumeration("VTextAlign", GUIAlignmentNames));
1546 1546
1547 // setOverrideFont(in->getAttributeAsFont("OverrideFont")); 1547 // setOverrideFont(in->getAttributeAsFont("OverrideFont"));
1548} 1548}
1549 1549
1550 1550
1551} // end namespace gui 1551} // end namespace gui
1552} // end namespace irr 1552} // end namespace irr
1553 1553
1554#endif // _IRR_COMPILE_WITH_GUI_ 1554#endif // _IRR_COMPILE_WITH_GUI_
1555 1555