From 642090fdc62bbf5df46a1135a006636c3ca63691 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Axel=20D=C3=B6rfler?= Date: Fri, 9 Jun 2006 16:03:16 +0000 Subject: [PATCH] * ScreenCornerSelector is now a BControl and fully keyboard navigable. * simplified drawing a bit, and got rid of those scary scale*() stuff (which also results in better looks). The monitor now looks like the one in Screen; I think it should either be a very reduced form or a very detailed form, but anything in between often looks just odd. * It now also listens to B_MOUSE_DOWN incl. mouse tracking, not only to B_MOUSE_UP. * Less flickering on state changes (and focus change). * Loading settings no longer overwrites defaults missing from the settings. * Renamed ScreenSaverSettings::GetBlankCorner() to BlankCorner(), LoadSettings() to Load(), GetState() to GetModuleState(), .... * Some more cleanup. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@17783 a95241bf-73f2-0310-859d-f6bbb57e9c96 --- .../screen_saver/ScreenSaverSettings.h | 27 +- .../filters/screensaver/ScreenSaverFilter.cpp | 18 +- src/bin/screen_blanker/ScreenBlanker.cpp | 4 +- src/kits/screensaver/ScreenSaverRunner.cpp | 2 +- src/kits/screensaver/ScreenSaverSettings.cpp | 72 ++-- .../screensaver/ScreenCornerSelector.cpp | 376 +++++++++++++----- .../screensaver/ScreenCornerSelector.h | 28 +- .../screensaver/ScreenSaverWindow.cpp | 32 +- 8 files changed, 383 insertions(+), 176 deletions(-) diff --git a/headers/private/screen_saver/ScreenSaverSettings.h b/headers/private/screen_saver/ScreenSaverSettings.h index 943b7c3e29..a4e76ef644 100644 --- a/headers/private/screen_saver/ScreenSaverSettings.h +++ b/headers/private/screen_saver/ScreenSaverSettings.h @@ -12,12 +12,12 @@ enum screen_corner { - NONE = -1, - UPLEFT, - UPRIGHT, - DOWNRIGHT, - DOWNLEFT, - CENTER + NO_CORNER = -1, + UP_LEFT_CORNER, + UP_RIGHT_CORNER, + DOWN_RIGHT_CORNER, + DOWN_LEFT_CORNER, + CENTER_CORNER }; // time flags @@ -37,7 +37,8 @@ class ScreenSaverSettings { public: ScreenSaverSettings(); - bool LoadSettings(); + bool Load(); + void Save(); void Defaults(); BPath& Path() { return fSettingsPath; } @@ -49,15 +50,15 @@ class ScreenSaverSettings { bigtime_t SuspendTime() { return fSuspendTime; } bigtime_t OffTime() { return fOffTime; } - screen_corner GetBlankCorner() { return fBlankCorner; } - screen_corner GetNeverBlankCorner() { return fNeverBlankCorner; } + screen_corner BlankCorner() { return fBlankCorner; } + screen_corner NeverBlankCorner() { return fNeverBlankCorner; } bool LockEnable() { return fLockEnabled; } bigtime_t PasswordTime() { return fPasswordTime; } const char *Password() { return fPassword.String(); } const char *LockMethod() { return fLockMethod.String(); } bool IsNetworkPassword() { return strcmp(fLockMethod.String(), "custom") != 0; } const char *ModuleName() { return fModuleName.String(); } - status_t GetState(const char *name, BMessage *stateMsg); + status_t GetModuleState(const char *name, BMessage *stateMsg); void SetWindowFrame(const BRect &fr) { fWindowFrame = fr; } void SetWindowTab(int32 tab) { fWindowTab = tab; } @@ -74,9 +75,9 @@ class ScreenSaverSettings { // Cannot set network password from here. void SetLockMethod(const char *method) { fLockMethod = method; } void SetModuleName(const char *mn) { fModuleName = mn; } - void SetState(const char *name, BMessage *stateMsg); - void SaveSettings(); - BMessage& GetSettings(); + void SetModuleState(const char *name, BMessage *stateMsg); + + BMessage& Message(); private: BRect fWindowFrame; diff --git a/src/add-ons/input_server/filters/screensaver/ScreenSaverFilter.cpp b/src/add-ons/input_server/filters/screensaver/ScreenSaverFilter.cpp index 9c1eae8647..b0ef638eb3 100644 --- a/src/add-ons/input_server/filters/screensaver/ScreenSaverFilter.cpp +++ b/src/add-ons/input_server/filters/screensaver/ScreenSaverFilter.cpp @@ -101,7 +101,7 @@ ScreenSaverFilter::ScreenSaverFilter() fLastEventTime(0), fBlankTime(0), fSnoozeTime(0), - fCurrentCorner(NONE), + fCurrentCorner(NO_CORNER), fEnabled(false), fFrameNum(0), fRunner(NULL), @@ -192,10 +192,10 @@ ScreenSaverFilter::ReloadSettings() return; } - fSettings.LoadSettings(); + fSettings.Load(); - fBlankCorner = fSettings.GetBlankCorner(); - fNeverBlankCorner = fSettings.GetNeverBlankCorner(); + fBlankCorner = fSettings.BlankCorner(); + fNeverBlankCorner = fSettings.NeverBlankCorner(); fBlankTime = fSnoozeTime = fSettings.BlankTime(); CheckTime(); @@ -274,19 +274,19 @@ ScreenSaverFilter::_ScreenCorner(screen_corner corner, uint32 cornerSize) BRect frame = BScreen().Frame(); switch (corner) { - case UPLEFT: + case UP_LEFT_CORNER: return BRect(frame.left, frame.top, frame.left + cornerSize - 1, frame.top + cornerSize - 1); - case UPRIGHT: + case UP_RIGHT_CORNER: return BRect(frame.right - cornerSize + 1, frame.top, frame.right, frame.top + cornerSize - 1); - case DOWNRIGHT: + case DOWN_RIGHT_CORNER: return BRect(frame.right - cornerSize + 1, frame.bottom - cornerSize + 1, frame.right, frame.bottom); - case DOWNLEFT: + case DOWN_LEFT_CORNER: return BRect(frame.left, frame.bottom - cornerSize + 1, frame.left + cornerSize - 1, frame.bottom); @@ -330,7 +330,7 @@ ScreenSaverFilter::Filter(BMessage *message, BList *outList) if (fNeverBlankRect.Contains(where)) fCurrentCorner = fNeverBlankCorner; else - fCurrentCorner = NONE; + fCurrentCorner = NO_CORNER; break; } diff --git a/src/bin/screen_blanker/ScreenBlanker.cpp b/src/bin/screen_blanker/ScreenBlanker.cpp index 198f828de9..9ac976a16e 100644 --- a/src/bin/screen_blanker/ScreenBlanker.cpp +++ b/src/bin/screen_blanker/ScreenBlanker.cpp @@ -57,11 +57,11 @@ ScreenBlanker::~ScreenBlanker() void ScreenBlanker::ReadyToRun() { - if (!fSettings.LoadSettings()) { + if (!fSettings.Load()) { fprintf(stderr, "could not load settings\n"); exit(1); } - + // create a BDirectWindow and start the render thread. // TODO: we need a window per screen... BScreen screen(B_MAIN_SCREEN_ID); diff --git a/src/kits/screensaver/ScreenSaverRunner.cpp b/src/kits/screensaver/ScreenSaverRunner.cpp index 221f462389..bb6cac3be3 100644 --- a/src/kits/screensaver/ScreenSaverRunner.cpp +++ b/src/kits/screensaver/ScreenSaverRunner.cpp @@ -143,7 +143,7 @@ ScreenSaverRunner::_LoadAddOn() printf("Unable to find the instantiator\n"); } else { BMessage state; - fSettings.GetState(fSettings.ModuleName(), &state); + fSettings.GetModuleState(fSettings.ModuleName(), &state); fSaver = instantiate(&state, fAddonImage); } diff --git a/src/kits/screensaver/ScreenSaverSettings.cpp b/src/kits/screensaver/ScreenSaverSettings.cpp index 9ffadeade9..976e8ef7a5 100644 --- a/src/kits/screensaver/ScreenSaverSettings.cpp +++ b/src/kits/screensaver/ScreenSaverSettings.cpp @@ -36,7 +36,7 @@ ScreenSaverSettings::ScreenSaverSettings() //! Load the flattened settings BMessage from disk and parse it. bool -ScreenSaverSettings::LoadSettings() +ScreenSaverSettings::Load() { BFile file(fSettingsPath.Path(), B_READ_ONLY); if (file.InitCheck() != B_OK) @@ -48,31 +48,47 @@ ScreenSaverSettings::LoadSettings() PRINT_OBJECT(fSettings); - fSettings.FindRect("windowframe", &fWindowFrame); - fSettings.FindInt32("windowtab", &fWindowTab); - fSettings.FindInt32("timeflags", &fTimeFlags); + BRect rect; + if (fSettings.FindRect("windowframe", &rect) == B_OK) + fWindowFrame = rect; + int32 value; + if (fSettings.FindInt32("windowtab", &value) == B_OK) + fWindowTab = value; + if (fSettings.FindInt32("timeflags", &value) == B_OK) + fTimeFlags = value; - int32 blank_time, standByTime, suspendTime, offTime, passwordTime; - if (fSettings.FindInt32("timefade", &blank_time) == B_OK) - fBlankTime = blank_time * 1000000LL; - if (fSettings.FindInt32("timestandby", &standByTime) == B_OK) - fStandByTime = standByTime * 1000000LL; - if (fSettings.FindInt32("timesuspend", &suspendTime) == B_OK) - fSuspendTime = suspendTime * 1000000LL; - if (fSettings.FindInt32("timeoff", &offTime) == B_OK) - fOffTime = offTime * 1000000LL; - fSettings.FindInt32("cornernow", (int32*)&fBlankCorner); - fSettings.FindInt32("cornernever", (int32*)&fNeverBlankCorner); - fSettings.FindBool("lockenable", &fLockEnabled); - if (fSettings.FindInt32("lockdelay", &passwordTime) == B_OK) - fPasswordTime = passwordTime * 1000000LL; - fSettings.FindString("lockpassword", &fPassword); - fSettings.FindString("lockmethod", &fLockMethod); - fSettings.FindString("modulename", &fModuleName); + if (fSettings.FindInt32("timefade", &value) == B_OK) + fBlankTime = value * 1000000LL; + if (fSettings.FindInt32("timestandby", &value) == B_OK) + fStandByTime = value * 1000000LL; + if (fSettings.FindInt32("timesuspend", &value) == B_OK) + fSuspendTime = value * 1000000LL; + if (fSettings.FindInt32("timeoff", &value) == B_OK) + fOffTime = value * 1000000LL; + + if (fSettings.FindInt32("cornernow", &value) == B_OK) + fBlankCorner = (screen_corner)value; + if (fSettings.FindInt32("cornernever", &value) == B_OK) + fNeverBlankCorner = (screen_corner)value; + + bool lockEnabled; + if (fSettings.FindBool("lockenable", &lockEnabled) == B_OK) + fLockEnabled = lockEnabled; + if (fSettings.FindInt32("lockdelay", &value) == B_OK) + fPasswordTime = value * 1000000LL; + const char* string; + if (fSettings.FindString("lockpassword", &string) == B_OK) + fPassword = string; + if (fSettings.FindString("lockmethod", &string) == B_OK) + fLockMethod = string; + + if (fSettings.FindString("modulename", &string) == B_OK) + fModuleName = string; if (IsNetworkPassword()) { FILE *networkFile = NULL; char buffer[512], *start; + // TODO: this only works under R5 net_server! // This ugly piece opens the networking file and reads the password, if it exists. if ((networkFile = fopen(fNetworkPath.Path(),"r"))) while (fgets(buffer, 512, networkFile) != NULL) { @@ -100,8 +116,8 @@ ScreenSaverSettings::Defaults() fStandByTime = 120*1000000LL; fSuspendTime = 120*1000000LL; fOffTime = 120*1000000LL; - fBlankCorner = NONE; - fNeverBlankCorner = NONE; + fBlankCorner = NO_CORNER; + fNeverBlankCorner = NO_CORNER; fLockEnabled = false; fPasswordTime = 120*1000000LL; fPassword = ""; @@ -111,7 +127,7 @@ ScreenSaverSettings::Defaults() BMessage & -ScreenSaverSettings::GetSettings() +ScreenSaverSettings::Message() { // We can't just empty the message, because the module states are stored // in this message as well. @@ -153,7 +169,7 @@ ScreenSaverSettings::GetSettings() status_t -ScreenSaverSettings::GetState(const char *name, BMessage *stateMsg) +ScreenSaverSettings::GetModuleState(const char *name, BMessage *stateMsg) { BString stateName("modulesettings_"); stateName += name; @@ -162,7 +178,7 @@ ScreenSaverSettings::GetState(const char *name, BMessage *stateMsg) void -ScreenSaverSettings::SetState(const char *name, BMessage *stateMsg) +ScreenSaverSettings::SetModuleState(const char *name, BMessage *stateMsg) { BString stateName("modulesettings_"); stateName += name; @@ -172,9 +188,9 @@ ScreenSaverSettings::SetState(const char *name, BMessage *stateMsg) void -ScreenSaverSettings::SaveSettings() +ScreenSaverSettings::Save() { - BMessage &settings = GetSettings(); + BMessage &settings = Message(); PRINT_OBJECT(settings); BFile file(fSettingsPath.Path(), B_READ_WRITE | B_CREATE_FILE | B_ERASE_FILE); if (file.InitCheck() != B_OK || settings.Flatten(&file) != B_OK) diff --git a/src/preferences/screensaver/ScreenCornerSelector.cpp b/src/preferences/screensaver/ScreenCornerSelector.cpp index 2ff496c2d5..5b4e991b89 100644 --- a/src/preferences/screensaver/ScreenCornerSelector.cpp +++ b/src/preferences/screensaver/ScreenCornerSelector.cpp @@ -4,6 +4,7 @@ * * Authors: * Michael Phipps + * Axel Dörfler, axeld@pinc-software.de */ #include "ScreenCornerSelector.h" @@ -13,141 +14,314 @@ #include #include #include +#include +#include #include +static const float kAspectRatio = 4.0f / 3.0f; +static const float kMonitorBorderSize = 3.0f; +static const float kArrowSize = 11.0f; +static const float kStopSize = 15.0f; -inline BPoint -scale_arrow(int x, int y, BRect area, bool invertX, bool invertY) + +ScreenCornerSelector::ScreenCornerSelector(BRect frame, const char *name, + BMessage* message, uint32 resizingMode) + : BControl(frame, name, NULL, message, resizingMode, B_WILL_DRAW | B_NAVIGABLE), + fCurrentCorner(NO_CORNER), + fPreviousCorner(-1) { - float arrowX[] = {0, .25, .5, .66667, .90, .9}; - float arrowY[] = {0, .15, .25, .3333333, .6666667, 1.0}; - - return scale_direct(invertX ? 1 - arrowX[x] : arrowX[x], - invertY ? 1 - arrowY[y] : arrowY[y], area); + SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); } -// #pragma mark - - - -ScreenCornerSelector::ScreenCornerSelector(BRect frame, const char *name, uint32 resizingMode) - : BView(frame, name, resizingMode, B_WILL_DRAW), - fCurrentCorner(NONE) +BRect +ScreenCornerSelector::_MonitorFrame() const { - SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR)); + float width = Bounds().Width(); + float height = Bounds().Height(); + + if (width / kAspectRatio > height) + width = height * kAspectRatio; + else if (height * kAspectRatio > width) + height = width / kAspectRatio; + + return BRect((Bounds().Width() - width) / 2, (Bounds().Height() - height) / 2, + (Bounds().Width() + width) / 2, (Bounds().Height() + height) / 2); +} + + +BRect +ScreenCornerSelector::_InnerFrame(BRect monitorFrame) const +{ + return monitorFrame.InsetByCopy(kMonitorBorderSize + 3, + kMonitorBorderSize + 3); +} + + +BRect +ScreenCornerSelector::_CenterFrame(BRect innerFrame) const +{ + return innerFrame.InsetByCopy(kArrowSize, kArrowSize); } void ScreenCornerSelector::Draw(BRect update) { - // Top of monitor - SetHighColor(kGrey); - FillRoundRect(scale(0, 7, 0, 3, Bounds()), 4, 4); - SetHighColor(kBlack); - StrokeRoundRect(scale(0, 7, 0, 3, Bounds()), 4, 4); - SetHighColor(kLightBlue); - fMonitorFrame = scale(1, 6, 1, 2, Bounds()); - FillRect(fMonitorFrame); - SetHighColor(kDarkGrey); - StrokeRect(fMonitorFrame); + rgb_color darkColor = {160, 160, 160, 255}; + rgb_color blackColor = {0, 0, 0, 255}; + rgb_color redColor = {228, 0, 0, 255}; - // Base of monitor - SetHighColor(kGrey); - FillTriangle(scale(1,5,Bounds()),scale(3,4,Bounds()),scale(3,5,Bounds())); - FillTriangle(scale(4,5,Bounds()),scale(4,4,Bounds()),scale(6,5,Bounds())); - FillRect(scale(3,4,4,5,Bounds())); - FillRect(scale(3,4,3,4,Bounds())); - SetHighColor(kBlack); - StrokeRect(scale(3,4,3,4,Bounds())); - StrokeLine(scale(2,4,Bounds()),scale(1,5,Bounds())); - StrokeLine(scale(6,5,Bounds()),scale(1,5,Bounds())); - StrokeLine(scale(6,5,Bounds()),scale(5,4,Bounds())); - DrawArrow(); + BRect outerRect = _MonitorFrame(); + BRect innerRect(outerRect.InsetByCopy(kMonitorBorderSize + 2, + kMonitorBorderSize + 2)); + + SetDrawingMode(B_OP_OVER); + + if (!_InnerFrame(outerRect).Contains(update)) { + // frame & background + + // if the focus is changing, we don't redraw the whole view, but only + // the part that's affected by the change + if (!IsFocusChanging()) { + SetHighColor(darkColor); + FillRoundRect(outerRect, kMonitorBorderSize * 3 / 2, kMonitorBorderSize * 3 / 2); + } + + if (IsFocus() && Window()->IsActive()) + SetHighColor(ui_color(B_KEYBOARD_NAVIGATION_COLOR)); + else + SetHighColor(blackColor); + StrokeRoundRect(outerRect, kMonitorBorderSize * 3 / 2, kMonitorBorderSize * 3 / 2); + + if (!IsFocusChanging()) { + SetHighColor(210, 210, 255); + FillRoundRect(innerRect, kMonitorBorderSize, kMonitorBorderSize); + } + + if (IsFocus() && Window()->IsActive()) + SetHighColor(ui_color(B_KEYBOARD_NAVIGATION_COLOR)); + else + SetHighColor(blackColor); + StrokeRoundRect(innerRect, kMonitorBorderSize, kMonitorBorderSize); + + if (IsFocusChanging()) + return; + + // power light + + SetHighColor(redColor); + BPoint powerPos(outerRect.left + kMonitorBorderSize * 2, outerRect.bottom + - kMonitorBorderSize); + StrokeLine(powerPos, BPoint(powerPos.x + 2, powerPos.y)); + } + + innerRect = _InnerFrame(outerRect); + + if (fCurrentCorner != NO_CORNER) + _DrawArrow(innerRect); + else + _DrawStop(innerRect); + + SetDrawingMode(B_OP_COPY); +} + + +int32 +ScreenCornerSelector::Value() +{ + return (int32)fCurrentCorner; +} + + +void +ScreenCornerSelector::SetValue(int32 corner) +{ + switch (corner) { + case UP_LEFT_CORNER: + case UP_RIGHT_CORNER: + case DOWN_LEFT_CORNER: + case DOWN_RIGHT_CORNER: + case NO_CORNER: + break; + + default: + corner = NO_CORNER; + } + if ((screen_corner)corner == fCurrentCorner) + return; + + fCurrentCorner = (screen_corner)corner; + Invalidate(_InnerFrame(_MonitorFrame())); + Invoke(); +} + + +screen_corner +ScreenCornerSelector::Corner() const +{ + return fCurrentCorner; } void ScreenCornerSelector::SetCorner(screen_corner corner) { - fCurrentCorner = corner; - Invalidate(); -} - - -BRect -ScreenCornerSelector::_ArrowSize(BRect monitorRect, bool isCentered) -{ - int arrowSize = monitorRect.IntegerWidth(); - if (monitorRect.IntegerHeight() < arrowSize) - arrowSize = monitorRect.IntegerHeight(); - - arrowSize /= 3; - - BRect arrowRect(0, 0, arrowSize, arrowSize); - if (isCentered) { - arrowRect.OffsetBy(monitorRect.left + (monitorRect.Width() - arrowSize) / 2, - monitorRect.top + (monitorRect.Height() - arrowSize) / 2); - } - - return arrowRect; + // redirected to SetValue() to make sure only valid values are set + SetValue((int32)corner); } void -ScreenCornerSelector::DrawArrow() +ScreenCornerSelector::_DrawStop(BRect innerFrame) { - PushState(); - - BRect rect(_ArrowSize(fMonitorFrame, fCurrentCorner == NONE)); - - if (fCurrentCorner != NONE) { - bool invertX = fCurrentCorner == UPRIGHT || fCurrentCorner == DOWNRIGHT; - bool invertY = fCurrentCorner == UPRIGHT || fCurrentCorner == UPLEFT; - - float size = rect.Width(); - MovePenTo(invertX ? fMonitorFrame.right - size - 2 : 2 + fMonitorFrame.left, - !invertY ? fMonitorFrame.bottom - size - 2 : 2 + fMonitorFrame.top); - - BShape arrow; - arrow.MoveTo(scale_arrow(0, 1, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(0, 5, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(4, 5, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(3, 4, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(5, 3, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(2, 0, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(1, 2, rect, invertX, invertY)); - arrow.LineTo(scale_arrow(0, 1, rect, invertX, invertY)); - arrow.Close(); - SetHighColor(kBlack); - FillShape(&arrow, B_SOLID_HIGH); - } else { - SetHighColor(255, 0, 0); - SetPenSize(2); - StrokeEllipse(rect); - StrokeLine(BPoint(rect.right, rect.top), BPoint(rect.left, rect.bottom)); + BRect centerRect = _CenterFrame(innerFrame); + float size = kStopSize; + BRect rect; + rect.left = centerRect.left + (centerRect.Width() - size) / 2; + rect.top = centerRect.top + (centerRect.Height() - size) / 2; + if (rect.left < centerRect.left || rect.top < centerRect.top) { + size = centerRect.Height(); + rect.top = centerRect.top; + rect.left = centerRect.left + (centerRect.Width() - size) / 2; } + rect.right = rect.left + size - 1; + rect.bottom = rect.top + size - 1; - PopState(); + SetHighColor(255, 0, 0); + SetPenSize(2); + StrokeEllipse(rect); + + size -= ceilf(sin(PI / 4) * size) + 1; + rect.InsetBy(size, size); + StrokeLine(BPoint(rect.right, rect.top), BPoint(rect.left, rect.bottom)); + + SetPenSize(1); } void -ScreenCornerSelector::MouseUp(BPoint point) +ScreenCornerSelector::_DrawArrow(BRect innerFrame) { - if (fMonitorFrame.Contains(point)) { - if (_ArrowSize(fMonitorFrame, true).Contains(point)) - fCurrentCorner = NONE; - else { - float centerX = fMonitorFrame.left + fMonitorFrame.Width() / 2; - float centerY = fMonitorFrame.top + fMonitorFrame.Height() / 2; - if (point.x < centerX) - fCurrentCorner = point.y < centerY ? UPLEFT : DOWNLEFT; - else - fCurrentCorner = point.y < centerY ? UPRIGHT : DOWNRIGHT; - } - Draw(fMonitorFrame); + float size = kArrowSize; + float sizeX = fCurrentCorner == UP_LEFT_CORNER || fCurrentCorner == DOWN_LEFT_CORNER ? size : -size; + float sizeY = fCurrentCorner == UP_LEFT_CORNER || fCurrentCorner == UP_RIGHT_CORNER ? size : -size; + + innerFrame.InsetBy(2, 2); + BPoint origin(sizeX < 0 ? innerFrame.right : innerFrame.left, + sizeY < 0 ? innerFrame.bottom : innerFrame.top); + + SetHighColor(kBlack); + FillTriangle(BPoint(origin.x, origin.y), BPoint(origin.x, origin.y + sizeY), + BPoint(origin.x + sizeX, origin.y)); +} + + +screen_corner +ScreenCornerSelector::_ScreenCorner(BPoint point, screen_corner previousCorner) const +{ + BRect innerFrame = _InnerFrame(_MonitorFrame()); + + if (!innerFrame.Contains(point)) + return previousCorner; + + if (_CenterFrame(innerFrame).Contains(point)) + return NO_CORNER; + + float centerX = innerFrame.left + innerFrame.Width() / 2; + float centerY = innerFrame.top + innerFrame.Height() / 2; + if (point.x < centerX) + return point.y < centerY ? UP_LEFT_CORNER : DOWN_LEFT_CORNER; + + return point.y < centerY ? UP_RIGHT_CORNER : DOWN_RIGHT_CORNER; +} + + +void +ScreenCornerSelector::MouseDown(BPoint where) +{ + fPreviousCorner = Value(); + + SetValue(_ScreenCorner(where, (screen_corner)fPreviousCorner)); + SetMouseEventMask(B_POINTER_EVENTS, B_NO_POINTER_HISTORY); +} + + +void +ScreenCornerSelector::MouseUp(BPoint where) +{ + fPreviousCorner = -1; +} + + +void +ScreenCornerSelector::MouseMoved(BPoint where, uint32 transit, const BMessage* dragMessage) +{ + if (fPreviousCorner == -1) + return; + + SetValue(_ScreenCorner(where, (screen_corner)fPreviousCorner)); +} + + +void +ScreenCornerSelector::KeyDown(const char* bytes, int32 numBytes) +{ + switch (bytes[0]) { + // arrow keys + + case B_LEFT_ARROW: + case '4': + if (Corner() == UP_RIGHT_CORNER) + SetCorner(UP_LEFT_CORNER); + else if (Corner() == DOWN_RIGHT_CORNER) + SetCorner(DOWN_LEFT_CORNER); + break; + case B_RIGHT_ARROW: + case '6': + if (Corner() == UP_LEFT_CORNER) + SetCorner(UP_RIGHT_CORNER); + else if (Corner() == DOWN_LEFT_CORNER) + SetCorner(DOWN_RIGHT_CORNER); + break; + case B_UP_ARROW: + case '8': + if (Corner() == DOWN_LEFT_CORNER) + SetCorner(UP_LEFT_CORNER); + else if (Corner() == DOWN_RIGHT_CORNER) + SetCorner(UP_RIGHT_CORNER); + break; + case B_DOWN_ARROW: + case '2': + if (Corner() == UP_LEFT_CORNER) + SetCorner(DOWN_LEFT_CORNER); + else if (Corner() == UP_RIGHT_CORNER) + SetCorner(DOWN_RIGHT_CORNER); + break; + + // numlock keys + + case B_HOME: + case '7': + SetCorner(UP_LEFT_CORNER); + break; + case B_PAGE_UP: + case '9': + SetCorner(UP_RIGHT_CORNER); + break; + case B_PAGE_DOWN: + case '3': + SetCorner(DOWN_RIGHT_CORNER); + break; + case B_END: + case '1': + SetCorner(DOWN_LEFT_CORNER); + break; + + default: + BControl::KeyDown(bytes, numBytes); } } + diff --git a/src/preferences/screensaver/ScreenCornerSelector.h b/src/preferences/screensaver/ScreenCornerSelector.h index 5031559a58..632cf30157 100644 --- a/src/preferences/screensaver/ScreenCornerSelector.h +++ b/src/preferences/screensaver/ScreenCornerSelector.h @@ -4,6 +4,7 @@ * * Authors: * Michael Phipps + * Axel Dörfler, axeld@pinc-software.de */ #ifndef SCREEN_CORNER_SELECTOR_H #define SCREEN_CORNER_SELECTOR_H @@ -11,25 +12,36 @@ #include "ScreenSaverSettings.h" -#include +#include -class ScreenCornerSelector : public BView { +class ScreenCornerSelector : public BControl { public: - ScreenCornerSelector(BRect frame, const char *name, uint32 resizingMode); + ScreenCornerSelector(BRect frame, const char *name, BMessage* message, + uint32 resizingMode); virtual void Draw(BRect update); + virtual void MouseDown(BPoint point); virtual void MouseUp(BPoint point); + virtual void MouseMoved(BPoint where, uint32 transit, const BMessage* dragMessage); + virtual void KeyDown(const char* bytes, int32 numBytes); - void DrawArrow(); - inline screen_corner Corner() { return fCurrentCorner; } - void SetCorner(screen_corner direction); + virtual void SetValue(int32 value); + virtual int32 Value(); + + void SetCorner(screen_corner corner); + screen_corner Corner() const; private: - BRect _ArrowSize(BRect monitorRect, bool isCentered); + BRect _MonitorFrame() const; + BRect _InnerFrame(BRect monitorFrame) const; + BRect _CenterFrame(BRect innerFrame) const; + void _DrawStop(BRect innerFrame); + void _DrawArrow(BRect innerFrame); + screen_corner _ScreenCorner(BPoint point, screen_corner previous) const; - BRect fMonitorFrame; screen_corner fCurrentCorner; + int32 fPreviousCorner; }; #endif // SCREEN_CORNER_SELECTOR_H diff --git a/src/preferences/screensaver/ScreenSaverWindow.cpp b/src/preferences/screensaver/ScreenSaverWindow.cpp index 1e9500a7fa..ab24212e92 100644 --- a/src/preferences/screensaver/ScreenSaverWindow.cpp +++ b/src/preferences/screensaver/ScreenSaverWindow.cpp @@ -34,9 +34,6 @@ #include -#include -#define CALLED() PRINT(("%s\n", __PRETTY_FUNCTION__)) - const uint32 kPreviewMonitorGap = 16; const uint32 kMinSettingsWidth = 230; @@ -54,8 +51,12 @@ const int32 kMsgEnableScreenSaverBox = 'ESCH'; const int32 kMsgTurnOffCheckBox = 'TUOF'; const int32 kMsgTurnOffSliderChanged = 'TUCG'; +const int32 kMsgFadeCornerChanged = 'fdcc'; +const int32 kMsgNeverFadeCornerChanged = 'nfcc'; + static const uint32 kTimeSliderChanged = 'tsch'; + class TimeSlider : public BSlider { public: TimeSlider(BRect frame, const char* name, uint32 modificationMessage); @@ -371,9 +372,9 @@ ModulesView::MessageReceived(BMessage* message) case kMsgTestSaver: SaveState(); - fSettings.SaveSettings(); + fSettings.Save(); - be_roster->Launch(SCREEN_BLANKER_SIG, &fSettings.GetSettings()); + be_roster->Launch(SCREEN_BLANKER_SIG, &fSettings.Message()); break; case kMsgAddSaver: @@ -395,7 +396,7 @@ ModulesView::SaveState() BMessage state; if (saver->SaveState(&state) == B_OK) - fSettings.SetState(fCurrentName.String(), &state); + fSettings.SetModuleState(fCurrentName.String(), &state); } @@ -586,7 +587,7 @@ ScreenSaverWindow::ScreenSaverWindow() : BWindow(BRect(50, 50, 496, 375), "Screen Saver", B_TITLED_WINDOW, B_ASYNCHRONOUS_CONTROLS /*| B_NOT_ZOOMABLE | B_NOT_RESIZABLE*/) { - fSettings.LoadSettings(); + fSettings.Load(); BRect rect = Bounds(); @@ -622,8 +623,8 @@ ScreenSaverWindow::ScreenSaverWindow() fEnableCheckBox->SetValue(fSettings.TimeFlags() & ENABLE_SAVER ? B_CONTROL_ON : B_CONTROL_OFF); fRunSlider->SetTime(fSettings.BlankTime()); fTurnOffSlider->SetTime(fSettings.OffTime() + fSettings.BlankTime()); - fFadeNow->SetCorner(fSettings.GetBlankCorner()); - fFadeNever->SetCorner(fSettings.GetNeverBlankCorner()); + fFadeNow->SetCorner(fSettings.BlankCorner()); + fFadeNever->SetCorner(fSettings.NeverBlankCorner()); fPasswordCheckBox->SetValue(fSettings.LockEnable()); fPasswordSlider->SetTime(fSettings.PasswordTime()); @@ -714,10 +715,10 @@ ScreenSaverWindow::_SetupFadeTab(BRect rect) // Bottom - box->AddChild(fFadeNow = new ScreenCornerSelector(BRect(20,205,80,260),"fadeNow", - B_FOLLOW_LEFT | B_FOLLOW_BOTTOM)); - box->AddChild(fFadeNever = new ScreenCornerSelector(BRect(220,205,280,260),"fadeNever", - B_FOLLOW_LEFT | B_FOLLOW_BOTTOM)); + box->AddChild(fFadeNow = new ScreenCornerSelector(BRect(20,205,80,260), "FadeNow", + new BMessage(kMsgFadeCornerChanged), B_FOLLOW_LEFT | B_FOLLOW_BOTTOM)); + box->AddChild(fFadeNever = new ScreenCornerSelector(BRect(220,205,280,260), "FadeNever", + new BMessage(kMsgNeverFadeCornerChanged), B_FOLLOW_LEFT | B_FOLLOW_BOTTOM)); rect = BRect(90,215,193,230); stringView = new BStringView(rect, NULL, "Fade now when", @@ -842,7 +843,10 @@ ScreenSaverWindow::MessageReceived(BMessage *msg) case kMsgPasswordCheckBox: case kMsgEnableScreenSaverBox: + case kMsgFadeCornerChanged: + case kMsgNeverFadeCornerChanged: _UpdateStatus(); + fSettings.Save(); break; case kMsgChangePassword: @@ -871,7 +875,7 @@ ScreenSaverWindow::QuitRequested() { _UpdateStatus(); fModulesView->SaveState(); - fSettings.SaveSettings(); + fSettings.Save(); be_app->PostMessage(B_QUIT_REQUESTED); return true;