nux-1.14.0
HScrollBar.cpp
00001 /*
00002  * Copyright 2010 Inalogic® Inc.
00003  *
00004  * This program is free software: you can redistribute it and/or modify it
00005  * under the terms of the GNU Lesser General Public License, as
00006  * published by the  Free Software Foundation; either version 2.1 or 3.0
00007  * of the License.
00008  *
00009  * This program is distributed in the hope that it will be useful, but
00010  * WITHOUT ANY WARRANTY; without even the implied warranties of
00011  * MERCHANTABILITY, SATISFACTORY QUALITY or FITNESS FOR A PARTICULAR
00012  * PURPOSE.  See the applicable version of the GNU Lesser General Public
00013  * License for more details.
00014  *
00015  * You should have received a copy of both the GNU Lesser General Public
00016  * License along with this program. If not, see <http://www.gnu.org/licenses/>
00017  *
00018  * Authored by: Jay Taoko <jaytaoko@inalogic.com>
00019  *
00020  */
00021 
00022 
00023 #include "Nux.h"
00024 #include "Layout.h"
00025 #include "HLayout.h"
00026 #include "VLayout.h"
00027 #include "HScrollBar.h"
00028 
00029 namespace nux
00030 {
00031 
00032   const int HSCROLLBAR_WIDTH = 10;
00033   const int HSCROLLBAR_HEIGHT = 10;
00034 
00035   HScrollBar::HScrollBar (NUX_FILE_LINE_DECL)
00036     :   ScrollBar (NUX_FILE_LINE_PARAM)
00037   {
00038     content_width_      = 0;
00039     content_height_     = 0;
00040     container_width_    = 0;
00041     container_height_   = 0;
00042     m_TrackWidth        = 0;
00043     m_TrackHeight       = 0;
00044     m_SlideBarOffsetX   = 0;
00045     m_SlideBarOffsetY   = 0;
00046     content_offset_x_    = 0;
00047     content_offset_y_    = 0;
00048     b_MouseUpTimer      = false;
00049     b_MouseDownTimer    = false;
00050     m_color_factor      = 1.0f;
00051     m_LeftTimerHandler  = 0;
00052     m_RightTimerHandler = 0;
00053 
00054     hlayout = new HLayout (NUX_TRACKER_LOCATION);
00055     _scroll_left_button = new InputArea (NUX_TRACKER_LOCATION);
00056     _track = new InputArea (NUX_TRACKER_LOCATION);
00057     _scroll_right_button = new InputArea (NUX_TRACKER_LOCATION);
00058     _slider = new InputArea (NUX_TRACKER_LOCATION);
00059     _slider->SetParentObject(this);
00060 
00061     // Set Original State
00062     SetMinimumSize (AREA_MIN_WIDTH, HSCROLLBAR_HEIGHT);
00063     SetMaximumSize (AREA_MAX_WIDTH, HSCROLLBAR_HEIGHT);
00064 
00065     // Set Signals
00066     _scroll_right_button->mouse_down.connect ( sigc::mem_fun (this, &HScrollBar::RecvStartScrollRight) );
00067     _scroll_right_button->mouse_up.connect ( sigc::mem_fun (this, &HScrollBar::RecvEndScrollRight) );
00068     _scroll_left_button->mouse_down.connect ( sigc::mem_fun (this, &HScrollBar::RecvStartScrollLeft) );
00069     _scroll_left_button->mouse_up.connect ( sigc::mem_fun (this, &HScrollBar::RecvEndScrollLeft) );
00070 
00071     _slider->mouse_down.connect ( sigc::mem_fun (this, &HScrollBar::OnSliderMouseDown) );
00072     _slider->mouse_up.connect ( sigc::mem_fun (this, &HScrollBar::OnSliderMouseUp) );
00073     _slider->mouse_drag.connect ( sigc::mem_fun (this, &HScrollBar::OnSliderMouseDrag) );
00074 
00075     _track->mouse_down.connect ( sigc::mem_fun (this, &HScrollBar::RecvTrackMouseDown) );
00076     _track->mouse_up.connect ( sigc::mem_fun (this, &HScrollBar::RecvTrackMouseUp) );
00077     _track->mouse_drag.connect ( sigc::mem_fun (this, &HScrollBar::RecvTrackMouseDrag) );
00078 
00079     // Set Geometry
00080     _scroll_right_button->SetMinimumSize (HSCROLLBAR_WIDTH, HSCROLLBAR_HEIGHT);
00081     _scroll_right_button->SetMaximumSize (HSCROLLBAR_WIDTH, HSCROLLBAR_HEIGHT);
00082     _scroll_right_button->SetGeometry (Geometry (0, 0, HSCROLLBAR_WIDTH, HSCROLLBAR_HEIGHT) );
00083     _scroll_left_button->SetMinimumSize (HSCROLLBAR_WIDTH, HSCROLLBAR_HEIGHT);
00084     _scroll_left_button->SetMaximumSize (HSCROLLBAR_WIDTH, HSCROLLBAR_HEIGHT);
00085     _scroll_left_button->SetGeometry (Geometry (0, 0, HSCROLLBAR_WIDTH, HSCROLLBAR_HEIGHT) );
00086 
00087 
00088     hlayout->AddView (_scroll_left_button, 0, eCenter, eFix);
00089     hlayout->AddView (_track, 1, eCenter, eFull);
00090     hlayout->AddView (_scroll_right_button, 0, eCenter, eFix);
00091 
00092     callback = new TimerFunctor;
00093     callback->OnTimerExpired.connect (sigc::mem_fun (this, &HScrollBar::HScrollBarHandler) );
00094     left_callback = new TimerFunctor;
00095     left_callback->OnTimerExpired.connect (sigc::mem_fun (this, &HScrollBar::ScrollLeft) );
00096     right_callback = new TimerFunctor;
00097     right_callback->OnTimerExpired.connect (sigc::mem_fun (this, &HScrollBar::ScrollRight) );
00098     trackleft_callback = new TimerFunctor;
00099     trackleft_callback->OnTimerExpired.connect (sigc::mem_fun (this, &HScrollBar::TrackLeft) );
00100     trackright_callback = new TimerFunctor;
00101     trackright_callback->OnTimerExpired.connect (sigc::mem_fun (this, &HScrollBar::TrackRight) );
00102 
00103     SetLayout(hlayout);
00104     SetAcceptMouseWheelEvent(true);
00105   }
00106 
00107   HScrollBar::~HScrollBar()
00108   {
00109     _slider->UnReference();
00110     delete callback;
00111     delete left_callback;
00112     delete trackleft_callback;
00113     delete right_callback;
00114     delete trackright_callback;
00115   }
00116 
00117   void HScrollBar::HScrollBarHandler (void *v)
00118   {
00119     HScrollBar *scrollbar = static_cast<HScrollBar *> (v);
00120 
00121     if (scrollbar->b_MouseUpTimer && scrollbar->m_color_factor < 1)
00122     {
00123       scrollbar->m_color_factor += 0.1f;
00124 
00125       if (scrollbar->m_color_factor >= 1)
00126       {
00127         scrollbar->m_color_factor = 1;
00128         scrollbar->b_MouseUpTimer = false;
00129       }
00130       else
00131       {
00132         scrollbar->QueueDraw();
00133         GetTimer().AddTimerHandler (10, callback, scrollbar);
00134       }
00135     }
00136 
00137     if (scrollbar->b_MouseDownTimer && scrollbar->m_color_factor > 0)
00138     {
00139       scrollbar->m_color_factor -= 0.09f;
00140 
00141       if (scrollbar->m_color_factor <= 0)
00142       {
00143         scrollbar->m_color_factor = 0;
00144         scrollbar->b_MouseUpTimer = false;
00145       }
00146       else
00147       {
00148         scrollbar->QueueDraw();
00149         GetTimer().AddTimerHandler (10, callback, scrollbar);
00150       }
00151     }
00152   }
00153 
00154   void HScrollBar::ScrollRight (void *v)
00155   {
00156     OnScrollRight.emit (m_ScrollUnit, 1);
00157 
00158     if (AtMaximum())
00159       RecvEndScrollRight (0, 0, 0, 0);
00160     else
00161       m_RightTimerHandler = GetTimer().AddTimerHandler (10, right_callback, this);
00162 
00163     QueueDraw();
00164   }
00165 
00166   void HScrollBar::ScrollLeft (void *v)
00167   {
00168     OnScrollLeft.emit (m_ScrollUnit, 1);
00169 
00170     if (AtMaximum() )
00171       RecvEndScrollLeft (0, 0, 0, 0);
00172     else
00173       m_LeftTimerHandler = GetTimer().AddTimerHandler (10, left_callback, this);
00174 
00175     QueueDraw();
00176   }
00177 
00178   void HScrollBar::TrackLeft (void *v)
00179   {
00180     if (m_TrackMouseCoord.x < _slider->GetBaseX() - _track->GetBaseX() )
00181     {
00182       OnScrollLeft.emit (container_width_, 1);
00183       m_TrackLeftTimerHandler  = GetTimer().AddTimerHandler (10, trackleft_callback, this);
00184       QueueDraw();
00185     }
00186   }
00187 
00188   void HScrollBar::TrackRight (void *v)
00189   {
00190     if (m_TrackMouseCoord.x > _slider->GetBaseX() + _slider->GetBaseWidth() - _track->GetBaseX() )
00191     {
00192       OnScrollRight.emit (container_width_, 1);
00193       m_TrackRightTimerHandler  = GetTimer().AddTimerHandler (10, trackright_callback, this);
00194       QueueDraw();
00195     }
00196   }
00197 
00198   void HScrollBar::RecvStartScrollLeft (int x, int y, unsigned long button_flags, unsigned long key_flags)
00199   {
00200     if (!AtMinimum() )
00201       ScrollLeft (this);
00202   }
00203 
00204   void HScrollBar::RecvStartScrollRight (int x, int y, unsigned long button_flags, unsigned long key_flags)
00205   {
00206     if (!AtMaximum() )
00207       ScrollRight (this);
00208   }
00209 
00210   void HScrollBar::RecvEndScrollRight (int x, int y, unsigned long button_flags, unsigned long key_flags)
00211   {
00212     if (m_RightTimerHandler.IsValid() )
00213       GetTimer().RemoveTimerHandler (m_RightTimerHandler);
00214 
00215     m_RightTimerHandler = 0;
00216   }
00217 
00218   void HScrollBar::RecvEndScrollLeft (int x, int y, unsigned long button_flags, unsigned long key_flags)
00219   {
00220     if (m_LeftTimerHandler.IsValid() )
00221       GetTimer().RemoveTimerHandler (m_LeftTimerHandler);
00222 
00223     m_LeftTimerHandler = 0;
00224   }
00225 
00226   void HScrollBar::RecvTrackMouseDown (int x, int y, unsigned long button_flags, unsigned long key_flags)
00227   {
00228     m_TrackMouseCoord = Point (x, y);
00229 
00230     int X = _slider->GetBaseX() - _track->GetBaseX();
00231 
00232     if (x < X)
00233     {
00234       // move the slide bar up
00235       TrackLeft (this);
00236     }
00237     else
00238     {
00239       TrackRight (this);
00240       // move the slide bar down
00241     }
00242   }
00243 
00244   void HScrollBar::RecvTrackMouseUp (int x, int y, unsigned long button_flags, unsigned long key_flags)
00245   {
00246     if (m_TrackLeftTimerHandler.IsValid() )
00247       GetTimer().RemoveTimerHandler (m_TrackLeftTimerHandler);
00248 
00249     if (m_TrackRightTimerHandler.IsValid() )
00250       GetTimer().RemoveTimerHandler (m_TrackRightTimerHandler);
00251 
00252     m_TrackLeftTimerHandler = 0;
00253     m_TrackRightTimerHandler = 0;
00254   }
00255 
00256   void HScrollBar::RecvTrackMouseDrag (int x, int y, int dx, int dy, unsigned long button_flags, unsigned long key_flags)
00257   {
00258 
00259   }
00260 
00261   long HScrollBar::ProcessEvent (IEvent &ievent, long TraverseInfo, long ProcessEventInfo)
00262   {
00263     long ret = TraverseInfo;
00264     ret = _scroll_right_button->OnEvent (ievent, ret, ProcessEventInfo);
00265     ret = _scroll_left_button->OnEvent (ievent, ret, ProcessEventInfo);
00266     ret = _slider->OnEvent (ievent, ret, ProcessEventInfo);
00267     ret = _track->OnEvent (ievent, ret, ProcessEventInfo);
00268     ret = PostProcessEvent2 (ievent, ret, ProcessEventInfo);
00269 
00270     return ret;
00271   }
00272 
00273   Area* HScrollBar::FindAreaUnderMouse(const Point& mouse_position, NuxEventType event_type)
00274   {
00275     bool mouse_inside = TestMousePointerInclusionFilterMouseWheel(mouse_position, event_type);
00276 
00277     if(mouse_inside == false)
00278       return NULL;
00279 
00280     NUX_RETURN_VALUE_IF_TRUE(_scroll_right_button->TestMousePointerInclusion(mouse_position, event_type), _scroll_right_button);
00281     NUX_RETURN_VALUE_IF_TRUE(_scroll_left_button->TestMousePointerInclusion(mouse_position, event_type), _scroll_left_button);
00282     NUX_RETURN_VALUE_IF_TRUE(_slider->TestMousePointerInclusion(mouse_position, event_type), _slider);
00283     NUX_RETURN_VALUE_IF_TRUE(_track->TestMousePointerInclusion(mouse_position, event_type), _track);
00284 
00285     if((event_type == NUX_MOUSE_WHEEL) && (!AcceptMouseWheelEvent()))
00286       return NULL;
00287     return this;
00288   }
00289 
00290   void HScrollBar::Draw (GraphicsEngine &GfxContext, bool force_draw)
00291   {
00292     Geometry base = GetGeometry();
00293     GetPainter().PaintBackground (GfxContext, base);
00294     base.OffsetPosition (HSCROLLBAR_WIDTH, 0);
00295     base.OffsetSize (-2 * HSCROLLBAR_WIDTH, 0);
00296     GetPainter().PaintShape (GfxContext, base,
00297                          Color (COLOR_SCROLLBAR_TRACK), eHSCROLLBAR, false);
00298 
00299     GetPainter().PaintShape (GfxContext, _scroll_left_button->GetGeometry(), Color (0xFFFFFFFF), eSCROLLBAR_TRIANGLE_LEFT);
00300     GetPainter().PaintShape (GfxContext, _scroll_right_button->GetGeometry(), Color (0xFFFFFFFF), eSCROLLBAR_TRIANGLE_RIGHT);
00301 
00302     GetPainter().PaintShape (GfxContext, _slider->GetGeometry(),
00303                          Color (0.2156 * m_color_factor, 0.2156 * m_color_factor, 0.2156 * m_color_factor, 1.0f),
00304                          eHSCROLLBAR, true);
00305   };
00306 
00307   void HScrollBar::SetContainerSize (int x, int y, int w, int h)
00308   {
00309     // x and y are not needed
00310     container_width_ = w;
00311     container_height_ = h;
00312     ComputeScrolling();
00313   }
00314 
00315   void HScrollBar::SetContentSize (int x, int y, int w, int h)
00316   {
00317     // x and y are not needed
00318     content_width_ = w;
00319     content_height_ = h;
00320     ComputeScrolling();
00321   }
00322 
00323   void HScrollBar::SetContentOffset (float dx, float dy)
00324   {
00325     content_offset_x_ = dx;
00326     content_offset_y_ = dy;
00327     ComputeScrolling();
00328   }
00329 
00330   void HScrollBar::ComputeScrolling()
00331   {
00332     if (content_width_ == 0)
00333     {
00334       visibility_percentage_ = 100.0f;
00335     }
00336     else
00337     {
00338       visibility_percentage_ = Clamp<float>(100.0f * (float) container_width_ / (float) content_width_, 0.0f, 100.0f);
00339     }
00340 
00341     m_TrackWidth = _track->GetBaseWidth();
00342 
00343     int slider_height = _scroll_left_button->GetBaseHeight();
00344     int slider_width = m_TrackWidth * visibility_percentage_ / 100.0f;
00345 
00346     if (slider_width < 15)
00347     {
00348       slider_width = 15;
00349     }
00350 
00351     _slider->SetBaseWidth (slider_width);
00352     _slider->SetBaseHeight (slider_height);
00353     _slider->SetBaseY (_scroll_left_button->GetBaseY() );
00354 
00355 
00356     float pct;
00357 
00358     if (content_width_ - container_width_ > 0)
00359       pct = - (float) content_offset_x_ / (float) (content_width_ - container_width_);
00360     else
00361       pct = 0;
00362 
00363     int x = _track->GetBaseX() + pct * (m_TrackWidth - slider_width);
00364     _slider->SetBaseX (x);
00365   }
00366 
00367 
00369 //  RECEIVERS  //
00371   void HScrollBar::SetValue (float value)
00372   {
00373     //m_ValueString.setCaption(value);
00374   }
00375 
00376   void HScrollBar::SetParameterName (const char *parameter_name)
00377   {
00378     //m_ParameterName.setCaption(parameter_name);
00379   }
00380 
00382 //  EMITTERS  //
00384 
00385   void HScrollBar::OnSliderMouseDown (int x, int y, unsigned long button_flags, unsigned long key_flags)
00386   {
00387     m_SliderDragPositionX = x;
00388     m_SliderDragPositionY = y;
00389     //sigVScrollBarSliderMouseDown.emit();
00390     b_MouseDownTimer = true;
00391     b_MouseUpTimer = false;
00392     GetTimer().AddTimerHandler (10, callback, this);
00393   }
00394 
00395   void HScrollBar::OnSliderMouseUp (int x, int y, unsigned long button_flags, unsigned long key_flags)
00396   {
00397     b_MouseDownTimer = false;
00398     b_MouseUpTimer = true;
00399     GetTimer().AddTimerHandler (10, callback, this);
00400   }
00401 
00402   void HScrollBar::OnSliderMouseDrag (int x, int y, int dx, int dy, unsigned long button_flags, unsigned long key_flags)
00403   {
00404     if (_track->GetBaseWidth() - _slider->GetBaseWidth() > 0)
00405     {
00406       stepX = (float) (content_width_ - container_width_) / (float) (_track->GetBaseWidth() - _slider->GetBaseWidth() );
00407     }
00408     else
00409     {
00410       return;
00411     }
00412 
00413     if ( (dx > 0) && (x > m_SliderDragPositionX) )
00414     {
00415       OnScrollRight.emit (stepX, x - m_SliderDragPositionX);
00416     }
00417 
00418     if ( (dx < 0) && (x < m_SliderDragPositionX) )
00419     {
00420       OnScrollLeft.emit (stepX, m_SliderDragPositionX - x);
00421     }
00422   }
00423 
00424   bool HScrollBar::AtMaximum()
00425   {
00426     if (_slider->GetBaseX() + _slider->GetBaseWidth() == _track->GetBaseX() + _track->GetBaseWidth() )
00427       return TRUE;
00428 
00429     return FALSE;
00430   }
00431 
00432   bool HScrollBar::AtMinimum()
00433   {
00434     if (_slider->GetBaseX() == _track->GetBaseX() )
00435       return TRUE;
00436 
00437     return FALSE;
00438   }
00439 
00440   long HScrollBar::PostLayoutManagement (long LayoutResult)
00441   {
00442     long ret = ScrollBar::PostLayoutManagement (LayoutResult);
00443     ComputeScrolling();
00444     return ret;
00445   }
00446 
00447 }
 All Classes Namespaces Functions Variables Typedefs Enumerations Enumerator Friends