BScrollBar: style fixes, update copyright header

This commit is contained in:
John Scipione
2014-03-07 19:11:33 -05:00
parent ae63d4aa97
commit b7929c0574
+183 -141
View File
@@ -1,17 +1,23 @@
/* /*
* Copyright 2001-2009, Haiku, Inc. All rights reserved. * Copyright 2001-2014 Haiku, Inc. All rights reserved.
* Distributed under the terms of the MIT license. * Distributed under the terms of the MIT license.
* *
* Authors: * Authors:
* Marc Flerackers ([email protected]) * Stephan Aßmus, [email protected]
* DarkWyrm ([email protected]) * Stefano Ceccherini, [email protected]
* Stefano Ceccherini ([email protected]) * DarkWyrm, [email protected]
* Stephan Aßmus <[email protected]> * Marc Flerackers, [email protected]
* John Scipione, [email protected]
*/ */
#include <ScrollBar.h> #include <ScrollBar.h>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ControlLook.h> #include <ControlLook.h>
#include <LayoutUtils.h> #include <LayoutUtils.h>
#include <Message.h> #include <Message.h>
@@ -19,12 +25,9 @@
#include <Shape.h> #include <Shape.h>
#include <Window.h> #include <Window.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <binary_compatibility/Interface.h> #include <binary_compatibility/Interface.h>
//#define TRACE_SCROLLBAR //#define TRACE_SCROLLBAR
#ifdef TRACE_SCROLLBAR #ifdef TRACE_SCROLLBAR
# define TRACE(x...) printf(x) # define TRACE(x...) printf(x)
@@ -41,54 +44,56 @@ typedef enum {
ARROW_NONE ARROW_NONE
} arrow_direction; } arrow_direction;
#define SBC_SCROLLBYVALUE 0
#define SBC_SETDOUBLE 1 #define SBC_SCROLLBYVALUE 0
#define SBC_SETPROPORTIONAL 2 #define SBC_SETDOUBLE 1
#define SBC_SETSTYLE 3 #define SBC_SETPROPORTIONAL 2
#define SBC_SETSTYLE 3
// Quick constants for determining which arrow is down and are defined with // Quick constants for determining which arrow is down and are defined with
// respect to double arrow mode. ARROW1 and ARROW4 refer to the outer pair of // respect to double arrow mode. ARROW1 and ARROW4 refer to the outer pair of
// arrows and ARROW2 and ARROW3 refer to the inner ones. ARROW1 points left/up // arrows and ARROW2 and ARROW3 refer to the inner ones. ARROW1 points left/up
// and ARROW4 points right/down. // and ARROW4 points right/down.
#define ARROW1 0 #define ARROW1 0
#define ARROW2 1 #define ARROW2 1
#define ARROW3 2 #define ARROW3 2
#define ARROW4 3 #define ARROW4 3
#define THUMB 4 #define THUMB 4
#define NOARROW -1 #define NOARROW -1
static const bigtime_t kRepeatDelay = 300000; static const bigtime_t kRepeatDelay = 300000;
// Because the R5 version kept a lot of data on server-side, we need to kludge // Because the R5 version kept a lot of data on server-side, we need to kludge
// our way into binary compatibility // our way into binary compatibility
class BScrollBar::Private { class BScrollBar::Private {
public: public:
Private(BScrollBar* scrollBar) Private(BScrollBar* scrollBar)
: :
fScrollBar(scrollBar), fScrollBar(scrollBar),
fEnabled(true), fEnabled(true),
fRepeaterThread(-1), fRepeaterThread(-1),
fExitRepeater(false), fExitRepeater(false),
fRepeaterDelay(0), fRepeaterDelay(0),
fThumbFrame(0.0, 0.0, -1.0, -1.0), fThumbFrame(0.0, 0.0, -1.0, -1.0),
fDoRepeat(false), fDoRepeat(false),
fClickOffset(0.0, 0.0), fClickOffset(0.0, 0.0),
fThumbInc(0.0), fThumbInc(0.0),
fStopValue(0.0), fStopValue(0.0),
fUpArrowsEnabled(true), fUpArrowsEnabled(true),
fDownArrowsEnabled(true), fDownArrowsEnabled(true),
fBorderHighlighted(false), fBorderHighlighted(false),
fButtonDown(NOARROW) fButtonDown(NOARROW)
{ {
#ifdef TEST_MODE #ifdef TEST_MODE
fScrollBarInfo.proportional = true; fScrollBarInfo.proportional = true;
fScrollBarInfo.double_arrows = true; fScrollBarInfo.double_arrows = true;
fScrollBarInfo.knob = 0; fScrollBarInfo.knob = 0;
fScrollBarInfo.min_knob_size = 15; fScrollBarInfo.min_knob_size = 15;
#else #else
get_scroll_bar_info(&fScrollBarInfo); get_scroll_bar_info(&fScrollBarInfo);
#endif #endif
} }
~Private() ~Private()
@@ -100,12 +105,12 @@ public:
} }
} }
void DrawScrollBarButton(BScrollBar *owner, arrow_direction direction, void DrawScrollBarButton(BScrollBar* owner, arrow_direction direction,
BRect frame, bool down = false); BRect frame, bool down = false);
static int32 button_repeater_thread(void* data); static int32 button_repeater_thread(void* data);
int32 ButtonRepeaterThread(); int32 ButtonRepeaterThread();
BScrollBar* fScrollBar; BScrollBar* fScrollBar;
bool fEnabled; bool fEnabled;
@@ -138,7 +143,7 @@ public:
// This thread is spawned when a button is initially pushed and repeatedly scrolls // This thread is spawned when a button is initially pushed and repeatedly scrolls
// the scrollbar by a little bit after a short delay // the scrollbar by a little bit after a short delay
int32 int32
BScrollBar::Private::button_repeater_thread(void *data) BScrollBar::Private::button_repeater_thread(void* data)
{ {
BScrollBar::Private* privateData = (BScrollBar::Private*)data; BScrollBar::Private* privateData = (BScrollBar::Private*)data;
return privateData->ButtonRepeaterThread(); return privateData->ButtonRepeaterThread();
@@ -159,7 +164,6 @@ BScrollBar::Private::ButtonRepeaterThread()
// repeat loop // repeat loop
while (!fExitRepeater) { while (!fExitRepeater) {
if (fScrollBar->LockLooper()) { if (fScrollBar->LockLooper()) {
if (fDoRepeat) { if (fDoRepeat) {
float value = fScrollBar->Value() + fThumbInc; float value = fScrollBar->Value() + fThumbInc;
if (fButtonDown == NOARROW) { if (fButtonDown == NOARROW) {
@@ -168,9 +172,8 @@ BScrollBar::Private::ButtonRepeaterThread()
fScrollBar->SetValue(value); fScrollBar->SetValue(value);
if (fThumbInc < 0.0 && value >= fStopValue) if (fThumbInc < 0.0 && value >= fStopValue)
fScrollBar->SetValue(value); fScrollBar->SetValue(value);
} else { } else
fScrollBar->SetValue(value); fScrollBar->SetValue(value);
}
} }
fScrollBar->UnlockLooper(); fScrollBar->UnlockLooper();
@@ -189,19 +192,20 @@ BScrollBar::Private::ButtonRepeaterThread()
} }
// #pragma mark - // #pragma mark - BScrollBar
BScrollBar::BScrollBar(BRect frame, const char* name, BView *target, BScrollBar::BScrollBar(BRect frame, const char* name, BView* target,
float min, float max, orientation direction) float min, float max, orientation direction)
: BView(frame, name, B_FOLLOW_NONE, B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE :
| B_FRAME_EVENTS), BView(frame, name, B_FOLLOW_NONE,
B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE | B_FRAME_EVENTS),
fMin(min), fMin(min),
fMax(max), fMax(max),
fSmallStep(1), fSmallStep(1.0f),
fLargeStep(10), fLargeStep(10.0f),
fValue(0), fValue(0),
fProportion(0.0), fProportion(0.0f),
fTarget(NULL), fTarget(NULL),
fOrientation(direction), fOrientation(direction),
fTargetName(NULL) fTargetName(NULL)
@@ -222,15 +226,16 @@ BScrollBar::BScrollBar(BRect frame, const char* name, BView *target,
} }
BScrollBar::BScrollBar(const char* name, BView *target, BScrollBar::BScrollBar(const char* name, BView* target,
float min, float max, orientation direction) float min, float max, orientation direction)
: BView(name, B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE | B_FRAME_EVENTS), :
BView(name, B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE | B_FRAME_EVENTS),
fMin(min), fMin(min),
fMax(max), fMax(max),
fSmallStep(1), fSmallStep(1.0f),
fLargeStep(10), fLargeStep(10.0f),
fValue(0), fValue(0),
fProportion(0.0), fProportion(0.0f),
fTarget(NULL), fTarget(NULL),
fOrientation(direction), fOrientation(direction),
fTargetName(NULL) fTargetName(NULL)
@@ -248,7 +253,8 @@ BScrollBar::BScrollBar(const char* name, BView *target,
BScrollBar::BScrollBar(BMessage* data) BScrollBar::BScrollBar(BMessage* data)
: BView(data), :
BView(data),
fTarget(NULL), fTarget(NULL),
fTargetName(NULL) fTargetName(NULL)
{ {
@@ -257,15 +263,20 @@ BScrollBar::BScrollBar(BMessage* data)
// TODO: Does the BeOS implementation try to find the target // TODO: Does the BeOS implementation try to find the target
// by name again? Does it archive the name at all? // by name again? Does it archive the name at all?
if (data->FindFloat("_range", 0, &fMin) < B_OK) if (data->FindFloat("_range", 0, &fMin) < B_OK)
fMin = 0.0; fMin = 0.0f;
if (data->FindFloat("_range", 1, &fMax) < B_OK) if (data->FindFloat("_range", 1, &fMax) < B_OK)
fMax = 0.0; fMax = 0.0f;
if (data->FindFloat("_steps", 0, &fSmallStep) < B_OK) if (data->FindFloat("_steps", 0, &fSmallStep) < B_OK)
fSmallStep = 1.0; fSmallStep = 1.0f;
if (data->FindFloat("_steps", 1, &fLargeStep) < B_OK) if (data->FindFloat("_steps", 1, &fLargeStep) < B_OK)
fLargeStep = 10.0; fLargeStep = 10.0f;
if (data->FindFloat("_val", &fValue) < B_OK) if (data->FindFloat("_val", &fValue) < B_OK)
fValue = 0.0; fValue = 0.0;
int32 orientation; int32 orientation;
if (data->FindInt32("_orient", &orientation) < B_OK) { if (data->FindInt32("_orient", &orientation) < B_OK) {
fOrientation = B_VERTICAL; fOrientation = B_VERTICAL;
@@ -294,7 +305,7 @@ BScrollBar::~BScrollBar()
BArchivable* BArchivable*
BScrollBar::Instantiate(BMessage *data) BScrollBar::Instantiate(BMessage* data)
{ {
if (validate_instantiation(data, "BScrollBar")) if (validate_instantiation(data, "BScrollBar"))
return new BScrollBar(data); return new BScrollBar(data);
@@ -303,7 +314,7 @@ BScrollBar::Instantiate(BMessage *data)
status_t status_t
BScrollBar::Archive(BMessage *data, bool deep) const BScrollBar::Archive(BMessage* data, bool deep) const
{ {
status_t err = BView::Archive(data, deep); status_t err = BView::Archive(data, deep);
if (err != B_OK) if (err != B_OK)
@@ -383,7 +394,6 @@ BScrollBar::SetValue(float value)
return; return;
value = roundf(value); value = roundf(value);
if (value == fValue) if (value == fValue)
return; return;
@@ -410,17 +420,16 @@ BScrollBar::ValueChanged(float newValue)
{ {
TRACE("BScrollBar(%s)::ValueChanged(%.1f)\n", Name(), newValue); TRACE("BScrollBar(%s)::ValueChanged(%.1f)\n", Name(), newValue);
if (fTarget) { if (fTarget != NULL) {
// cache target bounds // cache target bounds
BRect targetBounds = fTarget->Bounds(); BRect targetBounds = fTarget->Bounds();
// if vertical, check bounds top and scroll if different from newValue // if vertical, check bounds top and scroll if different from newValue
if (fOrientation == B_VERTICAL && targetBounds.top != newValue) { if (fOrientation == B_VERTICAL && targetBounds.top != newValue)
fTarget->ScrollBy(0.0, newValue - targetBounds.top); fTarget->ScrollBy(0.0, newValue - targetBounds.top);
}
// if horizontal, check bounds left and scroll if different from newValue // if horizontal, check bounds left and scroll if different from newValue
if (fOrientation == B_HORIZONTAL && targetBounds.left != newValue) { if (fOrientation == B_HORIZONTAL && targetBounds.left != newValue)
fTarget->ScrollBy(newValue - targetBounds.left, 0.0); fTarget->ScrollBy(newValue - targetBounds.left, 0.0);
}
} }
TRACE(" -> %.1f\n", newValue); TRACE(" -> %.1f\n", newValue);
@@ -432,28 +441,28 @@ BScrollBar::ValueChanged(float newValue)
void void
BScrollBar::SetProportion(float value) BScrollBar::SetProportion(float value)
{ {
if (value < 0.0) if (value < 0.0f)
value = 0.0; value = 0.0f;
if (value > 1.0) else if (value > 1.0f)
value = 1.0; value = 1.0f;
if (value == fProportion) if (value == fProportion)
return; return;
TRACE("BScrollBar(%s)::SetProportion(%.1f)\n", Name(), value); TRACE("BScrollBar(%s)::SetProportion(%.1f)\n", Name(), value);
bool oldEnabled = fPrivateData->fEnabled && fMin < fMax bool oldEnabled = fPrivateData->fEnabled && fMin < fMax
&& fProportion < 1.0 && fProportion >= 0.0; && fProportion < 1.0f && fProportion >= 0.0f;
fProportion = value; fProportion = value;
bool newEnabled = fPrivateData->fEnabled && fMin < fMax bool newEnabled = fPrivateData->fEnabled && fMin < fMax
&& fProportion < 1.0 && fProportion >= 0.0; && fProportion < 1.0f && fProportion >= 0.0f;
_UpdateThumbFrame(); _UpdateThumbFrame();
if (oldEnabled != newEnabled) if (oldEnabled != newEnabled)
Invalidate(); Invalidate();
} }
@@ -467,9 +476,10 @@ BScrollBar::Proportion() const
void void
BScrollBar::SetRange(float min, float max) BScrollBar::SetRange(float min, float max)
{ {
if (min > max || isnanf(min) || isnanf(max) || isinff(min) || isinff(max)) { if (min > max || isnanf(min) || isnanf(max)
min = 0; || isinff(min) || isinff(max)) {
max = 0; min = 0.0f;
max = 0.0f;
} }
min = roundf(min); min = roundf(min);
@@ -492,7 +502,7 @@ BScrollBar::SetRange(float min, float max)
void void
BScrollBar::GetRange(float *min, float *max) const BScrollBar::GetRange(float* min, float* max) const
{ {
if (min != NULL) if (min != NULL)
*min = fMin; *min = fMin;
@@ -515,6 +525,7 @@ BScrollBar::SetSteps(float smallStep, float largeStep)
largeStep = roundf(largeStep); largeStep = roundf(largeStep);
if (fSmallStep == smallStep && fLargeStep == largeStep) if (fSmallStep == smallStep && fLargeStep == largeStep)
return; return;
TRACE("BScrollBar(%s)::SetSteps(small=%.1f, large=%.1f)\n", Name(), TRACE("BScrollBar(%s)::SetSteps(small=%.1f, large=%.1f)\n", Name(),
smallStep, largeStep); smallStep, largeStep);
@@ -536,9 +547,10 @@ BScrollBar::SetSteps(float smallStep, float largeStep)
void void
BScrollBar::GetSteps(float* smallStep, float* largeStep) const BScrollBar::GetSteps(float* smallStep, float* largeStep) const
{ {
if (smallStep) if (smallStep != NULL)
*smallStep = fSmallStep; *smallStep = fSmallStep;
if (largeStep)
if (largeStep != NULL)
*largeStep = fLargeStep; *largeStep = fLargeStep;
} }
@@ -642,13 +654,16 @@ BScrollBar::MessageReceived(BMessage* message)
int32 value; int32 value;
if (message->FindInt32("value", &value) == B_OK) if (message->FindInt32("value", &value) == B_OK)
ValueChanged(value); ValueChanged(value);
break; break;
} }
case B_MOUSE_WHEEL_CHANGED: case B_MOUSE_WHEEL_CHANGED:
{ {
// Must handle this here since BView checks for the existence of // Must handle this here since BView checks for the existence of
// scrollbars, which a scrollbar itself does not have // scrollbars, which a scrollbar itself does not have
float deltaX = 0.0f, deltaY = 0.0f; float deltaX = 0.0f;
float deltaY = 0.0f;
message->FindFloat("be:wheel_delta_x", &deltaX); message->FindFloat("be:wheel_delta_x", &deltaX);
message->FindFloat("be:wheel_delta_y", &deltaY); message->FindFloat("be:wheel_delta_y", &deltaY);
@@ -660,9 +675,9 @@ BScrollBar::MessageReceived(BMessage* message)
ScrollWithMouseWheelDelta(this, deltaY); ScrollWithMouseWheelDelta(this, deltaY);
} }
default: default:
BView::MessageReceived(message); BView::MessageReceived(message);
break;
} }
} }
@@ -677,8 +692,9 @@ BScrollBar::MouseDown(BPoint where)
int32 buttons; int32 buttons;
if (Looper() == NULL || Looper()->CurrentMessage() == NULL if (Looper() == NULL || Looper()->CurrentMessage() == NULL
|| Looper()->CurrentMessage()->FindInt32("buttons", &buttons) != B_OK) || Looper()->CurrentMessage()->FindInt32("buttons", &buttons) != B_OK) {
buttons = B_PRIMARY_MOUSE_BUTTON; buttons = B_PRIMARY_MOUSE_BUTTON;
}
if (buttons & B_SECONDARY_MOUSE_BUTTON) { if (buttons & B_SECONDARY_MOUSE_BUTTON) {
// special absolute scrolling: move thumb to where we clicked // special absolute scrolling: move thumb to where we clicked
@@ -713,15 +729,19 @@ BScrollBar::MouseDown(BPoint where)
case ARROW1: case ARROW1:
scrollValue = -buttonStepSize; scrollValue = -buttonStepSize;
break; break;
case ARROW2: case ARROW2:
scrollValue = buttonStepSize; scrollValue = buttonStepSize;
break; break;
case ARROW3: case ARROW3:
scrollValue = -buttonStepSize; scrollValue = -buttonStepSize;
break; break;
case ARROW4: case ARROW4:
scrollValue = buttonStepSize; scrollValue = buttonStepSize;
break; break;
case NOARROW: case NOARROW:
// we hit the empty area, figure out which side of the thumb // we hit the empty area, figure out which side of the thumb
if (fOrientation == B_VERTICAL) { if (fOrientation == B_VERTICAL) {
@@ -778,9 +798,10 @@ BScrollBar::MouseUp(BPoint pt)
void void
BScrollBar::MouseMoved(BPoint where, uint32 transit, const BMessage* message) BScrollBar::MouseMoved(BPoint where, uint32 transit, const BMessage* message)
{ {
if (!fPrivateData->fEnabled || fMin >= fMax || fProportion >= 1.0 if (!fPrivateData->fEnabled || fMin >= fMax || fProportion >= 1.0f
|| fProportion < 0.0) || fProportion < 0.0f) {
return; return;
}
if (fPrivateData->fButtonDown != NOARROW) { if (fPrivateData->fButtonDown != NOARROW) {
if (fPrivateData->fButtonDown == THUMB) { if (fPrivateData->fButtonDown == THUMB) {
@@ -854,10 +875,10 @@ BScrollBar::Draw(BRect updateRect)
} else } else
StrokeRect(bounds); StrokeRect(bounds);
bounds.InsetBy(1.0, 1.0); bounds.InsetBy(1.0f, 1.0f);
bool enabled = fPrivateData->fEnabled && fMin < fMax bool enabled = fPrivateData->fEnabled && fMin < fMax
&& fProportion < 1.0 && fProportion >= 0.0; && fProportion < 1.0f && fProportion >= 0.0f;
rgb_color light, dark, dark1, dark2; rgb_color light, dark, dark1, dark2;
if (enabled) { if (enabled) {
@@ -886,7 +907,7 @@ BScrollBar::Draw(BRect updateRect)
enabled, fPrivateData->fButtonDown == ARROW1); enabled, fPrivateData->fButtonDown == ARROW1);
if (doubleArrows) { if (doubleArrows) {
buttonFrame.OffsetBy(bounds.Height() + 1, 0.0); buttonFrame.OffsetBy(bounds.Height() + 1, 0.0f);
_DrawArrowButton(ARROW_RIGHT, doubleArrows, buttonFrame, updateRect, _DrawArrowButton(ARROW_RIGHT, doubleArrows, buttonFrame, updateRect,
enabled, fPrivateData->fButtonDown == ARROW2); enabled, fPrivateData->fButtonDown == ARROW2);
@@ -913,7 +934,7 @@ BScrollBar::Draw(BRect updateRect)
enabled, fPrivateData->fButtonDown == ARROW1); enabled, fPrivateData->fButtonDown == ARROW1);
if (doubleArrows) { if (doubleArrows) {
buttonFrame.OffsetBy(0.0, bounds.Width() + 1); buttonFrame.OffsetBy(0.0f, bounds.Width() + 1);
_DrawArrowButton(ARROW_DOWN, doubleArrows, buttonFrame, updateRect, _DrawArrowButton(ARROW_DOWN, doubleArrows, buttonFrame, updateRect,
enabled, fPrivateData->fButtonDown == ARROW2); enabled, fPrivateData->fButtonDown == ARROW2);
@@ -974,7 +995,7 @@ BScrollBar::Draw(BRect updateRect)
thumbColor, 0, BControlLook::B_ALL_BORDERS, fOrientation); thumbColor, 0, BControlLook::B_ALL_BORDERS, fOrientation);
// TODO: Add the other thumb styles - dots and lines // TODO: Add the other thumb styles - dots and lines
} else { } else {
if (fMin >= fMax || fProportion >= 1.0 || fProportion < 0.0) { if (fMin >= fMax || fProportion >= 1.0f || fProportion < 0.0f) {
// we cannot scroll at all // we cannot scroll at all
_DrawDisabledBackground(thumbBG, light, dark, dark1); _DrawDisabledBackground(thumbBG, light, dark, dark1);
} else { } else {
@@ -1038,7 +1059,7 @@ BScrollBar::FrameResized(float newWidth, float newHeight)
BHandler* BHandler*
BScrollBar::ResolveSpecifier(BMessage* message, int32 index, BScrollBar::ResolveSpecifier(BMessage* message, int32 index,
BMessage* specifier, int32 form, const char *property) BMessage* specifier, int32 form, const char* property)
{ {
return BView::ResolveSpecifier(message, index, specifier, form, property); return BView::ResolveSpecifier(message, index, specifier, form, property);
} }
@@ -1057,11 +1078,13 @@ BScrollBar::GetPreferredSize(float* _width, float* _height)
if (fOrientation == B_VERTICAL) { if (fOrientation == B_VERTICAL) {
if (_width) if (_width)
*_width = B_V_SCROLL_BAR_WIDTH; *_width = B_V_SCROLL_BAR_WIDTH;
if (_height) if (_height)
*_height = Bounds().Height(); *_height = Bounds().Height();
} else if (fOrientation == B_HORIZONTAL) { } else if (fOrientation == B_HORIZONTAL) {
if (_width) if (_width)
*_width = Bounds().Width(); *_width = Bounds().Width();
if (_height) if (_height)
*_height = B_H_SCROLL_BAR_HEIGHT; *_height = B_H_SCROLL_BAR_HEIGHT;
} }
@@ -1090,7 +1113,7 @@ BScrollBar::AllDetached()
status_t status_t
BScrollBar::GetSupportedSuites(BMessage *message) BScrollBar::GetSupportedSuites(BMessage* message)
{ {
return BView::GetSupportedSuites(message); return BView::GetSupportedSuites(message);
} }
@@ -1107,7 +1130,7 @@ BSize
BScrollBar::MaxSize() BScrollBar::MaxSize()
{ {
BSize maxSize = _MinSize(); BSize maxSize = _MinSize();
if (fOrientation == B_HORIZONTAL) if (fOrientation == B_HORIZONTAL)
maxSize.width = B_SIZE_UNLIMITED; maxSize.width = B_SIZE_UNLIMITED;
else else
maxSize.height = B_SIZE_UNLIMITED; maxSize.height = B_SIZE_UNLIMITED;
@@ -1119,10 +1142,11 @@ BSize
BScrollBar::PreferredSize() BScrollBar::PreferredSize()
{ {
BSize preferredSize = _MinSize(); BSize preferredSize = _MinSize();
if (fOrientation == B_HORIZONTAL) if (fOrientation == B_HORIZONTAL)
preferredSize.width *= 2; preferredSize.width *= 2;
else else
preferredSize.height *= 2; preferredSize.height *= 2;
return BLayoutUtils::ComposeSize(ExplicitPreferredSize(), preferredSize); return BLayoutUtils::ComposeSize(ExplicitPreferredSize(), preferredSize);
} }
@@ -1134,47 +1158,64 @@ BScrollBar::Perform(perform_code code, void* _data)
case PERFORM_CODE_MIN_SIZE: case PERFORM_CODE_MIN_SIZE:
((perform_data_min_size*)_data)->return_value ((perform_data_min_size*)_data)->return_value
= BScrollBar::MinSize(); = BScrollBar::MinSize();
return B_OK; return B_OK;
case PERFORM_CODE_MAX_SIZE: case PERFORM_CODE_MAX_SIZE:
((perform_data_max_size*)_data)->return_value ((perform_data_max_size*)_data)->return_value
= BScrollBar::MaxSize(); = BScrollBar::MaxSize();
return B_OK; return B_OK;
case PERFORM_CODE_PREFERRED_SIZE: case PERFORM_CODE_PREFERRED_SIZE:
((perform_data_preferred_size*)_data)->return_value ((perform_data_preferred_size*)_data)->return_value
= BScrollBar::PreferredSize(); = BScrollBar::PreferredSize();
return B_OK; return B_OK;
case PERFORM_CODE_LAYOUT_ALIGNMENT: case PERFORM_CODE_LAYOUT_ALIGNMENT:
((perform_data_layout_alignment*)_data)->return_value ((perform_data_layout_alignment*)_data)->return_value
= BScrollBar::LayoutAlignment(); = BScrollBar::LayoutAlignment();
return B_OK; return B_OK;
case PERFORM_CODE_HAS_HEIGHT_FOR_WIDTH: case PERFORM_CODE_HAS_HEIGHT_FOR_WIDTH:
((perform_data_has_height_for_width*)_data)->return_value ((perform_data_has_height_for_width*)_data)->return_value
= BScrollBar::HasHeightForWidth(); = BScrollBar::HasHeightForWidth();
return B_OK; return B_OK;
case PERFORM_CODE_GET_HEIGHT_FOR_WIDTH: case PERFORM_CODE_GET_HEIGHT_FOR_WIDTH:
{ {
perform_data_get_height_for_width* data perform_data_get_height_for_width* data
= (perform_data_get_height_for_width*)_data; = (perform_data_get_height_for_width*)_data;
BScrollBar::GetHeightForWidth(data->width, &data->min, &data->max, BScrollBar::GetHeightForWidth(data->width, &data->min, &data->max,
&data->preferred); &data->preferred);
return B_OK; return B_OK;
} }
case PERFORM_CODE_SET_LAYOUT: case PERFORM_CODE_SET_LAYOUT:
{ {
perform_data_set_layout* data = (perform_data_set_layout*)_data; perform_data_set_layout* data = (perform_data_set_layout*)_data;
BScrollBar::SetLayout(data->layout); BScrollBar::SetLayout(data->layout);
return B_OK; return B_OK;
} }
case PERFORM_CODE_LAYOUT_INVALIDATED: case PERFORM_CODE_LAYOUT_INVALIDATED:
{ {
perform_data_layout_invalidated* data perform_data_layout_invalidated* data
= (perform_data_layout_invalidated*)_data; = (perform_data_layout_invalidated*)_data;
BScrollBar::LayoutInvalidated(data->descendants); BScrollBar::LayoutInvalidated(data->descendants);
return B_OK; return B_OK;
} }
case PERFORM_CODE_DO_LAYOUT: case PERFORM_CODE_DO_LAYOUT:
{ {
BScrollBar::DoLayout(); BScrollBar::DoLayout();
return B_OK; return B_OK;
} }
} }
@@ -1199,7 +1240,6 @@ void BScrollBar::_ReservedScrollBar3() {}
void BScrollBar::_ReservedScrollBar4() {} void BScrollBar::_ReservedScrollBar4() {}
BScrollBar& BScrollBar&
BScrollBar::operator=(const BScrollBar&) BScrollBar::operator=(const BScrollBar&)
{ {
@@ -1261,6 +1301,7 @@ BScrollBar::_UpdateThumbFrame()
float proportion = fProportion; float proportion = fProportion;
if (fMin >= fMax || proportion > 1.0 || proportion < 0.0) if (fMin >= fMax || proportion > 1.0 || proportion < 0.0)
proportion = 1.0; proportion = 1.0;
if (proportion == 0.0) { if (proportion == 0.0) {
// Special case a proportion of 0.0, use the large step value // Special case a proportion of 0.0, use the large step value
// in that case (NOTE: fMin == fMax already handled above) // in that case (NOTE: fMin == fMax already handled above)
@@ -1281,16 +1322,16 @@ BScrollBar::_UpdateThumbFrame()
// the thumb can be scrolled within the remaining area "maxSize - thumbSize - 1.0" // the thumb can be scrolled within the remaining area "maxSize - thumbSize - 1.0"
float offset = 0.0; float offset = 0.0;
if (fMax > fMin) { if (fMax > fMin) {
offset = floorf(((fValue - fMin) / (fMax - fMin)) offset = floorf(((fValue - fMin) / (fMax - fMin))
* (maxSize - thumbSize - 1.0)); * (maxSize - thumbSize - 1.0));
} }
if (_DoubleArrows()) { if (_DoubleArrows()) {
offset += buttonSize * 2; offset += buttonSize * 2;
} else { } else
offset += buttonSize; offset += buttonSize;
}
// visual adjustments (room for darker line between thumb and buttons) // visual adjustments (room for darker line between thumb and buttons)
offset++; offset++;
@@ -1304,15 +1345,16 @@ BScrollBar::_UpdateThumbFrame()
fPrivateData->fThumbFrame.OffsetBy(offset, 0.0); fPrivateData->fThumbFrame.OffsetBy(offset, 0.0);
} }
if (Window()) { if (Window() != NULL) {
BRect invalid = oldFrame.IsValid() ? BRect invalid = oldFrame.IsValid()
oldFrame | fPrivateData->fThumbFrame ? oldFrame | fPrivateData->fThumbFrame
: fPrivateData->fThumbFrame; : fPrivateData->fThumbFrame;
// account for those two dark lines // account for those two dark lines
if (fOrientation == B_HORIZONTAL) if (fOrientation == B_HORIZONTAL)
invalid.InsetBy(-2.0, 0.0); invalid.InsetBy(-2.0, 0.0);
else else
invalid.InsetBy(0.0, -2.0); invalid.InsetBy(0.0, -2.0);
Invalidate(invalid); Invalidate(invalid);
} }
} }
@@ -1322,7 +1364,7 @@ float
BScrollBar::_ValueFor(BPoint where) const BScrollBar::_ValueFor(BPoint where) const
{ {
BRect bounds = Bounds(); BRect bounds = Bounds();
bounds.InsetBy(1.0, 1.0); bounds.InsetBy(1.0f, 1.0f);
float offset; float offset;
float thumbSize; float thumbSize;
@@ -1333,12 +1375,12 @@ BScrollBar::_ValueFor(BPoint where) const
offset = where.y; offset = where.y;
thumbSize = fPrivateData->fThumbFrame.Height(); thumbSize = fPrivateData->fThumbFrame.Height();
maxSize = bounds.Height(); maxSize = bounds.Height();
buttonSize = bounds.Width() + 1.0; buttonSize = bounds.Width() + 1.0f;
} else { } else {
offset = where.x; offset = where.x;
thumbSize = fPrivateData->fThumbFrame.Width(); thumbSize = fPrivateData->fThumbFrame.Width();
maxSize = bounds.Width(); maxSize = bounds.Width();
buttonSize = bounds.Height() + 1.0; buttonSize = bounds.Height() + 1.0f;
} }
if (_DoubleArrows()) { if (_DoubleArrows()) {
@@ -1356,11 +1398,8 @@ BScrollBar::_ValueFor(BPoint where) const
maxSize--; maxSize--;
offset++; offset++;
float value = fMin + (offset / (maxSize - thumbSize) * (fMax - fMin + 1.0)); return roundf(fMin + (offset / (maxSize - thumbSize)
if (value >= 0.0) * (fMax - fMin + 1.0f)));
return floorf(value + 0.5);
else
return ceilf(value - 0.5);
} }
@@ -1368,25 +1407,24 @@ int32
BScrollBar::_ButtonFor(BPoint where) const BScrollBar::_ButtonFor(BPoint where) const
{ {
BRect bounds = Bounds(); BRect bounds = Bounds();
bounds.InsetBy(1.0, 1.0); bounds.InsetBy(1.0f, 1.0f);
float buttonSize; float buttonSize = fOrientation == B_VERTICAL
if (fOrientation == B_VERTICAL) { ? bounds.Width() + 1.0f
buttonSize = bounds.Width() + 1.0; : bounds.Height() + 1.0f;
} else {
buttonSize = bounds.Height() + 1.0;
}
BRect rect(bounds.left, bounds.top, BRect rect(bounds.left, bounds.top,
bounds.left + buttonSize, bounds.top + buttonSize); bounds.left + buttonSize, bounds.top + buttonSize);
if (fOrientation == B_VERTICAL) { if (fOrientation == B_VERTICAL) {
if (rect.Contains(where)) if (rect.Contains(where))
return ARROW1; return ARROW1;
if (_DoubleArrows()) { if (_DoubleArrows()) {
rect.OffsetBy(0.0, buttonSize); rect.OffsetBy(0.0, buttonSize);
if (rect.Contains(where)) if (rect.Contains(where))
return ARROW2; return ARROW2;
rect.OffsetTo(bounds.left, bounds.bottom - 2 * buttonSize); rect.OffsetTo(bounds.left, bounds.bottom - 2 * buttonSize);
if (rect.Contains(where)) if (rect.Contains(where))
return ARROW3; return ARROW3;
@@ -1397,10 +1435,12 @@ BScrollBar::_ButtonFor(BPoint where) const
} else { } else {
if (rect.Contains(where)) if (rect.Contains(where))
return ARROW1; return ARROW1;
if (_DoubleArrows()) { if (_DoubleArrows()) {
rect.OffsetBy(buttonSize, 0.0); rect.OffsetBy(buttonSize, 0.0);
if (rect.Contains(where)) if (rect.Contains(where))
return ARROW2; return ARROW2;
rect.OffsetTo(bounds.right - 2 * buttonSize, bounds.top); rect.OffsetTo(bounds.right - 2 * buttonSize, bounds.top);
if (rect.Contains(where)) if (rect.Contains(where))
return ARROW3; return ARROW3;
@@ -1418,28 +1458,28 @@ BRect
BScrollBar::_ButtonRectFor(int32 button) const BScrollBar::_ButtonRectFor(int32 button) const
{ {
BRect bounds = Bounds(); BRect bounds = Bounds();
bounds.InsetBy(1.0, 1.0); bounds.InsetBy(1.0f, 1.0f);
float buttonSize; float buttonSize = fOrientation == B_VERTICAL
if (fOrientation == B_VERTICAL) { ? bounds.Width() + 1.0f
buttonSize = bounds.Width() + 1.0; : bounds.Height() + 1.0f;
} else {
buttonSize = bounds.Height() + 1.0;
}
BRect rect(bounds.left, bounds.top, BRect rect(bounds.left, bounds.top,
bounds.left + buttonSize - 1.0, bounds.top + buttonSize - 1.0); bounds.left + buttonSize - 1.0f, bounds.top + buttonSize - 1.0f);
if (fOrientation == B_VERTICAL) { if (fOrientation == B_VERTICAL) {
switch (button) { switch (button) {
case ARROW1: case ARROW1:
break; break;
case ARROW2: case ARROW2:
rect.OffsetBy(0.0, buttonSize); rect.OffsetBy(0.0, buttonSize);
break; break;
case ARROW3: case ARROW3:
rect.OffsetTo(bounds.left, bounds.bottom - 2 * buttonSize + 1); rect.OffsetTo(bounds.left, bounds.bottom - 2 * buttonSize + 1);
break; break;
case ARROW4: case ARROW4:
rect.OffsetTo(bounds.left, bounds.bottom - buttonSize + 1); rect.OffsetTo(bounds.left, bounds.bottom - buttonSize + 1);
break; break;
@@ -1448,12 +1488,15 @@ BScrollBar::_ButtonRectFor(int32 button) const
switch (button) { switch (button) {
case ARROW1: case ARROW1:
break; break;
case ARROW2: case ARROW2:
rect.OffsetBy(buttonSize, 0.0); rect.OffsetBy(buttonSize, 0.0);
break; break;
case ARROW3: case ARROW3:
rect.OffsetTo(bounds.right - 2 * buttonSize + 1, bounds.top); rect.OffsetTo(bounds.right - 2 * buttonSize + 1, bounds.top);
break; break;
case ARROW4: case ARROW4:
rect.OffsetTo(bounds.right - buttonSize + 1, bounds.top); rect.OffsetTo(bounds.right - buttonSize + 1, bounds.top);
break; break;
@@ -1499,13 +1542,13 @@ BScrollBar::_UpdateArrowButtons()
status_t status_t
control_scrollbar(scroll_bar_info *info, BScrollBar *bar) control_scrollbar(scroll_bar_info* info, BScrollBar* bar)
{ {
if (!bar || !info) if (bar == NULL || info == NULL)
return B_BAD_VALUE; return B_BAD_VALUE;
if (bar->fPrivateData->fScrollBarInfo.double_arrows if (bar->fPrivateData->fScrollBarInfo.double_arrows
!= info->double_arrows) { != info->double_arrows) {
bar->fPrivateData->fScrollBarInfo.double_arrows = info->double_arrows; bar->fPrivateData->fScrollBarInfo.double_arrows = info->double_arrows;
int8 multiplier = (info->double_arrows) ? 1 : -1; int8 multiplier = (info->double_arrows) ? 1 : -1;
@@ -1531,9 +1574,9 @@ control_scrollbar(scroll_bar_info *info, BScrollBar *bar)
return B_BAD_VALUE; return B_BAD_VALUE;
if (info->min_knob_size >= SCROLL_BAR_MINIMUM_KNOB_SIZE if (info->min_knob_size >= SCROLL_BAR_MINIMUM_KNOB_SIZE
&& info->min_knob_size <= SCROLL_BAR_MAXIMUM_KNOB_SIZE) && info->min_knob_size <= SCROLL_BAR_MAXIMUM_KNOB_SIZE) {
bar->fPrivateData->fScrollBarInfo.min_knob_size = info->min_knob_size; bar->fPrivateData->fScrollBarInfo.min_knob_size = info->min_knob_size;
else } else
return B_BAD_VALUE; return B_BAD_VALUE;
return B_OK; return B_OK;
@@ -1541,10 +1584,8 @@ control_scrollbar(scroll_bar_info *info, BScrollBar *bar)
void void
BScrollBar::_DrawDisabledBackground(BRect area, BScrollBar::_DrawDisabledBackground(BRect area, const rgb_color& light,
const rgb_color& light, const rgb_color& dark, const rgb_color& fill)
const rgb_color& dark,
const rgb_color& fill)
{ {
if (!area.IsValid()) if (!area.IsValid())
return; return;
@@ -1609,7 +1650,7 @@ BScrollBar::_DrawDisabledBackground(BRect area,
void void
BScrollBar::_DrawArrowButton(int32 direction, bool doubleArrows, BRect rect, BScrollBar::_DrawArrowButton(int32 direction, bool doubleArrows, BRect rect,
const BRect& updateRect, bool enabled, bool down) const BRect& updateRect, bool enabled, bool down)
{ {
if (!updateRect.Intersects(rect)) if (!updateRect.Intersects(rect))
return; return;
@@ -1617,6 +1658,7 @@ BScrollBar::_DrawArrowButton(int32 direction, bool doubleArrows, BRect rect,
uint32 flags = 0; uint32 flags = 0;
if (!enabled) if (!enabled)
flags |= BControlLook::B_DISABLED; flags |= BControlLook::B_DISABLED;
if (down && fPrivateData->fDoRepeat) if (down && fPrivateData->fDoRepeat)
flags |= BControlLook::B_ACTIVATED; flags |= BControlLook::B_ACTIVATED;
@@ -1630,7 +1672,7 @@ BScrollBar::_DrawArrowButton(int32 direction, bool doubleArrows, BRect rect,
// TODO: Why does BControlLook need this negative inset for the arrow to // TODO: Why does BControlLook need this negative inset for the arrow to
// look right? // look right?
rect.InsetBy(-1, -1); rect.InsetBy(-1.0f, -1.0f);
be_control_look->DrawArrowShape(this, rect, updateRect, be_control_look->DrawArrowShape(this, rect, updateRect,
baseColor, direction, flags, B_DARKEN_MAX_TINT); baseColor, direction, flags, B_DARKEN_MAX_TINT);
} }
@@ -1649,6 +1691,6 @@ BScrollBar::_MinSize() const
minSize.height = 2 * B_H_SCROLL_BAR_HEIGHT minSize.height = 2 * B_H_SCROLL_BAR_HEIGHT
+ 2 * fPrivateData->fScrollBarInfo.min_knob_size; + 2 * fPrivateData->fScrollBarInfo.min_knob_size;
} }
return minSize; return minSize;
} }