AutorÃa | Ultima modificación | Ver Log |
YUI.add('slider-value-range', function (Y, NAME) {/*** Adds value support for Slider as a range of integers between a configured* minimum and maximum value. For use with <code>Y.Base.build(..)</code> to* add the plumbing to <code>Y.SliderBase</code>.** @module slider* @submodule slider-value-range*/// Constants for compression or performancevar MIN = 'min',MAX = 'max',VALUE = 'value',// MINORSTEP = 'minorStep',// MAJORSTEP = 'majorStep',round = Math.round;/*** One class of value algorithm that can be built onto SliderBase. By default,* values range between 0 and 100, but you can configure these on the* built Slider class by setting the <code>min</code> and <code>max</code>* configurations. Set the initial value (will cause the thumb to move to the* appropriate location on the rail) in configuration as well if appropriate.** @class SliderValueRange*/function SliderValueRange() {this._initSliderValueRange();}Y.SliderValueRange = Y.mix( SliderValueRange, {// Prototype properties and methods that will be added onto host classprototype: {/*** Factor used to translate value -> position -> value.** @property _factor* @type {Number}* @protected*/_factor: 1,/*** Stub for construction logic. Override if extending this class and* you need to set something up during the initializer phase.** @method _initSliderValueRange* @protected*/_initSliderValueRange: function () {},/*** Override of stub method in SliderBase that is called at the end of* its bindUI stage of render(). Subscribes to internal events to* trigger UI and related state updates.** @method _bindValueLogic* @protected*/_bindValueLogic: function () {this.after( {minChange : this._afterMinChange,maxChange : this._afterMaxChange,valueChange: this._afterValueChange} );},/*** Move the thumb to appropriate position if necessary. Also resets* the cached offsets and recalculates the conversion factor to* translate position to value.** @method _syncThumbPosition* @protected*/_syncThumbPosition: function () {this._calculateFactor();this._setPosition( this.get( VALUE ) );},/*** Calculates and caches* (range between max and min) / (rail length)* for fast runtime calculation of position -> value.** @method _calculateFactor* @protected*/_calculateFactor: function () {var length = this.get( 'length' ),thumbSize = this.thumb.getStyle( this._key.dim ),min = this.get( MIN ),max = this.get( MAX );// The default thumb width is based on Sam skin's thumb dimension.// This attempts to allow for rendering off-DOM, then attaching// without the need to call syncUI(). It is still recommended// to call syncUI() in these cases though, just to be sure.length = parseFloat( length ) || 150;thumbSize = parseFloat( thumbSize ) || 15;this._factor = ( max - min ) / ( length - thumbSize );Y.log("Calculating factor(~" + this._factor.toFixed(3) + " = (max(" + max + ") - min(" + min + ")) / (length(" + length + ") - thumb size(" + thumbSize + "))","info","slider");},/*** Dispatch the new position of the thumb into the value setting* operations.** @method _defThumbMoveFn* @param e { EventFacade } The host's thumbMove event* @protected*/_defThumbMoveFn: function ( e ) {// To prevent set('value', x) from looping back aroundif (e.source !== 'set') {this.set(VALUE, this._offsetToValue(e.offset));}},/*** <p>Converts a pixel position into a value. Calculates current* thumb offset from the leading edge of the rail multiplied by the* ratio of <code>(max - min) / (constraining dim)</code>.</p>** <p>Override this if you want to use a different value mapping* algorithm.</p>** @method _offsetToValue* @param offset { Number } X or Y pixel offset* @return { mixed } Value corresponding to the provided pixel offset* @protected*/_offsetToValue: function ( offset ) {var value = round( offset * this._factor ) + this.get( MIN );Y.log("Offset: " + offset + " => Value: " + value, "info", "slider");return round( this._nearestValue( value ) );},/*** Converts a value into a pixel offset for use in positioning* the thumb according to the reverse of the* <code>_offsetToValue( xy )</code> operation.** @method _valueToOffset* @param val { Number } The value to map to pixel X or Y position* @return { Number } The pixel offset* @protected*/_valueToOffset: function ( value ) {var offset = round( ( value - this.get( MIN ) ) / this._factor );Y.log("Value: " + value + " => Offset: " + offset, "info", "slider");return offset;},/*** Returns the current value. Override this if you want to introduce* output formatting. Otherwise equivalent to slider.get( "value" );** @method getValue* @return {Number}*/getValue: function () {return this.get( VALUE );},/*** Updates the current value. Override this if you want to introduce* input value parsing or preprocessing. Otherwise equivalent to* slider.set( "value", v );** @method setValue* @param val {Number} The new value* @return {Slider}* @chainable*/setValue: function ( val ) {return this.set( VALUE, val );},/*** Update position according to new min value. If the new min results* in the current value being out of range, the value is set to the* closer of min or max.** @method _afterMinChange* @param e { EventFacade } The <code>min</code> attribute change event.* @protected*/_afterMinChange: function ( e ) {this._verifyValue();this._syncThumbPosition();},/*** Update position according to new max value. If the new max results* in the current value being out of range, the value is set to the* closer of min or max.** @method _afterMaxChange* @param e { EventFacade } The <code>max</code> attribute change event.* @protected*/_afterMaxChange: function ( e ) {this._verifyValue();this._syncThumbPosition();},/*** Verifies that the current value is within the min - max range. If* not, value is set to either min or max, depending on which is* closer.** @method _verifyValue* @protected*/_verifyValue: function () {var value = this.get( VALUE ),nearest = this._nearestValue( value );if ( value !== nearest ) {// @TODO Can/should valueChange, minChange, etc be queued// events? To make dd.set( 'min', n ); execute after minChange// subscribers before on/after valueChange subscribers.this.set( VALUE, nearest );}},/*** Propagate change to the thumb position unless the change originated* from the thumbMove event.** @method _afterValueChange* @param e { EventFacade } The <code>valueChange</code> event.* @protected*/_afterValueChange: function ( e ) {var val = e.newVal;Y.log("Positioning thumb after set('value',x)","info","slider");this._setPosition( val, { source: 'set' } );},/*** Positions the thumb and its ARIA attributes in accordance with the* translated value.** @method _setPosition* @param value {Number} Value to translate to a pixel position* @param [options] {Object} Details object to pass to `_uiMoveThumb`* @protected*/_setPosition: function ( value, options ) {this._uiMoveThumb( this._valueToOffset( value ), options );this.thumb.set('aria-valuenow', value);this.thumb.set('aria-valuetext', value);},/*** Validates new values assigned to <code>min</code> attribute. Numbers* are acceptable. Override this to enforce different rules.** @method _validateNewMin* @param value {Any} Value assigned to <code>min</code> attribute.* @return {Boolean} True for numbers. False otherwise.* @protected*/_validateNewMin: function ( value ) {return Y.Lang.isNumber( value );},/*** Validates new values assigned to <code>max</code> attribute. Numbers* are acceptable. Override this to enforce different rules.** @method _validateNewMax* @param value { mixed } Value assigned to <code>max</code> attribute.* @return { Boolean } True for numbers. False otherwise.* @protected*/_validateNewMax: function ( value ) {return Y.Lang.isNumber( value );},/*** Restricts new values assigned to <code>value</code> attribute to be* between the configured <code>min</code> and <code>max</code>.* Rounds to nearest integer value.** @method _setNewValue* @param value { Number } Value assigned to <code>value</code> attribute* @return { Number } Normalized and constrained value* @protected*/_setNewValue: function ( value ) {if ( Y.Lang.isNumber( value ) ) {return round( this._nearestValue( value ) );}return Y.Attribute.INVALID_VALUE;},/*** Returns the nearest valid value to the value input. If the provided* value is outside the min - max range, accounting for min > max* scenarios, the nearest of either min or max is returned. Otherwise,* the provided value is returned.** @method _nearestValue* @param value { mixed } Value to test against current min - max range* @return { Number } Current min, max, or value if within range* @protected*/_nearestValue: function ( value ) {var min = this.get( MIN ),max = this.get( MAX ),tmp;// Account for reverse value range (min > max)tmp = ( max > min ) ? max : min;min = ( max > min ) ? min : max;max = tmp;return ( value < min ) ?min :( value > max ) ?max :value;}},/*** Attributes that will be added onto host class.** @property ATTRS* @type {Object}* @static* @protected*/ATTRS: {/*** The value associated with the farthest top, left position of the* rail. Can be greater than the configured <code>max</code> if you* want values to increase from right-to-left or bottom-to-top.** @attribute min* @type { Number }* @default 0*/min: {value : 0,validator: '_validateNewMin'},/*** The value associated with the farthest bottom, right position of* the rail. Can be less than the configured <code>min</code> if* you want values to increase from right-to-left or bottom-to-top.** @attribute max* @type { Number }* @default 100*/max: {value : 100,validator: '_validateNewMax'},/*** amount to increment/decrement the Slider value* when the arrow up/down/left/right keys are pressed** @attribute minorStep* @type {Number}* @default 1*/minorStep : {value: 1},/*** amount to increment/decrement the Slider value* when the page up/down keys are pressed** @attribute majorStep* @type {Number}* @default 10*/majorStep : {value: 10},/*** The value associated with the thumb's current position on the* rail. Defaults to the value inferred from the thumb's current* position. Specifying value in the constructor will move the* thumb to the position that corresponds to the supplied value.** @attribute value* @type { Number }* @default (inferred from current thumb position)*/value: {value : 0,setter: '_setNewValue'}}}, true );}, '3.18.1', {"requires": ["slider-base"]});