a022aef3 by Zack Owens

updating fork

2 parents d0ec373e 7311b968
......@@ -2,8 +2,8 @@
"name": "rivets",
"repo": "mikeric/rivets",
"description": "Declarative data binding facility.",
"version": "0.4.5",
"keywords": ["data binding", "template"],
"version": "0.4.8",
"keywords": ["data binding", "templating"],
"scripts": ["lib/rivets.js"],
"main": "lib/rivets.js",
"license": "MIT"
......
// rivets.js
// version: 0.4.5
// version: 0.4.8
// author: Michael Richards
// license: MIT
(function() {
var Rivets, bindEvent, getInputValue, rivets, unbindEvent,
var Rivets, bindEvent, factory, getInputValue, unbindEvent,
__bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; },
__slice = [].slice,
__indexOf = [].indexOf || function(item) { for (var i = 0, l = this.length; i < l; i++) { if (i in this && this[i] === item) return i; } return -1; };
......@@ -405,21 +405,31 @@
getInputValue = function(el) {
var o, _i, _len, _results;
switch (el.type) {
case 'checkbox':
return el.checked;
case 'select-multiple':
_results = [];
for (_i = 0, _len = el.length; _i < _len; _i++) {
o = el[_i];
if (o.selected) {
_results.push(o.value);
if (window.jQuery != null) {
el = jQuery(el);
switch (el[0].type) {
case 'checkbox':
return el.is(':checked');
default:
return el.val();
}
} else {
switch (el.type) {
case 'checkbox':
return el.checked;
case 'select-multiple':
_results = [];
for (_i = 0, _len = el.length; _i < _len; _i++) {
o = el[_i];
if (o.selected) {
_results.push(o.value);
}
}
}
return _results;
break;
default:
return el.value;
return _results;
break;
default:
return el.value;
}
}
};
......@@ -439,8 +449,9 @@
return unbindEvent(el, 'change', this.currentListener);
},
routine: function(el, value) {
var _ref;
if (el.type === 'radio') {
return el.checked = el.value === value;
return el.checked = ((_ref = el.value) != null ? _ref.toString() : void 0) === (value != null ? value.toString() : void 0);
} else {
return el.checked = !!value;
}
......@@ -455,8 +466,9 @@
return unbindEvent(el, 'change', this.currentListener);
},
routine: function(el, value) {
var _ref;
if (el.type === 'radio') {
return el.checked = el.value !== value;
return el.checked = ((_ref = el.value) != null ? _ref.toString() : void 0) !== (value != null ? value.toString() : void 0);
} else {
return el.checked = !value;
}
......@@ -480,18 +492,25 @@
return unbindEvent(el, 'change', this.currentListener);
},
routine: function(el, value) {
var o, _i, _len, _ref, _results;
if (el.type === 'select-multiple') {
if (value != null) {
_results = [];
for (_i = 0, _len = el.length; _i < _len; _i++) {
o = el[_i];
_results.push(o.selected = (_ref = o.value, __indexOf.call(value, _ref) >= 0));
}
return _results;
var o, _i, _len, _ref, _ref1, _ref2, _results;
if (window.jQuery != null) {
el = jQuery(el);
if ((value != null ? value.toString() : void 0) !== ((_ref = el.val()) != null ? _ref.toString() : void 0)) {
return el.val(value != null ? value : '');
}
} else {
return el.value = value != null ? value : '';
if (el.type === 'select-multiple') {
if (value != null) {
_results = [];
for (_i = 0, _len = el.length; _i < _len; _i++) {
o = el[_i];
_results.push(o.selected = (_ref1 = o.value, __indexOf.call(value, _ref1) >= 0));
}
return _results;
}
} else if ((value != null ? value.toString() : void 0) !== ((_ref2 = el.value) != null ? _ref2.toString() : void 0)) {
return el.value = value != null ? value : '';
}
}
}
},
......@@ -581,11 +600,11 @@
Rivets.formatters = {};
rivets = {
binders: Rivets.binders,
formatters: Rivets.formatters,
config: Rivets.config,
configure: function(options) {
factory = function(exports) {
exports.binders = Rivets.binders;
exports.formatters = Rivets.formatters;
exports.config = Rivets.config;
exports.configure = function(options) {
var property, value;
if (options == null) {
options = {};
......@@ -594,8 +613,8 @@
value = options[property];
Rivets.config[property] = value;
}
},
bind: function(el, models) {
};
return exports.bind = function(el, models) {
var view;
if (models == null) {
models = {};
......@@ -603,13 +622,18 @@
view = new Rivets.View(el, models);
view.bind();
return view;
}
};
};
if (typeof module !== "undefined" && module !== null) {
module.exports = rivets;
if (typeof exports === 'object') {
factory(exports);
} else if (typeof define === 'function' && define.amd) {
define(['exports'], function(exports) {
factory(this.rivets = exports);
return exports;
});
} else {
this.rivets = rivets;
factory(this.rivets = {});
}
}).call(this);
......
{
"name" : "rivets",
"description" : "Declarative data binding facility.",
"version" : "0.4.5",
"version" : "0.4.8",
"author" : "Michael Richards",
"url" : "http://rivetsjs.com",
"main" : "./lib/rivets.js",
......
describe('Routines', function() {
var el, input;
var el, input, trueRadioInput, falseRadioInput, checkboxInput;
var createInputElement = function(type, value) {
var elem = document.createElement('input');
elem.setAttribute('type', type);
if (value !== undefined){
elem.setAttribute('value', value);
}
document.body.appendChild(elem);
return elem;
};
beforeEach(function() {
rivets.configure({
......@@ -12,8 +22,27 @@ describe('Routines', function() {
});
el = document.createElement('div');
input = document.createElement('input');
input.setAttribute('type', 'text');
document.body.appendChild(el);
input = createInputElement('text');
// to test the radio input scenario when its value is "true"
trueRadioInput = createInputElement('radio', 'true');
// to test the radio input scenario when its value is "false"
falseRadioInput = createInputElement('radio', 'false');
// to test the checkbox input scenario
checkboxInput = createInputElement('checkbox');
});
afterEach(function(){
el.parentNode.removeChild(el);
input.parentNode.removeChild(input);
trueRadioInput.parentNode.removeChild(trueRadioInput);
falseRadioInput.parentNode.removeChild(falseRadioInput);
checkboxInput.parentNode.removeChild(checkboxInput);
});
describe('text', function() {
......@@ -126,33 +155,101 @@ describe('Routines', function() {
});
describe('checked', function() {
describe('with a truthy value', function() {
it('checks the element', function() {
rivets.binders.checked.routine(el, true);
expect(el.checked).toBe(true);
describe('with a checkbox input', function() {
describe('and a truthy value', function() {
it('checks the checkbox input', function() {
rivets.binders.checked.routine(checkboxInput, true);
expect(checkboxInput.checked).toBe(true);
});
});
describe('with a falsey value', function() {
it('unchecks the checkbox input', function() {
rivets.binders.checked.routine(checkboxInput, false);
expect(checkboxInput.checked).toBe(false);
});
});
});
describe('with a falsey value', function() {
it('unchecks the element', function() {
rivets.binders.checked.routine(el, false);
expect(el.checked).toBe(false);
describe('with a radio input with value="true"', function() {
describe('and a truthy value', function() {
it('checks the radio input', function() {
rivets.binders.checked.routine(trueRadioInput, true);
expect(trueRadioInput.checked).toBe(true);
});
});
describe('with a falsey value', function() {
it('unchecks the radio input', function() {
rivets.binders.checked.routine(trueRadioInput, false);
expect(trueRadioInput.checked).toBe(false);
});
});
});
describe('with a radio input with value="false"', function() {
describe('and a truthy value', function() {
it('checks the radio input', function() {
rivets.binders.checked.routine(falseRadioInput, true);
expect(falseRadioInput.checked).toBe(false);
});
});
describe('with a falsey value', function() {
it('unchecks the radio input', function() {
rivets.binders.checked.routine(falseRadioInput, false);
expect(falseRadioInput.checked).toBe(true);
});
});
});
});
describe('unchecked', function() {
describe('with a truthy value', function() {
it('unchecks the element', function() {
rivets.binders.unchecked.routine(el, true);
expect(el.checked).toBe(false);
describe('and a truthy value', function() {
describe('and a truthy value', function() {
it('checks the checkbox input', function() {
rivets.binders.unchecked.routine(checkboxInput, true);
expect(checkboxInput.checked).toBe(false);
});
});
describe('with a falsey value', function() {
it('unchecks the checkbox input', function() {
rivets.binders.unchecked.routine(checkboxInput, false);
expect(checkboxInput.checked).toBe(true);
});
});
});
describe('with a falsey value', function() {
it('checks the element', function() {
rivets.binders.unchecked.routine(el, false);
expect(el.checked).toBe(true);
describe('with a radio input with value="true"', function() {
describe('and a truthy value', function() {
it('checks the radio input', function() {
rivets.binders.unchecked.routine(trueRadioInput, true);
expect(trueRadioInput.checked).toBe(false);
});
});
describe('with a falsey value', function() {
it('unchecks the radio input', function() {
rivets.binders.unchecked.routine(trueRadioInput, false);
expect(trueRadioInput.checked).toBe(true);
});
});
});
describe('with a radio input with value="false"', function() {
describe('and a truthy value', function() {
it('checks the radio input', function() {
rivets.binders.unchecked.routine(falseRadioInput, true);
expect(falseRadioInput.checked).toBe(true);
});
});
describe('with a falsey value', function() {
it('unchecks the radio input', function() {
rivets.binders.unchecked.routine(falseRadioInput, false);
expect(falseRadioInput.checked).toBe(false);
});
});
});
});
......
# rivets.js
# version : 0.4.5
# version : 0.4.8
# author : Michael Richards
# license : MIT
......@@ -256,12 +256,19 @@ unbindEvent = (el, event, fn) ->
event = 'on' + event
el.detachEvent event, fn
# Returns the current input value for the specified element.
# Cross-browser input value getter.
getInputValue = (el) ->
switch el.type
when 'checkbox' then el.checked
when 'select-multiple' then o.value for o in el when o.selected
else el.value
if window.jQuery?
el = jQuery el
switch el[0].type
when 'checkbox' then el.is ':checked'
else el.val()
else
switch el.type
when 'checkbox' then el.checked
when 'select-multiple' then o.value for o in el when o.selected
else el.value
# Core binding routines.
Rivets.binders =
......@@ -279,7 +286,7 @@ Rivets.binders =
unbindEvent el, 'change', @currentListener
routine: (el, value) ->
if el.type is 'radio'
el.checked = el.value is value
el.checked = el.value?.toString() is value?.toString()
else
el.checked = !!value
......@@ -291,7 +298,7 @@ Rivets.binders =
unbindEvent el, 'change', @currentListener
routine: (el, value) ->
if el.type is 'radio'
el.checked = el.value isnt value
el.checked = el.value?.toString() isnt value?.toString()
else
el.checked = !value
......@@ -311,10 +318,16 @@ Rivets.binders =
unbind: (el) ->
unbindEvent el, 'change', @currentListener
routine: (el, value) ->
if el.type is 'select-multiple'
o.selected = o.value in value for o in el if value?
if window.jQuery?
el = jQuery el
if value?.toString() isnt el.val()?.toString()
el.val if value? then value else ''
else
el.value = if value? then value else ''
if el.type is 'select-multiple'
o.selected = o.value in value for o in el if value?
else if value?.toString() isnt el.value?.toString()
el.value = if value? then value else ''
text: (el, value) ->
if el.innerText?
......@@ -331,7 +344,7 @@ Rivets.binders =
"each-*":
block: true
bind: (el, collection) ->
el.removeAttribute ['data', rivets.config.prefix, @type].join('-').replace '--', '-'
el.removeAttribute ['data', Rivets.config.prefix, @type].join('-').replace '--', '-'
routine: (el, collection) ->
if @iterated?
for view in @iterated
......@@ -350,12 +363,16 @@ Rivets.binders =
data[n] = m for n, m of @view.models
data[@args[0]] = item
itemEl = el.cloneNode true
if @iterated.length > 0
previous = @iterated[@iterated.length - 1].els[0]
previous = if @iterated.length
@iterated[@iterated.length - 1].els[0]
else
previous = @marker
@marker
@marker.parentNode.insertBefore itemEl, previous.nextSibling ? null
@iterated.push rivets.bind itemEl, data
view = new Rivets.View(itemEl, data)
view.bind()
@iterated.push view
"class-*": (el, value) ->
elClass = " #{el.className} "
......@@ -380,32 +397,36 @@ Rivets.config =
Rivets.formatters = {}
# The rivets module. This is the public interface that gets exported.
rivets =
factory = (exports) ->
# Exposes the core binding routines that can be extended or stripped down.
binders: Rivets.binders
exports.binders = Rivets.binders
# Exposes the formatters object to be extended.
formatters: Rivets.formatters
exports.formatters = Rivets.formatters
# Exposes the rivets configuration options. These can be set manually or from
# rivets.configure with an object literal.
config: Rivets.config
exports.config = Rivets.config
# Sets configuration options by merging an object literal.
configure: (options={}) ->
exports.configure = (options={}) ->
for property, value of options
Rivets.config[property] = value
return
# Binds a set of model objects to a parent DOM element. Returns a Rivets.View
# instance.
bind: (el, models = {}, options) ->
exports.bind = (el, models = {}, options = {}) ->
view = new Rivets.View(el, models, options)
view.bind()
view
# Exports rivets for both CommonJS and the browser.
if module?
module.exports = rivets
# Exports rivets for CommonJS, AMD and the browser.
if typeof exports == 'object'
factory(exports)
else if typeof define == 'function' && define.amd
define ['exports'], (exports) ->
factory(@rivets = exports)
return exports
else
@rivets = rivets
factory(@rivets = {})
......