1/* 2 * Copyright 2006-2010 Stephan A��mus <superstippi@gmx.de> 3 * All rights reserved. Distributed under the terms of the MIT License. 4 */ 5 6 7#include "SeekSlider.h" 8 9#include <stdio.h> 10#include <string.h> 11 12#include <ControlLook.h> 13#include <Region.h> 14#include <Shape.h> 15 16 17static const rgb_color kThumbRed = (rgb_color){ 255, 52, 52, 255 }; 18 19 20SeekSlider::SeekSlider(const char* name, BMessage* message, int32 minValue, 21 int32 maxValue) 22 : 23 BSlider(name, NULL, NULL, minValue, maxValue, B_HORIZONTAL, 24 B_TRIANGLE_THUMB), 25 fTracking(false), 26 fLastTrackTime(0), 27 fDisabledString(""), 28 fScale(0.0f) 29{ 30 BFont font(be_plain_font); 31 font.SetSize(font.Size() * 0.75f); 32 SetFont(&font); 33 SetSymbolScale(1.0); 34 rgb_color fillColor = tint_color(ui_color(B_PANEL_BACKGROUND_COLOR), 35 B_DARKEN_3_TINT); 36 UseFillColor(true, &fillColor); 37 SetModificationMessage(message); 38} 39 40 41SeekSlider::~SeekSlider() 42{ 43} 44 45 46status_t 47SeekSlider::Invoke(BMessage* message) 48{ 49 fLastTrackTime = system_time(); 50 return BSlider::Invoke(message); 51} 52 53 54BRect 55SeekSlider::ThumbFrame() const 56{ 57 BRect frame = BSlider::ThumbFrame(); 58 59 float center = (frame.left + frame.right) / 2.0f; 60 float height = ceilf(frame.Height() * fScale); 61 float width = ceilf(frame.Width() * fScale); 62 63 frame.left = floorf(center - width / 2) + 1; 64 frame.right = frame.left + width; 65 frame.bottom = frame.top + height; 66 67 return frame; 68} 69 70 71void 72SeekSlider::DrawBar() 73{ 74 BSlider::DrawBar(); 75 if (IsEnabled()) 76 return; 77 78 BRect r(BarFrame()); 79 font_height fh; 80 GetFontHeight(&fh); 81 float width = ceilf(StringWidth(fDisabledString.String())); 82 BPoint textPos; 83 textPos.x = r.left + (r.Width() - width) / 2.0; 84 textPos.y = (r.top + r.bottom - ceilf(fh.ascent + fh.descent)) / 2.0 85 + ceilf(fh.ascent); 86 87 SetHighColor(tint_color(ui_color(B_PANEL_BACKGROUND_COLOR), 88 B_DARKEN_3_TINT)); 89 SetDrawingMode(B_OP_OVER); 90 DrawString(fDisabledString.String(), textPos); 91} 92 93 94void 95SeekSlider::DrawThumb() 96{ 97 if (!IsEnabled()) 98 return; 99 100 BRect frame = ThumbFrame(); 101 be_control_look->DrawSliderTriangle(this, frame, frame, kThumbRed, 0, 102 B_HORIZONTAL); 103} 104 105 106void 107SeekSlider::MouseDown(BPoint where) 108{ 109 if (IsEnabled()) 110 fTracking = true; 111 BSlider::MouseDown(where); 112} 113 114 115void 116SeekSlider::MouseUp(BPoint where) 117{ 118 fTracking = false; 119 BSlider::MouseUp(where); 120} 121 122 123void 124SeekSlider::GetPreferredSize(float* _width, float* _height) 125{ 126 BSlider::GetPreferredSize(_width, _height); 127 if (_width != NULL) { 128 float minWidth = 15.0 + StringWidth(fDisabledString.String()) + 15.0; 129 *_width = max_c(*_width, minWidth); 130 } 131 if (_height != NULL) { 132 BRect unscaledThumbFrame = BSlider::ThumbFrame(); 133 BRect scaledThumbFrame = ThumbFrame(); 134 *_height += scaledThumbFrame.Height() - unscaledThumbFrame.Height(); 135 } 136} 137 138 139BSize 140SeekSlider::MinSize() 141{ 142 BSize size = BSlider::MinSize(); 143 144 BRect unscaledThumbFrame = BSlider::ThumbFrame(); 145 BRect scaledThumbFrame = ThumbFrame(); 146 size.height += scaledThumbFrame.Height() - unscaledThumbFrame.Height(); 147 148 return size; 149} 150 151 152BSize 153SeekSlider::MaxSize() 154{ 155 BSize size = BSlider::MaxSize(); 156 157 BRect unscaledThumbFrame = BSlider::ThumbFrame(); 158 BRect scaledThumbFrame = ThumbFrame(); 159 size.height += scaledThumbFrame.Height() - unscaledThumbFrame.Height(); 160 161 return size; 162} 163 164 165bool 166SeekSlider::IsTracking() const 167{ 168 if (fTracking) 169 return true; 170 return system_time() - fLastTrackTime < 250000; 171} 172 173 174void 175SeekSlider::SetDisabledString(const char* string) 176{ 177 if (string == NULL) 178 string = ""; 179 180 if (fDisabledString == string) 181 return; 182 183 fDisabledString = string; 184 185 if (!IsEnabled()) 186 Invalidate(); 187} 188 189 190void 191SeekSlider::SetSymbolScale(float scale) 192{ 193 if (scale == fScale) 194 return; 195 196 fScale = scale; 197 SetBarThickness(fScale * 15.0); 198 InvalidateLayout(); 199} 200 201 202