diff --git a/src/kits/interface/ColumnListView.cpp b/src/kits/interface/ColumnListView.cpp index 7ac13c02db..48f00a0868 100644 --- a/src/kits/interface/ColumnListView.cpp +++ b/src/kits/interface/ColumnListView.cpp @@ -144,10 +144,34 @@ static const float kDropHighlightLineHeight = 2.0; static const uint32 kToggleColumn = 'BTCL'; + +#ifdef DOUBLE_BUFFERED_COLUMN_RESIZE + +class ColumnResizeBufferView : public BView +{ +public: + ColumnResizeBufferView(); + virtual ~ColumnResizeBufferView(); + void UpdateMaxWidth(float width); + void UpdateMaxHeight(float height); + bool Lock(); + void Unlock(); + const BBitmap* Bitmap(); +private: + void _InitBitmap(); + void _FreeBitmap(); + + BBitmap* fDrawBuffer; +}; + +#endif + + class BRowContainer : public BObjectList { }; + class TitleView : public BView { typedef BView _inherited; public: @@ -198,10 +222,6 @@ private: // float fColumnsWidth; BRect fVisibleRect; -#if DOUBLE_BUFFERED_COLUMN_RESIZE - BBitmap* fDrawBuffer; - BView* fDrawBufferView; -#endif enum { INACTIVE, @@ -292,6 +312,10 @@ public: virtual void MouseUp(BPoint where); virtual void MessageReceived(BMessage* message); +#if DOUBLE_BUFFERED_COLUMN_RESIZE + ColumnResizeBufferView* ResizeBufferView(); +#endif + private: bool SortList(BRowContainer* list, bool isVisible); static int32 DeepSortThreadEntry(void* outlineView); @@ -311,8 +335,7 @@ private: BRect fVisibleRect; #if DOUBLE_BUFFERED_COLUMN_RESIZE - BBitmap* fDrawBuffer; - BView* fDrawBufferView; + ColumnResizeBufferView* fResizeBufferView; #endif BRow* fFocusRow; @@ -391,6 +414,101 @@ private: using namespace BPrivate; +#ifdef DOUBLE_BUFFERED_COLUMN_RESIZE + +ColumnResizeBufferView::ColumnResizeBufferView() + : BView(BRect(0, 0, 600, 35), "double_buffer_view", B_FOLLOW_ALL_SIDES, 0), fDrawBuffer(NULL) +{ + _InitBitmap(); +} + + +ColumnResizeBufferView::~ColumnResizeBufferView() +{ + _FreeBitmap(); +} + + +void +ColumnResizeBufferView::UpdateMaxWidth(float width) +{ + Lock(); + BRect bounds = Bounds(); + Unlock(); + + if (width > bounds.Width()) { + Lock(); + ResizeTo(width, bounds.Height()); + Unlock(); + _InitBitmap(); + } +} + + +void +ColumnResizeBufferView::UpdateMaxHeight(float height) +{ + Lock(); + BRect bounds = Bounds(); + Unlock(); + + if (height > bounds.Height()) { + Lock(); + ResizeTo(bounds.Width(), height); + Unlock(); + _InitBitmap(); + } +} + + +bool +ColumnResizeBufferView::Lock() +{ + return fDrawBuffer->Lock(); +} + + +void +ColumnResizeBufferView::Unlock() +{ + fDrawBuffer->Unlock(); +} + + +const BBitmap* +ColumnResizeBufferView::Bitmap() +{ + return fDrawBuffer; +} + + +void +ColumnResizeBufferView::_InitBitmap() +{ + _FreeBitmap(); + + fDrawBuffer = new BBitmap(Bounds(), B_RGB32, true); + fDrawBuffer->Lock(); + fDrawBuffer->AddChild(this); + fDrawBuffer->Unlock(); +} + + +void +ColumnResizeBufferView::_FreeBitmap() +{ + if (fDrawBuffer) { + fDrawBuffer->Lock(); + fDrawBuffer->RemoveChild(this); + fDrawBuffer->Unlock(); + delete fDrawBuffer; + fDrawBuffer = NULL; + } +} + +#endif + + BField::BField() { } @@ -2223,17 +2341,6 @@ TitleView::TitleView(BRect rect, OutlineView* horizontalSlave, { SetViewColor(B_TRANSPARENT_COLOR); -#if DOUBLE_BUFFERED_COLUMN_RESIZE - // xxx this needs to be smart about the size of the backbuffer. - BRect doubleBufferRect(0, 0, 600, 35); - fDrawBuffer = new BBitmap(doubleBufferRect, B_RGB32, true); - fDrawBufferView = new BView(doubleBufferRect, "double_buffer_view", - B_FOLLOW_ALL_SIDES, 0); - fDrawBuffer->Lock(); - fDrawBuffer->AddChild(fDrawBufferView); - fDrawBuffer->Unlock(); -#endif - fUpSortArrow = new BBitmap(BRect(0, 0, 7, 7), B_CMAP8); fDownSortArrow = new BBitmap(BRect(0, 0, 7, 7), B_CMAP8); @@ -2254,9 +2361,6 @@ TitleView::~TitleView() delete fColumnPop; fColumnPop = NULL; -#if DOUBLE_BUFFERED_COLUMN_RESIZE - delete fDrawBuffer; -#endif delete fUpSortArrow; delete fDownSortArrow; @@ -2270,6 +2374,9 @@ TitleView::~TitleView() void TitleView::ColumnAdded(BColumn* column) { +#ifdef DOUBLE_BUFFERED_COLUMN_RESIZE + fOutlineView->ResizeBufferView()->UpdateMaxWidth(column->MaxWidth()); +#endif // fColumnsWidth += column->Width(); FixScrollBar(false); Invalidate(); @@ -2481,13 +2588,14 @@ TitleView::ResizeSelectedColumn(BPoint position, bool preferred) destRect.OffsetBy(fSelectedColumnRect.left, 0); #if DOUBLE_BUFFERED_COLUMN_RESIZE - fDrawBuffer->Lock(); - DrawTitle(fDrawBufferView, sourceRect, fSelectedColumn, false); - fDrawBufferView->Sync(); - fDrawBuffer->Unlock(); + ColumnResizeBufferView* bufferView = fOutlineView->ResizeBufferView(); + bufferView->Lock(); + DrawTitle(bufferView, sourceRect, fSelectedColumn, false); + bufferView->Sync(); + bufferView->Unlock(); CopyBits(originalRect, movedRect); - DrawBitmap(fDrawBuffer, sourceRect, destRect); + DrawBitmap(bufferView->Bitmap(), sourceRect, destRect); #else CopyBits(originalRect, movedRect); DrawTitle(this, destRect, fSelectedColumn, false); @@ -3113,15 +3221,7 @@ OutlineView::OutlineView(BRect rect, BList* visibleColumns, BList* sortColumns, SetViewColor(B_TRANSPARENT_COLOR); #if DOUBLE_BUFFERED_COLUMN_RESIZE - // TODO: This needs to be smart about the size of the buffer. - // Also, the buffer can be shared with the title's buffer. - BRect doubleBufferRect(0, 0, 600, 35); - fDrawBuffer = new BBitmap(doubleBufferRect, B_RGB32, true); - fDrawBufferView = new BView(doubleBufferRect, "double_buffer_view", - B_FOLLOW_ALL_SIDES, 0); - fDrawBuffer->Lock(); - fDrawBuffer->AddChild(fDrawBufferView); - fDrawBuffer->Unlock(); + fResizeBufferView = new ColumnResizeBufferView(); #endif FixScrollBar(true); @@ -3133,7 +3233,7 @@ OutlineView::OutlineView(BRect rect, BList* visibleColumns, BList* sortColumns, OutlineView::~OutlineView() { #if DOUBLE_BUFFERED_COLUMN_RESIZE - delete fDrawBuffer; + delete fResizeBufferView; #endif Clear(); @@ -3275,15 +3375,15 @@ OutlineView::RedrawColumn(BColumn* column, float leftEdge, bool isFirstColumn) #if DOUBLE_BUFFERED_COLUMN_RESIZE - fDrawBuffer->Lock(); + fResizeBufferView->Lock(); - fDrawBufferView->SetHighColor(highColor); - fDrawBufferView->SetLowColor(lowColor); + fResizeBufferView->SetHighColor(highColor); + fResizeBufferView->SetLowColor(lowColor); BFont font; GetFont(&font); - fDrawBufferView->SetFont(&font); - fDrawBufferView->FillRect(sourceRect, B_SOLID_LOW); + fResizeBufferView->SetFont(&font); + fResizeBufferView->FillRect(sourceRect, B_SOLID_LOW); if (isFirstColumn) { // If this is the first column, double buffer drawing the latch @@ -3299,7 +3399,7 @@ OutlineView::RedrawColumn(BColumn* column, float leftEdge, bool isFirstColumn) BRect latchRect(sourceRect); latchRect.right = latchRect.left + fMasterView->LatchWidth(); - fMasterView->DrawLatch(fDrawBufferView, latchRect, pos, row); + fMasterView->DrawLatch(fResizeBufferView, latchRect, pos, row); } BField* field = row->GetField(column->fFieldID); @@ -3310,33 +3410,33 @@ OutlineView::RedrawColumn(BColumn* column, float leftEdge, bool isFirstColumn) #if CONSTRAIN_CLIPPING_REGION BRegion clipRegion(fieldRect); - fDrawBufferView->PushState(); - fDrawBufferView->ConstrainClippingRegion(&clipRegion); + fResizeBufferView->PushState(); + fResizeBufferView->ConstrainClippingRegion(&clipRegion); #endif - fDrawBufferView->SetHighColor(fMasterView->Color( + fResizeBufferView->SetHighColor(fMasterView->Color( row->fNextSelected ? B_COLOR_SELECTION_TEXT : B_COLOR_TEXT)); float baseline = floor(fieldRect.top + fh.ascent + (fieldRect.Height() + 1 - (fh.ascent+fh.descent)) / 2); - fDrawBufferView->MovePenTo(fieldRect.left + 8, baseline); - column->DrawField(field, fieldRect, fDrawBufferView); + fResizeBufferView->MovePenTo(fieldRect.left + 8, baseline); + column->DrawField(field, fieldRect, fResizeBufferView); #if CONSTRAIN_CLIPPING_REGION - fDrawBufferView->PopState(); + fResizeBufferView->PopState(); #endif } if (fFocusRow == row && !fEditMode && fMasterView->IsFocus() && Window()->IsActive()) { - fDrawBufferView->SetHighColor(fMasterView->Color( + fResizeBufferView->SetHighColor(fMasterView->Color( B_COLOR_ROW_DIVIDER)); - fDrawBufferView->StrokeRect(BRect(-1, sourceRect.top, + fResizeBufferView->StrokeRect(BRect(-1, sourceRect.top, 10000.0, sourceRect.bottom)); } - fDrawBufferView->Sync(); - fDrawBuffer->Unlock(); + fResizeBufferView->Sync(); + fResizeBufferView->Unlock(); SetDrawingMode(B_OP_COPY); - DrawBitmap(fDrawBuffer, sourceRect, destRect); + DrawBitmap(fResizeBufferView->Bitmap(), sourceRect, destRect); #else @@ -4013,6 +4113,17 @@ OutlineView::MessageReceived(BMessage* message) } +#if DOUBLE_BUFFERED_COLUMN_RESIZE + +ColumnResizeBufferView* +OutlineView::ResizeBufferView() +{ + return fResizeBufferView; +} + +#endif + + void OutlineView::ChangeFocusRow(bool up, bool updateSelection, bool addToCurrentSelection) @@ -4381,6 +4492,10 @@ OutlineView::AddRow(BRow* row, int32 Index, BRow* parentRow) } } +#ifdef DOUBLE_BUFFERED_COLUMN_RESIZE + ResizeBufferView()->UpdateMaxHeight(row->Height()); +#endif + if (parentRow == 0 || parentRow->fIsExpanded) fItemsHeight += row->Height() + 1;