@angular-wave/angular.ts 0.0.51 → 0.0.53
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/angular-ts.esm.js +2 -2
- package/dist/angular-ts.umd.js +2 -2
- package/package.json +1 -1
- package/src/animations/animate-children-directive.js +19 -99
- package/src/animations/animate-children-directive.md +80 -0
- package/src/animations/animate-css-driver.js +250 -256
- package/src/animations/animate-css.js +646 -875
- package/src/animations/animate-css.md +263 -0
- package/src/animations/animate-js-driver.js +54 -56
- package/src/animations/animate-js.js +303 -306
- package/src/animations/animate-queue.js +707 -716
- package/src/animations/animate-swap.js +30 -119
- package/src/animations/animate-swap.md +88 -0
- package/src/animations/animation.js +3 -3
- package/src/core/animate/animate-css.js +21 -6
- package/src/core/animate/animate-runner.js +147 -145
- package/src/core/animate/animate.js +572 -585
- package/src/core/animate/animate.spec.js +194 -286
- package/src/core/animate/anomate.md +13 -0
- package/src/core/animate/helpers.js +10 -0
- package/src/core/compile/compile.spec.js +5 -6
- package/src/core/core.html +0 -1
- package/src/directive/select/select.js +301 -305
- package/src/public.js +0 -1
- package/src/router/directives/state-directives.js +256 -574
- package/src/router/directives/state-directives.md +435 -0
- package/src/router/directives/view-directive.js +3 -3
- package/src/router/index.js +7 -7
- package/types/animations/animate-children-directive.d.ts +5 -80
- package/types/animations/animate-css-driver.d.ts +11 -0
- package/types/animations/animate-css.d.ts +8 -0
- package/types/animations/animate-js-driver.d.ts +8 -0
- package/types/animations/animate-js.d.ts +12 -0
- package/types/animations/animate-queue.d.ts +19 -0
- package/types/animations/animate-swap.d.ts +5 -89
- package/types/core/animate/animate-css.d.ts +1 -1
- package/types/core/animate/animate-runner.d.ts +32 -0
- package/types/core/animate/animate.d.ts +509 -0
- package/types/core/animate/helpers.d.ts +8 -0
- package/types/directive/select/select.d.ts +79 -0
- package/types/router/directives/state-directives.d.ts +31 -0
- package/src/core/document.spec.js +0 -52
|
@@ -32,347 +32,343 @@ function setOptionSelectedStatus(optionEl, value) {
|
|
|
32
32
|
* {@link ng.ngOptions ngOptions} select element.
|
|
33
33
|
*
|
|
34
34
|
*/
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
self.
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
$element.val(unknownVal);
|
|
73
|
-
};
|
|
35
|
+
SelectController.$inject = ["$element", "$scope"];
|
|
36
|
+
function SelectController($element, $scope) {
|
|
37
|
+
const self = this;
|
|
38
|
+
const optionsMap = new Map();
|
|
39
|
+
|
|
40
|
+
self.selectValueMap = {}; // Keys are the hashed values, values the original values
|
|
41
|
+
|
|
42
|
+
// If the ngModel doesn't get provided then provide a dummy noop version to prevent errors
|
|
43
|
+
self.ngModelCtrl = noopNgModelController;
|
|
44
|
+
self.multiple = false;
|
|
45
|
+
|
|
46
|
+
// The "unknown" option is one that is prepended to the list if the viewValue
|
|
47
|
+
// does not match any of the options. When it is rendered the value of the unknown
|
|
48
|
+
// option is '? XXX ?' where XXX is the hashKey of the value that is not known.
|
|
49
|
+
//
|
|
50
|
+
// Support: IE 9 only
|
|
51
|
+
// We can't just JQLite('<option>') since JQLite is not smart enough
|
|
52
|
+
// to create it in <select> and IE barfs otherwise.
|
|
53
|
+
self.unknownOption = JQLite(window.document.createElement("option"));
|
|
54
|
+
|
|
55
|
+
// The empty option is an option with the value '' that the application developer can
|
|
56
|
+
// provide inside the select. It is always selectable and indicates that a "null" selection has
|
|
57
|
+
// been made by the user.
|
|
58
|
+
// If the select has an empty option, and the model of the select is set to "undefined" or "null",
|
|
59
|
+
// the empty option is selected.
|
|
60
|
+
// If the model is set to a different unmatched value, the unknown option is rendered and
|
|
61
|
+
// selected, i.e both are present, because a "null" selection and an unknown value are different.
|
|
62
|
+
self.hasEmptyOption = false;
|
|
63
|
+
self.emptyOption = undefined;
|
|
64
|
+
|
|
65
|
+
self.renderUnknownOption = function (val) {
|
|
66
|
+
const unknownVal = self.generateUnknownOptionValue(val);
|
|
67
|
+
self.unknownOption.val(unknownVal);
|
|
68
|
+
$element.prepend(self.unknownOption);
|
|
69
|
+
setOptionSelectedStatus(self.unknownOption, true);
|
|
70
|
+
$element.val(unknownVal);
|
|
71
|
+
};
|
|
74
72
|
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
73
|
+
self.updateUnknownOption = function (val) {
|
|
74
|
+
const unknownVal = self.generateUnknownOptionValue(val);
|
|
75
|
+
self.unknownOption.val(unknownVal);
|
|
76
|
+
setOptionSelectedStatus(self.unknownOption, true);
|
|
77
|
+
$element.val(unknownVal);
|
|
78
|
+
};
|
|
81
79
|
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
80
|
+
self.generateUnknownOptionValue = function (val) {
|
|
81
|
+
return `? ${hashKey(val)} ?`;
|
|
82
|
+
};
|
|
85
83
|
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
84
|
+
self.removeUnknownOption = function () {
|
|
85
|
+
if (self.unknownOption.parent()) self.unknownOption.remove();
|
|
86
|
+
};
|
|
89
87
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
88
|
+
self.selectEmptyOption = function () {
|
|
89
|
+
if (self.emptyOption) {
|
|
90
|
+
$element.val("");
|
|
91
|
+
setOptionSelectedStatus(self.emptyOption, true);
|
|
92
|
+
}
|
|
93
|
+
};
|
|
96
94
|
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
95
|
+
self.unselectEmptyOption = function () {
|
|
96
|
+
if (self.hasEmptyOption) {
|
|
97
|
+
setOptionSelectedStatus(self.emptyOption, false);
|
|
98
|
+
}
|
|
99
|
+
};
|
|
102
100
|
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
101
|
+
$scope.$on("$destroy", () => {
|
|
102
|
+
// disable unknown option so that we don't do work when the whole select is being destroyed
|
|
103
|
+
self.renderUnknownOption = () => {};
|
|
104
|
+
});
|
|
107
105
|
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
val in self.selectValueMap ? self.selectValueMap[val] : val;
|
|
106
|
+
// Read the value of the select control, the implementation of this changes depending
|
|
107
|
+
// upon whether the select can have multiple values and whether ngOptions is at work.
|
|
108
|
+
self.readValue = function readSingleValue() {
|
|
109
|
+
const val = $element.val();
|
|
110
|
+
// ngValue added option values are stored in the selectValueMap, normal interpolations are not
|
|
111
|
+
const realVal = val in self.selectValueMap ? self.selectValueMap[val] : val;
|
|
115
112
|
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
113
|
+
if (self.hasOption(realVal)) {
|
|
114
|
+
return realVal;
|
|
115
|
+
}
|
|
119
116
|
|
|
120
|
-
|
|
121
|
-
|
|
117
|
+
return null;
|
|
118
|
+
};
|
|
122
119
|
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
120
|
+
// Write the value to the select control, the implementation of this changes depending
|
|
121
|
+
// upon whether the select can have multiple values and whether ngOptions is at work.
|
|
122
|
+
self.writeValue = function writeSingleValue(value) {
|
|
123
|
+
// Make sure to remove the selected attribute from the previously selected option
|
|
124
|
+
// Otherwise, screen readers might get confused
|
|
125
|
+
const currentlySelectedOption =
|
|
126
|
+
$element[0].options[$element[0].selectedIndex];
|
|
127
|
+
if (currentlySelectedOption)
|
|
128
|
+
setOptionSelectedStatus(JQLite(currentlySelectedOption), false);
|
|
129
|
+
|
|
130
|
+
if (self.hasOption(value)) {
|
|
131
|
+
self.removeUnknownOption();
|
|
132
|
+
|
|
133
|
+
const hashedVal = hashKey(value);
|
|
134
|
+
$element.val(hashedVal in self.selectValueMap ? hashedVal : value);
|
|
135
|
+
|
|
136
|
+
// Set selected attribute and property on selected option for screen readers
|
|
137
|
+
const selectedOption = $element[0].options[$element[0].selectedIndex];
|
|
138
|
+
setOptionSelectedStatus(JQLite(selectedOption), true);
|
|
139
|
+
} else {
|
|
140
|
+
self.selectUnknownOrEmptyOption(value);
|
|
141
|
+
}
|
|
142
|
+
};
|
|
146
143
|
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
144
|
+
// Tell the select control that an option, with the given value, has been added
|
|
145
|
+
self.addOption = function (value, element) {
|
|
146
|
+
// Skip comment nodes, as they only pollute the `optionsMap`
|
|
147
|
+
if (element[0].nodeType === Node.COMMENT_NODE) return;
|
|
151
148
|
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
149
|
+
assertNotHasOwnProperty(value, '"option value"');
|
|
150
|
+
if (value === "") {
|
|
151
|
+
self.hasEmptyOption = true;
|
|
152
|
+
self.emptyOption = element;
|
|
153
|
+
}
|
|
154
|
+
const count = optionsMap.get(value) || 0;
|
|
155
|
+
optionsMap.set(value, count + 1);
|
|
156
|
+
// Only render at the end of a digest. This improves render performance when many options
|
|
157
|
+
// are added during a digest and ensures all relevant options are correctly marked as selected
|
|
158
|
+
scheduleRender();
|
|
159
|
+
};
|
|
163
160
|
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
}
|
|
174
|
-
} else {
|
|
175
|
-
optionsMap.set(value, count - 1);
|
|
161
|
+
// Tell the select control that an option, with the given value, has been removed
|
|
162
|
+
self.removeOption = function (value) {
|
|
163
|
+
const count = optionsMap.get(value);
|
|
164
|
+
if (count) {
|
|
165
|
+
if (count === 1) {
|
|
166
|
+
optionsMap.delete(value);
|
|
167
|
+
if (value === "") {
|
|
168
|
+
self.hasEmptyOption = false;
|
|
169
|
+
self.emptyOption = undefined;
|
|
176
170
|
}
|
|
171
|
+
} else {
|
|
172
|
+
optionsMap.set(value, count - 1);
|
|
177
173
|
}
|
|
178
|
-
}
|
|
179
|
-
|
|
180
|
-
// Check whether the select control has an option matching the given value
|
|
181
|
-
self.hasOption = function (value) {
|
|
182
|
-
return !!optionsMap.get(value);
|
|
183
|
-
};
|
|
174
|
+
}
|
|
175
|
+
};
|
|
184
176
|
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
* @description
|
|
190
|
-
*
|
|
191
|
-
* Returns `true` if the select element currently has an empty option
|
|
192
|
-
* element, i.e. an option that signifies that the select is empty / the selection is null.
|
|
193
|
-
*
|
|
194
|
-
*/
|
|
195
|
-
self.$hasEmptyOption = function () {
|
|
196
|
-
return self.hasEmptyOption;
|
|
197
|
-
};
|
|
177
|
+
// Check whether the select control has an option matching the given value
|
|
178
|
+
self.hasOption = function (value) {
|
|
179
|
+
return !!optionsMap.get(value);
|
|
180
|
+
};
|
|
198
181
|
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
};
|
|
182
|
+
/**
|
|
183
|
+
* @ngdoc method
|
|
184
|
+
* @name select.SelectController#$hasEmptyOption
|
|
185
|
+
*
|
|
186
|
+
* @description
|
|
187
|
+
*
|
|
188
|
+
* Returns `true` if the select element currently has an empty option
|
|
189
|
+
* element, i.e. an option that signifies that the select is empty / the selection is null.
|
|
190
|
+
*
|
|
191
|
+
*/
|
|
192
|
+
self.$hasEmptyOption = function () {
|
|
193
|
+
return self.hasEmptyOption;
|
|
194
|
+
};
|
|
213
195
|
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
);
|
|
229
|
-
};
|
|
196
|
+
/**
|
|
197
|
+
* @ngdoc method
|
|
198
|
+
* @name select.SelectController#$isUnknownOptionSelected
|
|
199
|
+
*
|
|
200
|
+
* @description
|
|
201
|
+
*
|
|
202
|
+
* Returns `true` if the select element's unknown option is selected. The unknown option is added
|
|
203
|
+
* and automatically selected whenever the select model doesn't match any option.
|
|
204
|
+
*
|
|
205
|
+
*/
|
|
206
|
+
self.$isUnknownOptionSelected = function () {
|
|
207
|
+
// Presence of the unknown option means it is selected
|
|
208
|
+
return $element[0].options[0] === self.unknownOption[0];
|
|
209
|
+
};
|
|
230
210
|
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
211
|
+
/**
|
|
212
|
+
* @ngdoc method
|
|
213
|
+
* @name select.SelectController#$isEmptyOptionSelected
|
|
214
|
+
*
|
|
215
|
+
* @description
|
|
216
|
+
*
|
|
217
|
+
* Returns `true` if the select element has an empty option and this empty option is currently
|
|
218
|
+
* selected. Returns `false` if the select element has no empty option or it is not selected.
|
|
219
|
+
*
|
|
220
|
+
*/
|
|
221
|
+
self.$isEmptyOptionSelected = function () {
|
|
222
|
+
return (
|
|
223
|
+
self.hasEmptyOption &&
|
|
224
|
+
$element[0].options[$element[0].selectedIndex] === self.emptyOption[0]
|
|
225
|
+
);
|
|
226
|
+
};
|
|
241
227
|
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
228
|
+
self.selectUnknownOrEmptyOption = function (value) {
|
|
229
|
+
if (value == null && self.emptyOption) {
|
|
230
|
+
self.removeUnknownOption();
|
|
231
|
+
self.selectEmptyOption();
|
|
232
|
+
} else if (self.unknownOption.parent().length) {
|
|
233
|
+
self.updateUnknownOption(value);
|
|
234
|
+
} else {
|
|
235
|
+
self.renderUnknownOption(value);
|
|
250
236
|
}
|
|
237
|
+
};
|
|
251
238
|
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
239
|
+
let renderScheduled = false;
|
|
240
|
+
function scheduleRender() {
|
|
241
|
+
if (renderScheduled) return;
|
|
242
|
+
renderScheduled = true;
|
|
243
|
+
$scope.$$postDigest(() => {
|
|
244
|
+
renderScheduled = false;
|
|
245
|
+
self.ngModelCtrl.$render();
|
|
246
|
+
});
|
|
247
|
+
}
|
|
257
248
|
|
|
258
|
-
|
|
259
|
-
|
|
249
|
+
let updateScheduled = false;
|
|
250
|
+
function scheduleViewValueUpdate(renderAfter) {
|
|
251
|
+
if (updateScheduled) return;
|
|
260
252
|
|
|
261
|
-
|
|
262
|
-
self.ngModelCtrl.$setViewValue(self.readValue());
|
|
263
|
-
if (renderAfter) self.ngModelCtrl.$render();
|
|
264
|
-
});
|
|
265
|
-
}
|
|
253
|
+
updateScheduled = true;
|
|
266
254
|
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
optionElement,
|
|
270
|
-
optionAttrs,
|
|
271
|
-
interpolateValueFn,
|
|
272
|
-
interpolateTextFn,
|
|
273
|
-
) {
|
|
274
|
-
let oldVal;
|
|
275
|
-
let hashedVal;
|
|
276
|
-
if (optionAttrs.$attr.ngValue) {
|
|
277
|
-
// The value attribute is set by ngValue
|
|
278
|
-
|
|
279
|
-
optionAttrs.$observe("value", (newVal) => {
|
|
280
|
-
let removal;
|
|
281
|
-
const previouslySelected = optionElement[0].selected;
|
|
282
|
-
|
|
283
|
-
if (isDefined(hashedVal)) {
|
|
284
|
-
self.removeOption(oldVal);
|
|
285
|
-
delete self.selectValueMap[hashedVal];
|
|
286
|
-
removal = true;
|
|
287
|
-
}
|
|
255
|
+
$scope.$$postDigest(() => {
|
|
256
|
+
if ($scope.$$destroyed) return;
|
|
288
257
|
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
// from firing a second time. Other $observers on value will also get the result of the
|
|
295
|
-
// ngValue expression, not the hashed value
|
|
296
|
-
optionElement.attr("value", hashedVal);
|
|
297
|
-
|
|
298
|
-
if (removal && previouslySelected) {
|
|
299
|
-
scheduleViewValueUpdate();
|
|
300
|
-
}
|
|
301
|
-
});
|
|
302
|
-
} else if (interpolateValueFn) {
|
|
303
|
-
// The value attribute is interpolated
|
|
304
|
-
optionAttrs.$observe("value", (newVal) => {
|
|
305
|
-
// This method is overwritten in ngOptions and has side-effects!
|
|
306
|
-
self.readValue();
|
|
307
|
-
|
|
308
|
-
let removal;
|
|
309
|
-
const previouslySelected = optionElement[0].selected;
|
|
310
|
-
|
|
311
|
-
if (isDefined(oldVal)) {
|
|
312
|
-
self.removeOption(oldVal);
|
|
313
|
-
removal = true;
|
|
314
|
-
}
|
|
315
|
-
oldVal = newVal;
|
|
316
|
-
self.addOption(newVal, optionElement);
|
|
317
|
-
|
|
318
|
-
if (removal && previouslySelected) {
|
|
319
|
-
scheduleViewValueUpdate();
|
|
320
|
-
}
|
|
321
|
-
});
|
|
322
|
-
} else if (interpolateTextFn) {
|
|
323
|
-
// The text content is interpolated
|
|
324
|
-
optionScope.$watch(interpolateTextFn, (newVal, oldVal) => {
|
|
325
|
-
optionAttrs.$set("value", newVal);
|
|
326
|
-
const previouslySelected = optionElement[0].selected;
|
|
327
|
-
if (oldVal !== newVal) {
|
|
328
|
-
self.removeOption(oldVal);
|
|
329
|
-
}
|
|
330
|
-
self.addOption(newVal, optionElement);
|
|
258
|
+
updateScheduled = false;
|
|
259
|
+
self.ngModelCtrl.$setViewValue(self.readValue());
|
|
260
|
+
if (renderAfter) self.ngModelCtrl.$render();
|
|
261
|
+
});
|
|
262
|
+
}
|
|
331
263
|
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
264
|
+
self.registerOption = function (
|
|
265
|
+
optionScope,
|
|
266
|
+
optionElement,
|
|
267
|
+
optionAttrs,
|
|
268
|
+
interpolateValueFn,
|
|
269
|
+
interpolateTextFn,
|
|
270
|
+
) {
|
|
271
|
+
let oldVal;
|
|
272
|
+
let hashedVal;
|
|
273
|
+
if (optionAttrs.$attr.ngValue) {
|
|
274
|
+
// The value attribute is set by ngValue
|
|
275
|
+
|
|
276
|
+
optionAttrs.$observe("value", (newVal) => {
|
|
277
|
+
let removal;
|
|
278
|
+
const previouslySelected = optionElement[0].selected;
|
|
279
|
+
|
|
280
|
+
if (isDefined(hashedVal)) {
|
|
281
|
+
self.removeOption(oldVal);
|
|
282
|
+
delete self.selectValueMap[hashedVal];
|
|
283
|
+
removal = true;
|
|
284
|
+
}
|
|
340
285
|
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
286
|
+
hashedVal = hashKey(newVal);
|
|
287
|
+
oldVal = newVal;
|
|
288
|
+
self.selectValueMap[hashedVal] = newVal;
|
|
289
|
+
self.addOption(newVal, optionElement);
|
|
290
|
+
// Set the attribute directly instead of using optionAttrs.$set - this stops the observer
|
|
291
|
+
// from firing a second time. Other $observers on value will also get the result of the
|
|
292
|
+
// ngValue expression, not the hashed value
|
|
293
|
+
optionElement.attr("value", hashedVal);
|
|
294
|
+
|
|
295
|
+
if (removal && previouslySelected) {
|
|
296
|
+
scheduleViewValueUpdate();
|
|
297
|
+
}
|
|
298
|
+
});
|
|
299
|
+
} else if (interpolateValueFn) {
|
|
300
|
+
// The value attribute is interpolated
|
|
301
|
+
optionAttrs.$observe("value", (newVal) => {
|
|
302
|
+
// This method is overwritten in ngOptions and has side-effects!
|
|
303
|
+
self.readValue();
|
|
304
|
+
|
|
305
|
+
let removal;
|
|
306
|
+
const previouslySelected = optionElement[0].selected;
|
|
307
|
+
|
|
308
|
+
if (isDefined(oldVal)) {
|
|
309
|
+
self.removeOption(oldVal);
|
|
310
|
+
removal = true;
|
|
311
|
+
}
|
|
312
|
+
oldVal = newVal;
|
|
313
|
+
self.addOption(newVal, optionElement);
|
|
344
314
|
|
|
345
|
-
if (
|
|
346
|
-
|
|
347
|
-
scheduleViewValueUpdate(true);
|
|
348
|
-
} else {
|
|
349
|
-
self.ngModelCtrl.$setViewValue(null);
|
|
350
|
-
self.ngModelCtrl.$render();
|
|
351
|
-
}
|
|
315
|
+
if (removal && previouslySelected) {
|
|
316
|
+
scheduleViewValueUpdate();
|
|
352
317
|
}
|
|
353
318
|
});
|
|
319
|
+
} else if (interpolateTextFn) {
|
|
320
|
+
// The text content is interpolated
|
|
321
|
+
optionScope.$watch(interpolateTextFn, (newVal, oldVal) => {
|
|
322
|
+
optionAttrs.$set("value", newVal);
|
|
323
|
+
const previouslySelected = optionElement[0].selected;
|
|
324
|
+
if (oldVal !== newVal) {
|
|
325
|
+
self.removeOption(oldVal);
|
|
326
|
+
}
|
|
327
|
+
self.addOption(newVal, optionElement);
|
|
354
328
|
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
329
|
+
if (oldVal && previouslySelected) {
|
|
330
|
+
scheduleViewValueUpdate();
|
|
331
|
+
}
|
|
332
|
+
});
|
|
333
|
+
} else {
|
|
334
|
+
// The value attribute is static
|
|
335
|
+
self.addOption(optionAttrs.value, optionElement);
|
|
336
|
+
}
|
|
358
337
|
|
|
359
|
-
|
|
360
|
-
|
|
338
|
+
optionAttrs.$observe("disabled", (newVal) => {
|
|
339
|
+
// Since model updates will also select disabled options (like ngOptions),
|
|
340
|
+
// we only have to handle options becoming disabled, not enabled
|
|
361
341
|
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
currentValue &&
|
|
365
|
-
currentValue.indexOf(removeValue) !== -1) ||
|
|
366
|
-
currentValue === removeValue
|
|
367
|
-
) {
|
|
368
|
-
// When multiple (selected) options are destroyed at the same time, we don't want
|
|
369
|
-
// to run a model update for each of them. Instead, run a single update in the $$postDigest
|
|
342
|
+
if (newVal === "true" || (newVal && optionElement[0].selected)) {
|
|
343
|
+
if (self.multiple) {
|
|
370
344
|
scheduleViewValueUpdate(true);
|
|
345
|
+
} else {
|
|
346
|
+
self.ngModelCtrl.$setViewValue(null);
|
|
347
|
+
self.ngModelCtrl.$render();
|
|
371
348
|
}
|
|
372
|
-
}
|
|
373
|
-
};
|
|
374
|
-
|
|
375
|
-
|
|
349
|
+
}
|
|
350
|
+
});
|
|
351
|
+
|
|
352
|
+
optionElement.on("$destroy", () => {
|
|
353
|
+
const currentValue = self.readValue();
|
|
354
|
+
const removeValue = optionAttrs.value;
|
|
355
|
+
|
|
356
|
+
self.removeOption(removeValue);
|
|
357
|
+
scheduleRender();
|
|
358
|
+
|
|
359
|
+
if (
|
|
360
|
+
(self.multiple &&
|
|
361
|
+
currentValue &&
|
|
362
|
+
currentValue.indexOf(removeValue) !== -1) ||
|
|
363
|
+
currentValue === removeValue
|
|
364
|
+
) {
|
|
365
|
+
// When multiple (selected) options are destroyed at the same time, we don't want
|
|
366
|
+
// to run a model update for each of them. Instead, run a single update in the $$postDigest
|
|
367
|
+
scheduleViewValueUpdate(true);
|
|
368
|
+
}
|
|
369
|
+
});
|
|
370
|
+
};
|
|
371
|
+
}
|
|
376
372
|
|
|
377
373
|
/**
|
|
378
374
|
* @ngdoc directive
|
package/src/public.js
CHANGED
|
@@ -185,7 +185,6 @@ export function publishExternalAPI() {
|
|
|
185
185
|
$cacheFactory: CacheFactoryProvider,
|
|
186
186
|
$controller: $ControllerProvider,
|
|
187
187
|
$document: $DocumentProvider,
|
|
188
|
-
$$isDocumentHidden: $$IsDocumentHiddenProvider,
|
|
189
188
|
$exceptionHandler: $ExceptionHandlerProvider,
|
|
190
189
|
$filter: $FilterProvider,
|
|
191
190
|
$interpolate: $InterpolateProvider,
|