TickHook: Fix crash when TickHook isn't set.
[gemrb.git] / gemrb / core / GUI / TextEdit.cpp
blob2b6998106e837cac187dbd12eae6c8486b46d43e
1 /* GemRB - Infinity Engine Emulator
2 * Copyright (C) 2003 The GemRB Project
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License
6 * as published by the Free Software Foundation; either version 2
7 * of the License, or (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
22 #include "GUI/TextEdit.h"
24 #include "GameData.h"
25 #include "Interface.h"
26 #include "Palette.h"
27 #include "Video.h"
29 TextEdit::TextEdit(unsigned short maxLength, unsigned short px, unsigned short py)
31 max = maxLength;
32 FontPosX = px;
33 FontPosY = py;
34 Buffer = ( unsigned char * ) malloc( max + 1 );
35 font = NULL;
36 Cursor = NULL;
37 Back = NULL;
38 CurPos = 0;
39 Buffer[0] = 0;
40 ResetEventHandler( EditOnChange );
41 ResetEventHandler( EditOnDone );
42 ResetEventHandler( EditOnCancel );
43 Color white = {0xff, 0xff, 0xff, 0x00}, black = {0x00, 0x00, 0x00, 0x00};
44 palette = core->CreatePalette( white, black );
47 TextEdit::~TextEdit(void)
49 Video *video = core->GetVideoDriver();
50 gamedata->FreePalette( palette );
51 free( Buffer );
52 video->FreeSprite( Back );
53 video->FreeSprite( Cursor );
56 /** Draws the Control on the Output Display */
57 void TextEdit::Draw(unsigned short x, unsigned short y)
59 if (!Changed && !(Owner->Flags&WF_FLOAT)) {
60 return;
62 Changed = false;
63 if (Back) {
64 core->GetVideoDriver()->BlitSprite( Back, x + XPos, y + YPos, true );
67 if (!font)
68 return;
70 //The aligning of textedit fields is done by absolute positioning (FontPosX, FontPosY)
71 if (hasFocus) {
72 font->Print( Region( x + XPos + FontPosX, y + YPos + FontPosY, Width, Height ), Buffer,
73 palette, IE_FONT_ALIGN_LEFT | IE_FONT_ALIGN_TOP,
74 true, NULL, Cursor, CurPos );
75 } else {
76 font->Print( Region( x + XPos + FontPosX, y + YPos + FontPosY, Width, Height ), Buffer,
77 palette, IE_FONT_ALIGN_LEFT | IE_FONT_ALIGN_TOP, true );
81 /** Set Font */
82 void TextEdit::SetFont(Font* f)
84 if (f != NULL) {
85 font = f;
86 Changed = true;
87 return;
89 printMessage("TextEdit","Invalid font set!\n", LIGHT_RED);
92 Font *TextEdit::GetFont() { return font; }
94 /** Set Cursor */
95 void TextEdit::SetCursor(Sprite2D* cur)
97 core->GetVideoDriver()->FreeSprite( Cursor );
98 if (cur != NULL) {
99 Cursor = cur;
101 Changed = true;
104 /** Set BackGround */
105 void TextEdit::SetBackGround(Sprite2D* back)
107 //if 'back' is NULL then no BackGround will be drawn
108 if (Back)
109 core->GetVideoDriver()->FreeSprite(Back);
110 Back = back;
111 Changed = true;
114 /** Key Press Event */
115 void TextEdit::OnKeyPress(unsigned char Key, unsigned short /*Mod*/)
117 if (Key >= 0x20) {
118 if (Value && ( (Key<'0') || (Key>'9') ) )
119 return;
120 Owner->Invalidate();
121 Changed = true;
122 int len = ( int ) strlen( ( char* ) Buffer );
123 if (len + 1 < max) {
124 for (int i = len; i > CurPos; i--) {
125 Buffer[i] = Buffer[i - 1];
127 Buffer[CurPos] = Key;
128 Buffer[len + 1] = 0;
129 CurPos++;
131 RunEventHandler( EditOnChange );
134 /** Special Key Press */
135 void TextEdit::OnSpecialKeyPress(unsigned char Key)
137 int len;
139 Owner->Invalidate();
140 Changed = true;
141 switch (Key) {
142 case GEM_HOME:
143 CurPos = 0;
144 break;
145 case GEM_END:
146 CurPos = (ieWord) strlen( (char * ) Buffer);
147 break;
148 case GEM_LEFT:
149 if (CurPos > 0)
150 CurPos--;
151 break;
152 case GEM_RIGHT:
153 len = ( int ) strlen( ( char * ) Buffer );
154 if (CurPos < len) {
155 CurPos++;
157 break;
158 case GEM_DELETE:
159 len = ( int ) strlen( ( char * ) Buffer );
160 if (CurPos < len) {
161 for (int i = CurPos; i < len; i++) {
162 Buffer[i] = Buffer[i + 1];
165 break;
166 case GEM_BACKSP:
167 if (CurPos != 0) {
168 int len = ( int ) strlen( ( char* ) Buffer );
169 for (int i = CurPos; i < len; i++) {
170 Buffer[i - 1] = Buffer[i];
172 Buffer[len - 1] = 0;
173 CurPos--;
175 break;
176 case GEM_RETURN:
177 RunEventHandler( EditOnDone );
178 return;
181 RunEventHandler( EditOnChange );
184 /** Sets the Text of the current control */
185 int TextEdit::SetText(const char* string, int /*pos*/)
187 strncpy( ( char * ) Buffer, string, max );
188 Buffer[max]=0;
189 CurPos = (ieWord) strlen((char *) Buffer);
190 if (Owner) {
191 Owner->Invalidate();
193 return 0;
196 void TextEdit::SetBufferLength(ieWord buflen)
198 if(buflen<1) return;
199 if(buflen!=max) {
200 Buffer = (unsigned char *) realloc(Buffer, buflen+1);
201 max=(ieWord) buflen;
202 Buffer[max]=0;
206 /** Simply returns the pointer to the text, don't modify it! */
207 const char* TextEdit::QueryText()
209 return ( const char * ) Buffer;
212 bool TextEdit::SetEvent(int eventType, EventHandler handler)
214 Changed = true;
216 switch (eventType) {
217 case IE_GUI_EDIT_ON_CHANGE:
218 EditOnChange = handler;
219 break;
220 case IE_GUI_EDIT_ON_DONE:
221 EditOnDone = handler;
222 break;
223 case IE_GUI_EDIT_ON_CANCEL:
224 EditOnCancel = handler;
225 break;
226 default:
227 return false;
230 return true;