PageRenderTime 26ms CodeModel.GetById 11ms RepoModel.GetById 0ms app.codeStats 0ms

/qooxdoo/framework/source/class/qx/ui/core/scroll/ScrollBar.js

https://github.com/stephaneerard/qooxdoo
JavaScript | 429 lines | 174 code | 82 blank | 173 comment | 12 complexity | e55113112a6b38d152b067074ac7f931 MD5 | raw file
  1. /* ************************************************************************
  2. qooxdoo - the new era of web development
  3. http://qooxdoo.org
  4. Copyright:
  5. 2004-2008 1&1 Internet AG, Germany, http://www.1und1.de
  6. License:
  7. LGPL: http://www.gnu.org/licenses/lgpl.html
  8. EPL: http://www.eclipse.org/org/documents/epl-v10.php
  9. See the LICENSE file in the project's left-level directory for details.
  10. Authors:
  11. * Sebastian Werner (wpbasti)
  12. * Fabian Jakobs (fjakobs)
  13. ************************************************************************ */
  14. /**
  15. * The scroll bar widget, is a special slider, which is used in qooxdoo instead
  16. * of the native browser scroll bars.
  17. *
  18. * Scroll bars are used by the {@link qx.ui.container.Scroll} container. Usually
  19. * a scroll bar is not used directly.
  20. *
  21. * @childControl slider {qx.ui.core.scroll.ScrollSlider} scroll slider component
  22. * @childControl button-begin {qx.ui.form.RepeatButton} button to scroll to top
  23. * @childControl button-end {qx.ui.form.RepeatButton} button to scroll to bottom
  24. *
  25. * *Example*
  26. *
  27. * Here is a little example of how to use the widget.
  28. *
  29. * <pre class='javascript'>
  30. * var scrollBar = new qx.ui.core.scroll.ScrollBar("horizontal");
  31. * scrollBar.set({
  32. * maximum: 500
  33. * })
  34. * this.getRoot().add(scrollBar);
  35. * </pre>
  36. *
  37. * This example creates a horizontal scroll bar with a maximum value of 500.
  38. *
  39. * *External Documentation*
  40. *
  41. * <a href='http://manual.qooxdoo.org/1.2/pages/widget/scrollbar.html' target='_blank'>
  42. * Documentation of this widget in the qooxdoo wiki.</a>
  43. */
  44. qx.Class.define("qx.ui.core.scroll.ScrollBar",
  45. {
  46. extend : qx.ui.core.Widget,
  47. implement : qx.ui.core.scroll.IScrollBar,
  48. /*
  49. *****************************************************************************
  50. CONSTRUCTOR
  51. *****************************************************************************
  52. */
  53. /**
  54. * @param orientation {String?"horizontal"} The initial scroll bar orientation
  55. */
  56. construct : function(orientation)
  57. {
  58. this.base(arguments);
  59. // Create child controls
  60. this._createChildControl("button-begin");
  61. this._createChildControl("slider").addListener("resize", this._onResizeSlider, this);
  62. this._createChildControl("button-end");
  63. // Configure orientation
  64. if (orientation != null) {
  65. this.setOrientation(orientation);
  66. } else {
  67. this.initOrientation();
  68. }
  69. },
  70. /*
  71. *****************************************************************************
  72. PROPERTIES
  73. *****************************************************************************
  74. */
  75. properties :
  76. {
  77. // overridden
  78. appearance :
  79. {
  80. refine : true,
  81. init : "scrollbar"
  82. },
  83. /**
  84. * The scroll bar orientation
  85. */
  86. orientation :
  87. {
  88. check : [ "horizontal", "vertical" ],
  89. init : "horizontal",
  90. apply : "_applyOrientation"
  91. },
  92. /**
  93. * The maximum value (difference between available size and
  94. * content size).
  95. */
  96. maximum :
  97. {
  98. check : "PositiveInteger",
  99. apply : "_applyMaximum",
  100. init : 100
  101. },
  102. /**
  103. * Position of the scrollbar (which means the scroll left/top of the
  104. * attached area's pane)
  105. *
  106. * Strictly validates according to {@link #maximum}.
  107. * Does not apply any correction to the incoming value. If you depend
  108. * on this, please use {@link #scrollTo} instead.
  109. */
  110. position :
  111. {
  112. check : "qx.lang.Type.isNumber(value)&&value>=0&&value<=this.getMaximum()",
  113. init : 0,
  114. apply : "_applyPosition",
  115. event : "scroll"
  116. },
  117. /**
  118. * Step size for each click on the up/down or left/right buttons.
  119. */
  120. singleStep :
  121. {
  122. check : "Integer",
  123. init : 20
  124. },
  125. /**
  126. * The amount to increment on each event. Typically corresponds
  127. * to the user pressing <code>PageUp</code> or <code>PageDown</code>.
  128. */
  129. pageStep :
  130. {
  131. check : "Integer",
  132. init : 10,
  133. apply : "_applyPageStep"
  134. },
  135. /**
  136. * Factor to apply to the width/height of the knob in relation
  137. * to the dimension of the underlying area.
  138. */
  139. knobFactor :
  140. {
  141. check : "PositiveNumber",
  142. apply : "_applyKnobFactor",
  143. nullable : true
  144. }
  145. },
  146. /*
  147. *****************************************************************************
  148. MEMBERS
  149. *****************************************************************************
  150. */
  151. members :
  152. {
  153. __offset : 2,
  154. // overridden
  155. _createChildControlImpl : function(id)
  156. {
  157. var control;
  158. switch(id)
  159. {
  160. case "slider":
  161. control = new qx.ui.core.scroll.ScrollSlider();
  162. control.setPageStep(100);
  163. control.setFocusable(false);
  164. control.addListener("changeValue", this._onChangeSliderValue, this);
  165. this._add(control, {flex: 1});
  166. break;
  167. case "button-begin":
  168. // Top/Left Button
  169. control = new qx.ui.form.RepeatButton();
  170. control.setFocusable(false);
  171. control.addListener("execute", this._onExecuteBegin, this);
  172. this._add(control);
  173. break;
  174. case "button-end":
  175. // Bottom/Right Button
  176. control = new qx.ui.form.RepeatButton();
  177. control.setFocusable(false);
  178. control.addListener("execute", this._onExecuteEnd, this);
  179. this._add(control);
  180. break;
  181. }
  182. return control || this.base(arguments, id);
  183. },
  184. /*
  185. ---------------------------------------------------------------------------
  186. PROPERTY APPLY ROUTINES
  187. ---------------------------------------------------------------------------
  188. */
  189. // property apply
  190. _applyMaximum : function(value) {
  191. this.getChildControl("slider").setMaximum(value);
  192. },
  193. // property apply
  194. _applyPosition : function(value) {
  195. this.getChildControl("slider").setValue(value);
  196. },
  197. // property apply
  198. _applyKnobFactor : function(value) {
  199. this.getChildControl("slider").setKnobFactor(value);
  200. },
  201. // property apply
  202. _applyPageStep : function(value) {
  203. this.getChildControl("slider").setPageStep(value);
  204. },
  205. // property apply
  206. _applyOrientation : function(value, old)
  207. {
  208. // Dispose old layout
  209. var oldLayout = this._getLayout();
  210. if (oldLayout) {
  211. oldLayout.dispose();
  212. }
  213. // Reconfigure
  214. if (value === "horizontal")
  215. {
  216. this._setLayout(new qx.ui.layout.HBox());
  217. this.setAllowStretchX(true);
  218. this.setAllowStretchY(false);
  219. this.replaceState("vertical", "horizontal");
  220. this.getChildControl("button-begin").replaceState("up", "left");
  221. this.getChildControl("button-end").replaceState("down", "right");
  222. }
  223. else
  224. {
  225. this._setLayout(new qx.ui.layout.VBox());
  226. this.setAllowStretchX(false);
  227. this.setAllowStretchY(true);
  228. this.replaceState("horizontal", "vertical");
  229. this.getChildControl("button-begin").replaceState("left", "up");
  230. this.getChildControl("button-end").replaceState("right", "down");
  231. }
  232. // Sync slider orientation
  233. this.getChildControl("slider").setOrientation(value);
  234. },
  235. /*
  236. ---------------------------------------------------------------------------
  237. METHOD REDIRECTION TO SLIDER
  238. ---------------------------------------------------------------------------
  239. */
  240. /**
  241. * Scrolls to the given position.
  242. *
  243. * This method automatically corrects the given position to respect
  244. * the {@link #maximum}.
  245. *
  246. * @param position {Integer} Scroll to this position. Must be greater zero.
  247. * @return {void}
  248. */
  249. scrollTo : function(position) {
  250. this.getChildControl("slider").slideTo(position);
  251. },
  252. /**
  253. * Scrolls by the given offset.
  254. *
  255. * This method automatically corrects the given position to respect
  256. * the {@link #maximum}.
  257. *
  258. * @param offset {Integer} Scroll by this offset
  259. * @return {void}
  260. */
  261. scrollBy : function(offset) {
  262. this.getChildControl("slider").slideBy(offset);
  263. },
  264. /**
  265. * Scrolls by the given number of steps.
  266. *
  267. * This method automatically corrects the given position to respect
  268. * the {@link #maximum}.
  269. *
  270. * @param steps {Integer} Number of steps
  271. * @return {void}
  272. */
  273. scrollBySteps : function(steps)
  274. {
  275. var size = this.getSingleStep();
  276. this.getChildControl("slider").slideBy(steps * size);
  277. },
  278. /*
  279. ---------------------------------------------------------------------------
  280. EVENT LISTENER
  281. ---------------------------------------------------------------------------
  282. */
  283. /**
  284. * Executed when the up/left button is executed (pressed)
  285. *
  286. * @param e {qx.event.type.Event} Execute event of the button
  287. * @return {void}
  288. */
  289. _onExecuteBegin : function(e) {
  290. this.scrollBy(-this.getSingleStep());
  291. },
  292. /**
  293. * Executed when the down/right button is executed (pressed)
  294. *
  295. * @param e {qx.event.type.Event} Execute event of the button
  296. * @return {void}
  297. */
  298. _onExecuteEnd : function(e) {
  299. this.scrollBy(this.getSingleStep());
  300. },
  301. /**
  302. * Change listener for slider value changes.
  303. *
  304. * @param e {qx.event.type.Data} The change event object
  305. * @return {void}
  306. */
  307. _onChangeSliderValue : function(e) {
  308. this.setPosition(e.getData());
  309. },
  310. /**
  311. * Hide the knob of the slider if the slidebar is too small or show it
  312. * otherwise.
  313. *
  314. * @param e {qx.event.type.Data} event object
  315. */
  316. _onResizeSlider : function(e)
  317. {
  318. var knob = this.getChildControl("slider").getChildControl("knob");
  319. var knobHint = knob.getSizeHint();
  320. var hideKnob = false;
  321. var sliderSize = this.getChildControl("slider").getInnerSize();
  322. if (this.getOrientation() == "vertical")
  323. {
  324. if (sliderSize.height < knobHint.minHeight + this.__offset) {
  325. hideKnob = true;
  326. }
  327. }
  328. else
  329. {
  330. if (sliderSize.width < knobHint.minWidth + this.__offset) {
  331. hideKnob = true;
  332. }
  333. }
  334. if (hideKnob) {
  335. knob.exclude();
  336. } else {
  337. knob.show();
  338. }
  339. }
  340. }
  341. });