]> git.saurik.com Git - wxWidgets.git/blame - src/os2/textctrl.cpp
new wxASSERT implementation using wxAssert() helper function
[wxWidgets.git] / src / os2 / textctrl.cpp
CommitLineData
0e320a79
DW
1/////////////////////////////////////////////////////////////////////////////
2// Name: textctrl.cpp
3// Purpose: wxTextCtrl
d90895ac 4// Author: David Webster
0e320a79 5// Modified by:
d90895ac 6// Created: 10/17/99
0e320a79 7// RCS-ID: $Id$
d90895ac
DW
8// Copyright: (c) David Webster
9// Licence: wxWindows licence
0e320a79
DW
10/////////////////////////////////////////////////////////////////////////////
11
d90895ac
DW
12// ----------------------------------------------------------------------------
13// headers
14// ----------------------------------------------------------------------------
15
16// For compilers that support precompilation, includes "wx.h".
17#include "wx/wxprec.h"
18
19#ifndef WX_PRECOMP
20 #include "wx/textctrl.h"
19193a2c 21 #include "wx/scrolwin.h"
d90895ac
DW
22 #include "wx/settings.h"
23 #include "wx/brush.h"
24 #include "wx/utils.h"
25 #include "wx/log.h"
0e320a79
DW
26#endif
27
d90895ac
DW
28#if wxUSE_CLIPBOARD
29 #include "wx/app.h"
30 #include "wx/clipbrd.h"
31#endif
0e320a79 32
d90895ac
DW
33#include "wx/textfile.h"
34
35#include "wx/os2/private.h"
36
37#include <string.h>
38#include <stdlib.h>
39#include <sys/types.h>
0e320a79 40
d90895ac
DW
41#if wxUSE_IOSTREAMH
42# include <fstream.h>
0e320a79 43#else
d90895ac 44# include <fstream>
0e320a79
DW
45#endif
46
19193a2c 47#if !defined(MLE_INDEX)
a92d9721
SN
48#define MLE_INDEX 0
49#define MLE_RGB 1
50#endif
51
d90895ac
DW
52
53// ----------------------------------------------------------------------------
54// event tables and other macros
55// ----------------------------------------------------------------------------
56
0e320a79
DW
57IMPLEMENT_DYNAMIC_CLASS(wxTextCtrl, wxControl)
58
59BEGIN_EVENT_TABLE(wxTextCtrl, wxControl)
d90895ac
DW
60 EVT_CHAR(wxTextCtrl::OnChar)
61 EVT_DROP_FILES(wxTextCtrl::OnDropFiles)
62
0e320a79
DW
63 EVT_MENU(wxID_CUT, wxTextCtrl::OnCut)
64 EVT_MENU(wxID_COPY, wxTextCtrl::OnCopy)
65 EVT_MENU(wxID_PASTE, wxTextCtrl::OnPaste)
66 EVT_MENU(wxID_UNDO, wxTextCtrl::OnUndo)
67 EVT_MENU(wxID_REDO, wxTextCtrl::OnRedo)
68
69 EVT_UPDATE_UI(wxID_CUT, wxTextCtrl::OnUpdateCut)
70 EVT_UPDATE_UI(wxID_COPY, wxTextCtrl::OnUpdateCopy)
71 EVT_UPDATE_UI(wxID_PASTE, wxTextCtrl::OnUpdatePaste)
72 EVT_UPDATE_UI(wxID_UNDO, wxTextCtrl::OnUpdateUndo)
73 EVT_UPDATE_UI(wxID_REDO, wxTextCtrl::OnUpdateRedo)
74END_EVENT_TABLE()
0e320a79 75
d90895ac
DW
76
77// ============================================================================
78// implementation
79// ============================================================================
80
81// ----------------------------------------------------------------------------
82// creation
83// ----------------------------------------------------------------------------
84
0e320a79 85wxTextCtrl::wxTextCtrl()
0e320a79 86{
0e320a79
DW
87}
88
3bd418ca
DW
89bool wxTextCtrl::Create(
90 wxWindow* pParent
91, wxWindowID vId
92, const wxString& rsValue
93, const wxPoint& rPos
94, const wxSize& rSize
95, long lStyle
5d4b632b 96#if wxUSE_VALIDATORS
3bd418ca 97, const wxValidator& rValidator
5d4b632b 98#endif
3bd418ca
DW
99, const wxString& rsName
100)
101{
39c26ef2
DW
102 HWND hParent;
103 int nTempy;
3bd418ca
DW
104 //
105 // Base initialization
106 //
107 if ( !CreateBase( pParent
108 ,vId
109 ,rPos
110 ,rSize
111 ,lStyle
112#if wxUSE_VALIDATORS
113 ,rValidator
114#endif
115 ,rsName
116 ))
d90895ac 117 return FALSE;
0e320a79 118
45bfc84b 119 wxPoint vPos = rPos; // The OS/2 position
5d44b24e 120 SWP vSwp;
45bfc84b 121
3bd418ca 122 if (pParent )
45bfc84b 123 {
3bd418ca 124 pParent->AddChild(this);
45bfc84b 125 }
0e320a79 126
3bd418ca 127 m_windowStyle = lStyle;
d90895ac 128
3bd418ca
DW
129 long lSstyle = WS_VISIBLE | WS_TABSTOP;
130
131 //
132 // Single and multiline edit fields are two different controls in PM
133 //
d90895ac
DW
134 if ( m_windowStyle & wxTE_MULTILINE )
135 {
9c88ff79 136 lSstyle |= MLS_BORDER | MLS_WORDWRAP;
3bd418ca 137 m_bIsMLE = TRUE;
d90895ac 138
d90895ac 139 if ((m_windowStyle & wxTE_NO_VSCROLL) == 0)
3bd418ca
DW
140 lSstyle |= MLS_VSCROLL;
141 if (m_windowStyle & wxHSCROLL)
142 lSstyle |= MLS_HSCROLL;
143 if (m_windowStyle & wxTE_READONLY)
144 lSstyle |= MLS_READONLY;
d90895ac 145 }
0e320a79 146 else
3bd418ca 147 {
987da0d4 148 lSstyle |= ES_LEFT | ES_AUTOSCROLL | ES_MARGIN;
3bd418ca
DW
149
150 if (m_windowStyle & wxHSCROLL)
151 lSstyle |= ES_AUTOSCROLL;
152 if (m_windowStyle & wxTE_READONLY)
153 lSstyle |= ES_READONLY;
154 if (m_windowStyle & wxTE_PASSWORD) // hidden input
155 lSstyle |= ES_UNREADABLE;
156 }
5d44b24e 157
3bd418ca
DW
158 if (m_bIsMLE)
159 {
160 m_hWnd = (WXHWND)::WinCreateWindow( (HWND)GetHwndOf(pParent) // Parent window handle
161 ,WC_MLE // Window class
162 ,(PSZ)rsValue.c_str() // Initial Text
163 ,(ULONG)lSstyle // Style flags
716ed225
DW
164 ,(LONG)0 // X pos of origin
165 ,(LONG)0 // Y pos of origin
166 ,(LONG)0 // field width
167 ,(LONG)0 // field height
3bd418ca
DW
168 ,(HWND)GetHwndOf(pParent) // owner window handle (same as parent
169 ,HWND_TOP // initial z position
170 ,(ULONG)vId // Window identifier
171 ,NULL // no control data
172 ,NULL // no Presentation parameters
173 );
174 }
175 else
176 {
177 m_hWnd = (WXHWND)::WinCreateWindow( (HWND)GetHwndOf(pParent) // Parent window handle
178 ,WC_ENTRYFIELD // Window class
179 ,(PSZ)rsValue.c_str() // Initial Text
180 ,(ULONG)lSstyle // Style flags
716ed225
DW
181 ,(LONG)0 // X pos of origin
182 ,(LONG)0 // Y pos of origin
183 ,(LONG)0 // field width
184 ,(LONG)0 // field height
3bd418ca
DW
185 ,(HWND)GetHwndOf(pParent) // owner window handle (same as parent
186 ,HWND_TOP // initial z position
187 ,(ULONG)vId // Window identifier
188 ,NULL // no control data
189 ,NULL // no Presentation parameters
190 );
191 }
192
193 if (m_hWnd == 0)
194 {
195 return FALSE;
196 }
197
d90895ac
DW
198 SubclassWin(GetHWND());
199
3bd418ca
DW
200 //
201 // Set font, position, size and initial value
202 //
2c1e8f2e
DW
203 wxFont* pTextFont = new wxFont( 10
204 ,wxMODERN
205 ,wxNORMAL
206 ,wxNORMAL
207 );
208 SetFont(*pTextFont);
3bd418ca
DW
209 if (!rsValue.IsEmpty())
210 {
211 SetValue(rsValue);
212 }
213 SetupColours();
5d44b24e
DW
214 //
215 // If X and/or Y are not zero the difference is the compensation value
216 // for margins for OS/2 controls.
217 //
218 ::WinQueryWindowPos(m_hWnd, &vSwp);
219 SetXComp(vSwp.x);
220 SetYComp(vSwp.y);
39c26ef2
DW
221 SetSize( vPos.x
222 ,vPos.y
3bd418ca
DW
223 ,rSize.x
224 ,rSize.y
225 );
b3260bce 226 delete pTextFont;
0e320a79 227 return TRUE;
3bd418ca 228} // end of wxTextCtrl::Create
0e320a79 229
3bd418ca 230//
d90895ac 231// Make sure the window style (etc.) reflects the HWND style (roughly)
3bd418ca 232//
d90895ac
DW
233void wxTextCtrl::AdoptAttributesFromHWND()
234{
3bd418ca
DW
235 HWND hWnd = GetHwnd();
236 LONG lStyle = ::WinQueryWindowULong(hWnd, QWL_STYLE);
d90895ac 237
3bd418ca 238 wxWindow::AdoptAttributesFromHWND();
d90895ac 239
3bd418ca
DW
240 if (m_bIsMLE)
241 {
242 m_windowStyle |= wxTE_MULTILINE;
243 if (lStyle & MLS_READONLY)
244 m_windowStyle |= wxTE_READONLY;
245 }
246 else
247 {
248 if (lStyle & ES_UNREADABLE)
249 m_windowStyle |= wxTE_PASSWORD;
250 if (lStyle & ES_READONLY)
251 m_windowStyle |= wxTE_READONLY;
252 }
c4955899 253} // end of wxTextCtrl::AdoptAttributesFromHWND
d90895ac 254
b9b1d6c8
DW
255WXDWORD wxTextCtrl::OS2GetStyle(
256 long lStyle
257, WXDWORD* pdwExstyle
258) const
259{
260 //
261 // Default border for the text controls is the sunken one
262 //
263 if ((lStyle & wxBORDER_MASK) == wxBORDER_DEFAULT )
264 {
265 lStyle |= wxBORDER_SUNKEN;
266 }
267
268 long dwStyle = wxControl::OS2GetStyle( lStyle
269 ,pdwExstyle
270 );
271
272 dwStyle = WS_VISIBLE | WS_TABSTOP;
273
274 //
275 // Single and multiline edit fields are two different controls in PM
276 //
277 if ( m_windowStyle & wxTE_MULTILINE )
278 {
279 dwStyle |= MLS_BORDER | MLS_WORDWRAP;
280 if ((m_windowStyle & wxTE_NO_VSCROLL) == 0)
281 dwStyle |= MLS_VSCROLL;
282 if (m_windowStyle & wxHSCROLL)
283 dwStyle |= MLS_HSCROLL;
284 if (m_windowStyle & wxTE_READONLY)
285 dwStyle |= MLS_READONLY;
286 }
287 else
288 {
289 dwStyle |= ES_LEFT | ES_AUTOSCROLL | ES_MARGIN;
290 if (m_windowStyle & wxHSCROLL)
291 dwStyle |= ES_AUTOSCROLL;
292 if (m_windowStyle & wxTE_READONLY)
293 dwStyle |= ES_READONLY;
294 if (m_windowStyle & wxTE_PASSWORD) // hidden input
295 dwStyle |= ES_UNREADABLE;
296 }
297 return dwStyle;
298} // end of wxTextCtrl::OS2GetStyle
299
300void wxTextCtrl::SetWindowStyleFlag(
301 long lStyle
302)
303{
304 wxControl::SetWindowStyleFlag(lStyle);
305} // end of wxTextCtrl::SetWindowStyleFlag
306
d90895ac
DW
307void wxTextCtrl::SetupColours()
308{
c4955899
DW
309 wxColour vBkgndColour;
310
a756f210 311 vBkgndColour = wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW);
c4955899 312 SetBackgroundColour(vBkgndColour);
d90895ac 313 SetForegroundColour(GetParent()->GetForegroundColour());
9c88ff79
DW
314 if (m_bIsMLE)
315 {
316 ::WinSendMsg( GetHwnd()
317 ,MLM_SETTEXTCOLOR
318 ,(MPARAM)GetParent()->GetForegroundColour().GetPixel()
319 ,(MPARAM)MLE_RGB
320 );
321 }
c4955899 322} // end of wxTextCtrl::SetupColours
d90895ac
DW
323
324// ----------------------------------------------------------------------------
325// set/get the controls text
326// ----------------------------------------------------------------------------
327
0e320a79
DW
328wxString wxTextCtrl::GetValue() const
329{
c4955899
DW
330 wxString sStr = wxGetWindowText(GetHWND());
331 char* zStr = (char*)sStr.c_str();
d90895ac 332
c4955899
DW
333 for ( ; *zStr; zStr++ )
334 {
335 //
336 // this will replace \r\n with just \n
337 //
338 if (*zStr == '\n')
339 *zStr = '\0';
340 if (*zStr == '\r')
341 *zStr = '\n';
342 }
343 sStr = zStr;
344 return sStr;
345} // end of wxTextCtrl::GetValue
0e320a79 346
c4955899
DW
347void wxTextCtrl::SetValue(
348 const wxString& rsValue
349)
0e320a79 350{
c4955899
DW
351 //
352 // If the text is long enough, it's faster to just set it instead of first
353 // comparing it with the old one (chances are that it will be different
354 // anyhow, this comparison is there to avoid flicker for small single-line
355 // edit controls mostly)
356 //
357 if ((rsValue.length() > 0x400) || (rsValue != GetValue()))
358 {
359 ::WinSetWindowText(GetHwnd(), rsValue.c_str());
360 AdjustSpaceLimit();
361 }
362} // end of wxTextCtrl::SetValue
d90895ac 363
c4955899
DW
364void wxTextCtrl::WriteText(
365 const wxString& rsValue
366)
367{
b3260bce
DW
368 if (m_bIsMLE)
369 ::WinSendMsg(GetHwnd(), MLM_INSERT, MPARAM((PCHAR)rsValue.c_str()), MPARAM(0));
370 else
371 ::WinSetWindowText(GetHwnd(), rsValue.c_str());
d90895ac 372 AdjustSpaceLimit();
c4955899 373} // end of wxTextCtrl::WriteText
0e320a79 374
c4955899
DW
375void wxTextCtrl::AppendText(
376 const wxString& rsText
377)
d90895ac 378{
d90895ac 379 SetInsertionPointEnd();
c4955899
DW
380 WriteText(rsText);
381} // end of wxTextCtrl::AppendText
d90895ac
DW
382
383void wxTextCtrl::Clear()
384{
c4955899
DW
385 ::WinSetWindowText(GetHwnd(), "");
386} // end of wxTextCtrl::Clear
d90895ac 387
a086de98
DW
388bool wxTextCtrl::EmulateKeyPress(
389 const wxKeyEvent& rEvent
390)
391{
392 SetFocus();
393 return(wxTextCtrlBase::EmulateKeyPress(rEvent));
394} // end of wxTextCtrl::EmulateKeyPress
395
d90895ac 396// ----------------------------------------------------------------------------
0e320a79 397// Clipboard operations
d90895ac
DW
398// ----------------------------------------------------------------------------
399
0e320a79
DW
400void wxTextCtrl::Copy()
401{
d90895ac
DW
402 if (CanCopy())
403 {
404 HWND hWnd = GetHwnd();
3bd418ca
DW
405 if (m_bIsMLE)
406 ::WinSendMsg(hWnd, MLM_COPY, 0, 0);
407 else
408 ::WinSendMsg(hWnd, EM_COPY, 0, 0);
d90895ac 409 }
3bd418ca 410} // end of wxTextCtrl::Copy
0e320a79
DW
411
412void wxTextCtrl::Cut()
413{
d90895ac
DW
414 if (CanCut())
415 {
416 HWND hWnd = GetHwnd();
3bd418ca
DW
417
418 if (m_bIsMLE)
419 ::WinSendMsg(hWnd, MLM_CUT, 0, 0);
420 else
421 ::WinSendMsg(hWnd, EM_CUT, 0, 0);
d90895ac 422 }
c4955899 423} // end of wxTextCtrl::Cut
0e320a79
DW
424
425void wxTextCtrl::Paste()
426{
d90895ac
DW
427 if (CanPaste())
428 {
c4955899
DW
429 HWND hWnd = GetHwnd();
430
431 ::WinSendMsg(hWnd, EM_PASTE, 0, 0);
d90895ac 432 }
c4955899 433} // end of wxTextCtrl::Paste
d90895ac
DW
434
435bool wxTextCtrl::CanCopy() const
436{
c4955899 437 //
d90895ac 438 // Can copy if there's a selection
c4955899
DW
439 //
440 long lFrom = 0L;
441 long lTo = 0L;
442
443 GetSelection(&lFrom, &lTo);
444 return (lFrom != lTo);
445} // end of wxTextCtrl::CanCopy
d90895ac
DW
446
447bool wxTextCtrl::CanCut() const
448{
c4955899 449 //
d90895ac 450 // Can cut if there's a selection
c4955899
DW
451 //
452 long lFrom = 0L;
453 long lTo = 0L;
454
455 GetSelection(&lFrom, &lTo);
456 return (lFrom != lTo);
457} // end of wxTextCtrl::CanCut
d90895ac
DW
458
459bool wxTextCtrl::CanPaste() const
460{
3bd418ca
DW
461 bool bIsTextAvailable = FALSE;
462
d90895ac
DW
463 if (!IsEditable())
464 return FALSE;
465
3bd418ca
DW
466 //
467 // Check for straight text on clipboard
468 //
469 if (::WinOpenClipbrd(vHabmain))
d90895ac 470 {
3bd418ca
DW
471 bIsTextAvailable = (::WinQueryClipbrdData(vHabmain, CF_TEXT) != 0);
472 ::WinCloseClipbrd(vHabmain);
d90895ac 473 }
3bd418ca
DW
474 return bIsTextAvailable;
475} // end of wxTextCtrl::CanPaste
0e320a79 476
d90895ac
DW
477// ----------------------------------------------------------------------------
478// Accessors
479// ----------------------------------------------------------------------------
480
c4955899
DW
481void wxTextCtrl::SetEditable(
482 bool bEditable
483)
0e320a79 484{
c4955899
DW
485 HWND hWnd = GetHwnd();
486
487 if (m_bIsMLE)
488 ::WinSendMsg(hWnd, MLM_SETREADONLY, MPFROMLONG(!bEditable), (MPARAM)0);
489 else
490 ::WinSendMsg(hWnd, EM_SETREADONLY, MPFROMLONG(!bEditable), (MPARAM)0);
491} // end of wxTextCtrl::SetEditable
0e320a79 492
c4955899
DW
493void wxTextCtrl::SetInsertionPoint(
494 long lPos
495)
0e320a79 496{
c4955899
DW
497 HWND hWnd = GetHwnd();
498
499 if (m_bIsMLE)
500 ::WinSendMsg(hWnd, MLM_SETSEL, (MPARAM)lPos, (MPARAM)lPos);
501 else
502 ::WinSendMsg(hWnd, EM_SETSEL, MPFROM2SHORT((USHORT)lPos, (USHORT)lPos), (MPARAM)0);
503} // end of wxTextCtrl::SetInsertionPoint
0e320a79
DW
504
505void wxTextCtrl::SetInsertionPointEnd()
506{
c4955899
DW
507 long lPos = GetLastPosition();
508
509 SetInsertionPoint(lPos);
510} // end of wxTextCtrl::SetInsertionPointEnd
0e320a79
DW
511
512long wxTextCtrl::GetInsertionPoint() const
513{
3bd418ca
DW
514 WXDWORD dwPos = 0L;
515
516 if (m_bIsMLE)
517 dwPos = (WXDWORD)::WinSendMsg(GetHwnd(), MLM_QUERYSEL, (MPARAM)MLFQS_MINSEL, 0);
518 else
519 {
520 dwPos = (WXDWORD)::WinSendMsg(GetHwnd(), EM_QUERYSEL, 0, 0);
521 dwPos = SHORT1FROMMP((MPARAM)dwPos); // the first 16 bit value is the min pos
522 }
523 return (dwPos & 0xFFFF);
524} // end of wxTextCtrl::GetInsertionPoint
0e320a79
DW
525
526long wxTextCtrl::GetLastPosition() const
527{
3bd418ca
DW
528 HWND hWnd = GetHwnd();
529 long lCharIndex;
530 long lLineLength;
0e320a79 531
3bd418ca
DW
532 if (m_bIsMLE)
533 {
534 lCharIndex = 0;
d90895ac 535
3bd418ca
DW
536 //
537 // This just gets the total text length. The last will be this value
538 //
539 lLineLength = (long)::WinSendMsg(hWnd, MLM_QUERYTEXTLENGTH, 0, 0);
540 }
541 else
542 {
543 WNDPARAMS vParams;
544
545 lCharIndex = 0;
546 vParams.fsStatus = WPM_CCHTEXT;
547 if (::WinSendMsg( GetHwnd()
548 ,WM_QUERYWINDOWPARAMS
549 ,&vParams
550 ,0
551 ))
552 {
553 lLineLength = (long)vParams.cchText;
554 }
555 else
556 lLineLength = 0;
557 }
558 return(lCharIndex + lLineLength);
559} // end of wxTextCtrl::GetLastPosition
0e320a79 560
d90895ac
DW
561// If the return values from and to are the same, there is no
562// selection.
c4955899
DW
563void wxTextCtrl::GetSelection(
564 long* plFrom
565, long* plTo
566) const
0e320a79 567{
c4955899 568 WXDWORD dwPos;
0e320a79 569
c4955899
DW
570 if (m_bIsMLE)
571 dwPos = (WXDWORD)::WinSendMsg(GetHwnd(), MLM_QUERYSEL, (MPARAM)MLFQS_MINSEL, 0);
572 else
573 {
574 dwPos = (WXDWORD)::WinSendMsg(GetHwnd(), EM_QUERYSEL, 0, 0);
575 }
576 *plFrom = SHORT1FROMMP((MPARAM)dwPos); // the first 16 bit value is the min pos
577 *plTo = SHORT2FROMMP((MPARAM)dwPos); // the first 16 bit value is the min pos
578} // end of wxTextCtrl::GetSelection
0e320a79 579
d90895ac
DW
580bool wxTextCtrl::IsEditable() const
581{
c4955899
DW
582 if (m_bIsMLE)
583 return((bool)LONGFROMMR(::WinSendMsg(GetHwnd(), MLM_QUERYREADONLY, 0, 0)));
584 else
585 return((bool)LONGFROMMR(::WinSendMsg(GetHwnd(), EM_QUERYREADONLY, 0, 0)));
586} // end of wxTextCtrl::IsEditable
0e320a79 587
d90895ac
DW
588// ----------------------------------------------------------------------------
589// Editing
590// ----------------------------------------------------------------------------
591
c4955899
DW
592void wxTextCtrl::Replace(
593 long lFrom
594, long lTo
595, const wxString& rsValue
596)
0e320a79 597{
d90895ac 598#if wxUSE_CLIPBOARD
c4955899
DW
599 HWND hWnd = GetHwnd();
600 long lFromChar = lFrom;
601 long lToChar = lTo;
0e320a79 602
c4955899 603 //
d90895ac 604 // Set selection and remove it
c4955899
DW
605 //
606 if (m_bIsMLE)
607 {
608 ::WinSendMsg(hWnd, MLM_SETSEL, MPFROM2SHORT((USHORT)lFrom, (USHORT)lTo), 0);
609 ::WinSendMsg(hWnd, MLM_CUT, 0, 0);
610 }
611 else
612 {
613 ::WinSendMsg(hWnd, EM_SETSEL, MPFROM2SHORT((USHORT)lFrom, (USHORT)lTo), 0);
614 ::WinSendMsg(hWnd, EM_CUT, 0, 0);
615 }
0e320a79 616
c4955899 617 //
d90895ac 618 // Now replace with 'value', by pasting.
c4955899
DW
619 //
620 wxSetClipboardData(wxDF_TEXT, (wxObject *) (const wxChar *)rsValue, 0, 0);
0e320a79 621
d90895ac 622 // Paste into edit control
c4955899
DW
623 if (m_bIsMLE)
624 ::WinSendMsg(hWnd, MLM_PASTE, (MPARAM)0, (MPARAM)0);
625 else
626 ::WinSendMsg(hWnd, EM_PASTE, (MPARAM)0, (MPARAM)0);
d90895ac
DW
627#else
628 wxFAIL_MSG("wxTextCtrl::Replace not implemented if wxUSE_CLIPBOARD is 0.");
629#endif
c4955899 630} // end of wxTextCtrl::Replace
0e320a79 631
c4955899
DW
632void wxTextCtrl::Remove(
633 long lFrom
634, long lTo
635)
0e320a79 636{
c4955899
DW
637 HWND hWnd = GetHwnd();
638 long lFromChar = lFrom;
639 long lToChar = lTo;
d90895ac 640
c4955899
DW
641 if (m_bIsMLE)
642 {
643 ::WinSendMsg(hWnd, MLM_SETSEL, MPFROM2SHORT((USHORT)lFrom, (USHORT)lTo), 0);
644 ::WinSendMsg(hWnd, MLM_CUT, 0, 0);
645 }
646 else
647 {
648 ::WinSendMsg(hWnd, EM_SETSEL, MPFROM2SHORT((USHORT)lFrom, (USHORT)lTo), 0);
649 ::WinSendMsg(hWnd, EM_CUT, 0, 0);
650 }
651} // end of wxTextCtrl::Remove
0e320a79 652
c4955899
DW
653void wxTextCtrl::SetSelection(
654 long lFrom
655, long lTo
656)
0e320a79 657{
c4955899
DW
658 HWND hWnd = GetHwnd();
659 long lFromChar = lFrom;
660 long lToChar = lTo;
d90895ac 661
c4955899
DW
662 //
663 // If from and to are both -1, it means (in wxWindows) that all text should
d90895ac 664 // be selected. Translate into Windows convention
c4955899
DW
665 //
666 if ((lFrom == -1L) && (lTo == -1L))
d90895ac 667 {
c4955899
DW
668 lFromChar = 0L;
669 lToChar = -1L;
d90895ac 670 }
c4955899
DW
671 if (m_bIsMLE)
672 ::WinSendMsg(hWnd, MLM_SETSEL, (MPARAM)lFromChar, (MPARAM)lToChar);
673 else
674 ::WinSendMsg(hWnd, EM_SETSEL, MPFROM2SHORT((USHORT)lFromChar, (USHORT)lToChar), (MPARAM)0);
675} // end of wxTextCtrl::SetSelection
d90895ac 676
c4955899
DW
677bool wxTextCtrl::LoadFile(
678 const wxString& rsFile
679)
0e320a79 680{
c4955899 681 if ( wxTextCtrlBase::LoadFile(rsFile) )
d90895ac 682 {
c4955899
DW
683 //
684 // Update the size limit if needed
685 //
d90895ac 686 AdjustSpaceLimit();
d90895ac
DW
687 return TRUE;
688 }
d90895ac 689 return FALSE;
c4955899 690} // end of wxTextCtrl::LoadFile
0e320a79
DW
691
692bool wxTextCtrl::IsModified() const
693{
c4955899
DW
694 bool bRc;
695
696 if (m_bIsMLE)
697 bRc = (bool)LONGFROMMR(::WinSendMsg(GetHwnd(), MLM_QUERYCHANGED, 0, 0));
698 else
699 bRc = (bool)LONGFROMMR(::WinSendMsg(GetHwnd(), EM_QUERYCHANGED, 0, 0));
700 return bRc;
701} // end of wxTextCtrl::IsModified
0e320a79 702
3bd418ca 703//
0e320a79 704// Makes 'unmodified'
3bd418ca 705//
0e320a79
DW
706void wxTextCtrl::DiscardEdits()
707{
3bd418ca
DW
708 if (m_bIsMLE)
709 ::WinSendMsg(GetHwnd(), MLM_SETCHANGED, MPFROMLONG(FALSE), 0);
710 else
711 //
712 // EM controls do not have a SETCHANGED but issuing a query should reset it
713 //
714 ::WinSendMsg(GetHwnd(), EM_QUERYCHANGED, 0, 0);
715} // end of wxTextCtrl::DiscardEdits
0e320a79
DW
716
717int wxTextCtrl::GetNumberOfLines() const
718{
c4955899 719 int nNumLines;
0e320a79 720
c4955899
DW
721 if (m_bIsMLE)
722 nNumLines = (int)::WinSendMsg(GetHwnd(), MLM_QUERYLINECOUNT, 0, 0);
723 else
724 nNumLines = 1;
725 return nNumLines;
726} // end of wxTextCtrl::GetNumberOfLines
d90895ac 727
c4955899
DW
728long wxTextCtrl::XYToPosition(
729 long lX
730, long lY
731) const
732{
733 HWND hWnd = GetHwnd();
734 long lCharIndex = 0L;
735 long lLen;
0e320a79 736
c4955899
DW
737 if (m_bIsMLE)
738 {
739 lLen = (long)::WinSendMsg(GetHwnd(), MLM_QUERYLINELENGTH, 0, 0);
740 lCharIndex = ((lLen * lY) + lX);
741 }
742 else
743 lCharIndex = lX;
744 return lCharIndex;
745} // end of wxTextCtrl::XYToPosition
746
747bool wxTextCtrl::PositionToXY(
748 long lPos
749, long* plX
750, long* plY
751) const
0e320a79 752{
c4955899
DW
753 HWND hWnd = GetHwnd();
754 long nLineNo = -1;
755 long lCharIndex = 0;
d90895ac 756
c4955899
DW
757 if (m_bIsMLE)
758 nLineNo = (long)::WinSendMsg(hWnd, MLM_LINEFROMCHAR, (MPARAM)lPos, 0);
759 else
760 nLineNo = 0;
d90895ac 761
c4955899 762 if (nLineNo == -1)
d90895ac
DW
763 {
764 // no such line
765 return FALSE;
766 }
767
c4955899 768 //
d90895ac 769 // This gets the char index for the _beginning_ of this line
c4955899
DW
770 //
771 long lLineWidth;
772
773 if (m_bIsMLE)
774 {
775 lLineWidth = (long)::WinSendMsg(hWnd, MLM_QUERYLINELENGTH, (MPARAM)0, (MPARAM)0);
776 lCharIndex = (nLineNo + 1) * lLineWidth;
777 }
778 else
779 {
780 WNDPARAMS vParams;
781
782 vParams.fsStatus = WPM_CCHTEXT;
783 if (::WinSendMsg( hWnd
784 ,WM_QUERYWINDOWPARAMS
785 ,&vParams
786 ,0
787 ))
788 {
789 lCharIndex = vParams.cchText;
790 }
791 else
792 lCharIndex = 32;
793 }
794
795 if (lCharIndex == -1)
d90895ac
DW
796 {
797 return FALSE;
798 }
799
c4955899
DW
800 //
801 // The X position must therefore be the difference between pos and charIndex
802 //
803 if (plX)
804 *plX = lPos - lCharIndex;
805 if (plY)
806 *plY = nLineNo;
d90895ac
DW
807
808 return TRUE;
c4955899 809} // end of wxTextCtrl::PositionToXY
0e320a79 810
c4955899
DW
811void wxTextCtrl::ShowPosition(
812 long lPos
813)
0e320a79 814{
c4955899
DW
815 HWND hWnd = GetHwnd();
816 long lCurrentLineLineNo = 0L;
d90895ac
DW
817
818 // To scroll to a position, we pass the number of lines and characters
819 // to scroll *by*. This means that we need to:
820 // (1) Find the line position of the current line.
821 // (2) Find the line position of pos.
822 // (3) Scroll by (pos - current).
823 // For now, ignore the horizontal scrolling.
824
c4955899 825 //
d90895ac
DW
826 // Is this where scrolling is relative to - the line containing the caret?
827 // Or is the first visible line??? Try first visible line.
c4955899
DW
828 //
829 if (m_bIsMLE)
830 {
831 //
832 // In PM this is the actual char position
833 //
834 lCurrentLineLineNo = (long)::WinSendMsg(hWnd, MLM_QUERYFIRSTCHAR, (MPARAM)0, (MPARAM)0);
d90895ac 835
c4955899
DW
836 //
837 // This will cause a scroll to the selected position
838 //
839 ::WinSendMsg(hWnd, MLM_SETSEL, (MPARAM)lCurrentLineLineNo, (MPARAM)lCurrentLineLineNo);
840 }
841} // end of wxTextCtrl::ShowPosition
0e320a79 842
3bd418ca
DW
843int wxTextCtrl::GetLineLength(
844 long lLineNo
845) const
0e320a79 846{
3bd418ca 847 long lLen = 0L;
d90895ac 848
3bd418ca
DW
849 if (m_bIsMLE)
850 lLen = (long)::WinSendMsg(GetHwnd(), MLM_QUERYLINELENGTH, 0, 0);
851 else
852 {
853 WNDPARAMS vParams;
854
855 vParams.fsStatus = WPM_CCHTEXT;
856 if (::WinSendMsg( GetHwnd()
857 ,WM_QUERYWINDOWPARAMS
858 ,&vParams
859 ,0
860 ))
861 {
862 lLen = vParams.cchText;
863 }
864 else
865 lLen = 32;
866 }
867 return lLen;
c4955899 868} // end ofwxTextCtrl::GetLineLength
0e320a79 869
c4955899
DW
870wxString wxTextCtrl::GetLineText(
871 long lLineNo
872) const
0e320a79 873{
c4955899
DW
874 long lLen = (long)GetLineLength((long)lLineNo) + 1;
875 wxString sStr;
876 char* zBuf;
0e320a79 877
c4955899
DW
878 //
879 // There must be at least enough place for the length WORD in the
880 // buffer
881 //
882 lLen += sizeof(WORD);
883 zBuf = new char[lLen];
884 if (m_bIsMLE)
885 {
886 long lIndex;
887 long lBuflen;
888 long lCopied;
0e320a79 889
c4955899
DW
890 lLen = (long)::WinSendMsg(GetHwnd(), MLM_QUERYLINELENGTH, 0, 0);
891 lIndex = lLen * lLineNo;
0e320a79 892
c4955899
DW
893 ::WinSendMsg(GetHwnd(), MLM_SETSEL, (MPARAM)lIndex, (MPARAM)lIndex);
894 ::WinSendMsg(GetHwnd(), MLM_SETIMPORTEXPORT, MPFROMP(zBuf), MPFROMSHORT((USHORT)sizeof(zBuf)));
895 lBuflen = (long)::WinSendMsg(GetHwnd(), MLM_QUERYFORMATTEXTLENGTH, MPFROMLONG(lIndex), MPFROMLONG(-1));
896 lCopied = (long)::WinSendMsg(GetHwnd(), MLM_EXPORT, MPFROMP(&lIndex), MPFROMP(&lBuflen));
897 zBuf[lCopied] = '\0';
898 }
899 else
900 {
901 WNDPARAMS vParams;
902
903 vParams.fsStatus = WPM_CCHTEXT;
904 if (::WinSendMsg( GetHwnd()
905 ,WM_QUERYWINDOWPARAMS
906 ,&vParams
907 ,0
908 ))
909 memcpy(zBuf, vParams.pszText, vParams.cchText);
910 zBuf[vParams.cchText] = '\0';
911 }
912 sStr = zBuf;
913 delete [] zBuf;
914 return sStr;
915} // end of wxTextCtrl::GetLineText
0e320a79 916
d90895ac 917// ----------------------------------------------------------------------------
0e320a79 918// Undo/redo
d90895ac
DW
919// ----------------------------------------------------------------------------
920
0e320a79
DW
921void wxTextCtrl::Undo()
922{
d90895ac
DW
923 if (CanUndo())
924 {
c4955899
DW
925 if (m_bIsMLE)
926 ::WinSendMsg(GetHwnd(), MLM_UNDO, 0, 0);
927 // Simple entryfields cannot be undone
d90895ac 928 }
c4955899 929} // end of wxTextCtrl::Undo
0e320a79
DW
930
931void wxTextCtrl::Redo()
932{
d90895ac
DW
933 if (CanRedo())
934 {
c4955899
DW
935 if (m_bIsMLE)
936 ::WinSendMsg(GetHwnd(), MLM_UNDO, 0, 0);
937 // Simple entryfields cannot be undone
d90895ac 938 }
c4955899 939} // end of wxTextCtrl::Redo
0e320a79
DW
940
941bool wxTextCtrl::CanUndo() const
942{
3bd418ca
DW
943 bool bOk;
944
945 if (m_bIsMLE)
946 bOk = (::WinSendMsg(GetHwnd(), MLM_QUERYUNDO, 0, 0) != 0);
947 else
948 bOk = FALSE; // can't undo regular edit fields in PM
949 return bOk;
950} // end of wxTextCtrl::CanUndo
0e320a79
DW
951
952bool wxTextCtrl::CanRedo() const
953{
3bd418ca
DW
954 bool bOk;
955
956 if (m_bIsMLE)
957 bOk = (::WinSendMsg(GetHwnd(), MLM_QUERYUNDO, 0, 0) != 0);
958 else
959 bOk = FALSE; // can't undo regular edit fields in PM
960 return bOk;
961} // end of wxTextCtrl::CanRedo
0e320a79 962
d90895ac
DW
963// ----------------------------------------------------------------------------
964// implemenation details
965// ----------------------------------------------------------------------------
0e320a79 966
c4955899
DW
967void wxTextCtrl::Command(
968 wxCommandEvent& rEvent
969)
0e320a79 970{
c4955899
DW
971 SetValue(rEvent.GetString());
972 ProcessCommand (rEvent);
973} // end of wxTextCtrl::Command
0e320a79 974
c4955899
DW
975void wxTextCtrl::OnDropFiles(
976 wxDropFilesEvent& rEvent
977)
0e320a79
DW
978{
979 // By default, load the first file into the text window.
c4955899 980 if (rEvent.GetNumberOfFiles() > 0)
0e320a79 981 {
c4955899 982 LoadFile(rEvent.GetFiles()[0]);
0e320a79 983 }
c4955899
DW
984} // end of wxTextCtrl::OnDropFiles
985
986WXHBRUSH wxTextCtrl::OnCtlColor(
987 WXHDC hWxDC
988, WXHWND hWnd
989, WXUINT uCtlColor
990, WXUINT uMessage
991, WXWPARAM wParam
992, WXLPARAM lParam
993)
d90895ac 994{
c4955899
DW
995 HPS hPS = (HPS)hWxDC;
996 wxBrush* pBrush = NULL;
997 wxColour vColBack = GetBackgroundColour();
998 wxColour vColFore = GetForegroundColour();
999 wxBrush* pBackgroundBrush = wxTheBrushList->FindOrCreateBrush( GetBackgroundColour()
1000 ,wxSOLID
1001 );
1002
1003 if (m_bUseCtl3D)
1004 {
1005 HBRUSH hBrush = NULLHANDLE;
0e320a79 1006
c4955899
DW
1007 return hBrush;
1008 }
1009 if (GetParent()->GetTransparentBackground())
1010 ::GpiSetBackMix(hPS, BM_LEAVEALONE);
1011 else
1012 ::GpiSetBackMix(hPS, BM_OVERPAINT);
1013 if (!IsEnabled() && (GetWindowStyle() & wxTE_MULTILINE) == 0)
a756f210 1014 vColBack = wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE);
c4955899
DW
1015 ::GpiSetBackColor(hPS, vColBack.GetPixel());
1016 ::GpiSetColor(hPS, vColFore.GetPixel());
1017 return (WXHBRUSH)pBackgroundBrush->GetResourceHandle();
1018} // end of wxTextCtrl::OnCtlColor
1019
54ffa107
DW
1020bool wxTextCtrl::OS2ShouldPreProcessMessage(
1021 WXMSG* pMsg
1022)
1023{
1024 return wxControl::OS2ShouldPreProcessMessage(pMsg);
1025} // end of wxTextCtrl::OS2ShouldPreProcessMessage
1026
c4955899
DW
1027void wxTextCtrl::OnChar(
1028 wxKeyEvent& rEvent
1029)
0e320a79 1030{
c4955899 1031 switch (rEvent.KeyCode())
d90895ac 1032 {
d90895ac
DW
1033 case WXK_RETURN:
1034 if ( !(m_windowStyle & wxTE_MULTILINE) )
1035 {
c4955899
DW
1036 wxCommandEvent vEvent(wxEVT_COMMAND_TEXT_ENTER, m_windowId);
1037
1038 vEvent.SetEventObject(this);
1039 if ( GetEventHandler()->ProcessEvent(vEvent))
d90895ac
DW
1040 return;
1041 }
1042 //else: multiline controls need Enter for themselves
1043
1044 break;
1045
1046 case WXK_TAB:
1047 // always produce navigation event - even if we process TAB
1048 // ourselves the fact that we got here means that the user code
1049 // decided to skip processing of this TAB - probably to let it
1050 // do its default job.
1051 //
1052 // NB: Notice that Ctrl-Tab is handled elsewhere and Alt-Tab is
1053 // handled by Windows
1054 {
c4955899 1055 wxNavigationKeyEvent vEventNav;
d90895ac 1056
c4955899
DW
1057 vEventNav.SetDirection(!rEvent.ShiftDown());
1058 vEventNav.SetWindowChange(FALSE);
1059 vEventNav.SetEventObject(this);
1060
1061 if ( GetEventHandler()->ProcessEvent(vEventNav) )
d90895ac
DW
1062 return;
1063 }
1064 break;
d90895ac 1065 }
c4955899
DW
1066 rEvent.Skip();
1067} // end of wxTextCtrl::OnChar
0e320a79 1068
c4955899
DW
1069bool wxTextCtrl::OS2Command(
1070 WXUINT uParam
1071, WXWORD WXUNUSED(vId)
1072)
0e320a79 1073{
c4955899 1074 switch (uParam)
d90895ac 1075 {
d90895ac
DW
1076 case EN_SETFOCUS:
1077 case EN_KILLFOCUS:
1078 {
c4955899
DW
1079 wxFocusEvent vEvent( uParam == EN_KILLFOCUS ? wxEVT_KILL_FOCUS
1080 : wxEVT_SET_FOCUS
1081 ,m_windowId
1082 );
1083
1084 vEvent.SetEventObject(this);
1085 GetEventHandler()->ProcessEvent(vEvent);
d90895ac
DW
1086 }
1087 break;
1088
1089 case EN_CHANGE:
1090 {
c4955899
DW
1091 wxCommandEvent vEvent( wxEVT_COMMAND_TEXT_UPDATED
1092 ,m_windowId
1093 );
1094
1095 InitCommandEvent(vEvent);
1096 vEvent.SetString((char*)GetValue().c_str());
1097 ProcessCommand(vEvent);
d90895ac
DW
1098 }
1099 break;
1100
c4955899
DW
1101 case EN_OVERFLOW:
1102 //
1103 // The text size limit has been hit - increase it
1104 //
d90895ac
DW
1105 AdjustSpaceLimit();
1106 break;
1107
c4955899
DW
1108 case EN_SCROLL:
1109 case EN_INSERTMODETOGGLE:
1110 case EN_MEMERROR:
1111 return FALSE;
d90895ac
DW
1112 default:
1113 return FALSE;
1114 }
1115
c4955899
DW
1116 //
1117 // Processed
1118 //
d90895ac 1119 return TRUE;
c4955899 1120} // end of wxTextCtrl::OS2Command
0e320a79 1121
d90895ac 1122void wxTextCtrl::AdjustSpaceLimit()
0e320a79 1123{
3bd418ca
DW
1124 unsigned int uLen = 0;
1125 unsigned int uLimit = 0;
d90895ac 1126
3bd418ca
DW
1127 uLen = ::WinQueryWindowTextLength(GetHwnd());
1128 if (m_bIsMLE)
1129 {
1130 uLimit = (unsigned int)::WinSendMsg( GetHwnd()
1131 ,MLM_QUERYTEXTLIMIT
1132 ,0
1133 ,0
1134 );
1135 }
1136 else
1137 {
1138 ENTRYFDATA* pEfd;
1139 WNDPARAMS vParams;
1140
1141 vParams.fsStatus = WPM_CBCTLDATA;
1142 vParams.cbCtlData = sizeof(ENTRYFDATA);
1143
1144 if (::WinSendMsg( GetHwnd()
1145 ,WM_QUERYWINDOWPARAMS
1146 ,&vParams
1147 ,0
1148 ))
1149 {
1150 pEfd = (ENTRYFDATA*)vParams.pCtlData;
1151 uLimit = (unsigned int)pEfd->cchEditLimit;
1152 }
d90895ac 1153 else
3bd418ca 1154 uLimit = 32; //PM's default
d90895ac 1155 }
3bd418ca
DW
1156 if (uLen >= uLimit)
1157 {
1158 uLimit = uLen + 0x8000; // 32Kb
1159 if (uLimit > 0xffff)
1160 {
1161 uLimit = 0L;
1162 }
1163 if (m_bIsMLE)
1164 ::WinSendMsg(GetHwnd(), MLM_SETTEXTLIMIT, MPFROMLONG(uLimit), 0);
1165 else
1166 ::WinSendMsg(GetHwnd(), EM_SETTEXTLIMIT, MPFROMLONG(uLimit), 0);
1167 }
1168} // end of wxTextCtrl::AdjustSpaceLimit
0e320a79 1169
d90895ac 1170bool wxTextCtrl::AcceptsFocus() const
0e320a79 1171{
c4955899
DW
1172 //
1173 // We don't want focus if we can't be edited
1174 //
d90895ac 1175 return IsEditable() && wxControl::AcceptsFocus();
c4955899 1176} // end of wxTextCtrl::Command
0e320a79 1177
e78c4d50 1178wxSize wxTextCtrl::DoGetBestSize() const
0e320a79 1179{
c4955899
DW
1180 int nCx;
1181 int nCy;
0e320a79 1182
c4955899 1183 wxGetCharSize(GetHWND(), &nCx, &nCy, (wxFont*)&GetFont());
d90895ac 1184
c4955899 1185 int wText = DEFAULT_ITEM_WIDTH;
987da0d4 1186 int hText = (EDIT_HEIGHT_FROM_CHAR_HEIGHT(nCy) * .8);
c4955899
DW
1187
1188 if (m_windowStyle & wxTE_MULTILINE)
d90895ac 1189 {
239c2e96 1190 hText *= wxMax(GetNumberOfLines(), 5);
d90895ac
DW
1191 }
1192 //else: for single line control everything is ok
d90895ac 1193 return wxSize(wText, hText);
c4955899 1194} // end of wxTextCtrl::DoGetBestSize
0e320a79 1195
d90895ac
DW
1196// ----------------------------------------------------------------------------
1197// standard handlers for standard edit menu events
1198// ----------------------------------------------------------------------------
1199
c4955899
DW
1200void wxTextCtrl::OnCut(
1201 wxCommandEvent& rEvent
1202)
0e320a79
DW
1203{
1204 Cut();
c4955899 1205} // end of wxTextCtrl::OnCut
0e320a79 1206
c4955899
DW
1207void wxTextCtrl::OnCopy(
1208 wxCommandEvent& rEvent
1209)
0e320a79
DW
1210{
1211 Copy();
c4955899 1212} // end of wxTextCtrl::OnCopy
0e320a79 1213
c4955899
DW
1214void wxTextCtrl::OnPaste(
1215 wxCommandEvent& rEvent
1216)
0e320a79
DW
1217{
1218 Paste();
c4955899 1219} // end of wxTextCtrl::OnPaste
0e320a79 1220
c4955899
DW
1221void wxTextCtrl::OnUndo(
1222 wxCommandEvent& rEvent
1223)
0e320a79
DW
1224{
1225 Undo();
c4955899 1226} // end of wxTextCtrl::OnUndo
0e320a79 1227
c4955899
DW
1228void wxTextCtrl::OnRedo(
1229 wxCommandEvent& rEvent
1230)
0e320a79
DW
1231{
1232 Redo();
c4955899 1233} // end of wxTextCtrl::OnRedo
0e320a79 1234
c4955899
DW
1235void wxTextCtrl::OnUpdateCut(
1236 wxUpdateUIEvent& rEvent
1237)
0e320a79 1238{
c4955899
DW
1239 rEvent.Enable(CanCut());
1240} // end of wxTextCtrl::OnUpdateCut
0e320a79 1241
c4955899
DW
1242void wxTextCtrl::OnUpdateCopy(
1243 wxUpdateUIEvent& rEvent
1244)
0e320a79 1245{
c4955899
DW
1246 rEvent.Enable(CanCopy());
1247} // end of wxTextCtrl::OnUpdateCopy
0e320a79 1248
c4955899
DW
1249void wxTextCtrl::OnUpdatePaste(
1250 wxUpdateUIEvent& rEvent
1251)
0e320a79 1252{
c4955899
DW
1253 rEvent.Enable(CanPaste());
1254} // end of wxTextCtrl::OnUpdatePaste
0e320a79 1255
c4955899
DW
1256void wxTextCtrl::OnUpdateUndo(
1257 wxUpdateUIEvent& rEvent
1258)
0e320a79 1259{
c4955899
DW
1260 rEvent.Enable(CanUndo());
1261} // end of wxTextCtrl::OnUpdateUndo
1262
1263void wxTextCtrl::OnUpdateRedo(
1264 wxUpdateUIEvent& rEvent
1265)
1266{
1267 rEvent.Enable(CanRedo());
1268} // end of wxTextCtrl::OnUpdateRedo
0e320a79 1269
c4955899
DW
1270bool wxTextCtrl::SetBackgroundColour(
1271 const wxColour& rColour
1272)
0e320a79 1273{
c4955899
DW
1274 if (m_bIsMLE)
1275 ::WinSendMsg(GetHwnd(), MLM_SETBACKCOLOR, (MPARAM)rColour.GetPixel(), MLE_INDEX);
1276 return TRUE;
1277} // end of wxTextCtrl::SetBackgroundColour
1278
1279bool wxTextCtrl::SetForegroundColour(
1280 const wxColour& rColour
1281)
1282{
1283 if (m_bIsMLE)
1284 ::WinSendMsg(GetHwnd(), MLM_SETTEXTCOLOR, (MPARAM)rColour.GetPixel(), MLE_INDEX);
1285 return TRUE;
1286} // end of wxTextCtrl::SetForegroundColour
d90895ac 1287
39c26ef2
DW
1288bool wxTextCtrl::SetStyle(
1289 long lStart
1290, long lEnd
1291, const wxTextAttr& rStyle
1292)
1293{
1294 HWND hWnd = GetHwnd();
1295
1296 if (lStart > lEnd)
1297 {
1298 long lTmp = lStart;
1299
1300 lStart = lEnd;
1301 lEnd = lTmp;
1302 }
1303
1304 //
1305 // We can only change the format of the selection, so select the range we
1306 // want and restore the old selection later
1307 //
1308 long lStartOld;
1309 long lEndOld;
1310
1311 GetSelection( &lStartOld
1312 ,&lEndOld
1313 );
1314
1315 //
1316 // But do we really have to change the selection?
1317 //
1318 bool bChangeSel = lStart != lStartOld ||
1319 lEnd != lEndOld;
1320
1321 if (bChangeSel)
1322 {
1323 if (m_bIsMLE)
1324 ::WinSendMsg(hWnd, MLM_SETSEL, MPFROM2SHORT((USHORT)lStart, (USHORT)lEnd), 0);
1325 else
1326 ::WinSendMsg(hWnd, EM_SETSEL, MPFROM2SHORT((USHORT)lStart, (USHORT)lEnd), 0);
1327 }
1328
1329 //
1330 // TODO:: finish this part
1331 //
1332 return TRUE;
1333} // end of wxTextCtrl::SetStyle
1334