UI: Replace custom wxCheckedListCtrl with new wxListCtrl checkboxes

This allows us to patch the game list offset more easily, since we can utilize game
This commit is contained in:
Crementif 2025-07-15 17:44:20 +02:00
parent 22c64282ea
commit 7f57039420
7 changed files with 16 additions and 630 deletions

View file

@ -114,8 +114,6 @@ add_library(CemuWxGui
windows/TextureRelationViewer
windows/TextureRelationViewer/TextureRelationWindow.cpp
windows/TextureRelationViewer/TextureRelationWindow.h
wxcomponents/checkedlistctrl.cpp
wxcomponents/checkedlistctrl.h
wxcomponents/checktree.cpp
wxcomponents/checktree.h
wxgui.h

View file

@ -3,7 +3,6 @@
#include <wx/wx.h>
#include <wx/dataview.h>
#include <wx/infobar.h>
#include "wxcomponents/checkedlistctrl.h"
#include "wxgui/PadViewFrame.h"
#include "wxgui/MemorySearcherTool.h"

View file

@ -4,6 +4,8 @@
#include <thread>
#include <atomic>
#include <wx/listctrl.h>
#include "Cafe/HW/MMU/MMU.h"
#include "util/helpers/helpers.h"
#include "wxgui/helpers/wxCustomEvents.h"

View file

@ -32,8 +32,8 @@ BreakpointWindow::BreakpointWindow(DebuggerWindow2& parent, const wxPoint& main_
wxBoxSizer* main_sizer = new wxBoxSizer(wxVERTICAL);
m_breakpoints = new wxCheckedListCtrl(this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxLC_REPORT);
m_breakpoints = new wxListView(this, wxID_ANY, wxDefaultPosition, wxDefaultSize);
m_breakpoints->EnableCheckBoxes(true);
wxListItem col0;
col0.SetId(ColumnEnabled);
@ -69,8 +69,8 @@ BreakpointWindow::BreakpointWindow(DebuggerWindow2& parent, const wxPoint& main_
if (parent.GetConfig().data().pin_to_main)
OnMainMove(main_position, main_size);
m_breakpoints->Bind(wxEVT_COMMAND_LIST_ITEM_CHECKED, (wxObjectEventFunction)&BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Bind(wxEVT_COMMAND_LIST_ITEM_UNCHECKED, (wxObjectEventFunction)&BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Bind(wxEVT_LIST_ITEM_CHECKED, &BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Bind(wxEVT_LIST_ITEM_UNCHECKED, &BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Bind(wxEVT_LEFT_DCLICK, &BreakpointWindow::OnLeftDClick, this);
m_breakpoints->Bind(wxEVT_RIGHT_DOWN, &BreakpointWindow::OnRightDown, this);
@ -79,8 +79,10 @@ BreakpointWindow::BreakpointWindow(DebuggerWindow2& parent, const wxPoint& main_
BreakpointWindow::~BreakpointWindow()
{
m_breakpoints->Unbind(wxEVT_COMMAND_LIST_ITEM_CHECKED, (wxObjectEventFunction)&BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Unbind(wxEVT_COMMAND_LIST_ITEM_UNCHECKED, (wxObjectEventFunction)&BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Unbind(wxEVT_LIST_ITEM_CHECKED, &BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Unbind(wxEVT_LIST_ITEM_UNCHECKED, &BreakpointWindow::OnBreakpointToggled, this);
m_breakpoints->Unbind(wxEVT_LEFT_DCLICK, &BreakpointWindow::OnLeftDClick, this);
m_breakpoints->Unbind(wxEVT_RIGHT_DOWN, &BreakpointWindow::OnRightDown, this);
}
void BreakpointWindow::OnMainMove(const wxPoint& main_position, const wxSize& main_size)
@ -105,11 +107,10 @@ void BreakpointWindow::OnUpdateView()
uint32_t i = 0;
for (const auto bpBase : debuggerState.breakpoints)
{
DebuggerBreakpoint* bp = bpBase;
while (bp)
{
wxListItem item;
wxListItem item = {};
item.SetId(i++);
const auto index = m_breakpoints->InsertItem(item);
@ -128,12 +129,11 @@ void BreakpointWindow::OnUpdateView()
m_breakpoints->SetItem(index, ColumnType, typeName);
m_breakpoints->SetItem(index, ColumnComment, bp->comment);
m_breakpoints->SetItemPtrData(item, (wxUIntPtr)bp);
m_breakpoints->Check(index, bp->enabled);
m_breakpoints->CheckItem(index, bp->enabled);
m_breakpoints->SetItemPtrData(index, (wxUIntPtr)bp);
bp = bp->next;
}
}
}
@ -150,11 +150,12 @@ void BreakpointWindow::OnBreakpointToggled(wxListEvent& event)
const int32_t index = event.GetIndex();
if (0 <= index && index < m_breakpoints->GetItemCount())
{
const bool state = m_breakpoints->IsChecked(index);
const bool state = m_breakpoints->IsItemChecked(index);
wxString line = m_breakpoints->GetItemText(index, ColumnAddress);
DebuggerBreakpoint* bp = (DebuggerBreakpoint*)m_breakpoints->GetItemData(index);
const uint32 address = std::stoul(line.c_str().AsChar(), nullptr, 16);
debugger_toggleBreakpoint(address, state, bp);
m_breakpoints->CheckItem(index, state);
}
}

View file

@ -1,5 +1,4 @@
#pragma once
#include "wxgui/wxcomponents/checkedlistctrl.h"
class DebuggerWindow2;
@ -21,5 +20,5 @@ private:
void OnContextMenuClick(wxCommandEvent& evt);
void OnContextMenuClickSelected(wxCommandEvent& evt);
wxCheckedListCtrl* m_breakpoints;
wxListView* m_breakpoints;
};

View file

@ -1,435 +0,0 @@
/////////////////////////////////////////////////////////////////////////////
// Name: checkedlistctrl.cpp
// Purpose: wxCheckedListCtrl
// Author: Unknown ? (found at http://wiki.wxwidgets.org/wiki.pl?WxListCtrl)
// Modified by: Francesco Montorsi
// Created: 2005/06/29
// RCS-ID: $Id: checkedlistctrl.cpp 1309 2010-05-01 09:49:59Z frm $
// Copyright: (c) 2005 Francesco Montorsi
// Licence: wxWidgets licence
/////////////////////////////////////////////////////////////////////////////
// For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
// includes
#include "wxgui/wxcomponents/checkedlistctrl.h"
#include <wx/icon.h>
#include <wx/settings.h>
#if wxUSE_CHECKEDLISTCTRL
#include <wx/renderer.h>
IMPLEMENT_CLASS(wxCheckedListCtrl, wxListCtrl)
BEGIN_EVENT_TABLE(wxCheckedListCtrl, wxListCtrl)
EVT_LEFT_DOWN(wxCheckedListCtrl::OnMouseEvent)
END_EVENT_TABLE()
DEFINE_EVENT_TYPE(wxEVT_COMMAND_LIST_ITEM_CHECKED);
DEFINE_EVENT_TYPE(wxEVT_COMMAND_LIST_ITEM_UNCHECKED);
// ------------------
// wxCHECKEDLISTCTRL
// ------------------
bool wxCheckedListCtrl::Create(wxWindow* parent, wxWindowID id, const wxPoint& pt,
const wxSize& sz, long style, const wxValidator& validator, const wxString& name)
{
if (!wxListCtrl::Create(parent, id, pt, sz, style, validator, name))
return FALSE;
// Get the native size of the checkbox
int width = wxRendererNative::Get().GetCheckBoxSize(this).GetWidth();
int height = wxRendererNative::Get().GetCheckBoxSize(this).GetHeight();
m_imageList = new wxImageList(width, height, TRUE);
SetImageList(m_imageList, wxIMAGE_LIST_SMALL);
wxBitmap unchecked_bmp(width, height),
checked_bmp(width, height),
unchecked_disabled_bmp(width, height),
checked_disabled_bmp(width, height);
wxMemoryDC renderer_dc;
// Unchecked
renderer_dc.SelectObject(unchecked_bmp);
renderer_dc.SetBackground(*wxTheBrushList->FindOrCreateBrush(GetBackgroundColour(), wxSOLID));
renderer_dc.Clear();
wxRendererNative::Get().DrawCheckBox(this, renderer_dc, wxRect(0, 0, width, height), 0);
// Checked
renderer_dc.SelectObject(checked_bmp);
renderer_dc.SetBackground(*wxTheBrushList->FindOrCreateBrush(GetBackgroundColour(), wxSOLID));
renderer_dc.Clear();
wxRendererNative::Get().DrawCheckBox(this, renderer_dc, wxRect(0, 0, width, height), wxCONTROL_CHECKED);
// Unchecked and Disabled
renderer_dc.SelectObject(unchecked_disabled_bmp);
renderer_dc.SetBackground(*wxTheBrushList->FindOrCreateBrush(GetBackgroundColour(), wxSOLID));
renderer_dc.Clear();
wxRendererNative::Get().DrawCheckBox(this, renderer_dc, wxRect(0, 0, width, height), 0 | wxCONTROL_DISABLED);
// Checked and Disabled
renderer_dc.SelectObject(checked_disabled_bmp);
renderer_dc.SetBackground(*wxTheBrushList->FindOrCreateBrush(GetBackgroundColour(), wxSOLID));
renderer_dc.Clear();
wxRendererNative::Get().DrawCheckBox(this, renderer_dc, wxRect(0, 0, width, height), wxCONTROL_CHECKED | wxCONTROL_DISABLED);
// Deselect the renderers Object
renderer_dc.SelectObject(wxNullBitmap);
// the add order is important: the first added image will be
m_imageList->Add(unchecked_bmp);
m_imageList->Add(checked_bmp);
m_imageList->Add(unchecked_disabled_bmp);
m_imageList->Add(checked_disabled_bmp);
return TRUE;
}
/* static */
int wxCheckedListCtrl::GetItemImageFromAdditionalState(int addstate)
{
bool checked = (addstate & wxLIST_STATE_CHECKED) != 0;
bool enabled = (addstate & wxLIST_STATE_ENABLED) != 0;
if (checked && enabled)
return wxCLC_CHECKED_IMGIDX;
else if (checked && !enabled)
return wxCLC_DISABLED_CHECKED_IMGIDX;
else if (!checked && enabled)
return wxCLC_UNCHECKED_IMGIDX;
wxASSERT(!checked && !enabled); // this is the last possibility
return wxCLC_DISABLED_UNCHECKED_IMGIDX;
}
wxColour wxCheckedListCtrl::GetBgColourFromAdditionalState(int additionalstate)
{
if ((additionalstate & wxLIST_STATE_ENABLED) && this->IsEnabled())
return wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW);
#ifdef __WXMSW__
return wxSystemSettings::GetColour(wxSYS_COLOUR_INFOBK);
#else
return wxSystemSettings::GetColour(wxSYS_COLOUR_GRAYTEXT);
#endif
}
/* static */
int wxCheckedListCtrl::GetAndRemoveAdditionalState(long *state, int statemask)
{
int additionalstate = 0;
if (!state) return -1;
// extract the bits we are interested in
bool checked = (*state & wxLIST_STATE_CHECKED) != 0;
bool enabled = (*state & wxLIST_STATE_ENABLED) != 0;
// and set them in a different variable if they are included in the statemask
if (checked && (statemask & wxLIST_STATE_CHECKED)) additionalstate |= wxLIST_STATE_CHECKED;
if (enabled && (statemask & wxLIST_STATE_ENABLED)) additionalstate |= wxLIST_STATE_ENABLED;
// remove them from the original state var...
*state &= ~wxLIST_STATE_CHECKED;
*state &= ~wxLIST_STATE_ENABLED;
return additionalstate;
}
bool wxCheckedListCtrl::GetItem(wxListItem& info) const
{
// wx internal wxListCtrl::GetItem remove from the state mask the
// wxLIST_STATE_CHECKED & wxLIST_STATE_ENABLED bits since they
// are not part of wx standard flags... so we need to check those
// flags against the original wxListItem's statemask...
wxListItem original(info);
#ifdef __WXDEBUG__
// we always want to retrieve also the image state for checking purposes...
info.m_mask |= wxLIST_MASK_IMAGE;
#endif
if (!wxListCtrl::GetItem(info))
return FALSE;
// these are our additional supported states: read them from m_stateList
bool checked = (m_stateList[info.m_itemId] & wxLIST_STATE_CHECKED) != 0;
bool enabled = (m_stateList[info.m_itemId] & wxLIST_STATE_ENABLED) != 0;
// now intercept state requests about enable or check mode
if ((original.m_mask & wxLIST_MASK_STATE) &&
(original.m_stateMask & wxLIST_STATE_CHECKED)) {
info.m_state |= (m_stateList[info.m_itemId] & wxLIST_STATE_CHECKED);
info.m_stateMask |= wxLIST_STATE_CHECKED;
info.m_mask |= wxLIST_MASK_STATE; // contains valid info !
}
if ((original.m_mask & wxLIST_MASK_STATE) &&
(original.m_stateMask & wxLIST_STATE_ENABLED)) {
info.m_state |= (m_stateList[info.m_itemId] & wxLIST_STATE_ENABLED);
info.m_stateMask |= wxLIST_STATE_ENABLED;
info.m_mask |= wxLIST_MASK_STATE; // contains valid info !
}
// check that state & image are synch
#ifdef __WXDEBUG__
wxASSERT_MSG((int)m_stateList.GetCount() == (int)GetItemCount(),
wxS("Something wrong ! See InsertItem()"));
// read info by image index
bool imagecheck = (info.m_image == wxCLC_CHECKED_IMGIDX) ||
(info.m_image == wxCLC_DISABLED_CHECKED_IMGIDX);
bool imageenabled = (info.m_image == wxCLC_CHECKED_IMGIDX) ||
(info.m_image == wxCLC_UNCHECKED_IMGIDX);
wxASSERT_MSG((checked && imagecheck) || (!checked && !imagecheck),
wxS("This is item has checked state but it's shown as unchecked (or viceversa)"));
wxASSERT_MSG((enabled && imageenabled) || (!enabled && !imageenabled),
wxS("This is item has enabled state but it's shown as disabled (or viceversa)"));
#endif
return TRUE;
}
bool wxCheckedListCtrl::SetItem(wxListItem& info)
{
// remove the checked & enabled states from the state flag:
// we'll store them in our separate array
int additionalstate = GetAndRemoveAdditionalState(&info.m_state, info.m_stateMask);
// set image index
// we will ignore the info.m_image field since we need
// to overwrite it...
if (info.m_mask & wxLIST_MASK_STATE) {
// if some state is not included in the state mask, then get the state info
// from our internal state array
if (!(info.m_stateMask & wxLIST_STATE_ENABLED))
additionalstate |= (m_stateList[info.m_itemId] & wxLIST_STATE_ENABLED);
if (!(info.m_stateMask & wxLIST_STATE_CHECKED))
additionalstate |= (m_stateList[info.m_itemId] & wxLIST_STATE_CHECKED);
// state is valid: use it to determine the image to set...
info.m_mask |= wxLIST_MASK_IMAGE;
info.m_image = GetItemImageFromAdditionalState(additionalstate);
// since when changing the background color, also the foreground color
// and the font of the item are changed, we try to respect the user
// choices of such attributes
info.SetTextColour(this->GetItemTextColour(info.GetId()));
#if wxCHECK_VERSION(2, 6, 2)
// before wx 2.6.2 the wxListCtrl::SetItemFont function is missing
info.SetFont(this->GetItemFont(info.GetId()));
#endif
// change the background color to respect the enabled/disabled status...
info.SetBackgroundColour(GetBgColourFromAdditionalState(additionalstate));
m_stateList[info.m_itemId] = additionalstate;
} else {
// state is invalid; don't change image
info.m_mask &= ~wxLIST_MASK_IMAGE;
}
// save the changes
return wxListCtrl::SetItem(info);
}
long wxCheckedListCtrl::InsertItem(wxListItem &info)
{
int additionalstate = GetAndRemoveAdditionalState(&info.m_state, info.m_stateMask);
if (!(info.m_mask & wxLIST_MASK_STATE) ||
!(info.m_stateMask & wxLIST_STATE_ENABLED)) {
// if not specified, the default additional state is ENABLED
additionalstate = wxLIST_STATE_ENABLED;
}
// we always want to insert items with images...
info.m_mask |= wxLIST_MASK_IMAGE;
info.m_image = GetItemImageFromAdditionalState(additionalstate);
info.SetBackgroundColour(GetBgColourFromAdditionalState(additionalstate));
int itemcount = GetItemCount();
wxASSERT_MSG(info.m_itemId <= itemcount, wxS("Invalid index !"));
wxASSERT_MSG((int)m_stateList.GetCount() == (int)GetItemCount(),
wxS("Something wrong !"));
if (info.m_itemId == itemcount) {
// we are adding a new item at the end of the list
m_stateList.Add(additionalstate);
} else {
// we must shift all following items
cemu_assert_suspicious();
//for (int i=itemcount; i > info.m_itemId; i--)
// m_stateList[i] = m_stateList[i-1];
m_stateList[info.m_itemId] = additionalstate;
}
return wxListCtrl::InsertItem(info);
}
bool wxCheckedListCtrl::SetItemState(long item, long state, long stateMask)
{
wxListItem li;
li.SetId(item);
li.SetMask(wxLIST_MASK_STATE);
li.SetState(state);
li.SetStateMask(stateMask);
// so we are sure to use wxCheckedListCtrl::SetItem
// (and not wxListCtrl::SetItem)
return SetItem(li);
}
int wxCheckedListCtrl::GetItemState(long item, long stateMask) const
{
wxListItem li;
li.SetId(item);
li.SetMask(wxLIST_MASK_STATE);
li.SetStateMask(stateMask);
// so we are sure to use wxCheckedListCtrl::GetItem
// (and not wxListCtrl::GetItem)
if (!GetItem(li))
return -1;
return li.GetState();
}
long wxCheckedListCtrl::SetItem(long index, int col, const wxString& label, int WXUNUSED(imageId))
{
wxListItem li;
li.SetId(index);
li.SetColumn(col);
li.SetText(label);
li.SetMask(wxLIST_MASK_TEXT);
// so we are sure to use wxCheckedListCtrl::SetItem
// (and not wxListCtrl::SetItem)
return SetItem(li);
}
long wxCheckedListCtrl::InsertItem( long index, const wxString& label, int WXUNUSED(imageIndex) )
{
wxListItem info;
info.m_text = label;
info.m_mask = wxLIST_MASK_TEXT;
info.m_itemId = index;
return InsertItem(info);
}
void wxCheckedListCtrl::Check(long item, bool checked)
{
// NB: the "statemask" is not the "mask" of a list item;
// in the "mask" you use the wxLIST_MASK_XXXX defines;
// in the "statemask" you use the wxLIST_STATE_XXX defines
// to set a specific bit of the wxListInfo::m_state var
if (checked)
// the 2nd parameter says: activate the STATE bit relative to CHECK feature
// the 3rd parameter says: set only *that* bit
SetItemState(item, wxLIST_STATE_CHECKED, wxLIST_STATE_CHECKED);
else
SetItemState(item, 0, wxLIST_STATE_CHECKED);
}
void wxCheckedListCtrl::Enable(long item, bool enable)
{
if (enable)
// the 2nd parameter says: activate the STATE bit relative to ENABLE feature
// the 3rd parameter says: set only *that* bit
SetItemState(item, wxLIST_STATE_ENABLED, wxLIST_STATE_ENABLED);
else
SetItemState(item, 0, wxLIST_STATE_ENABLED);
}
void wxCheckedListCtrl::EnableAll(bool enable)
{
for (int i=0; i < GetItemCount(); i++)
Enable(i, enable);
}
void wxCheckedListCtrl::CheckAll(bool check)
{
for (int i=0; i < GetItemCount(); i++)
Check(i, check);
}
bool wxCheckedListCtrl::DeleteItem(long item)
{
// shift our additional state array
//for (int i=item,max=GetItemCount(); i < max-1; i++)
// m_stateList[i] = m_stateList[i+1];
m_stateList.RemoveAt(item, 1);
return wxListCtrl::DeleteItem(item);
}
int wxCheckedListCtrl::GetCheckedItemCount() const
{
int res = 0;
for (int i=0; i<GetItemCount(); i++)
if (IsChecked(i))
res++;
return res;
}
// event handlers
void wxCheckedListCtrl::OnMouseEvent(wxMouseEvent& event)
{
if (!event.LeftDown()) {
event.Skip();
return;
}
int flags;
long item = HitTest(event.GetPosition(), flags);
if (item == wxNOT_FOUND || !IsEnabled(item)) {
// skip this item
event.Skip();
return;
}
// user clicked exactly on the checkbox or on the item row ?
bool processcheck = (flags & wxLIST_HITTEST_ONITEMICON) ||
((GetWindowStyle() & wxCLC_CHECK_WHEN_SELECTING) &&
(flags & wxLIST_HITTEST_ONITEM));
if (processcheck) {
wxListEvent ev(wxEVT_NULL, GetId());
ev.m_itemIndex = item;
// send the check event
if (IsChecked(item)) {
ev.SetEventType(wxEVT_COMMAND_LIST_ITEM_UNCHECKED);
Check(item, FALSE);
AddPendingEvent(ev);
} else {
ev.SetEventType(wxEVT_COMMAND_LIST_ITEM_CHECKED);
Check(item, TRUE);
AddPendingEvent(ev);
}
}
event.Skip();
}
#endif // wxUSE_CHECKEDLISTCTRL

View file

@ -1,178 +0,0 @@
#pragma once
/////////////////////////////////////////////////////////////////////////////
// Name: checkedlistctrl.h
// Purpose: wxCheckedListCtrl
// Author: Unknown ? (found at http://wiki.wxwidgets.org/wiki.pl?WxListCtrl)
// Modified by: Francesco Montorsi
// Created: 2005/06/29
// RCS-ID: $Id: checkedlistctrl.h 448 2007-03-06 22:06:38Z frm $
// Copyright: (c) 2005 Francesco Montorsi
// Licence: wxWidgets licence
/////////////////////////////////////////////////////////////////////////////
#define wxUSE_CHECKEDLISTCTRL 1
#ifndef _WX_CHECKEDLISTCTRL_H_
#define _WX_CHECKEDLISTCTRL_H_
// wxWidgets headers
//#include "wx/webupdatedef.h" // for the WXDLLIMPEXP_WEBUPDATE macro
#include <wx/listctrl.h>
#include <wx/imaglist.h>
#if wxUSE_CHECKEDLISTCTRL
// image indexes (used internally by wxCheckedListCtrl)
#define wxCLC_UNCHECKED_IMGIDX 0 // unchecked & enabled
#define wxCLC_CHECKED_IMGIDX 1 // checked & enabled
#define wxCLC_DISABLED_UNCHECKED_IMGIDX 2 // unchecked & disabled
#define wxCLC_DISABLED_CHECKED_IMGIDX 3 // checked & disabled
// additional state flags (wx's defines should end at 0x0100; see listbase.h)
#define wxLIST_STATE_CHECKED 0x010000
#define wxLIST_STATE_ENABLED 0x100000
// additional wxCheckedListCtrl style flags
// (wx's defines should at 0x8000; see listbase.h)
#define wxCLC_CHECK_WHEN_SELECTING 0x10000
// -------------------------
// wxCheckedListCtrl events
// -------------------------
//DECLARE_EXPORTED_EVENT_TYPE(WXDLLIMPEXP_WEBUPDATE, wxEVT_COMMAND_LIST_ITEM_CHECKED, -1);
//DECLARE_EXPORTED_EVENT_TYPE(WXDLLIMPEXP_WEBUPDATE, wxEVT_COMMAND_LIST_ITEM_UNCHECKED, -1);
DECLARE_EXPORTED_EVENT_TYPE(WXEXPORT, wxEVT_COMMAND_LIST_ITEM_CHECKED, -1);
DECLARE_EXPORTED_EVENT_TYPE(WXEXPORT, wxEVT_COMMAND_LIST_ITEM_UNCHECKED, -1);
//DEFINE_EVENT_TYPE(wxEVT_COMMAND_LIST_ITEM_CHECKED);
//DEFINE_EVENT_TYPE(wxEVT_COMMAND_LIST_ITEM_UNCHECKED);
#ifndef EVT_LIST_ITEM_CHECKED
#define EVT_LIST_ITEM_CHECKED(id, fn) \
DECLARE_EVENT_TABLE_ENTRY( \
wxEVT_COMMAND_LIST_ITEM_CHECKED, id, -1, \
(wxObjectEventFunction)(wxEventFunction)(wxListEventFunction)&fn, \
(wxObject *) NULL \
),
#endif
#ifndef EVT_LIST_ITEM_UNCHECKED
#define EVT_LIST_ITEM_UNCHECKED(id, fn) \
DECLARE_EVENT_TABLE_ENTRY( \
wxEVT_COMMAND_LIST_ITEM_UNCHECKED, id, -1, \
(wxObjectEventFunction)(wxEventFunction)(wxListEventFunction)&fn, \
(wxObject *) NULL \
),
#endif
//! This is the class which performs all transactions with the server.
//! It uses the wxSocket facilities.
class wxCheckedListCtrl : public wxListView
{
protected:
// we have to keep a different array to keep track of the additional
// states we support....
wxArrayInt m_stateList;
// our set of checkbox images...
wxImageList* m_imageList;
public:
wxCheckedListCtrl()
: wxListView() {}
wxCheckedListCtrl(wxWindow *parent, wxWindowID id = wxID_ANY,
const wxPoint& pt = wxDefaultPosition,
const wxSize& sz = wxDefaultSize,
long style = wxCLC_CHECK_WHEN_SELECTING,
const wxValidator& validator = wxDefaultValidator,
const wxString& name = wxListCtrlNameStr)
: wxListView()
{ Create(parent, id, pt, sz, style, validator, name); }
bool Create(wxWindow *parent, wxWindowID id = wxID_ANY,
const wxPoint& pt = wxDefaultPosition,
const wxSize& sz = wxDefaultSize,
long style = wxCLC_CHECK_WHEN_SELECTING,
const wxValidator& validator = wxDefaultValidator,
const wxString& name = wxListCtrlNameStr);
virtual ~wxCheckedListCtrl() {}
public: // utilities
// core overloads (i.e. the most generic overloads)
bool GetItem(wxListItem& info) const;
bool SetItem(wxListItem& info);
long InsertItem(wxListItem& info);
bool DeleteItem(long item);
bool DeleteAllItems()
{ m_stateList.Clear(); return wxListCtrl::DeleteAllItems(); }
bool SortItems(wxListCtrlCompare, long)
{ wxASSERT_MSG(0, wxT("Not implemented yet ! sorry... ")); return FALSE; }
// shortcuts to the SetItemState function
void Check(long item, bool checked);
void Enable(long item, bool enable);
void CheckAll(bool checked = true);
void EnableAll(bool enable = true);
// this needs to be redeclared otherwise it's hidden by our other Enable() function.
// However you should use #EnableAll instead of this function if you want to get
// good graphics (try to understand)
virtual bool Enable(bool enable = true)
{ return wxListCtrl::Enable(enable); }
// shortcuts to the GetItemState function
bool IsChecked(long item) const
{ return GetItemState(item, wxLIST_STATE_CHECKED) != 0; }
bool IsEnabled(long item) const
{ return GetItemState(item, wxLIST_STATE_ENABLED) != 0; }
// this needs to be redeclared otherwise it's hidden by our other IsEnabled() function.
bool IsEnabled() const
{ return wxWindow::IsEnabled(); }
//! Returns the number of checked items in the control.
int GetCheckedItemCount() const;
// we overload these so we are sure they will use our
// #GetItem and #SetItem functions...
bool SetItemState(long item, long state, long stateMask);
int GetItemState(long item, long stateMask) const;
long InsertItem( long index, const wxString& label, int imageIndex = -1);
long SetItem(long index, int col, const wxString& label, int imageId = -1);
// the image associated with an element is already in used by wxCheckedListCtrl
// itself to show the checkbox and it cannot be handled by the user !
bool SetItemImage(long, int)
{ wxASSERT_MSG(0, wxT("This function cannot be used with wxCheckedListCtrl !")); return FALSE; }
protected: // event handlers
void OnMouseEvent(wxMouseEvent& event);
protected: // internal utilities
static int GetItemImageFromAdditionalState(int addstate);
static int GetAndRemoveAdditionalState(long *state, int statemask);
wxColour GetBgColourFromAdditionalState(int additionalstate);
private:
DECLARE_CLASS(wxCheckedListCtrl)
DECLARE_EVENT_TABLE()
};
#endif // wxUSE_CHECKEDLISTCTRL
#endif // _WX_CHECKEDLISTCTRL_H_