Skip to content

Commit

Permalink
Monitor an input field's values and reflect the change in the control
Browse files Browse the repository at this point in the history
  • Loading branch information
leegee committed Oct 17, 2012
1 parent ba4fb68 commit 2fbe428
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 2 deletions.
9 changes: 9 additions & 0 deletions README.md
Expand Up @@ -94,6 +94,8 @@ The following options are available. Some may be supplied as
* **wrappernostyle**: (*false*) By default, the anchor that wraps the knob, to allow keyboard focus, has CSS styles alter (no text-decoration, border or padding). This can be prevented though this attribute.
* **keychangeby**: (*1*) When arrow keys control the knob, the **value** field is increased by this factor
* **keychangebywithshift**: (*10*) As **keychangeby**, above, but for when shift, alt, or meta key is also pressed
* **monitor**: A name for, or instance of, a DOM element that has a **value** field that shoudl be monitored for changes, to be reflected by this control. Intended for text input elements.
* **monitorMs**: (*250*) The interval, in milliseconds, at which to check the **monitor** element, if supplied.

EVENTS
------
Expand All @@ -114,3 +116,10 @@ of the widget, using the following object fields:

The **onTick** event could just be used to update a text display field.

PUBLIC METHODS
--------------

* **render**: Update the control to reflect the current state of the **value** field, which may be set by supply a single, numeric argument
* **attach**: Called at instantiation to attach eveents to allow the control to operate
* **detach**: Removes events

30 changes: 28 additions & 2 deletions Source/Knob.js
Expand Up @@ -45,12 +45,18 @@ var Knob = new Class({
keychangeby: 1, /* When arrow keys control knob, incrase knob value by this */
keychangebywithshift: 10, /* As keyUnit but for when shift key is also pressed */

monitor: null, /* May be a string or DOM element to monitor: changes in this elements *value* attribute will change the control's *value* attribute, and cause the control to be re-rendered. */
monitorMs: 1000/4, /* Frequency of checking for monitor.value changes */

onTick: function(){},
onMousedown: function(){},
onMouseUp: function(){}
},

element: null,
monitor: null, /* See options.monitor */
monitorOldValue: null,
monitorTimer: null, /* setInterval timer for checking monitor.value */
wrapper: null, /* Anchor element that wraps element to allow focus */
movement: null, /* The Euclidean distance of dragged cursor from origin in element */
anchor: null, /* Position of element at knob mouse down */
Expand All @@ -68,6 +74,10 @@ var Knob = new Class({
document.id(this.options.element)
: this.element = this.options.element;

this.monitor = (typeof this.options.monitor == 'string')?
document.id(this.options.monitor)
: this.monitor = this.options.monitor;

var wrapperStyle = this.options.wrappernostyle?
{} : {
'text-decoration' : 'none',
Expand Down Expand Up @@ -103,11 +113,25 @@ var Knob = new Class({

attach: function(){
this.element.addEvent('mousedown', this.mousedown);
this.monitor.addEvent('change', this.monitorValueChange);
this.monitorTimer = this.monitorValueChange.periodical(
this.options.monitorMs, this
);
},

/* Monitor changes in the .monitor field's value, and update control */
monitorValueChange: function(e){
var v = this.monitor.get('value');
if (v != this.monitorOldValue){
this.value = v;
this.render();
}
},

destroy: function(){ this.detach() },

detach: function(){
if (this.monitorTimer) clearInterval( this.monitorTimer );
this.element.removeEvent('mousedown', this.mousedown);
if (this.dragging)
window.removeEvent('mouseup', __ActiveMooToolsKnobCtrl__.mouseup);
Expand Down Expand Up @@ -235,9 +259,11 @@ var Knob = new Class({

/* Rotates the control knob.
Requires this.value to be set.
Sets this.degrees, and element's aria-valuenow/-valuetext
Sets this.degrees, and element's aria-valuenow/-valuetext.
If a parameter is supplied, it sets this.value
*/
render: function(){
render: function(v){
if (typeof v != 'undefined') this.value = v;
this.degrees = this.value * (360 / this.range);
this.element.set('aria-valuenow', this.value);
this.element.set('aria-valuetext', this.value);
Expand Down

0 comments on commit 2fbe428

Please sign in to comment.