From 7ba49d0dba6ea3c638936907a37e11b2212d842c Mon Sep 17 00:00:00 2001 From: Mikoto Okumura Date: Tue, 22 Jan 2013 00:11:20 +0900 Subject: [PATCH 1/2] Implementing "input's type property CAN be changed" This directive enables to write an input tag with a variable type property like: You can not write the following code without this directive: because jQuery throws an error: "type property can't be changed" when an type property is dynamically changed. This is due to an IE problem: http://stackoverflow.com/questions/1544317/jquery-change-type-of-input-field --- modules/directives/input2/input2.js | 33 ++++++++++++++ modules/directives/input2/test/input2Spec.js | 47 ++++++++++++++++++++ 2 files changed, 80 insertions(+) create mode 100644 modules/directives/input2/input2.js create mode 100644 modules/directives/input2/test/input2Spec.js diff --git a/modules/directives/input2/input2.js b/modules/directives/input2/input2.js new file mode 100644 index 0000000..2ee4b53 --- /dev/null +++ b/modules/directives/input2/input2.js @@ -0,0 +1,33 @@ +/* + * Defines the ui-input2 tag, attribute and class(restrict ECA). This allow an input property to be changed + */ +angular.module('ui.directives').directive('uiInput2', ['$compile', function($compile) { + return { + restrict: 'ECA', + replace: true, + template: '', + link: function(scope, iElement, iAttrs, controller) { + var clone = (function() { + var cursor = iElement; + return function(type) { + var input = angular.element(''); + angular.forEach(iAttrs.$attr, function(v,k) { + input.attr(v, iAttrs[k]); + }); + input.removeAttr('ui-input2'); + input.attr('type', type); + cursor.after(input); + cursor.remove(); + cursor = input; + return input; + }; + })(); + + clone('text'); + iAttrs.$observe('type', function(type) { + var input = clone(type || 'text'); + $compile(input)(scope); + }); + } + }; +}]); diff --git a/modules/directives/input2/test/input2Spec.js b/modules/directives/input2/test/input2Spec.js new file mode 100644 index 0000000..727926d --- /dev/null +++ b/modules/directives/input2/test/input2Spec.js @@ -0,0 +1,47 @@ +describe('ui-input2', function () { + var scope, $compile, elm, + inputTypes = ['text', 'number', 'checkbox', 'radio']; + + beforeEach(module('ui.directives')); + beforeEach(inject(function ($rootScope, _$compile_) { + function makeInput (type) { + return $(''); + } + + scope = $rootScope.$new(); + $compile = _$compile_; + elm = $('
'); + + angular.forEach(inputTypes, function(type) { + elm.append(makeInput(type)); + }); + + + var dynamic = makeInput('{{type}}'); + dynamic.attr('ui-input2',''); + dynamic.attr('name','dynamic'); + dynamic.attr('class','dynamic'); + elm.append(dynamic); + + $compile(elm)(scope); + })); + + function getDynamicInput() { + return $('.dynamic',elm).last(); + } + function getInput(type) { + return $('.'+type); + } + + it('should change a type property of input tag witout errors', function () { + // Default is text + expect(getDynamicInput().attr('type')).toBe('text'); + + angular.forEach(inputTypes, function(type) { + scope.$apply(function() { + scope.type = type; + }); + expect(getDynamicInput().attr('type')).toBe(type); + }); + }); +}); From 95e0b9fbeec8bd54486cf4893196fd5c13e5b16a Mon Sep 17 00:00:00 2001 From: Mikoto Okumura Date: Tue, 22 Jan 2013 04:13:15 +0900 Subject: [PATCH 2/2] fix(uiInput2) Do not use attr() method for type property --- modules/directives/input2/input2.js | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/modules/directives/input2/input2.js b/modules/directives/input2/input2.js index 2ee4b53..10697eb 100644 --- a/modules/directives/input2/input2.js +++ b/modules/directives/input2/input2.js @@ -10,12 +10,13 @@ angular.module('ui.directives').directive('uiInput2', ['$compile', function($com var clone = (function() { var cursor = iElement; return function(type) { - var input = angular.element(''); + var input = angular.element(''); angular.forEach(iAttrs.$attr, function(v,k) { - input.attr(v, iAttrs[k]); + if (v != 'type') { + input.attr(v, iAttrs[k]); + } }); input.removeAttr('ui-input2'); - input.attr('type', type); cursor.after(input); cursor.remove(); cursor = input;