@@ -37,24 +37,34 @@ angular.module('ui.bootstrap.typeahead', ['ui.bootstrap.position'])
37
37
require :'ngModel' ,
38
38
link :function ( originalScope , element , attrs , modelCtrl ) {
39
39
40
- var $setModelValue = $parse ( attrs . ngModel ) . assign ;
40
+ //SUPPORTED ATTRIBUTES (OPTIONS)
41
41
42
42
//minimal no of characters that needs to be entered before typeahead kicks-in
43
43
var minSearch = originalScope . $eval ( attrs . typeaheadMinLength ) || 1 ;
44
44
45
45
//minimal wait time after last character typed before typehead kicks-in
46
46
var waitTime = originalScope . $eval ( attrs . typeaheadWaitMs ) || 0 ;
47
47
48
- //expressions used by typeahead
49
- var parserResult = typeaheadParser . parse ( attrs . typeahead ) ;
50
-
51
48
//should it restrict model values to the ones selected from the popup only?
52
49
var isEditable = originalScope . $eval ( attrs . typeaheadEditable ) !== false ;
53
50
51
+ //binding to a variable that indicates if matches are being retrieved asynchronously
54
52
var isLoadingSetter = $parse ( attrs . typeaheadLoading ) . assign || angular . noop ;
55
53
54
+ //a callback executed when a match is selected
56
55
var onSelectCallback = $parse ( attrs . typeaheadOnSelect ) ;
57
56
57
+ var inputFormatter = attrs . typeaheadInputFormatter ? $parse ( attrs . typeaheadInputFormatter ) : undefined ;
58
+
59
+ //INTERNAL VARIABLES
60
+
61
+ //model setter executed upon match selection
62
+ var $setModelValue = $parse ( attrs . ngModel ) . assign ;
63
+
64
+ //expressions used by typeahead
65
+ var parserResult = typeaheadParser . parse ( attrs . typeahead ) ;
66
+
67
+
58
68
//pop-up element used to display matches
59
69
var popUpEl = angular . element ( '<typeahead-popup></typeahead-popup>' ) ;
60
70
popUpEl . attr ( {
@@ -147,16 +157,25 @@ angular.module('ui.bootstrap.typeahead', ['ui.bootstrap.position'])
147
157
} ) ;
148
158
149
159
modelCtrl . $formatters . push ( function ( modelValue ) {
160
+
150
161
var candidateViewValue , emptyViewValue ;
151
162
var locals = { } ;
152
- locals [ parserResult . itemName ] = modelValue ;
153
163
154
- //it might happen that we don't have enough info to properly render input value
155
- //we need to check for this
156
- candidateViewValue = parserResult . viewMapper ( originalScope , locals ) ;
157
- emptyViewValue = parserResult . viewMapper ( originalScope , { } ) ;
164
+ if ( inputFormatter ) {
158
165
159
- return candidateViewValue !== emptyViewValue ? candidateViewValue : modelValue ;
166
+ locals [ '$model' ] = modelValue ;
167
+ return inputFormatter ( originalScope , locals ) ;
168
+
169
+ } else {
170
+ locals [ parserResult . itemName ] = modelValue ;
171
+
172
+ //it might happen that we don't have enough info to properly render input value
173
+ //we need to check for this situation and simply return model value if we can't apply custom formatting
174
+ candidateViewValue = parserResult . viewMapper ( originalScope , locals ) ;
175
+ emptyViewValue = parserResult . viewMapper ( originalScope , { } ) ;
176
+
177
+ return candidateViewValue !== emptyViewValue ? candidateViewValue : modelValue ;
178
+ }
160
179
} ) ;
161
180
162
181
scope . select = function ( activeIdx ) {
0 commit comments