static void EventFlagsToSelType(long style,
bool shiftDown,
bool ctrlDown,
- bool *is_multiple,
- bool *extended_select,
- bool *unselect_others)
+ bool &is_multiple,
+ bool &extended_select,
+ bool &unselect_others)
{
- *is_multiple = (style & wxTR_MULTIPLE) != 0;
- *extended_select = shiftDown && is_multiple;
- *unselect_others = !(extended_select || (ctrlDown && is_multiple));
+ is_multiple = (style & wxTR_MULTIPLE) != 0;
+ extended_select = shiftDown && is_multiple;
+ unselect_others = !(extended_select || (ctrlDown && is_multiple));
}
// -----------------------------------------------------------------------------
m_dragCount = 0;
m_isDragging = FALSE;
- m_dropTarget = (wxGenericTreeItem *)NULL;
+ m_dropTarget =
+ m_oldSelection = (wxGenericTreeItem *)NULL;
m_renameTimer = new wxTreeRenameTimer( this );
void wxTreeCtrl::Delete(const wxTreeItemId& itemId)
{
wxGenericTreeItem *item = itemId.m_pItem;
- wxGenericTreeItem *parent = item->GetParent();
+ // don't stay with invalid m_key_current or we will crash in the next call
+ // to OnChar()
+ bool changeKeyCurrent = FALSE;
+ wxGenericTreeItem *itemKey = m_key_current;
+ while ( itemKey && !changeKeyCurrent )
+ {
+ if ( itemKey == item )
+ {
+ // m_key_current is a descendant of the item being deleted
+ changeKeyCurrent = TRUE;
+ }
+ else
+ {
+ itemKey = itemKey->GetParent();
+ }
+ }
+
+ wxGenericTreeItem *parent = item->GetParent();
if ( parent )
{
parent->GetChildren().Remove( item ); // remove by value
}
+ if ( changeKeyCurrent )
+ {
+ // may be NULL or not
+ m_key_current = parent;
+ }
+
item->DeleteChildren(this);
SendDeleteEvent(item);
delete item;
// shift press
if (extended_select)
{
- if (m_current == NULL) m_current=m_key_current=GetRootItem().m_pItem;
+ if ( !m_current )
+ {
+ m_current =
+ m_key_current = GetRootItem().m_pItem;
+ }
+
// don't change the mark (m_current)
SelectItemRange(m_current, item);
}
{
m_imageListNormal = imageList;
+ if ( !m_imageListNormal )
+ return;
+
// Calculate a m_lineHeight value from the image sizes.
// May be toggle off. Then wxTreeCtrl will spread when
// necessary (which might look ugly).
-#if 1
wxClientDC dc(this);
m_lineHeight = (int)(dc.GetCharHeight() + 4);
int width = 0, height = 0,
m_lineHeight += 2; // at least 2 pixels
else
m_lineHeight += m_lineHeight/10; // otherwise 10% extra spacing
-#endif
}
void wxTreeCtrl::SetStateImageList(wxImageList *imageList)
int image = item->GetCurrentImage();
if ( image != NO_IMAGE )
{
- m_imageListNormal->GetSize( image, image_w, image_h );
- image_w += 4;
+ if ( m_imageListNormal )
+ {
+ m_imageListNormal->GetSize( image, image_w, image_h );
+ image_w += 4;
+ }
+ else
+ {
+ image = NO_IMAGE;
+ }
}
int total_h = GetLineHeight(item);
EventFlagsToSelType(GetWindowStyleFlag(),
event.ShiftDown(),
event.ControlDown(),
- &is_multiple, &extended_select, &unselect_others);
-
+ is_multiple, extended_select, unselect_others);
+
+ // + : Expand
+ // - : Collaspe
+ // * : Toggle Expand/Collapse
+ // ' ' | return : activate
+ // up : go up (not last children!)
+ // down : go down
+ // left : go to parent
+ // right : open if parent and go next
+ // home : go to root
+ // end : go to last item without opening parents
switch (event.KeyCode())
{
case '+':
else
{
wxTreeItemId next = GetNextSibling( m_key_current );
-// if (next == 0)
if (!next)
{
wxTreeItemId current = m_key_current;
if (current) next = GetNextSibling( current );
}
}
-// if (next != 0)
if (next)
{
SelectItem( next, unselect_others, extended_select );
int image = m_currentEdit->GetCurrentImage();
if ( image != NO_IMAGE )
{
- m_imageListNormal->GetSize( image, image_w, image_h );
- image_w += 4;
+ if ( m_imageListNormal )
+ {
+ m_imageListNormal->GetSize( image, image_w, image_h );
+ image_w += 4;
+ }
+ else
+ {
+ wxFAIL_MSG(_T("you must create an image list to use images!"));
+ }
}
x += image_w;
w -= image_w + 4; // I don't know why +4 is needed
// we're going to drag this item
m_isDragging = TRUE;
+ // remember the old cursor because we will change it while
+ // dragging
+ m_oldCursor = m_cursor;
+
+ // in a single selection control, hide the selection temporarily
+ if ( !(GetWindowStyleFlag() & wxTR_MULTIPLE) )
+ {
+ m_oldSelection = GetSelection().m_pItem;
+
+ if ( m_oldSelection )
+ {
+ m_oldSelection->SetHilight(FALSE);
+ RefreshLine(m_oldSelection);
+ }
+ }
+
CaptureMouse();
}
}
m_isDragging = FALSE;
m_dropTarget = (wxGenericTreeItem *)NULL;
+ if ( m_oldSelection )
+ {
+ m_oldSelection->SetHilight(TRUE);
+ RefreshLine(m_oldSelection);
+ m_oldSelection = (wxGenericTreeItem *)NULL;
+ }
+
ReleaseMouse();
- SetCursor(wxCURSOR_DEFAULT);
+ SetCursor(m_oldCursor);
wxYield();
}
EventFlagsToSelType(GetWindowStyleFlag(),
event.ShiftDown(),
event.ControlDown(),
- &is_multiple, &extended_select, &unselect_others);
+ is_multiple, extended_select, unselect_others);
if ( onButton )
{
void wxTreeCtrl::CalculateSize( wxGenericTreeItem *item, wxDC &dc )
{
- int text_w = 0;
- int text_h = 0;
+ wxCoord text_w = 0;
+ wxCoord text_h = 0;
if (item->IsBold())
dc.SetFont(m_boldFont);
int image = item->GetCurrentImage();
if ( image != NO_IMAGE )
{
- m_imageListNormal->GetSize( image, image_w, image_h );
- image_w += 4;
+ if ( m_imageListNormal )
+ {
+ m_imageListNormal->GetSize( image, image_w, image_h );
+ image_w += 4;
+ }
}
int total_h = (image_h > text_h) ? image_h : text_h;