wxSTCListBox(wxWindow* parent, wxWindowID id,
const wxPoint& pos, const wxSize& size,
long style)
- : wxListView(parent, id, pos, size, style)
- {}
+ : wxListView()
+ {
+#ifdef __WXMSW__
+ Hide(); // don't flicker as we move it around...
+#endif
+ Create(parent, id, pos, size, style);
+ }
void OnFocus(wxFocusEvent& event) {
+#if wxUSE_POPUPWIN //-----------------------------------
+#include <wx/popupwin.h>
+
+
+//
+// TODO: Refactor these two classes to have a common base (or a mix-in) to get
+// rid of the code duplication. (Either that or convince somebody to
+// implement wxPopupWindow for the Mac!!)
+//
+// In the meantime, be careful to duplicate any changes as needed...
+//
+
+// A popup window to place the wxSTCListBox upon
+class wxSTCListBoxWin : public wxPopupWindow
+{
+private:
+ wxListView* lv;
+ CallBackAction doubleClickAction;
+ void* doubleClickActionData;
+public:
+ wxSTCListBoxWin(wxWindow* parent, wxWindowID id) :
+ wxPopupWindow(parent, wxBORDER_NONE)
+ {
+ SetBackgroundColour(*wxBLACK); // for our simple border
+
+ lv = new wxSTCListBox(parent, id, wxDefaultPosition, wxDefaultSize,
+ wxLC_REPORT | wxLC_SINGLE_SEL | wxLC_NO_HEADER | wxBORDER_NONE);
+ lv->SetCursor(wxCursor(wxCURSOR_ARROW));
+ lv->InsertColumn(0, wxEmptyString);
+ lv->InsertColumn(1, wxEmptyString);
+
+ // NOTE: We need to fool the wxListView into thinking that it has the
+ // focus so it will use the normal selection colour and will look
+ // "right" to the user. But since the wxPopupWindow or its children
+ // can't receive focus then we have to pull a fast one and temporarily
+ // parent the listctrl on the STC window and then call SetFocus and
+ // then reparent it back to the popup.
+ lv->SetFocus();
+ lv->Reparent(this);
+#ifdef __WXMSW__
+ lv->Show();
+#endif
+ }
+
+
+ // Set position in client coords
+ virtual void DoSetSize(int x, int y,
+ int width, int height,
+ int sizeFlags = wxSIZE_AUTO) {
+ if (x != wxDefaultCoord) {
+ GetParent()->ClientToScreen(&x, NULL);
+ }
+ if (y != wxDefaultCoord) {
+ GetParent()->ClientToScreen(NULL, &y);
+ }
+ wxPopupWindow::DoSetSize(x, y, width, height, sizeFlags);
+ }
+
+ // return position as if it were in client coords
+ virtual void DoGetPosition( int *x, int *y ) const {
+ int sx, sy;
+ wxPopupWindow::DoGetPosition(&sx, &sy);
+ GetParent()->ScreenToClient(&sx, &sy);
+ if (x) *x = sx;
+ if (y) *y = sy;
+ }
+
+
+ bool Destroy() {
+ if ( !wxPendingDelete.Member(this) )
+ wxPendingDelete.Append(this);
+ return true;
+ }
+
+
+ int IconWidth() {
+ wxImageList* il = lv->GetImageList(wxIMAGE_LIST_SMALL);
+ if (il != NULL) {
+ int w, h;
+ il->GetSize(0, w, h);
+ return w;
+ }
+ return 0;
+ }
+
+
+ void SetDoubleClickAction(CallBackAction action, void *data) {
+ doubleClickAction = action;
+ doubleClickActionData = data;
+ }
+
+
+ void OnFocus(wxFocusEvent& event) {
+ GetParent()->SetFocus();
+ event.Skip();
+ }
+
+ void OnSize(wxSizeEvent& event) {
+ // resize the child
+ wxSize sz = GetSize();
+ sz.x -= 2;
+ sz.y -= 2;
+ lv->SetSize(1, 1, sz.x, sz.y);
+ // reset the column widths
+ lv->SetColumnWidth(0, IconWidth()+4);
+ lv->SetColumnWidth(1, sz.x - 2 - lv->GetColumnWidth(0) -
+ wxSystemSettings::GetMetric(wxSYS_VSCROLL_X));
+ event.Skip();
+ }
+
+ void OnActivate(wxListEvent& WXUNUSED(event)) {
+ doubleClickAction(doubleClickActionData);
+ }
+
+ wxListView* GetLB() { return lv; }
+
+private:
+ DECLARE_EVENT_TABLE()
+
+};
+
+BEGIN_EVENT_TABLE(wxSTCListBoxWin, wxPopupWindow)
+ EVT_SET_FOCUS ( wxSTCListBoxWin::OnFocus)
+ EVT_SIZE ( wxSTCListBoxWin::OnSize)
+ EVT_LIST_ITEM_ACTIVATED(wxID_ANY, wxSTCListBoxWin::OnActivate)
+END_EVENT_TABLE()
+
+
+
+#else // wxUSE_POPUPWIN -----------------------------------
-// A window to place the wxSTCListBox upon
+// A normal window to place the wxSTCListBox upon.
class wxSTCListBoxWin : public wxWindow {
private:
wxListView* lv;
EVT_LIST_ITEM_ACTIVATED(wxID_ANY, wxSTCListBoxWin::OnActivate)
END_EVENT_TABLE()
+#endif // wxUSE_POPUPWIN -----------------------------------
inline wxSTCListBoxWin* GETLBW(WindowID win) {
HorizontalScrollTo(column * vs.spaceWidth);
}
-#ifdef __WXGTK__
-void ScintillaWX::ClipChildren(wxDC& dc, PRectangle rect) {
- wxRegion rgn(wxRectFromPRectangle(rect));
- if (ac.Active()) {
- wxRect childRect = ((wxWindow*)ac.lb->GetID())->GetRect();
- rgn.Subtract(childRect);
- }
- if (ct.inCallTipMode) {
- wxSTCCallTip* tip = (wxSTCCallTip*)ct.wCallTip.GetID();
- wxRect childRect = tip->GetRect();
-#if wxUSE_POPUPWIN && wxSTC_USE_POPUP
- childRect.SetPosition(tip->GetMyPosition());
-#endif
- rgn.Subtract(childRect);
- }
-
- dc.SetClippingRegion(rgn);
-}
-#else
-void ScintillaWX::ClipChildren(wxDC& WXUNUSED(dc), PRectangle WXUNUSED(rect)) {
+// wxGTK doesn't appear to need this explicit clipping code any longer, but I
+// will leave it here commented out for a while just in case...
+void ScintillaWX::ClipChildren(wxDC& WXUNUSED(dc), PRectangle WXUNUSED(rect))
+{
+// wxRegion rgn(wxRectFromPRectangle(rect));
+// if (ac.Active()) {
+// wxRect childRect = ((wxWindow*)ac.lb->GetID())->GetRect();
+// rgn.Subtract(childRect);
+// }
+// if (ct.inCallTipMode) {
+// wxSTCCallTip* tip = (wxSTCCallTip*)ct.wCallTip.GetID();
+// wxRect childRect = tip->GetRect();
+// #if wxUSE_POPUPWIN && wxSTC_USE_POPUP
+// childRect.SetPosition(tip->GetMyPosition());
+// #endif
+// rgn.Subtract(childRect);
+// }
+// dc.SetClippingRegion(rgn);
}
-#endif
void ScintillaWX::SetUseAntiAliasing(bool useAA) {
wxSTCListBox(wxWindow* parent, wxWindowID id,
const wxPoint& pos, const wxSize& size,
long style)
- : wxListView(parent, id, pos, size, style)
- {}
+ : wxListView()
+ {
+#ifdef __WXMSW__
+ Hide(); // don't flicker as we move it around...
+#endif
+ Create(parent, id, pos, size, style);
+ }
void OnFocus(wxFocusEvent& event) {
+#if wxUSE_POPUPWIN //-----------------------------------
+#include <wx/popupwin.h>
+
+
+//
+// TODO: Refactor these two classes to have a common base (or a mix-in) to get
+// rid of the code duplication. (Either that or convince somebody to
+// implement wxPopupWindow for the Mac!!)
+//
+// In the meantime, be careful to duplicate any changes as needed...
+//
+
+// A popup window to place the wxSTCListBox upon
+class wxSTCListBoxWin : public wxPopupWindow
+{
+private:
+ wxListView* lv;
+ CallBackAction doubleClickAction;
+ void* doubleClickActionData;
+public:
+ wxSTCListBoxWin(wxWindow* parent, wxWindowID id) :
+ wxPopupWindow(parent, wxBORDER_NONE)
+ {
+ SetBackgroundColour(*wxBLACK); // for our simple border
+
+ lv = new wxSTCListBox(parent, id, wxDefaultPosition, wxDefaultSize,
+ wxLC_REPORT | wxLC_SINGLE_SEL | wxLC_NO_HEADER | wxBORDER_NONE);
+ lv->SetCursor(wxCursor(wxCURSOR_ARROW));
+ lv->InsertColumn(0, wxEmptyString);
+ lv->InsertColumn(1, wxEmptyString);
+
+ // NOTE: We need to fool the wxListView into thinking that it has the
+ // focus so it will use the normal selection colour and will look
+ // "right" to the user. But since the wxPopupWindow or its children
+ // can't receive focus then we have to pull a fast one and temporarily
+ // parent the listctrl on the STC window and then call SetFocus and
+ // then reparent it back to the popup.
+ lv->SetFocus();
+ lv->Reparent(this);
+#ifdef __WXMSW__
+ lv->Show();
+#endif
+ }
+
+
+ // Set position in client coords
+ virtual void DoSetSize(int x, int y,
+ int width, int height,
+ int sizeFlags = wxSIZE_AUTO) {
+ if (x != wxDefaultCoord) {
+ GetParent()->ClientToScreen(&x, NULL);
+ }
+ if (y != wxDefaultCoord) {
+ GetParent()->ClientToScreen(NULL, &y);
+ }
+ wxPopupWindow::DoSetSize(x, y, width, height, sizeFlags);
+ }
+
+ // return position as if it were in client coords
+ virtual void DoGetPosition( int *x, int *y ) const {
+ int sx, sy;
+ wxPopupWindow::DoGetPosition(&sx, &sy);
+ GetParent()->ScreenToClient(&sx, &sy);
+ if (x) *x = sx;
+ if (y) *y = sy;
+ }
+
+
+ bool Destroy() {
+ if ( !wxPendingDelete.Member(this) )
+ wxPendingDelete.Append(this);
+ return true;
+ }
+
+
+ int IconWidth() {
+ wxImageList* il = lv->GetImageList(wxIMAGE_LIST_SMALL);
+ if (il != NULL) {
+ int w, h;
+ il->GetSize(0, w, h);
+ return w;
+ }
+ return 0;
+ }
+
+
+ void SetDoubleClickAction(CallBackAction action, void *data) {
+ doubleClickAction = action;
+ doubleClickActionData = data;
+ }
+
+
+ void OnFocus(wxFocusEvent& event) {
+ GetParent()->SetFocus();
+ event.Skip();
+ }
+
+ void OnSize(wxSizeEvent& event) {
+ // resize the child
+ wxSize sz = GetSize();
+ sz.x -= 2;
+ sz.y -= 2;
+ lv->SetSize(1, 1, sz.x, sz.y);
+ // reset the column widths
+ lv->SetColumnWidth(0, IconWidth()+4);
+ lv->SetColumnWidth(1, sz.x - 2 - lv->GetColumnWidth(0) -
+ wxSystemSettings::GetMetric(wxSYS_VSCROLL_X));
+ event.Skip();
+ }
+
+ void OnActivate(wxListEvent& WXUNUSED(event)) {
+ doubleClickAction(doubleClickActionData);
+ }
+
+ wxListView* GetLB() { return lv; }
+
+private:
+ DECLARE_EVENT_TABLE()
+
+};
+
+BEGIN_EVENT_TABLE(wxSTCListBoxWin, wxPopupWindow)
+ EVT_SET_FOCUS ( wxSTCListBoxWin::OnFocus)
+ EVT_SIZE ( wxSTCListBoxWin::OnSize)
+ EVT_LIST_ITEM_ACTIVATED(wxID_ANY, wxSTCListBoxWin::OnActivate)
+END_EVENT_TABLE()
+
+
+
+#else // wxUSE_POPUPWIN -----------------------------------
-// A window to place the wxSTCListBox upon
+// A normal window to place the wxSTCListBox upon.
class wxSTCListBoxWin : public wxWindow {
private:
wxListView* lv;
EVT_LIST_ITEM_ACTIVATED(wxID_ANY, wxSTCListBoxWin::OnActivate)
END_EVENT_TABLE()
+#endif // wxUSE_POPUPWIN -----------------------------------
inline wxSTCListBoxWin* GETLBW(WindowID win) {
HorizontalScrollTo(column * vs.spaceWidth);
}
-#ifdef __WXGTK__
-void ScintillaWX::ClipChildren(wxDC& dc, PRectangle rect) {
- wxRegion rgn(wxRectFromPRectangle(rect));
- if (ac.Active()) {
- wxRect childRect = ((wxWindow*)ac.lb->GetID())->GetRect();
- rgn.Subtract(childRect);
- }
- if (ct.inCallTipMode) {
- wxSTCCallTip* tip = (wxSTCCallTip*)ct.wCallTip.GetID();
- wxRect childRect = tip->GetRect();
-#if wxUSE_POPUPWIN && wxSTC_USE_POPUP
- childRect.SetPosition(tip->GetMyPosition());
-#endif
- rgn.Subtract(childRect);
- }
-
- dc.SetClippingRegion(rgn);
-}
-#else
-void ScintillaWX::ClipChildren(wxDC& WXUNUSED(dc), PRectangle WXUNUSED(rect)) {
+// wxGTK doesn't appear to need this explicit clipping code any longer, but I
+// will leave it here commented out for a while just in case...
+void ScintillaWX::ClipChildren(wxDC& WXUNUSED(dc), PRectangle WXUNUSED(rect))
+{
+// wxRegion rgn(wxRectFromPRectangle(rect));
+// if (ac.Active()) {
+// wxRect childRect = ((wxWindow*)ac.lb->GetID())->GetRect();
+// rgn.Subtract(childRect);
+// }
+// if (ct.inCallTipMode) {
+// wxSTCCallTip* tip = (wxSTCCallTip*)ct.wCallTip.GetID();
+// wxRect childRect = tip->GetRect();
+// #if wxUSE_POPUPWIN && wxSTC_USE_POPUP
+// childRect.SetPosition(tip->GetMyPosition());
+// #endif
+// rgn.Subtract(childRect);
+// }
+// dc.SetClippingRegion(rgn);
}
-#endif
void ScintillaWX::SetUseAntiAliasing(bool useAA) {