1 /////////////////////////////////////////////////////////////////////////////
2 // Name: src/os2/textctrl.cpp
4 // Author: David Webster
7 // Copyright: (c) David Webster
8 // Licence: wxWindows licence
9 /////////////////////////////////////////////////////////////////////////////
11 // ----------------------------------------------------------------------------
13 // ----------------------------------------------------------------------------
15 // For compilers that support precompilation, includes "wx.h".
16 #include "wx/wxprec.h"
18 #include "wx/textctrl.h"
21 #include "wx/scrolwin.h"
22 #include "wx/settings.h"
30 #include "wx/clipbrd.h"
33 #include "wx/textfile.h"
35 #include "wx/os2/private.h"
39 #include <sys/types.h>
47 #if !defined(MLE_INDEX)
53 // ----------------------------------------------------------------------------
54 // event tables and other macros
55 // ----------------------------------------------------------------------------
57 BEGIN_EVENT_TABLE(wxTextCtrl
, wxTextCtrlBase
)
58 EVT_CHAR(wxTextCtrl::OnChar
)
59 EVT_DROP_FILES(wxTextCtrl::OnDropFiles
)
61 EVT_MENU(wxID_CUT
, wxTextCtrl::OnCut
)
62 EVT_MENU(wxID_COPY
, wxTextCtrl::OnCopy
)
63 EVT_MENU(wxID_PASTE
, wxTextCtrl::OnPaste
)
64 EVT_MENU(wxID_UNDO
, wxTextCtrl::OnUndo
)
65 EVT_MENU(wxID_REDO
, wxTextCtrl::OnRedo
)
67 EVT_UPDATE_UI(wxID_CUT
, wxTextCtrl::OnUpdateCut
)
68 EVT_UPDATE_UI(wxID_COPY
, wxTextCtrl::OnUpdateCopy
)
69 EVT_UPDATE_UI(wxID_PASTE
, wxTextCtrl::OnUpdatePaste
)
70 EVT_UPDATE_UI(wxID_UNDO
, wxTextCtrl::OnUpdateUndo
)
71 EVT_UPDATE_UI(wxID_REDO
, wxTextCtrl::OnUpdateRedo
)
75 // ============================================================================
77 // ============================================================================
79 // ----------------------------------------------------------------------------
81 // ----------------------------------------------------------------------------
83 wxTextCtrl::wxTextCtrl()
87 wxTextCtrl::~wxTextCtrl()
91 bool wxTextCtrl::Create(
94 , const wxString
& rsValue
98 , const wxValidator
& rValidator
99 , const wxString
& rsName
103 // Base initialization
105 if ( !CreateBase( pParent
115 wxPoint vPos
= rPos
; // The OS/2 position
120 pParent
->AddChild(this);
123 m_windowStyle
= lStyle
;
125 m_bSkipUpdate
= false;
127 long lSstyle
= WS_VISIBLE
| WS_TABSTOP
;
130 // Single and multiline edit fields are two different controls in PM
132 if ( m_windowStyle
& wxTE_MULTILINE
)
134 lSstyle
|= MLS_BORDER
| MLS_WORDWRAP
;
137 if ((m_windowStyle
& wxTE_NO_VSCROLL
) == 0)
138 lSstyle
|= MLS_VSCROLL
;
139 if (m_windowStyle
& wxHSCROLL
)
140 lSstyle
|= MLS_HSCROLL
;
141 if (m_windowStyle
& wxTE_READONLY
)
142 lSstyle
|= MLS_READONLY
;
146 lSstyle
|= ES_LEFT
| ES_AUTOSCROLL
| ES_MARGIN
;
148 if (m_windowStyle
& wxHSCROLL
)
149 lSstyle
|= ES_AUTOSCROLL
;
150 if (m_windowStyle
& wxTE_READONLY
)
151 lSstyle
|= ES_READONLY
;
152 if (m_windowStyle
& wxTE_PASSWORD
) // hidden input
153 lSstyle
|= ES_UNREADABLE
;
158 m_hWnd
= (WXHWND
)::WinCreateWindow( (HWND
)GetHwndOf(pParent
) // Parent window handle
159 ,WC_MLE
// Window class
160 ,rsValue
.c_str() // Initial Text
161 ,(ULONG
)lSstyle
// Style flags
162 ,(LONG
)0 // X pos of origin
163 ,(LONG
)0 // Y pos of origin
164 ,(LONG
)0 // field width
165 ,(LONG
)0 // field height
166 ,(HWND
)GetHwndOf(pParent
) // owner window handle (same as parent
167 ,HWND_TOP
// initial z position
168 ,(ULONG
)vId
// Window identifier
169 ,NULL
// no control data
170 ,NULL
// no Presentation parameters
175 m_hWnd
= (WXHWND
)::WinCreateWindow( (HWND
)GetHwndOf(pParent
) // Parent window handle
176 ,WC_ENTRYFIELD
// Window class
177 ,rsValue
.c_str() // Initial Text
178 ,(ULONG
)lSstyle
// Style flags
179 ,(LONG
)0 // X pos of origin
180 ,(LONG
)0 // Y pos of origin
181 ,(LONG
)0 // field width
182 ,(LONG
)0 // field height
183 ,(HWND
)GetHwndOf(pParent
) // owner window handle (same as parent
184 ,HWND_TOP
// initial z position
185 ,(ULONG
)vId
// Window identifier
186 ,NULL
// no control data
187 ,NULL
// no Presentation parameters
196 SubclassWin(GetHWND());
199 // Set font, position, size and initial value
201 wxFont
* pTextFont
= new wxFont( 8
207 if (!rsValue
.empty())
213 // If X and/or Y are not zero the difference is the compensation value
214 // for margins for OS/2 controls.
216 ::WinQueryWindowPos(m_hWnd
, &vSwp
);
219 SetSize( vPos
.x
- GetXComp()
226 } // end of wxTextCtrl::Create
229 // Make sure the window style (etc.) reflects the HWND style (roughly)
231 void wxTextCtrl::AdoptAttributesFromHWND()
233 HWND hWnd
= GetHwnd();
234 LONG lStyle
= ::WinQueryWindowULong(hWnd
, QWL_STYLE
);
236 wxWindow::AdoptAttributesFromHWND();
240 m_windowStyle
|= wxTE_MULTILINE
;
241 if (lStyle
& MLS_READONLY
)
242 m_windowStyle
|= wxTE_READONLY
;
246 if (lStyle
& ES_UNREADABLE
)
247 m_windowStyle
|= wxTE_PASSWORD
;
248 if (lStyle
& ES_READONLY
)
249 m_windowStyle
|= wxTE_READONLY
;
251 } // end of wxTextCtrl::AdoptAttributesFromHWND
253 WXDWORD
wxTextCtrl::OS2GetStyle(
255 , WXDWORD
* pdwExstyle
259 // Default border for the text controls is the sunken one
261 if ((lStyle
& wxBORDER_MASK
) == wxBORDER_DEFAULT
)
263 lStyle
|= wxBORDER_SUNKEN
;
266 long dwStyle
= wxControl::OS2GetStyle( lStyle
270 dwStyle
= WS_VISIBLE
| WS_TABSTOP
;
273 // Single and multiline edit fields are two different controls in PM
275 if ( m_windowStyle
& wxTE_MULTILINE
)
277 dwStyle
|= MLS_BORDER
| MLS_WORDWRAP
;
278 if ((m_windowStyle
& wxTE_NO_VSCROLL
) == 0)
279 dwStyle
|= MLS_VSCROLL
;
280 if (m_windowStyle
& wxHSCROLL
)
281 dwStyle
|= MLS_HSCROLL
;
282 if (m_windowStyle
& wxTE_READONLY
)
283 dwStyle
|= MLS_READONLY
;
287 dwStyle
|= ES_LEFT
| ES_AUTOSCROLL
| ES_MARGIN
;
288 if (m_windowStyle
& wxHSCROLL
)
289 dwStyle
|= ES_AUTOSCROLL
;
290 if (m_windowStyle
& wxTE_READONLY
)
291 dwStyle
|= ES_READONLY
;
292 if (m_windowStyle
& wxTE_PASSWORD
) // hidden input
293 dwStyle
|= ES_UNREADABLE
;
296 } // end of wxTextCtrl::OS2GetStyle
298 void wxTextCtrl::SetWindowStyleFlag(
302 wxControl::SetWindowStyleFlag(lStyle
);
303 } // end of wxTextCtrl::SetWindowStyleFlag
305 void wxTextCtrl::SetupColours()
307 wxColour vBkgndColour
;
309 vBkgndColour
= wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW
);
310 SetBackgroundColour(vBkgndColour
);
311 SetForegroundColour(GetParent()->GetForegroundColour());
314 ::WinSendMsg( GetHwnd()
316 ,(MPARAM
)GetParent()->GetForegroundColour().GetPixel()
320 } // end of wxTextCtrl::SetupColours
322 // ----------------------------------------------------------------------------
323 // set/get the controls text
324 // ----------------------------------------------------------------------------
326 wxString
wxTextCtrl::GetValue() const
328 wxString sStr
= wxGetWindowText(GetHWND());
329 wxCharBuffer
buf(sStr
.char_str());
330 char* zStr
= buf
.data();
332 for ( ; *zStr
; zStr
++ )
335 // this will replace \r\n with just \n
343 } // end of wxTextCtrl::GetValue
345 void wxTextCtrl::DoSetValue(
346 const wxString
& rsValue
,
351 // If the text is long enough, it's faster to just set it instead of first
352 // comparing it with the old one (chances are that it will be different
353 // anyhow, this comparison is there to avoid flicker for small single-line
354 // edit controls mostly)
356 if ((rsValue
.length() > 0x400) || (rsValue
!= GetValue()))
358 if ( flags
& SetValue_SendEvent
)
359 m_bSkipUpdate
= true;
361 ::WinSetWindowText(GetHwnd(), rsValue
.c_str());
364 } // end of wxTextCtrl::SetValue
366 void wxTextCtrl::WriteText(
367 const wxString
& rsValue
371 ::WinSendMsg(GetHwnd(), MLM_INSERT
, MPARAM(rsValue
.wx_str()), MPARAM(0));
373 ::WinSetWindowText(GetHwnd(), rsValue
.c_str());
375 } // end of wxTextCtrl::WriteText
377 void wxTextCtrl::AppendText(
378 const wxString
& rsText
381 SetInsertionPointEnd();
383 } // end of wxTextCtrl::AppendText
385 void wxTextCtrl::Clear()
387 ::WinSetWindowText(GetHwnd(), "");
388 } // end of wxTextCtrl::Clear
390 bool wxTextCtrl::EmulateKeyPress(
391 const wxKeyEvent
& rEvent
395 return(wxTextCtrlBase::EmulateKeyPress(rEvent
));
396 } // end of wxTextCtrl::EmulateKeyPress
398 // ----------------------------------------------------------------------------
399 // Clipboard operations
400 // ----------------------------------------------------------------------------
402 void wxTextCtrl::Copy()
406 HWND hWnd
= GetHwnd();
408 ::WinSendMsg(hWnd
, MLM_COPY
, 0, 0);
410 ::WinSendMsg(hWnd
, EM_COPY
, 0, 0);
412 } // end of wxTextCtrl::Copy
414 void wxTextCtrl::Cut()
418 HWND hWnd
= GetHwnd();
421 ::WinSendMsg(hWnd
, MLM_CUT
, 0, 0);
423 ::WinSendMsg(hWnd
, EM_CUT
, 0, 0);
425 } // end of wxTextCtrl::Cut
427 void wxTextCtrl::Paste()
431 HWND hWnd
= GetHwnd();
433 ::WinSendMsg(hWnd
, EM_PASTE
, 0, 0);
435 } // end of wxTextCtrl::Paste
437 bool wxTextCtrl::CanCopy() const
440 // Can copy if there's a selection
445 GetSelection(&lFrom
, &lTo
);
446 return (lFrom
!= lTo
);
447 } // end of wxTextCtrl::CanCopy
449 bool wxTextCtrl::CanCut() const
452 // Can cut if there's a selection
457 GetSelection(&lFrom
, &lTo
);
458 return (lFrom
!= lTo
);
459 } // end of wxTextCtrl::CanCut
461 bool wxTextCtrl::CanPaste() const
463 bool bIsTextAvailable
= false;
469 // Check for straight text on clipboard
471 if (::WinOpenClipbrd(vHabmain
))
473 bIsTextAvailable
= (::WinQueryClipbrdData(vHabmain
, CF_TEXT
) != 0);
474 ::WinCloseClipbrd(vHabmain
);
476 return bIsTextAvailable
;
477 } // end of wxTextCtrl::CanPaste
479 // ----------------------------------------------------------------------------
481 // ----------------------------------------------------------------------------
483 void wxTextCtrl::SetEditable(
487 HWND hWnd
= GetHwnd();
490 ::WinSendMsg(hWnd
, MLM_SETREADONLY
, MPFROMLONG(!bEditable
), (MPARAM
)0);
492 ::WinSendMsg(hWnd
, EM_SETREADONLY
, MPFROMLONG(!bEditable
), (MPARAM
)0);
493 } // end of wxTextCtrl::SetEditable
495 void wxTextCtrl::SetInsertionPoint(
499 HWND hWnd
= GetHwnd();
502 ::WinSendMsg(hWnd
, MLM_SETSEL
, (MPARAM
)lPos
, (MPARAM
)lPos
);
504 ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lPos
, (USHORT
)lPos
), (MPARAM
)0);
505 } // end of wxTextCtrl::SetInsertionPoint
507 void wxTextCtrl::SetInsertionPointEnd()
509 wxTextPos lPos
= GetLastPosition();
512 // We must not do anything if the caret is already there because calling
513 // SetInsertionPoint() thaws the controls if Freeze() had been called even
514 // if it doesn't actually move the caret anywhere and so the simple fact of
515 // doing it results in horrible flicker when appending big amounts of text
516 // to the control in a few chunks (see DoAddText() test in the text sample)
518 if (GetInsertionPoint() == GetLastPosition())
520 SetInsertionPoint(lPos
);
521 } // end of wxTextCtrl::SetInsertionPointEnd
523 long wxTextCtrl::GetInsertionPoint() const
528 dwPos
= (WXDWORD
)::WinSendMsg(GetHwnd(), MLM_QUERYSEL
, (MPARAM
)MLFQS_MINSEL
, 0);
531 dwPos
= (WXDWORD
)::WinSendMsg(GetHwnd(), EM_QUERYSEL
, 0, 0);
532 dwPos
= SHORT1FROMMP((MPARAM
)dwPos
); // the first 16 bit value is the min pos
534 return (dwPos
& 0xFFFF);
535 } // end of wxTextCtrl::GetInsertionPoint
537 wxTextPos
wxTextCtrl::GetLastPosition() const
539 HWND hWnd
= GetHwnd();
548 // This just gets the total text length. The last will be this value
550 lLineLength
= (long)::WinSendMsg(hWnd
, MLM_QUERYTEXTLENGTH
, 0, 0);
557 vParams
.fsStatus
= WPM_CCHTEXT
;
558 if (::WinSendMsg( GetHwnd()
559 ,WM_QUERYWINDOWPARAMS
564 lLineLength
= (long)vParams
.cchText
;
569 return(lCharIndex
+ lLineLength
);
570 } // end of wxTextCtrl::GetLastPosition
572 // If the return values from and to are the same, there is no
574 void wxTextCtrl::GetSelection(
582 dwPos
= (WXDWORD
)::WinSendMsg(GetHwnd(), MLM_QUERYSEL
, (MPARAM
)MLFQS_MINSEL
, 0);
585 dwPos
= (WXDWORD
)::WinSendMsg(GetHwnd(), EM_QUERYSEL
, 0, 0);
587 *plFrom
= SHORT1FROMMP((MPARAM
)dwPos
); // the first 16 bit value is the min pos
588 *plTo
= SHORT2FROMMP((MPARAM
)dwPos
); // the first 16 bit value is the min pos
589 } // end of wxTextCtrl::GetSelection
591 bool wxTextCtrl::IsEditable() const
594 return((bool)LONGFROMMR(::WinSendMsg(GetHwnd(), MLM_QUERYREADONLY
, 0, 0)));
596 return((bool)LONGFROMMR(::WinSendMsg(GetHwnd(), EM_QUERYREADONLY
, 0, 0)));
597 } // end of wxTextCtrl::IsEditable
599 // ----------------------------------------------------------------------------
601 // ----------------------------------------------------------------------------
603 void wxTextCtrl::Replace( long lFrom
,
605 const wxString
& rsValue
)
608 HWND hWnd
= GetHwnd();
611 // Set selection and remove it
615 ::WinSendMsg(hWnd
, MLM_SETSEL
, MPFROM2SHORT((USHORT
)lFrom
, (USHORT
)lTo
), 0);
616 ::WinSendMsg(hWnd
, MLM_CUT
, 0, 0);
620 ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lFrom
, (USHORT
)lTo
), 0);
621 ::WinSendMsg(hWnd
, EM_CUT
, 0, 0);
625 // Now replace with 'value', by pasting.
627 wxSetClipboardData(wxDF_TEXT
, (wxObject
*) (const wxChar
*)rsValue
, 0, 0);
629 // Paste into edit control
631 ::WinSendMsg(hWnd
, MLM_PASTE
, (MPARAM
)0, (MPARAM
)0);
633 ::WinSendMsg(hWnd
, EM_PASTE
, (MPARAM
)0, (MPARAM
)0);
637 wxUnusedVar(rsValue
);
638 wxFAIL_MSG("wxTextCtrl::Replace not implemented if wxUSE_CLIPBOARD is 0.");
640 } // end of wxTextCtrl::Replace
642 void wxTextCtrl::Remove(
647 HWND hWnd
= GetHwnd();
651 ::WinSendMsg(hWnd
, MLM_SETSEL
, MPFROM2SHORT((USHORT
)lFrom
, (USHORT
)lTo
), 0);
652 ::WinSendMsg(hWnd
, MLM_CUT
, 0, 0);
656 ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lFrom
, (USHORT
)lTo
), 0);
657 ::WinSendMsg(hWnd
, EM_CUT
, 0, 0);
659 } // end of wxTextCtrl::Remove
661 void wxTextCtrl::SetSelection(
666 HWND hWnd
= GetHwnd();
667 long lFromChar
= lFrom
;
671 // If from and to are both -1, it means (in wxWidgets) that all text should
672 // be selected. Translate into Windows convention
674 if ((lFrom
== -1L) && (lTo
== -1L))
680 ::WinSendMsg(hWnd
, MLM_SETSEL
, (MPARAM
)lFromChar
, (MPARAM
)lToChar
);
682 ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lFromChar
, (USHORT
)lToChar
), (MPARAM
)0);
683 } // end of wxTextCtrl::SetSelection
685 bool wxTextCtrl::DoLoadFile(
686 const wxString
& rsFile
,
690 if ( wxTextCtrlBase::DoLoadFile(rsFile
, fileType
) )
693 // Update the size limit if needed
699 } // end of wxTextCtrl::DoLoadFile
701 bool wxTextCtrl::IsModified() const
706 bRc
= (bool)LONGFROMMR(::WinSendMsg(GetHwnd(), MLM_QUERYCHANGED
, 0, 0));
708 bRc
= (bool)LONGFROMMR(::WinSendMsg(GetHwnd(), EM_QUERYCHANGED
, 0, 0));
710 } // end of wxTextCtrl::IsModified
712 void wxTextCtrl::MarkDirty()
715 ::WinSendMsg(GetHwnd(), MLM_SETCHANGED
, MPFROMLONG(TRUE
), 0);
717 // EM controls do not have a SETCHANGED, what can we do??
718 wxFAIL_MSG( wxT("not implemented") );
722 // Makes 'unmodified'
724 void wxTextCtrl::DiscardEdits()
727 ::WinSendMsg(GetHwnd(), MLM_SETCHANGED
, MPFROMLONG(FALSE
), 0);
730 // EM controls do not have a SETCHANGED but issuing a query should reset it
732 ::WinSendMsg(GetHwnd(), EM_QUERYCHANGED
, 0, 0);
733 } // end of wxTextCtrl::DiscardEdits
735 int wxTextCtrl::GetNumberOfLines() const
740 nNumLines
= (int)::WinSendMsg(GetHwnd(), MLM_QUERYLINECOUNT
, 0, 0);
744 } // end of wxTextCtrl::GetNumberOfLines
746 long wxTextCtrl::XYToPosition(
751 long lCharIndex
= 0L;
756 lLen
= (long)::WinSendMsg(GetHwnd(), MLM_QUERYLINELENGTH
, 0, 0);
757 lCharIndex
= ((lLen
* lY
) + lX
);
762 } // end of wxTextCtrl::XYToPosition
764 bool wxTextCtrl::PositionToXY(
770 HWND hWnd
= GetHwnd();
775 nLineNo
= (long)::WinSendMsg(hWnd
, MLM_LINEFROMCHAR
, (MPARAM
)lPos
, 0);
786 // This gets the char index for the _beginning_ of this line
792 lLineWidth
= (long)::WinSendMsg(hWnd
, MLM_QUERYLINELENGTH
, (MPARAM
)0, (MPARAM
)0);
793 lCharIndex
= (nLineNo
+ 1) * lLineWidth
;
799 vParams
.fsStatus
= WPM_CCHTEXT
;
800 if (::WinSendMsg( hWnd
801 ,WM_QUERYWINDOWPARAMS
806 lCharIndex
= vParams
.cchText
;
812 if (lCharIndex
== -1)
818 // The X position must therefore be the difference between pos and charIndex
821 *plX
= lPos
- lCharIndex
;
826 } // end of wxTextCtrl::PositionToXY
828 void wxTextCtrl::ShowPosition( long WXUNUSED(lPos
) )
830 HWND hWnd
= GetHwnd();
831 long lCurrentLineLineNo
= 0L;
833 // To scroll to a position, we pass the number of lines and characters
834 // to scroll *by*. This means that we need to:
835 // (1) Find the line position of the current line.
836 // (2) Find the line position of pos.
837 // (3) Scroll by (pos - current).
838 // For now, ignore the horizontal scrolling.
841 // Is this where scrolling is relative to - the line containing the caret?
842 // Or is the first visible line??? Try first visible line.
847 // In PM this is the actual char position
849 lCurrentLineLineNo
= (long)::WinSendMsg(hWnd
, MLM_QUERYFIRSTCHAR
, (MPARAM
)0, (MPARAM
)0);
852 // This will cause a scroll to the selected position
854 ::WinSendMsg(hWnd
, MLM_SETSEL
, (MPARAM
)lCurrentLineLineNo
, (MPARAM
)lCurrentLineLineNo
);
856 } // end of wxTextCtrl::ShowPosition
858 int wxTextCtrl::GetLineLength( long WXUNUSED(lLineNo
) ) const
864 lLen
= (long)::WinSendMsg(GetHwnd(), MLM_QUERYLINELENGTH
, 0, 0);
870 vParams
.fsStatus
= WPM_CCHTEXT
;
871 if (::WinSendMsg( GetHwnd()
872 ,WM_QUERYWINDOWPARAMS
877 lLen
= vParams
.cchText
;
883 } // end ofwxTextCtrl::GetLineLength
885 wxString
wxTextCtrl::GetLineText(
889 long lLen
= (long)GetLineLength((long)lLineNo
) + 1;
894 // There must be at least enough place for the length WORD in the
897 lLen
+= sizeof(WORD
);
898 zBuf
= new wxChar
[lLen
];
905 lLen
= (long)::WinSendMsg(GetHwnd(), MLM_QUERYLINELENGTH
, 0, 0);
906 lIndex
= lLen
* lLineNo
;
908 ::WinSendMsg(GetHwnd(), MLM_SETSEL
, (MPARAM
)lIndex
, (MPARAM
)lIndex
);
909 ::WinSendMsg(GetHwnd(), MLM_SETIMPORTEXPORT
, MPFROMP(zBuf
), MPFROMSHORT((USHORT
)WXSIZEOF(zBuf
)));
910 lBuflen
= (long)::WinSendMsg(GetHwnd(), MLM_QUERYFORMATTEXTLENGTH
, MPFROMLONG(lIndex
), MPFROMLONG(-1));
911 lCopied
= (long)::WinSendMsg(GetHwnd(), MLM_EXPORT
, MPFROMP(&lIndex
), MPFROMP(&lBuflen
));
912 zBuf
[lCopied
] = '\0';
918 vParams
.fsStatus
= WPM_CCHTEXT
;
919 if (::WinSendMsg( GetHwnd()
920 ,WM_QUERYWINDOWPARAMS
924 memcpy((char*)zBuf
, vParams
.pszText
, vParams
.cchText
);
925 zBuf
[vParams
.cchText
] = '\0';
930 } // end of wxTextCtrl::GetLineText
932 // ----------------------------------------------------------------------------
934 // ----------------------------------------------------------------------------
936 void wxTextCtrl::Undo()
941 ::WinSendMsg(GetHwnd(), MLM_UNDO
, 0, 0);
942 // Simple entryfields cannot be undone
944 } // end of wxTextCtrl::Undo
946 void wxTextCtrl::Redo()
951 ::WinSendMsg(GetHwnd(), MLM_UNDO
, 0, 0);
952 // Simple entryfields cannot be undone
954 } // end of wxTextCtrl::Redo
956 bool wxTextCtrl::CanUndo() const
961 bOk
= (::WinSendMsg(GetHwnd(), MLM_QUERYUNDO
, 0, 0) != 0);
963 bOk
= false; // can't undo regular edit fields in PM
965 } // end of wxTextCtrl::CanUndo
967 bool wxTextCtrl::CanRedo() const
972 bOk
= (::WinSendMsg(GetHwnd(), MLM_QUERYUNDO
, 0, 0) != 0);
974 bOk
= false; // can't undo regular edit fields in PM
976 } // end of wxTextCtrl::CanRedo
978 // ----------------------------------------------------------------------------
979 // implemenation details
980 // ----------------------------------------------------------------------------
982 void wxTextCtrl::Command(
983 wxCommandEvent
& rEvent
986 SetValue(rEvent
.GetString());
987 ProcessCommand (rEvent
);
988 } // end of wxTextCtrl::Command
990 void wxTextCtrl::OnDropFiles(
991 wxDropFilesEvent
& rEvent
994 // By default, load the first file into the text window.
995 if (rEvent
.GetNumberOfFiles() > 0)
997 LoadFile(rEvent
.GetFiles()[0]);
999 } // end of wxTextCtrl::OnDropFiles
1001 WXHBRUSH
wxTextCtrl::OnCtlColor( WXHDC hWxDC
,
1002 WXHWND
WXUNUSED(hWnd
),
1003 WXUINT
WXUNUSED(uCtlColor
),
1004 WXUINT
WXUNUSED(uMessage
),
1005 WXWPARAM
WXUNUSED(wParam
),
1006 WXLPARAM
WXUNUSED(lParam
) )
1008 HPS hPS
= (HPS
)hWxDC
;
1009 wxColour vColBack
= GetBackgroundColour();
1010 wxColour vColFore
= GetForegroundColour();
1011 wxBrush
* pBackgroundBrush
= wxTheBrushList
->FindOrCreateBrush( vColBack
, wxSOLID
);
1015 HBRUSH hBrush
= NULLHANDLE
;
1019 if (GetParent()->GetTransparentBackground())
1020 ::GpiSetBackMix(hPS
, BM_LEAVEALONE
);
1022 ::GpiSetBackMix(hPS
, BM_OVERPAINT
);
1023 if (!IsEnabled() && (GetWindowStyle() & wxTE_MULTILINE
) == 0)
1024 vColBack
= wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE
);
1025 ::GpiSetBackColor(hPS
, vColBack
.GetPixel());
1026 ::GpiSetColor(hPS
, vColFore
.GetPixel());
1027 return (WXHBRUSH
)pBackgroundBrush
->GetResourceHandle();
1028 } // end of wxTextCtrl::OnCtlColor
1030 bool wxTextCtrl::OS2ShouldPreProcessMessage(
1034 return wxControl::OS2ShouldPreProcessMessage(pMsg
);
1035 } // end of wxTextCtrl::OS2ShouldPreProcessMessage
1037 void wxTextCtrl::OnChar(
1041 switch (rEvent
.GetKeyCode())
1044 if ( !(m_windowStyle
& wxTE_MULTILINE
) )
1046 wxCommandEvent
vEvent(wxEVT_TEXT_ENTER
, m_windowId
);
1048 vEvent
.SetEventObject(this);
1049 if ( HandleWindowEvent(vEvent
))
1052 //else: multiline controls need Enter for themselves
1057 // always produce navigation event - even if we process TAB
1058 // ourselves the fact that we got here means that the user code
1059 // decided to skip processing of this TAB - probably to let it
1060 // do its default job.
1062 // NB: Notice that Ctrl-Tab is handled elsewhere and Alt-Tab is
1063 // handled by Windows
1065 wxNavigationKeyEvent vEventNav
;
1067 vEventNav
.SetDirection(!rEvent
.ShiftDown());
1068 vEventNav
.SetWindowChange(false);
1069 vEventNav
.SetEventObject(this);
1071 if ( HandleWindowEvent(vEventNav
) )
1077 } // end of wxTextCtrl::OnChar
1079 bool wxTextCtrl::OS2Command(
1081 , WXWORD
WXUNUSED(vId
)
1089 wxFocusEvent
vEvent( uParam
== EN_KILLFOCUS
? wxEVT_KILL_FOCUS
1094 vEvent
.SetEventObject(this);
1095 HandleWindowEvent(vEvent
);
1103 m_bSkipUpdate
= false;
1107 wxCommandEvent
vEvent( wxEVT_TEXT
1111 InitCommandEvent(vEvent
);
1112 ProcessCommand(vEvent
);
1118 // The text size limit has been hit - increase it
1124 case EN_INSERTMODETOGGLE
:
1135 } // end of wxTextCtrl::OS2Command
1137 void wxTextCtrl::AdjustSpaceLimit()
1139 unsigned int uLen
= 0;
1140 unsigned int uLimit
= 0;
1142 uLen
= ::WinQueryWindowTextLength(GetHwnd());
1145 uLimit
= (unsigned int)::WinSendMsg( GetHwnd()
1156 vParams
.fsStatus
= WPM_CBCTLDATA
;
1157 vParams
.pCtlData
= &Efd
;
1158 vParams
.cbCtlData
= sizeof(ENTRYFDATA
);
1160 if (::WinSendMsg( GetHwnd()
1161 ,WM_QUERYWINDOWPARAMS
1165 uLimit
= (unsigned int)Efd
.cchEditLimit
;
1167 uLimit
= 32; //PM's default
1173 uLimit
= uLen
+ 0x8000; // 32Kb
1174 if (uLimit
> 0xffff)
1183 ::WinSendMsg(GetHwnd(), MLM_SETTEXTLIMIT
, MPFROMLONG(uLimit
), 0);
1185 ::WinSendMsg(GetHwnd(), EM_SETTEXTLIMIT
, MPFROMSHORT(uLimit
), 0);
1187 } // end of wxTextCtrl::AdjustSpaceLimit
1189 bool wxTextCtrl::AcceptsFocus() const
1192 // We don't want focus if we can't be edited unless we're a multiline
1193 // control because then it might be still nice to get focus from keyboard
1194 // to be able to scroll it without mouse
1196 return (IsEditable() || IsMultiLine()) && wxControl::AcceptsFocus();
1197 } // end of wxTextCtrl::Command
1199 wxSize
wxTextCtrl::DoGetBestSize() const
1203 wxFont vFont
= (wxFont
)GetFont();
1205 wxGetCharSize(GetHWND(), &nCx
, &nCy
, &vFont
);
1207 int wText
= DEFAULT_ITEM_WIDTH
;
1208 int hText
= (int)(EDIT_HEIGHT_FROM_CHAR_HEIGHT(nCy
) * .8);
1210 if (m_windowStyle
& wxTE_MULTILINE
)
1212 hText
*= wxMax(GetNumberOfLines(), 5);
1214 //else: for single line control everything is ok
1215 return wxSize(wText
, hText
);
1216 } // end of wxTextCtrl::DoGetBestSize
1218 // ----------------------------------------------------------------------------
1219 // standard handlers for standard edit menu events
1220 // ----------------------------------------------------------------------------
1222 void wxTextCtrl::OnCut( wxCommandEvent
& WXUNUSED(rEvent
) )
1225 } // end of wxTextCtrl::OnCut
1227 void wxTextCtrl::OnCopy( wxCommandEvent
& WXUNUSED(rEvent
) )
1230 } // end of wxTextCtrl::OnCopy
1232 void wxTextCtrl::OnPaste( wxCommandEvent
& WXUNUSED(rEvent
) )
1235 } // end of wxTextCtrl::OnPaste
1237 void wxTextCtrl::OnUndo( wxCommandEvent
& WXUNUSED(rEvent
) )
1240 } // end of wxTextCtrl::OnUndo
1242 void wxTextCtrl::OnRedo( wxCommandEvent
& WXUNUSED(rEvent
) )
1245 } // end of wxTextCtrl::OnRedo
1247 void wxTextCtrl::OnDelete( wxCommandEvent
& WXUNUSED(rEvent
) )
1251 GetSelection( &lFrom
, &lTo
);
1253 if (lFrom
!= -1 && lTo
!= -1)
1254 Remove( lFrom
, lTo
);
1255 } // end of wxTextCtrl::OnDelete
1257 void wxTextCtrl::OnSelectAll( wxCommandEvent
& WXUNUSED(rEvent
) )
1259 SetSelection(-1, -1);
1260 } // end of wxTextCtrl::OnSelectAll
1262 void wxTextCtrl::OnUpdateCut( wxUpdateUIEvent
& rEvent
)
1264 rEvent
.Enable(CanCut());
1265 } // end of wxTextCtrl::OnUpdateCut
1267 void wxTextCtrl::OnUpdateCopy( wxUpdateUIEvent
& rEvent
)
1269 rEvent
.Enable(CanCopy());
1270 } // end of wxTextCtrl::OnUpdateCopy
1272 void wxTextCtrl::OnUpdatePaste( wxUpdateUIEvent
& rEvent
)
1274 rEvent
.Enable(CanPaste());
1275 } // end of wxTextCtrl::OnUpdatePaste
1277 void wxTextCtrl::OnUpdateUndo( wxUpdateUIEvent
& rEvent
)
1279 rEvent
.Enable(CanUndo());
1280 } // end of wxTextCtrl::OnUpdateUndo
1282 void wxTextCtrl::OnUpdateRedo( wxUpdateUIEvent
& rEvent
)
1284 rEvent
.Enable(CanRedo());
1285 } // end of wxTextCtrl::OnUpdateRedo
1287 void wxTextCtrl::OnUpdateDelete( wxUpdateUIEvent
& rEvent
)
1291 GetSelection( &lFrom
, &lTo
);
1292 rEvent
.Enable( lFrom
!= -1L && lTo
!= -1L && lFrom
!= lTo
&& IsEditable()) ;
1293 } // end of wxTextCtrl::OnUpdateDelete
1295 void wxTextCtrl::OnUpdateSelectAll( wxUpdateUIEvent
& rEvent
)
1297 rEvent
.Enable(GetLastPosition() > 0);
1298 } // end of wxTextCtrl::OnUpdateSelectAll
1300 bool wxTextCtrl::SetBackgroundColour( const wxColour
& rColour
)
1303 ::WinSendMsg(GetHwnd(), MLM_SETBACKCOLOR
, (MPARAM
)rColour
.GetPixel(), MLE_INDEX
);
1305 } // end of wxTextCtrl::SetBackgroundColour
1307 bool wxTextCtrl::SetForegroundColour( const wxColour
& rColour
)
1310 ::WinSendMsg(GetHwnd(), MLM_SETTEXTCOLOR
, (MPARAM
)rColour
.GetPixel(), MLE_INDEX
);
1312 } // end of wxTextCtrl::SetForegroundColour
1314 bool wxTextCtrl::SetStyle( long lStart
,
1316 const wxTextAttr
& WXUNUSED(rStyle
) )
1318 HWND hWnd
= GetHwnd();
1329 // We can only change the format of the selection, so select the range we
1330 // want and restore the old selection later
1332 long lStartOld
, lEndOld
;
1334 GetSelection( &lStartOld
, &lEndOld
);
1337 // But do we really have to change the selection?
1339 bool bChangeSel
= lStart
!= lStartOld
||
1345 ::WinSendMsg(hWnd
, MLM_SETSEL
, MPFROM2SHORT((USHORT
)lStart
, (USHORT
)lEnd
), 0);
1347 ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lStart
, (USHORT
)lEnd
), 0);
1351 // TODO:: finish this part
1354 } // end of wxTextCtrl::SetStyle