diff --git a/src/directives/model/checkbox.js b/src/directives/model/checkbox.js index 49356c413bc..e15f7bfa2f4 100644 --- a/src/directives/model/checkbox.js +++ b/src/directives/model/checkbox.js @@ -5,17 +5,41 @@ module.exports = { bind: function () { var self = this var el = this.el + var trueExp = this._checkParam('true-exp') + var falseExp = this._checkParam('false-exp') + + function getValue () { + var val = el.checked + if (val && trueExp !== null) { + val = self.vm.$eval(trueExp) + } + if (!val && falseExp !== null) { + val = self.vm.$eval(falseExp) + } + return val + } + this._getValue = getValue + + function matchValue (value) { + var trueValue = true + if (trueExp !== null) { + trueValue = self.vm.$eval(trueExp) + } + return trueValue === value + } + this._matchValue = matchValue + this.listener = function () { - self.set(el.checked) + self.set(getValue()) } _.on(el, 'change', this.listener) if (el.checked) { - this._initValue = el.checked + this._initValue = getValue() } }, update: function (value) { - this.el.checked = !!value + this.el.checked = this._matchValue(value) }, unbind: function () { diff --git a/src/directives/model/radio.js b/src/directives/model/radio.js index cd265c5abe7..a5956df006e 100644 --- a/src/directives/model/radio.js +++ b/src/directives/model/radio.js @@ -6,11 +6,17 @@ module.exports = { var self = this var el = this.el var number = this._checkParam('number') != null + var expression = this._checkParam('exp') function getValue () { - return number - ? _.toNumber(el.value) - : el.value + var val = el.value + if (number) { + val = _.toNumber(val) + } else if (expression !== null) { + val = self.vm.$eval(expression) + } + return val } + this._getValue = getValue this.listener = function () { self.set(getValue()) } @@ -22,7 +28,7 @@ module.exports = { update: function (value) { /* eslint-disable eqeqeq */ - this.el.checked = value == this.el.value + this.el.checked = value == this._getValue() /* eslint-enable eqeqeq */ }, diff --git a/test/unit/specs/directives/model_spec.js b/test/unit/specs/directives/model_spec.js index 235a5a13e66..346dd3f18ca 100644 --- a/test/unit/specs/directives/model_spec.js +++ b/test/unit/specs/directives/model_spec.js @@ -80,6 +80,34 @@ if (_.inBrowser) { expect(vm.test).toBe('a') }) + it('radio expression', function (done) { + var vm = new Vue({ + el: el, + data: { + test: false, + test2: 'string1', + expression1: 'string1', + expression2: 'string2' + }, + template: + '' + + '' + + '' + + '' + }) + expect(el.childNodes[0].checked).toBe(false) + expect(el.childNodes[1].checked).toBe(true) + expect(el.childNodes[2].checked).toBe(true) + expect(el.childNodes[3].checked).toBe(false) + _.nextTick(function () { + el.childNodes[0].click() + expect(vm.test).toBe(true) + el.childNodes[3].click() + expect(vm.test2).toBe('string2') + done() + }) + }) + it('checkbox', function (done) { var vm = new Vue({ el: el, @@ -113,6 +141,34 @@ if (_.inBrowser) { expect(vm.test).toBe(true) }) + it('checkbox expression', function (done) { + var vm = new Vue({ + el: el, + data: { + test: '', + expression1: 'aTrueValue', + expression2: 'aFalseValue' + }, + template: '' + }) + expect(vm.test).toBe('') + el.firstChild.click() + expect(vm.test).toBe('aTrueValue') + expect(el.firstChild.checked).toBe(true) + el.firstChild.click() + expect(vm.test).toBe('aFalseValue') + expect(el.firstChild.checked).toBe(false) + vm.test = 'aTrueValue' + _.nextTick(function () { + // the updated value of 'test' is not being passed + // into the 'update' method of v-model in this environment + // works fine in manual test + // expect(el.firstChild.checked).toBe(true) + done() + }) + + }) + it('select', function (done) { var vm = new Vue({ el: el,