#include "wx/dcscreen.h"
#include "wx/app.h"
-#include "wx/generic/listctrl.h"
+#include "wx/listctrl.h"
#include "wx/generic/imaglist.h"
+#ifndef wxUSE_GENERIC_LIST_EXTENSIONS
+#define wxUSE_GENERIC_LIST_EXTENSIONS 0
+#endif
+
//-----------------------------------------------------------------------------
// wxListItemData
//-----------------------------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(wxListItemData,wxObject);
-wxListItemData::wxListItemData(void)
+wxListItemData::wxListItemData()
{
m_image = -1;
m_data = 0;
m_colour = col;
}
-bool wxListItemData::HasImage(void) const
+bool wxListItemData::HasImage() const
{
return (m_image >= 0);
}
-bool wxListItemData::HasText(void) const
+bool wxListItemData::HasText() const
{
return (!m_text.IsNull());
}
s = m_text;
}
-int wxListItemData::GetX( void ) const
+int wxListItemData::GetX() const
{
return m_xpos;
}
-int wxListItemData::GetY( void ) const
+int wxListItemData::GetY() const
{
return m_ypos;
}
-int wxListItemData::GetWidth(void) const
+int wxListItemData::GetWidth() const
{
return m_width;
}
-int wxListItemData::GetHeight(void) const
+int wxListItemData::GetHeight() const
{
return m_height;
}
-int wxListItemData::GetImage(void) const
+int wxListItemData::GetImage() const
{
return m_image;
}
info.m_text = m_text;
info.m_image = m_image;
info.m_data = m_data;
+ info.m_colour = m_colour;
}
-wxColour *wxListItemData::GetColour(void)
+wxColour *wxListItemData::GetColour()
{
return m_colour;
}
IMPLEMENT_DYNAMIC_CLASS(wxListHeaderData,wxObject);
-wxListHeaderData::wxListHeaderData(void)
+wxListHeaderData::wxListHeaderData()
{
m_mask = 0;
m_image = 0;
m_format = format;
}
-bool wxListHeaderData::HasImage(void) const
+bool wxListHeaderData::HasImage() const
{
return (m_image != 0);
}
-bool wxListHeaderData::HasText(void) const
+bool wxListHeaderData::HasText() const
{
return (m_text.Length() > 0);
}
s = m_text;
}
-int wxListHeaderData::GetImage(void) const
+int wxListHeaderData::GetImage() const
{
return m_image;
}
-int wxListHeaderData::GetWidth(void) const
+int wxListHeaderData::GetWidth() const
{
return m_width;
}
-int wxListHeaderData::GetFormat(void) const
+int wxListHeaderData::GetFormat() const
{
return m_format;
}
dc->GetTextExtent( s, &lw, &lh );
m_bound_all.width = lw;
m_bound_all.height = lh;
+ if (item->HasImage())
+ {
+ int w = 0;
+ int h = 0;
+ m_owner->GetImageSize( item->GetImage(), w, h );
+ m_bound_all.width += 4 + w;
+ if (h > m_bound_all.height) m_bound_all.height = h;
+ }
}
break;
}
void wxListLineData::SetPosition( wxDC *dc, int x, int y, int window_width )
{
- m_bound_all.x = x;
- m_bound_all.y = y;
- switch (m_mode)
- {
- case wxLC_ICON:
- {
- AssignRect( m_bound_icon, 0, 0, 0, 0 );
- AssignRect( m_bound_label, 0, 0, 0, 0 );
- AssignRect( m_bound_hilight, m_bound_all );
- wxNode *node = m_items.First();
- if (node)
- {
- wxListItemData *item = (wxListItemData*)node->Data();
- if (item->HasImage())
+ m_bound_all.x = x;
+ m_bound_all.y = y;
+ switch (m_mode)
+ {
+ case wxLC_ICON:
{
- wxListItemData *item = (wxListItemData*)node->Data();
- int w = 0;
- int h = 0;
- m_owner->GetImageSize( item->GetImage(), w, h );
- m_bound_icon.x = m_bound_all.x + (m_spacing/2) - (w/2);
- m_bound_icon.y = m_bound_all.y + m_spacing - h - 5;
- m_bound_icon.width = w;
- m_bound_icon.height = h;
- if (!item->HasText())
- {
- AssignRect( m_bound_hilight, m_bound_icon );
- m_bound_hilight.x -= 5;
- m_bound_hilight.y -= 5;
- m_bound_hilight.width += 9;
- m_bound_hilight.height += 9;
- }
+ AssignRect( m_bound_icon, 0, 0, 0, 0 );
+ AssignRect( m_bound_label, 0, 0, 0, 0 );
+ AssignRect( m_bound_hilight, m_bound_all );
+ wxNode *node = m_items.First();
+ if (node)
+ {
+ wxListItemData *item = (wxListItemData*)node->Data();
+ if (item->HasImage())
+ {
+ wxListItemData *item = (wxListItemData*)node->Data();
+ int w = 0;
+ int h = 0;
+ m_owner->GetImageSize( item->GetImage(), w, h );
+ m_bound_icon.x = m_bound_all.x + (m_spacing/2) - (w/2);
+ m_bound_icon.y = m_bound_all.y + m_spacing - h - 5;
+ m_bound_icon.width = w;
+ m_bound_icon.height = h;
+ if (!item->HasText())
+ {
+ AssignRect( m_bound_hilight, m_bound_icon );
+ m_bound_hilight.x -= 5;
+ m_bound_hilight.y -= 5;
+ m_bound_hilight.width += 9;
+ m_bound_hilight.height += 9;
+ }
+ }
+ if (item->HasText())
+ {
+ wxString s;
+ item->GetText( s );
+ long lw,lh;
+ dc->GetTextExtent( s, &lw, &lh );
+ if (m_bound_all.width > m_spacing)
+ m_bound_label.x = m_bound_all.x;
+ else
+ m_bound_label.x = m_bound_all.x + (m_spacing/2) - lw/2;
+ m_bound_label.y = m_bound_all.y + m_bound_all.height - lh;
+ m_bound_label.width = lw;
+ m_bound_label.height = lh;
+ AssignRect( m_bound_hilight, m_bound_label );
+ m_bound_hilight.x -= 2;
+ m_bound_hilight.y -= 2;
+ m_bound_hilight.width += 4;
+ m_bound_hilight.height += 4;
+ }
+ }
+ break;
}
- if (item->HasText())
+ case wxLC_LIST:
{
- wxString s;
- item->GetText( s );
- long lw,lh;
- dc->GetTextExtent( s, &lw, &lh );
- if (m_bound_all.width > m_spacing)
- m_bound_label.x = m_bound_all.x;
- else
- m_bound_label.x = m_bound_all.x + (m_spacing/2) - lw/2;
- m_bound_label.y = m_bound_all.y + m_bound_all.height - lh;
- m_bound_label.width = lw;
- m_bound_label.height = lh;
- AssignRect( m_bound_hilight, m_bound_label );
- m_bound_hilight.x -= 2;
- m_bound_hilight.y -= 2;
- m_bound_hilight.width += 4;
- m_bound_hilight.height += 4;
+ AssignRect( m_bound_label, m_bound_all );
+ m_bound_all.x -= 2;
+ m_bound_all.y -= 2;
+ m_bound_all.width += 4;
+ m_bound_all.height += 3;
+ AssignRect( m_bound_hilight, m_bound_all );
+ AssignRect( m_bound_icon, 0, 0, 0, 0 );
+ wxNode *node = m_items.First();
+ if (node)
+ {
+ wxListItemData *item = (wxListItemData*)node->Data();
+ if (item->HasImage())
+ {
+ m_bound_icon.x = m_bound_all.x + 2;
+ m_bound_icon.y = m_bound_all.y + 2;
+ int w;
+ int h;
+ m_owner->GetImageSize( item->GetImage(), w, h );
+ m_bound_icon.width = w;
+ m_bound_icon.height = h;
+ m_bound_label.x += 4 + w;
+ m_bound_label.width -= 4 + w;
+ }
+ }
+ break;
+ }
+ case wxLC_REPORT:
+ {
+ long lw,lh;
+ dc->GetTextExtent( "H", &lw, &lh );
+ m_bound_all.x = 0;
+ m_bound_all.y -= 0;
+ m_bound_all.height = lh+3;
+ m_bound_all.width = window_width;
+ AssignRect( m_bound_hilight, m_bound_all );
+ AssignRect( m_bound_label, m_bound_all );
+ AssignRect( m_bound_icon, 0, 0, 0, 0 );
+ wxNode *node = m_items.First();
+ if (node)
+ {
+ wxListItemData *item = (wxListItemData*)node->Data();
+ wxString s;
+ item->GetText( s );
+ if (s.IsEmpty()) s = wxT("H");
+ long lw,lh;
+ dc->GetTextExtent( s, &lw, &lh );
+ m_bound_label.width = lw;
+ m_bound_label.height = lh;
+ if (item->HasImage())
+ {
+ m_bound_icon.x = m_bound_all.x + 2;
+ m_bound_icon.y = m_bound_all.y + 2;
+ int w;
+ int h;
+ m_owner->GetImageSize( item->GetImage(), w, h );
+ m_bound_icon.width = w;
+ m_bound_icon.height = h;
+ m_bound_label.x += 4 + w;
+ }
+ }
+ break;
}
- }
- break;
- }
- case wxLC_LIST:
- {
- AssignRect( m_bound_label, m_bound_all );
- m_bound_all.x -= 2;
- m_bound_all.y -= 2;
- m_bound_all.width += 4;
- m_bound_all.height += 3;
- AssignRect( m_bound_hilight, m_bound_all );
- AssignRect( m_bound_icon, 0, 0, 0, 0 );
- break;
- }
- case wxLC_REPORT:
- {
- long lw,lh;
- dc->GetTextExtent( "H", &lw, &lh );
- m_bound_all.x = 0;
- m_bound_all.y -= 0;
- m_bound_all.height = lh+3;
- m_bound_all.width = window_width;
- AssignRect( m_bound_hilight, m_bound_all );
- AssignRect( m_bound_label, 0, 0, 0 ,0 );
- AssignRect( m_bound_icon, 0, 0, 0, 0 );
- break;
}
- }
}
void wxListLineData::SetColumnPosition( int index, int x )
long dev_y = dc->LogicalToDeviceY( m_bound_all.y-2 );
long dev_w = dc->LogicalToDeviceXRel( m_bound_all.width+4 );
long dev_h = dc->LogicalToDeviceYRel( m_bound_all.height+4 );
-
+
if (!m_owner->IsExposed( dev_x, dev_y, dev_w, dev_h ))
- {
+ {
return;
}
dc->DrawRectangle( m_bound_hilight.x, m_bound_hilight.y,
m_bound_hilight.width, m_bound_hilight.height );
}
-
+
dc->SetBackgroundMode(wxTRANSPARENT);
if (m_mode == wxLC_REPORT)
{
bool wxListLineData::IsInRect( int x, int y, const wxRect &rect )
{
- return ((x >= rect.x) && (x <= rect.x+rect.width) &&
+ return ((x >= rect.x) && (x <= rect.x+rect.width) &&
(y >= rect.y) && (y <= rect.y+rect.height));
}
m_owner = (wxListMainWindow *) NULL;
m_currentCursor = (wxCursor *) NULL;
m_resizeCursor = (wxCursor *) NULL;
- m_isDraging = FALSE;
+ m_isDragging = FALSE;
}
wxListHeaderWindow::wxListHeaderWindow( wxWindow *win, wxWindowID id, wxListMainWindow *owner,
// m_currentCursor = wxSTANDARD_CURSOR;
m_currentCursor = (wxCursor *) NULL;
m_resizeCursor = new wxCursor( wxCURSOR_SIZEWE );
- m_isDraging = FALSE;
+ m_isDragging = FALSE;
+ SetBackgroundColour( wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNFACE ) );
}
wxListHeaderWindow::~wxListHeaderWindow( void )
dc->DrawRectangle( x, y+h, w+1, 1 ); // bottom (outer)
wxPen pen( wxSystemSettings::GetSystemColour( wxSYS_COLOUR_BTNSHADOW ), 1, wxSOLID );
-
+
dc->SetPen( pen );
dc->DrawLine( x+w-m_corner, y, x+w-1, y+h ); // right (inner)
dc->DrawRectangle( x+1, y+h-1, w-2, 1 ); // bottom (inner)
{
wxPaintDC dc( this );
PrepareDC( dc );
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ if ( m_owner->GetMode() & wxLC_REPORT )
+ {
+ int x , y ;
+ int xpix , ypix ;
+ m_owner->GetScrollPixelsPerUnit( &xpix , &ypix ) ;
+ m_owner->ViewStart( &x, &y ) ;
+ dc.SetDeviceOrigin( -x * xpix, 0 );
+ }
+#endif
dc.BeginDrawing();
dc.SetFont( GetFont() );
{
m_owner->GetColumn( i, item );
int cw = item.m_width-2;
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ if ((i+1 == numColumns) || ( dc.LogicalToDeviceX(x+item.m_width) > w-5))
+ cw = dc.DeviceToLogicalX(w)-x-1;
+#else
if ((i+1 == numColumns) || (x+item.m_width > w-5)) cw = w-x-1;
+#endif
dc.SetPen( *wxWHITE_PEN );
DoDrawRect( &dc, x, y, cw, h-2 );
dc.DrawText( item.m_text, x+4, y+3 );
dc.DestroyClippingRegion();
x += item.m_width;
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ if (dc.LogicalToDeviceX(x) > w+5) break;
+#else
if (x > w+5) break;
+#endif
}
dc.EndDrawing();
}
m_owner->ClientToScreen( &x2, &y2 );
wxScreenDC dc;
- dc.SetLogicalFunction( wxXOR );
+ dc.SetLogicalFunction( wxINVERT );
dc.SetPen( wxPen( *wxBLACK, 2, wxSOLID ) );
dc.SetBrush( *wxTRANSPARENT_BRUSH );
{
int x = event.GetX();
int y = event.GetY();
- if (m_isDraging)
+ if (m_isDragging)
{
DrawCurrent();
if (event.ButtonUp())
{
ReleaseMouse();
- m_isDraging = FALSE;
+ m_isDragging = FALSE;
m_owner->SetColumnWidth( m_column, m_currentX-m_minX );
}
else
m_minX = 0;
bool hit_border = FALSE;
int xpos = 0;
- for (int j = 0; j < m_owner->GetColumnCount(); j++)
+ for (int j = 0; j < m_owner->GetColumnCount()-1; j++)
{
xpos += m_owner->GetColumnWidth( j );
+ m_column = j;
if ((abs(x-xpos) < 3) && (y < 22))
{
hit_border = TRUE;
- m_column = j;
+ break;
+ }
+ if (x-xpos < 0)
+ {
break;
}
m_minX = xpos;
}
- if (event.LeftDown() && hit_border)
+ if (event.LeftDown())
{
- m_isDraging = TRUE;
- m_currentX = x;
- DrawCurrent();
- CaptureMouse();
- return;
+ if (hit_border)
+ {
+ m_isDragging = TRUE;
+ m_currentX = x;
+ DrawCurrent();
+ CaptureMouse();
+ return;
+ }
+ else
+ {
+ wxListEvent le( wxEVT_COMMAND_LIST_COL_CLICK, GetParent()->GetId() );
+ le.SetEventObject( GetParent() );
+ le.m_col = m_column;
+ GetParent()->GetEventHandler()->ProcessEvent( le );
+ return;
+ }
}
if (event.Moving())
wxListTextCtrl::wxListTextCtrl( wxWindow *parent, const wxWindowID id,
bool *accept, wxString *res, wxListMainWindow *owner,
const wxString &value, const wxPoint &pos, const wxSize &size,
+#if wxUSE_VALIDATORS
int style, const wxValidator& validator, const wxString &name ) :
+#endif
wxTextCtrl( parent, id, value, pos, size, style, validator, name )
{
m_res = res;
m_accept = accept;
m_owner = owner;
+ (*m_accept) = FALSE;
+ (*m_res) = "";
+ m_startValue = value;
}
void wxListTextCtrl::OnChar( wxKeyEvent &event )
{
(*m_accept) = TRUE;
(*m_res) = GetValue();
- m_owner->OnRenameAccept();
-// Show( FALSE );
- Destroy();
+ m_owner->SetFocus();
return;
}
if (event.m_keyCode == WXK_ESCAPE)
{
(*m_accept) = FALSE;
(*m_res) = "";
-// Show( FALSE );
- Destroy();
+ m_owner->SetFocus();
return;
}
event.Skip();
void wxListTextCtrl::OnKillFocus( wxFocusEvent &WXUNUSED(event) )
{
- (*m_accept) = FALSE;
- (*m_res) = "";
-// Show( FALSE );
- Destroy();
- return;
+ if (wxPendingDelete.Member(this)) return;
+
+ wxPendingDelete.Append(this);
+
+ if ((*m_accept) && ((*m_res) != m_startValue))
+ m_owner->OnRenameAccept();
}
//-----------------------------------------------------------------------------
EVT_KEY_DOWN (wxListMainWindow::OnKeyDown)
EVT_SET_FOCUS (wxListMainWindow::OnSetFocus)
EVT_KILL_FOCUS (wxListMainWindow::OnKillFocus)
+ EVT_SCROLLWIN (wxListMainWindow::OnScroll)
END_EVENT_TABLE()
-wxListMainWindow::wxListMainWindow( void )
+wxListMainWindow::wxListMainWindow()
{
m_mode = 0;
m_lines.DeleteContents( TRUE );
if (m_mode & wxLC_REPORT)
{
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ m_xScroll = 15;
+#else
m_xScroll = 0;
+#endif
m_yScroll = 15;
}
else
SetBackgroundColour( *wxWHITE );
}
-wxListMainWindow::~wxListMainWindow( void )
+wxListMainWindow::~wxListMainWindow()
{
if (m_hilightBrush) delete m_hilightBrush;
-
+
delete m_renameTimer;
}
PrepareDC( dc );
if (m_dirty) return;
-
+
if (m_lines.GetCount() == 0) return;
dc.BeginDrawing();
dc.SetFont( GetFont() );
-
+
if (m_mode & wxLC_REPORT)
{
int lineSpacing = 0;
int dummy = 0;
line->GetSize( dummy, lineSpacing );
lineSpacing += 1;
-
+
int y_s = m_yScroll*GetScrollPos( wxVERTICAL );
-
+
wxNode *node = m_lines.Nth( y_s / lineSpacing );
- for (int i = 0; i < m_visibleLines+2; i++)
- {
- if (!node) break;
-
+ for (int i = 0; i < m_visibleLines+2; i++)
+ {
+ if (!node) break;
+
line = (wxListLineData*)node->Data();
line->Draw( &dc );
node = node->Next();
- }
+ }
}
else
{
node = node->Next();
}
}
-
+
if (m_current) m_current->DrawRubberBand( &dc, m_hasFocus );
dc.EndDrawing();
SendNotify( line, wxEVT_COMMAND_LIST_DELETE_ITEM );
}
-void wxListMainWindow::StartLabelEdit( wxListLineData *line )
-{
- SendNotify( line, wxEVT_COMMAND_LIST_BEGIN_LABEL_EDIT );
-}
+/* *** */
-void wxListMainWindow::RenameLine( wxListLineData *line, const wxString &newName )
+void wxListMainWindow::EditLabel( long item )
{
- wxListEvent le( wxEVT_COMMAND_LIST_END_LABEL_EDIT, GetParent()->GetId() );
+ wxNode *node = m_lines.Nth( item );
+ wxCHECK_RET( node, wxT("wrong index in wxListCtrl::Edit()") );
+
+ m_currentEdit = (wxListLineData*) node->Data();
+
+ wxListEvent le( wxEVT_COMMAND_LIST_BEGIN_LABEL_EDIT, GetParent()->GetId() );
le.SetEventObject( GetParent() );
- le.m_itemIndex = GetIndexOfLine( line );
- line->GetItem( 0, le.m_item );
- le.m_item.m_text = newName;
+ le.m_itemIndex = GetIndexOfLine( m_currentEdit );
+ m_currentEdit->GetItem( 0, le.m_item );
GetParent()->GetEventHandler()->ProcessEvent( le );
-}
-void wxListMainWindow::OnRenameTimer()
-{
- StartLabelEdit( m_current );
+ if (!le.IsAllowed())
+ return;
+
+ // We have to call this here because the label in
+ // question might just have been added and no screen
+ // update taken place.
+ if (m_dirty) wxYield();
+
wxString s;
- m_current->GetText( 0, s );
+ m_currentEdit->GetText( 0, s );
int x = 0;
int y = 0;
int w = 0;
int h = 0;
- m_current->GetLabelExtent( x, y, w, h );
+ m_currentEdit->GetLabelExtent( x, y, w, h );
wxClientDC dc(this);
PrepareDC( dc );
text->SetFocus();
}
+void wxListMainWindow::OnRenameTimer()
+{
+ wxCHECK_RET( m_current, wxT("invalid m_current") );
+
+ Edit( m_lines.IndexOf( m_current ) );
+}
+
void wxListMainWindow::OnRenameAccept()
{
- RenameLine( m_current, m_renameRes );
+ wxListEvent le( wxEVT_COMMAND_LIST_END_LABEL_EDIT, GetParent()->GetId() );
+ le.SetEventObject( GetParent() );
+ le.m_itemIndex = GetIndexOfLine( m_currentEdit );
+ m_currentEdit->GetItem( 0, le.m_item );
+ le.m_item.m_text = m_renameRes;
+ GetParent()->GetEventHandler()->ProcessEvent( le );
+
+ if (!le.IsAllowed()) return;
+
+ wxListItem info;
+ info.m_mask = wxLIST_MASK_TEXT;
+ info.m_itemId = le.m_itemIndex;
+ info.m_text = m_renameRes;
+ info.m_colour = le.m_item.m_colour;
+ SetItem( info );
}
void wxListMainWindow::OnMouse( wxMouseEvent &event )
if (!m_current) return;
if (m_dirty) return;
+ if ( !(event.Dragging() || event.ButtonDown() || event.LeftUp() || event.ButtonDClick()) ) return;
wxClientDC dc(this);
PrepareDC(dc);
long x = dc.DeviceToLogicalX( (long)event.GetX() );
long y = dc.DeviceToLogicalY( (long)event.GetY() );
-
+
/* Did we actually hit an item ? */
long hitResult = 0;
wxNode *node = m_lines.First();
node = node->Next();
}
- if (!event.Dragging())
- m_dragCount = 0;
- else
+ if (event.Dragging())
+ {
+ if (m_dragCount == 0)
+ m_dragStart = wxPoint(x,y);
+
m_dragCount++;
- if (event.Dragging() && (m_dragCount > 3))
+ if (m_dragCount != 3) return;
+
+ int command = wxEVT_COMMAND_LIST_BEGIN_DRAG;
+ if (event.RightIsDown()) command = wxEVT_COMMAND_LIST_BEGIN_RDRAG;
+
+ wxListEvent le( command, GetParent()->GetId() );
+ le.SetEventObject( GetParent() );
+ le.m_pointDrag = m_dragStart;
+ GetParent()->GetEventHandler()->ProcessEvent( le );
+
+ return;
+ }
+ else
{
m_dragCount = 0;
-
- wxListEvent le( wxEVT_COMMAND_LIST_BEGIN_DRAG, GetParent()->GetId() );
- le.SetEventObject( GetParent() );
- le.m_pointDrag.x = x;
- le.m_pointDrag.y = y;
- GetParent()->GetEventHandler()->ProcessEvent( le );
-
- return;
}
if (!line) return;
m_usedKeys = FALSE;
m_lastOnSame = FALSE;
m_renameTimer->Stop();
-
+
SendNotify( line, wxEVT_COMMAND_LIST_ITEM_ACTIVATED );
-
+
return;
}
SendNotify( line, wxEVT_COMMAND_LIST_ITEM_RIGHT_CLICK );
return;
}
-
+
if (event.MiddleDown())
{
SendNotify( line, wxEVT_COMMAND_LIST_ITEM_MIDDLE_CLICK );
return;
}
-
+
if (event.LeftDown())
{
m_usedKeys = FALSE;
else if (event.ControlDown())
{
m_current = line;
-
+
int numOfCurrent = -1;
node = m_lines.First();
while (node)
if (test_line == oldCurrent) break;
node = node->Next();
}
-
+
int numOfLine = -1;
node = m_lines.First();
while (node)
}
if (numOfLine < numOfCurrent)
- {
- int i = numOfLine;
- numOfLine = numOfCurrent;
- numOfCurrent = i;
- }
-
+ {
+ int i = numOfLine;
+ numOfLine = numOfCurrent;
+ numOfCurrent = i;
+ }
+
wxNode *node = m_lines.Nth( numOfCurrent );
for (int i = 0; i <= numOfLine-numOfCurrent; i++)
{
}
}
-void wxListMainWindow::MoveToFocus( void )
+void wxListMainWindow::MoveToFocus()
{
if (!m_current) return;
-
+
int x = 0;
int y = 0;
int w = 0;
int h = 0;
m_current->GetExtent( x, y, w, h );
-
+
int w_p = 0;
int h_p = 0;
GetClientSize( &w_p, &h_p );
-
+
if (m_mode & wxLC_REPORT)
{
int y_s = m_yScroll*GetScrollPos( wxVERTICAL );
if ((y > y_s) && (y+h < y_s+h_p)) return;
- if (y-y_s < 5) { Scroll( -1, (y-5-h_p/2)/m_yScroll ); Refresh(); }
- if (y+h+5 > y_s+h_p) { Scroll( -1, (y+h-h_p/2+h+15)/m_yScroll); Refresh(); }
+ if (y-y_s < 5) { Scroll( -1, (y-5-h_p/2)/m_yScroll ); }
+ if (y+h+5 > y_s+h_p) { Scroll( -1, (y+h-h_p/2+h+15)/m_yScroll); }
}
else
{
int x_s = m_xScroll*GetScrollPos( wxHORIZONTAL );
if ((x > x_s) && (x+w < x_s+w_p)) return;
- if (x-x_s < 5) { Scroll( (x-5)/m_xScroll, -1 ); Refresh(); }
- if (x+w-5 > x_s+w_p) { Scroll( (x+w-w_p+15)/m_xScroll, -1 ); Refresh(); }
+ if (x-x_s < 5) { Scroll( (x-5)/m_xScroll, -1 ); }
+ if (x+w-5 > x_s+w_p) { Scroll( (x+w-w_p+15)/m_xScroll, -1 ); }
}
}
void wxListMainWindow::OnKeyDown( wxKeyEvent &event )
{
wxWindow *parent = GetParent();
-
+
/* we propagate the key event up */
wxKeyEvent ke( wxEVT_KEY_DOWN );
ke.m_shiftDown = event.m_shiftDown;
ke.m_y = event.m_y;
ke.SetEventObject( parent );
if (parent->GetEventHandler()->ProcessEvent( ke )) return;
-
+
event.Skip();
}
-
+
void wxListMainWindow::OnChar( wxKeyEvent &event )
{
wxWindow *parent = GetParent();
-
+
/* we send a list_key event up */
wxListEvent le( wxEVT_COMMAND_LIST_KEY_DOWN, GetParent()->GetId() );
le.m_code = event.KeyCode();
ke.m_y = event.m_y;
ke.SetEventObject( parent );
if (parent->GetEventHandler()->ProcessEvent( ke )) return;
-
+
+ if (event.KeyCode() == WXK_TAB)
+ {
+ wxNavigationKeyEvent nevent;
+ nevent.SetDirection( !event.ShiftDown() );
+ nevent.SetCurrentFocus( m_parent );
+ if (m_parent->GetEventHandler()->ProcessEvent( nevent )) return;
+ }
+
/* no item -> nothing to do */
if (!m_current)
{
case WXK_PRIOR:
{
int steps = 0;
- if (m_mode & wxLC_REPORT)
- {
- steps = m_visibleLines-1;
- }
+ if (m_mode & wxLC_REPORT)
+ {
+ steps = m_visibleLines-1;
+ }
else
{
int pos = 0;
case WXK_NEXT:
{
int steps = 0;
- if (m_mode & wxLC_REPORT)
- {
- steps = m_visibleLines-1;
- }
+ if (m_mode & wxLC_REPORT)
+ {
+ steps = m_visibleLines-1;
+ }
else
{
int pos = 0; wxNode *node = m_lines.First();
m_usedKeys = TRUE;
}
+#ifdef __WXGTK__
+extern wxWindow *g_focusWindow;
+#endif
+
void wxListMainWindow::OnSetFocus( wxFocusEvent &WXUNUSED(event) )
{
m_hasFocus = TRUE;
if (!GetParent()) return;
+#ifdef __WXGTK__
+ g_focusWindow = GetParent();
+#endif
+
wxFocusEvent event( wxEVT_SET_FOCUS, GetParent()->GetId() );
event.SetEventObject( GetParent() );
GetParent()->GetEventHandler()->ProcessEvent( event );
{
/*
We don't even allow the wxScrolledWindow::AdjustScrollbars() call
-
+
*/
}
{
m_small_image_list->Draw( index, *dc, x, y, wxIMAGELIST_DRAW_TRANSPARENT );
}
+ if ((m_mode & wxLC_LIST) && (m_small_image_list))
+ {
+ m_small_image_list->Draw( index, *dc, x, y, wxIMAGELIST_DRAW_TRANSPARENT );
+ }
if ((m_mode & wxLC_REPORT) && (m_small_image_list))
{
m_small_image_list->Draw( index, *dc, x, y, wxIMAGELIST_DRAW_TRANSPARENT );
m_small_image_list->GetSize( index, width, height );
return;
}
+ if ((m_mode & wxLC_LIST) && (m_small_image_list))
+ {
+ m_small_image_list->GetSize( index, width, height );
+ return;
+ }
if ((m_mode & wxLC_REPORT) && (m_small_image_list))
{
m_small_image_list->GetSize( index, width, height );
m_dirty = TRUE;
- wxNode *node = m_columns.Nth( col );
+ wxNode *node = (wxNode*) NULL;
+
+ if (width == wxLIST_AUTOSIZE_USEHEADER) width = 80;
+ if (width == wxLIST_AUTOSIZE)
+ {
+ wxClientDC dc(this);
+ dc.SetFont( GetFont() );
+ int max = 10;
+ node = m_lines.First();
+ while (node)
+ {
+ wxListLineData *line = (wxListLineData*)node->Data();
+ wxNode *n = line->m_items.Nth( col );
+ if (n)
+ {
+ wxListItemData *item = (wxListItemData*)n->Data();
+ int current = 0, ix = 0, iy = 0;
+ long lx = 0, ly = 0;
+ if (item->HasImage())
+ {
+ GetImageSize( item->GetImage(), ix, iy );
+ current = ix + 5;
+ }
+ if (item->HasText())
+ {
+ wxString str;
+ item->GetText( str );
+ dc.GetTextExtent( str, &lx, &ly );
+ current += lx;
+ }
+ if (current > max) max = current;
+ }
+ node = node->Next();
+ }
+ width = max+10;
+ }
+
+ node = m_columns.Nth( col );
if (node)
{
wxListHeaderData *column = (wxListHeaderData*)node->Data();
}
else
{
- return 0;
+ return 0;
}
}
-int wxListMainWindow::GetColumnCount( void )
+int wxListMainWindow::GetColumnCount()
{
return m_columns.Number();
}
-int wxListMainWindow::GetCountPerPage( void )
+int wxListMainWindow::GetCountPerPage()
{
return m_visibleLines;
}
m_current = line;
FocusLine( m_current );
RefreshLine( m_current );
- RefreshLine( oldCurrent );
+ if (oldCurrent) RefreshLine( oldCurrent );
}
}
UnfocusLine( m_current );
m_current = line;
FocusLine( m_current );
- oldCurrent->Hilight( FALSE );
+ if (oldCurrent) oldCurrent->Hilight( FALSE );
RefreshLine( m_current );
- RefreshLine( oldCurrent );
+ if (oldCurrent) RefreshLine( oldCurrent );
}
bool on = state & wxLIST_STATE_SELECTED;
- if (on != line->IsHilighted())
- {
+ if (on != line->IsHilighted())
+ {
line->Hilight( on );
RefreshLine( line );
- }
+ }
}
}
}
}
}
-int wxListMainWindow::GetItemCount( void )
+int wxListMainWindow::GetItemCount()
{
return m_lines.Number();
}
return TRUE;
}
-int wxListMainWindow::GetSelectedItemCount( void )
+int wxListMainWindow::GetSelectedItemCount()
{
int ret = 0;
wxNode *node = m_lines.First();
if (m_mode & wxLC_REPORT)
{
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ m_xScroll = 15;
+#else
m_xScroll = 0;
+#endif
m_yScroll = 15;
}
else
}
}
-long wxListMainWindow::GetMode( void ) const
+long wxListMainWindow::GetMode() const
{
return m_mode;
}
-void wxListMainWindow::CalculatePositions( void )
+void wxListMainWindow::CalculatePositions()
{
if (!m_lines.First()) return;
int iconSpacing = 0;
if (m_mode & wxLC_ICON) iconSpacing = m_normal_spacing;
if (m_mode & wxLC_SMALL_ICON) iconSpacing = m_small_spacing;
-
+
// we take the first line (which also can be an icon or
// an a text item in wxLC_ICON and wxLC_LIST modes) to
// measure the size of the line
-
+
int lineWidth = 0;
int lineHeight = 0;
int lineSpacing = 0;
int y = 1;
int entireHeight = m_lines.Number() * lineSpacing + 2;
int scroll_pos = GetScrollPos( wxVERTICAL );
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ int x_scroll_pos = GetScrollPos( wxHORIZONTAL );
+#else
SetScrollbars( m_xScroll, m_yScroll, 0, (entireHeight+15) / m_yScroll, 0, scroll_pos, TRUE );
+#endif
GetClientSize( &clientWidth, &clientHeight );
wxNode* node = m_lines.First();
+ int entireWidth = 0 ;
while (node)
{
wxListLineData *line = (wxListLineData*)node->Data();
line->SetColumnPosition( i, col_x );
col_x += GetColumnWidth( i );
}
+ entireWidth = wxMax( entireWidth , col_x ) ;
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ line->SetPosition( &dc, x, y, col_x );
+#endif
y += lineSpacing; // one pixel blank line between items
node = node->Next();
}
- m_visibleLines = clientHeight / lineSpacing;
+ m_visibleLines = clientHeight / lineSpacing;
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+ SetScrollbars( m_xScroll, m_yScroll, entireWidth / m_xScroll , (entireHeight+15) / m_yScroll, x_scroll_pos , scroll_pos, TRUE );
+#endif
}
else
{
// at first we try without any scrollbar. if the items don't
// fit into the window, we recalculate after subtracting an
// approximated 15 pt for the horizontal scrollbar
-
+
GetSize( &clientWidth, &clientHeight );
- clientHeight -= 4; // sunken frame
+ clientHeight -= 4; // sunken frame
int entireWidth = 0;
int x = 5; // painting is done at x-2
int y = 5; // painting is done at y-2
int maxWidth = 0;
+ m_visibleLines = 0;
+ int m_currentVisibleLines = 0;
wxNode *node = m_lines.First();
while (node)
{
+ m_currentVisibleLines++;
wxListLineData *line = (wxListLineData*)node->Data();
line->CalculateSize( &dc, iconSpacing );
line->SetPosition( &dc, x, y, clientWidth );
line->GetSize( lineWidth, lineHeight );
if (lineWidth > maxWidth) maxWidth = lineWidth;
y += lineSpacing;
+ if (m_currentVisibleLines > m_visibleLines)
+ m_visibleLines = m_currentVisibleLines;
if (y+lineSpacing-6 >= clientHeight) // -6 for earlier "line breaking"
{
+ m_currentVisibleLines = 0;
y = 5;
x += maxWidth+6;
entireWidth += maxWidth+6;
if ((tries == 0) && (entireWidth > clientWidth))
{
clientHeight -= 15; // scrollbar height
+ m_visibleLines = 0;
+ m_currentVisibleLines = 0;
break;
}
if (!node) tries = 1; // everything fits, no second try required
}
}
- m_visibleLines = (clientHeight+6) / (lineSpacing); // +6 for earlier "line breaking"
-
+
int scroll_pos = GetScrollPos( wxHORIZONTAL );
SetScrollbars( m_xScroll, m_yScroll, (entireWidth+15) / m_xScroll, 0, scroll_pos, 0, TRUE );
}
void wxListMainWindow::DeleteColumn( int col )
{
wxCHECK_RET( col < (int)m_columns.GetCount(),
- _T("attempting to delete inexistent column in wxListView") );
+ wxT("attempting to delete inexistent column in wxListView") );
m_dirty = TRUE;
wxNode *node = m_columns.Nth( col );
{
m_dirty = TRUE;
m_current = (wxListLineData *) NULL;
+
+ // to make the deletion of all items faster, we don't send the
+ // notifications in this case: this is compatible with wxMSW and
+ // documented in DeleteAllItems() description
+#if 0
wxNode *node = m_lines.First();
while (node)
{
wxListLineData *line = (wxListLineData*)node->Data();
+
DeleteLine( line );
+
node = node->Next();
}
+#endif // 0
+
m_lines.Clear();
}
void wxListMainWindow::EnsureVisible( long index )
{
+ // We have to call this here because the label in
+ // question might just have been added and no screen
+ // update taken place.
+ if (m_dirty) wxYield();
+
wxListLineData *oldCurrent = m_current;
m_current = (wxListLineData *) NULL;
int i = index;
else if (m_mode & wxLC_LIST) mode = wxLC_LIST;
else if (m_mode & wxLC_ICON) mode = wxLC_ICON;
else if (m_mode & wxLC_SMALL_ICON) mode = wxLC_ICON; // no typo
-
+
wxListLineData *line = new wxListLineData( this, mode, m_hilightBrush );
-
+
if (m_mode & wxLC_REPORT)
{
line->InitItems( GetColumnCount() );
{
line->InitItems( 1 );
}
-
+
line->SetItem( 0, item );
if ((item.m_itemId >= 0) && (item.m_itemId < (int)m_lines.GetCount()))
{
wxListCtrlCompare list_ctrl_compare_func_2;
long list_ctrl_compare_data;
-int list_ctrl_compare_func_1( const void *arg1, const void *arg2 )
+int LINKAGEMODE list_ctrl_compare_func_1( const void *arg1, const void *arg2 )
{
wxListLineData *line1 = *((wxListLineData**)arg1);
wxListLineData *line2 = *((wxListLineData**)arg2);
m_lines.Sort( list_ctrl_compare_func_1 );
}
+void wxListMainWindow::OnScroll(wxScrollWinEvent& event)
+{
+ wxScrolledWindow::OnScroll( event ) ;
+#if wxUSE_GENERIC_LIST_EXTENSIONS
+
+ if (event.GetOrientation() == wxHORIZONTAL && ( m_mode & wxLC_REPORT ))
+ {
+ wxListCtrl* lc = wxDynamicCast( GetParent() , wxListCtrl ) ;
+ if ( lc )
+ {
+ lc->m_headerWin->Refresh() ;
+#ifdef __WXMAC__
+ lc->m_headerWin->MacUpdateImmediately() ;
+#endif
+ }
+ }
+#endif
+}
+
// -------------------------------------------------------------------------------------
// wxListItem
// -------------------------------------------------------------------------------------
IMPLEMENT_DYNAMIC_CLASS(wxListItem, wxObject)
-wxListItem::wxListItem(void)
+wxListItem::wxListItem()
{
m_mask = 0;
m_itemId = 0;
EVT_IDLE (wxListCtrl::OnIdle)
END_EVENT_TABLE()
-wxListCtrl::wxListCtrl(void)
+wxListCtrl::wxListCtrl()
{
m_imageListNormal = (wxImageList *) NULL;
m_imageListSmall = (wxImageList *) NULL;
m_headerWin = (wxListHeaderWindow*) NULL;
}
-wxListCtrl::~wxListCtrl(void)
+wxListCtrl::~wxListCtrl()
{
}
bool wxListCtrl::Create( wxWindow *parent, wxWindowID id,
const wxPoint &pos, const wxSize &size,
+#if wxUSE_VALIDATORS
long style, const wxValidator &validator,
+#endif
const wxString &name )
{
m_imageListNormal = (wxImageList *) NULL;
long s = style;
- if ((s & wxLC_REPORT == 0) &&
+#ifdef __VMS__
+#pragma message disable codcauunr
+ // VMS reports on this part the warning:
+ // statement either is unreachable or causes unreachable code
+#endif
+ if ((s & wxLC_REPORT == 0) &&
(s & wxLC_LIST == 0) &&
(s & wxLC_ICON == 0))
{
s = s | wxLC_LIST;
}
+#ifdef __VMS__
+#pragma message enable codcauunr
+#endif
bool ret = wxControl::Create( parent, id, pos, size, s, name );
+#if wxUSE_VALIDATORS
SetValidator( validator );
-
+#endif
+
if (s & wxSUNKEN_BORDER) s -= wxSUNKEN_BORDER;
m_mainWin = new wxListMainWindow( this, -1, wxPoint(0,0), size, s );
{
if (!m_headerWin)
{
- m_headerWin = new wxListHeaderWindow( this, -1, m_mainWin,
- wxPoint(0,0), wxSize(width,23), wxTAB_TRAVERSAL );
+ m_headerWin = new wxListHeaderWindow( this, -1, m_mainWin,
+ wxPoint(0,0), wxSize(width,23), wxTAB_TRAVERSAL );
+ if (HasFlag(wxLC_NO_HEADER))
+ m_headerWin->Show( FALSE );
}
else
- {
- m_headerWin->Show( TRUE );
- }
+ {
+ if (flag & wxLC_NO_HEADER)
+ m_headerWin->Show( FALSE );
+ else
+ m_headerWin->Show( TRUE );
+ }
}
}
else
{
- if (HasFlag(wxLC_REPORT))
+ if (HasFlag(wxLC_REPORT) && !(HasFlag(wxLC_NO_HEADER)))
{
m_headerWin->Show( FALSE );
}
- }
+ }
}
-
+
wxWindow::SetWindowStyleFlag( flag );
}
return TRUE;
}
-int wxListCtrl::GetCountPerPage(void) const
+int wxListCtrl::GetCountPerPage() const
{
return m_mainWin->GetCountPerPage(); // different from Windows ?
}
-/*
-wxText& wxListCtrl::GetEditControl(void) const
-{
-}
-*/
-
bool wxListCtrl::GetItem( wxListItem &info ) const
{
m_mainWin->GetItem( info );
return 0;
}
-int wxListCtrl::GetItemCount(void) const
+int wxListCtrl::GetItemCount() const
{
return m_mainWin->GetItemCount();
}
-int wxListCtrl::GetColumnCount(void) const
+int wxListCtrl::GetColumnCount() const
{
return m_mainWin->GetColumnCount();
}
return m_mainWin->GetItemSpacing( isSmall );
}
-int wxListCtrl::GetSelectedItemCount(void) const
+int wxListCtrl::GetSelectedItemCount() const
{
return m_mainWin->GetSelectedItemCount();
}
/*
-wxColour wxListCtrl::GetTextColour(void) const
+wxColour wxListCtrl::GetTextColour() const
{
}
}
*/
-long wxListCtrl::GetTopItem(void) const
+long wxListCtrl::GetTopItem() const
{
return 0;
}
return TRUE;
}
-bool wxListCtrl::DeleteAllItems(void)
+bool wxListCtrl::DeleteAllItems()
{
m_mainWin->DeleteAllItems();
return TRUE;
{
for ( size_t n = 0; n < m_mainWin->m_columns.GetCount(); n++ )
DeleteColumn(n);
-
+
return TRUE;
}
return TRUE;
}
-/*
-wxText& wxListCtrl::Edit( long WXUNUSED(item ) )
+void wxListCtrl::Edit( long item )
{
+ m_mainWin->Edit( item );
}
-*/
bool wxListCtrl::EnsureVisible( long item )
{
long wxListCtrl::InsertItem( wxListItem& info )
{
m_mainWin->InsertItem( info );
- return 0;
+ return info.m_itemId;
}
long wxListCtrl::InsertItem( long index, const wxString &label )
int w = 0;
int h = 0;
- if (HasFlag(wxLC_REPORT))
+ if (HasFlag(wxLC_REPORT) && !HasFlag(wxLC_NO_HEADER))
{
m_headerWin->GetPosition( &x, &y );
m_headerWin->GetSize( &w, &h );
m_mainWin->SetBackgroundColour( colour );
m_mainWin->m_dirty = TRUE;
}
-
+
if (m_headerWin)
{
- m_headerWin->SetBackgroundColour( colour );
+// m_headerWin->SetBackgroundColour( colour );
}
return TRUE;
{
if ( !wxWindow::SetForegroundColour( colour ) )
return FALSE;
-
+
if (m_mainWin)
{
m_mainWin->SetForegroundColour( colour );
m_mainWin->m_dirty = TRUE;
}
-
+
if (m_headerWin)
{
m_headerWin->SetForegroundColour( colour );
{
if ( !wxWindow::SetFont( font ) )
return FALSE;
-
+
if (m_mainWin)
{
m_mainWin->SetFont( font );
m_mainWin->m_dirty = TRUE;
}
-
+
if (m_headerWin)
{
m_headerWin->SetFont( font );