Skip to content
This repository has been archived by the owner on May 29, 2019. It is now read-only.

fix(typeahead): add support for ngModelOptions getterSetter #3865

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions src/typeahead/test/typeahead.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -709,6 +709,19 @@ describe('typeahead tests', function () {

expect($scope.test.typeahead.$error.parse).toBeUndefined();
});

it('issue #3823 - should support ng-model-options getterSetter', function () {
function resultSetter(state) {
return state;
}
$scope.result = resultSetter;
var element = prepareInputEl('<div><input name="typeahead" ng-model="result" ng-model-options="{getterSetter: true}" typeahead="state as state.name for state in states | filter:$viewValue" typeahead-editable="false"></div>');

changeInputValueTo(element, 'Alaska');
triggerKeyDown(element, 13);

expect($scope.result).toBe(resultSetter);
});
});

describe('input formatting', function () {
Expand Down
18 changes: 14 additions & 4 deletions src/typeahead/typeahead.js
Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,10 @@ angular.module('ui.bootstrap.typeahead', ['ui.bootstrap.position', 'ui.bootstrap
var HOT_KEYS = [9, 13, 27, 38, 40];

return {
require:'ngModel',
link:function (originalScope, element, attrs, modelCtrl) {

require:['ngModel', '^?ngModelOptions'],
link:function (originalScope, element, attrs, ctrls) {
var modelCtrl = ctrls[0];
var ngModelOptions = ctrls[1];
//SUPPORTED ATTRIBUTES (OPTIONS)

//minimal no of characters that needs to be entered before typeahead kicks-in
Expand Down Expand Up @@ -67,7 +68,16 @@ angular.module('ui.bootstrap.typeahead', ['ui.bootstrap.position', 'ui.bootstrap
//INTERNAL VARIABLES

//model setter executed upon match selection
var $setModelValue = $parse(attrs.ngModel).assign;
var parsedModel = $parse(attrs.ngModel);
var invokeModelSetter = $parse(attrs.ngModel + '($$$p)');
var $setModelValue = function(scope, newValue) {
if (angular.isFunction(parsedModel(originalScope)) &&
ngModelOptions && ngModelOptions.$options && ngModelOptions.$options.getterSetter) {
return invokeModelSetter(scope, {$$$p: newValue});
} else {
return parsedModel.assign(scope, newValue);
}
};

//expressions used by typeahead
var parserResult = typeaheadParser.parse(attrs.typeahead);
Expand Down