Skip to content
This repository was archived by the owner on Jul 5, 2023. It is now read-only.

Commit 6b92ec2

Browse files
committed
Release v1.0.3.
The release includes a bug fix for the ngInclude issue (issue #7).
1 parent 3f1cbbb commit 6b92ec2

File tree

2 files changed

+90
-27
lines changed

2 files changed

+90
-27
lines changed

scalyr.js

Lines changed: 89 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/**
2-
* @license scalyr v1.0.2
2+
* @license scalyr v1.0.3
33
* (c) 2013 Scalyr, Inc. http://scalyr.com
44
* License: MIT
55
*/
@@ -352,9 +352,10 @@ function defineScalyrAngularModule(moduleName, dependencies) {
352352
*
353353
* slyEvaluateOnlyWhen: A directive that prevents updating / evaluating
354354
* all bindings for the current element and its children unless
355-
* the expression has changed values. It currently assumes the
355+
* the expression has changed values. If new children are added, they
356+
* are always evaluated at least once. It currently assumes the
356357
* expression evaluates to an object and detects changes only by
357-
* a change in object reference.
358+
* a change in object reference.
358359
*
359360
* slyAlwaysEvaluate: Can only be used in conjunction with the
360361
* slyEvaluateOnlyWhen directive. This directive will ensure that
@@ -419,7 +420,7 @@ defineScalyrAngularModule('slyEvaluate', ['gatedScope'])
419420
// be gated.
420421
return isNull(alwaysEvaluateString) ||
421422
!(isStringNonempty(watchExpression) && (watchExpression.indexOf(alwaysEvaluateString) >= 0));
422-
});
423+
}, true /* Evaluate any newly added watchers when they are added */);
423424
},
424425
};
425426
},
@@ -755,6 +756,7 @@ defineScalyrAngularModule('gatedScope', [])
755756
result.$$parentGatingFunction = this.$$gatingFunction;
756757
result.$$shouldGateFunction = this.$$shouldGateFunction;
757758
result.$$gatedWatchers = [];
759+
result.$$cleanUpQueue = this.$$cleanUpQueue;
758760

759761
return result;
760762
};
@@ -786,6 +788,14 @@ defineScalyrAngularModule('gatedScope', [])
786788
if (watch.gatingFunction !== targetGatingFunction)
787789
continue;
788790

791+
// Since we are about to execute the watcher as part of a digestGated
792+
// call, we can remove it from the normal digest queue if it was placed
793+
// there because the watcher was added after the gate function's first
794+
// evaluation.
795+
if (watch && !isNull(watch.cleanUp)) {
796+
watch.cleanUp();
797+
watch.cleanUp = null;
798+
}
789799
// Most common watches are on primitives, in which case we can short
790800
// circuit it with === operator, only when === fails do we use .equals
791801
if (watch && (value = watch.get(current)) !== (last = watch.last) &&
@@ -820,6 +830,8 @@ defineScalyrAngularModule('gatedScope', [])
820830
}
821831
} while ((current = next));
822832

833+
// Mark that this gating function has digested all children.
834+
targetGatingFunction.hasDigested = true;
823835
return dirty;
824836
};
825837

@@ -844,11 +856,38 @@ defineScalyrAngularModule('gatedScope', [])
844856
var result = scopePrototype.$watch.call(this, watchExpression, listener, objectEquality);
845857
this.$$watchers = tmp;
846858
this.$$gatedWatchers[0].gatingFunction = this.$$gatingFunction;
859+
this.$$gatedWatchers[0].cleanUp = null;
847860

848861
// We know that the last field of the watcher object will be set to initWatchVal, so we
849862
// grab it here.
850863
initWatchVal = this.$$gatedWatchers[0].last;
864+
var watch = this.$$gatedWatchers[0];
865+
866+
// We should make sure the watch expression gets evaluated fully on at least one
867+
// digest cycle even if the gate function is now closed if requested by the gating function's
868+
// value for shouldEvalNewWatchers. We do this by adding in normal watcher that will execute
869+
// the watcher we just added and remove itself after the digest cycle completes.
870+
if (this.$$gatingFunction.shouldEvalNewWatchers && this.$$gatingFunction.hasDigested) {
871+
var self = this;
872+
watch.cleanUp = scopePrototype.$watch.call(self, function() {
873+
if (!isNull(watch.cleanUp)) {
874+
self.$$cleanUpQueue.unshift(watch.cleanUp);
875+
watch.cleanUp = null;
876+
}
877+
var value;
878+
var last = initWatchVal;
851879

880+
if (watch && (value = watch.get(self)) !== (last = watch.last) &&
881+
!(watch.eq
882+
? areEqual(value, last)
883+
: (typeof value == 'number' && typeof last == 'number'
884+
&& isNaN(value) && isNaN(last)))) {
885+
watch.last = watch.eq ? copy(value) : value;
886+
watch.fn(value, ((last === initWatchVal) ? value : last), self);
887+
}
888+
return watch.last;
889+
});
890+
}
852891
return result;
853892
} else {
854893
return scopePrototype.$watch.call(this, watchExpression, listener, objectEquality);
@@ -871,8 +910,8 @@ defineScalyrAngularModule('gatedScope', [])
871910
// functions and should be evaluated at all. However, if a caller is invoking
872911
// $digest on a particular scope, we assume the caller is doing that because it
873912
// knows the watchers should be evaluated.
913+
var dirty = false;
874914
if (!isNull(this.$$parentGatingFunction) && this.$$parentGatingFunction()) {
875-
var dirty = false;
876915
var ttl = 5;
877916
do {
878917
dirty = this.$digestGated(this.$$parentGatingFunction);
@@ -884,7 +923,19 @@ defineScalyrAngularModule('gatedScope', [])
884923
}
885924
} while (dirty);
886925
}
887-
return scopePrototype.$digest.call(this) || dirty;
926+
927+
dirty = scopePrototype.$digest.call(this) || dirty;
928+
929+
var cleanUpQueue = this.$$cleanUpQueue;
930+
931+
while (cleanUpQueue.length)
932+
try {
933+
cleanUpQueue.shift()();
934+
} catch (e) {
935+
$exceptionHandler(e);
936+
}
937+
938+
return dirty;
888939
}
889940

890941
/**
@@ -901,8 +952,13 @@ defineScalyrAngularModule('gatedScope', [])
901952
* a new watcher will be gated using gatingFunction. It is evaluated with the
902953
* arguments to $watch and should return true if the watcher created by those
903954
* arguments should be gated
955+
* @param {Boolean} shouldEvalNewWatchers If true, if a watcher is added
956+
* after the gating function has returned true on a previous digest cycle, the
957+
* the new watcher will be evaluated on the next digest cycle even if the
958+
* gating function is currently return false.
904959
*/
905-
methodsToAdd.$addWatcherGate = function(gatingFunction, shouldGateFunction) {
960+
methodsToAdd.$addWatcherGate = function(gatingFunction, shouldGateFunction,
961+
shouldEvalNewWatchers) {
906962
var changeCount = 0;
907963
var self = this;
908964

@@ -918,30 +974,36 @@ defineScalyrAngularModule('gatedScope', [])
918974
// true (which we can tell if the watcher we register here is evaluated), then
919975
// we always evaluate our watcher until our gating function returns true.
920976
var hasNestedGates = !isNull(this.$$gatingFunction);
921-
var promotedWatcher = null;
922-
923-
this.$watch(function() {
924-
if (gatingFunction()) {
925-
if (self.$digestGated(gatingFunction))
926-
++changeCount;
927-
} else if (hasNestedGates && isNull(promotedWatcher)) {
928-
promotedWatcher = scopePrototype.$watch.call(self, function() {
929-
if (gatingFunction()) {
930-
promotedWatcher();
931-
promotedWatcher = null;
932-
if (self.$digestGated(gatingFunction))
933-
++changeCount;
934-
}
935-
return changeCount;
936-
});
937-
}
938-
return changeCount;
939-
});
977+
978+
(function() {
979+
var promotedWatcher = null;
980+
981+
self.$watch(function() {
982+
if (gatingFunction()) {
983+
if (self.$digestGated(gatingFunction))
984+
++changeCount;
985+
} else if (hasNestedGates && isNull(promotedWatcher)) {
986+
promotedWatcher = scopePrototype.$watch.call(self, function() {
987+
if (gatingFunction()) {
988+
promotedWatcher();
989+
promotedWatcher = null;
990+
if (self.$digestGated(gatingFunction))
991+
++changeCount;
992+
}
993+
return changeCount;
994+
});
995+
}
996+
return changeCount;
997+
});
998+
})();
940999

9411000

9421001
if (isUndefined(shouldGateFunction))
9431002
shouldGateFunction = null;
1003+
if (isUndefined(shouldEvalNewWatchers))
1004+
shouldEvalNewWatchers = false;
9441005
this.$$gatingFunction = gatingFunction;
1006+
this.$$gatingFunction.shouldEvalNewWatchers = shouldEvalNewWatchers;
9451007
this.$$shouldGateFunction = shouldGateFunction;
9461008
};
9471009

@@ -957,6 +1019,7 @@ defineScalyrAngularModule('gatedScope', [])
9571019
$rootScope.$$parentGatingFunction = null;
9581020
$rootScope.$$shouldGateFunction = null;
9591021
$rootScope.$$gatedWatchers = [];
1022+
$rootScope.$$cleanUpQueue = [];
9601023

9611024
return $rootScope;
9621025
}]);

scripts/includeFiles/header.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/**
2-
* @license scalyr v1.0.2
2+
* @license scalyr v1.0.3
33
* (c) 2013 Scalyr, Inc. http://scalyr.com
44
* License: MIT
55
*/

0 commit comments

Comments
 (0)