1 ///////////////////////////////////////////////////////////////////////////// 
   3 // Purpose:     wxComboBox class 
   4 // Author:      David Webster 
   8 // Copyright:   (c) David Webster 
   9 // Licence:     wxWindows licence 
  10 ///////////////////////////////////////////////////////////////////////////// 
  12 #include "wx/combobox.h" 
  14 // For compilers that support precompilation, includes "wx.h". 
  15 #include "wx/wxprec.h" 
  19     #include "wx/settings.h" 
  24 #include "wx/combobox.h" 
  25 #include "wx/clipbrd.h" 
  26 #include "wx/os2/private.h" 
  28 #define OWNER_DRAWN_LISTBOX_EXTRA_SPACE    (1) 
  30 MRESULT EXPENTRY 
wxComboEditWndProc( HWND   hWnd
 
  36 // The pointer to standard wnd proc 
  38 static WXFARPROC gfnWndprocEdit     
= (WXFARPROC
)NULL
; 
  40 IMPLEMENT_DYNAMIC_CLASS(wxComboBox
, wxControl
) 
  42 bool wxComboBox::OS2Command( 
  44 , WXWORD                            
WXUNUSED(wId
) 
  53             if (GetSelection() > -1) 
  55                 wxCommandEvent      
vEvent( wxEVT_COMMAND_COMBOBOX_SELECTED
 
  59                 vEvent
.SetInt(GetSelection()); 
  60                 vEvent
.SetEventObject(this); 
  61                 vEvent
.SetString((char*)GetStringSelection().c_str()); 
  62                 ProcessCommand(vEvent
); 
  68                 wxCommandEvent      
vEvent( wxEVT_COMMAND_TEXT_UPDATED
 
  76                 vEvent
.SetString((char*)GetValue().c_str()); 
  77                 vEvent
.SetEventObject(this); 
  78                 ProcessCommand(vEvent
); 
  83     // There is no return value for the CBN_ notifications, so always return 
  84     // FALSE from here to pass the message to DefWindowProc() 
  87 } // end of wxComboBox::OS2Command 
  89 bool wxComboBox::Create( 
  92 , const wxString
&                   rsValue
 
  96 , const wxString                    asChoices
[] 
  99 , const wxValidator
&                rValidator
 
 101 , const wxString
&                   rsName
 
 105     if (!CreateControl( pParent
 
 118     // Get the right style 
 122     lSstyle 
= WS_TABSTOP   
| 
 125     if (lStyle 
& wxCLIP_SIBLINGS 
) 
 126         lSstyle 
|= WS_CLIPSIBLINGS
; 
 127     if (lStyle 
& wxCB_READONLY
) 
 128         lSstyle 
|= CBS_DROPDOWNLIST
; 
 129     else if (lStyle 
& wxCB_SIMPLE
) 
 130         lSstyle 
|= CBS_SIMPLE
; // A list (shown always) and edit control 
 132         lSstyle 
|= CBS_DROPDOWN
; 
 135     if (!OS2CreateControl( "COMBOBOX" 
 141     // A choice/combobox normally has a white background (or other, depending 
 142     // on global settings) rather than inheriting the parent's background colour. 
 144     SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW
)); 
 146     wxFont
*                          pTextFont 
= new wxFont( 10 
 154     for (i 
= 0; i 
< n
; i
++) 
 156         Append(asChoices
[i
]); 
 164     if (!rsValue
.IsEmpty()) 
 168     gfnWndprocEdit 
= (WXFARPROC
)::WinSubclassWindow( (HWND
)GetHwnd() 
 169                                                     ,(PFNWP
)wxComboEditWndProc
 
 171     ::WinSetWindowULong(GetHwnd(), QWL_USER
, (ULONG
)this); 
 174 } // end of wxComboBox::Create 
 176 void wxComboBox::SetValue( 
 177   const wxString
&                   rsValue
 
 181     // If newlines are denoted by just 10, must stick 13 in front. 
 184     int                             nLen 
= rsValue
.Length(); 
 187     for (i 
= 0; i 
< nLen
; i 
++) 
 189         if ((i 
> 0) && (rsValue
[i
] == 10) && (rsValue
[i 
- 1] != 13)) 
 194         wxChar
*                     zTmp 
= new wxChar
[nLen 
+ nSingletons 
+ 1]; 
 197         for (i 
= 0; i 
< nLen
; i 
++) 
 199             if ((i 
> 0) && (rsValue
[i
] == 10) && (rsValue
[i 
- 1] != 13)) 
 204             zTmp
[j
] = rsValue
[i
]; 
 208         ::WinSetWindowText(GetHwnd(), zTmp
); 
 212         ::WinSetWindowText(GetHwnd(), rsValue
.c_str()); 
 213 } // end of wxComboBox::SetValue 
 216 // Clipboard operations 
 218 void wxComboBox::Copy() 
 220     HWND                            hWnd 
= GetHwnd(); 
 222     ::WinSendMsg(hWnd
, EM_COPY
, (MPARAM
)0, (MPARAM
)0); 
 223 } // end of wxComboBox::Copy 
 225 void wxComboBox::Cut() 
 227     HWND                            hWnd 
= GetHwnd(); 
 229     ::WinSendMsg(hWnd
, EM_CUT
, (MPARAM
)0, (MPARAM
)0); 
 230 } // end of wxComboBox::Cut 
 232 void wxComboBox::Paste() 
 234     HWND                            hWnd 
= GetHwnd(); 
 236     ::WinSendMsg(hWnd
, EM_PASTE
, (MPARAM
)0, (MPARAM
)0); 
 237 } // end of wxComboBox::Paste 
 239 void wxComboBox::SetEditable( 
 243     HWND                            hWnd 
= GetHwnd(); 
 245     ::WinSendMsg(hWnd
, EM_SETREADONLY
, (MPARAM
)!bEditable
, (MPARAM
)0L); 
 246 } // end of wxComboBox::SetEditable 
 248 void wxComboBox::SetInsertionPoint( 
 252     HWND                            hWnd 
= GetHwnd(); 
 254     ::WinSendMsg(hWnd
, EM_SETFIRSTCHAR
, MPFROMLONG(lPos
), (MPARAM
)0); 
 255 } // end of wxComboBox::SetInsertionPoint 
 257 void wxComboBox::SetInsertionPointEnd() 
 259     long                            lPos 
= GetLastPosition(); 
 261     SetInsertionPoint(lPos
); 
 262 } // end of wxComboBox::SetInsertionPointEnd 
 264 long wxComboBox::GetInsertionPoint() const 
 266     long                            lPos 
= LONGFROMMR(::WinSendMsg( GetHwnd() 
 271    if (lPos 
== LIT_NONE
) 
 274 } // end of wxComboBox::GetInsertionPoint 
 276 long wxComboBox::GetLastPosition() const 
 278     HWND                            hEditWnd 
= GetHwnd(); 
 279     long                            lLineLength 
= 0L; 
 283     // Get number of characters in the last (only) line. We'll add this to the character 
 284     // index for the last line, 1st position. 
 288     vParams
.fsStatus 
= WPM_CCHTEXT
; 
 289     if (::WinSendMsg( GetHwnd() 
 290                      ,WM_QUERYWINDOWPARAMS
 
 295         lLineLength 
= (long)vParams
.cchText
; 
 300 } // end of wxComboBox::GetLastPosition 
 302 void wxComboBox::Replace( 
 305 , const wxString
&                   rsValue
 
 309     HWND                            hWnd 
= GetHwnd(); 
 310     long                            lFromChar 
= lFrom
; 
 314     // Set selection and remove it 
 316     ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lFrom
, (USHORT
)lTo
), 0); 
 317     ::WinSendMsg(hWnd
, EM_CUT
, (MPARAM
)0, (MPARAM
)0); 
 320     // Now replace with 'value', by pasting. 
 322     wxSetClipboardData( wxDF_TEXT
 
 323                        ,(wxObject 
*)rsValue
.c_str() 
 329     // Paste into edit control 
 331     ::WinSendMsg(hWnd
, EM_PASTE
, (MPARAM
)0, (MPARAM
)0L); 
 333 } // end of wxComboBox::Replace 
 335 void wxComboBox::Remove( 
 341     HWND                            hWnd 
= GetHwnd(); 
 342     long                            lFromChar 
= lFrom
; 
 345     ::WinSendMsg(hWnd
, EM_SETSEL
, MPFROM2SHORT((USHORT
)lFrom
, (USHORT
)lTo
), 0); 
 346     ::WinSendMsg(hWnd
, EM_CUT
, (MPARAM
)0, (MPARAM
)0); 
 348 } // end of wxComboBox::Remove 
 350 void wxComboBox::SetSelection( 
 355     HWND                            hWnd 
= GetHwnd(); 
 356     long                            lFromChar 
= lFrom
; 
 360     // If from and to are both -1, it means 
 361     // (in wxWindows) that all text should be selected. 
 362     // This translates into Windows convention 
 364     if ((lFrom 
== -1L) && (lTo 
== -1L)) 
 372                  ,MPFROM2SHORT((USHORT
)lFromChar
, (USHORT
)lToChar
) 
 375 } // end of wxComboBox::SetSelection 
 377 void wxComboBox::DoSetSize( 
 385     wxControl::DoSetSize( nX
 
 391 } // end of wxComboBox::DoSetSize 
 393 bool wxComboBox::ProcessEditMsg( 
 402             vFlag 
= SHORT1FROMMP(wParam
); 
 406                     return (HandleChar( SHORT1FROMMP(wParam
) 
 412                     return (HandleKeyDown( SHORT1FROMMP(wParam
) 
 417                     return (HandleKeyUp( SHORT1FROMMP(wParam
) 
 424 } // end of WinGuiBase_CComboBox::ProcessEditMsg 
 426 MRESULT EXPENTRY 
wxComboEditWndProc( 
 434     wxWindow
*                       pWin 
= NULL
; 
 436     hWndCombo 
= ::WinQueryWindow(hWnd
, QW_PARENT
); 
 437     pWin 
= (wxWindow
*)wxFindWinFromHandle((WXHWND
)hWndCombo
); 
 441         // Forward some messages to the combobox 
 445                 wxComboBox
*         pCombo 
= wxDynamicCast( pWin
 
 449                 if (pCombo
->ProcessEditMsg( uMessage
 
 458         // TODO: Deal with tooltips here 
 461     return (gfnWndprocEdit(hWnd
, (ULONG
)uMessage
, (MPARAM
)wParam
, (MPARAM
)lParam
)); 
 462 } // end of wxComboEditWndProc