Der folgende einfache HTML-Code veranschaulicht das Problem:
<!DOCTYPE html>
<html>
<head>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.16/angular.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.16/angular-route.js"></script>
<script>
angular.module('fail', ['ngRoute'])
.config(function($routeProvider) {
$routeProvider
.when('/a', {
template: '<a ng-href="#/b">a</a>'
})
.when('/b', {
template: '<a ng-href="#/a">b</a>'
})
.otherwise({
redirectTo: '/a'
});
});
</script>
</head>
<body ng-app="fail">
<div ng-view></div>
</body>
</html>
Dies wird auf den meisten Geräten wie erwartet ausgeführt, löst jedoch unter iOS 9 eine unendliche Digest-Ausnahme aus.
Ich kann sowohl auf dem iPad Air 2 als auch auf dem iPad der 4. Generation mit iOS 9 Beta 2 reproduzieren.
Mir ist klar, dass es wahrscheinlich ein Problem in iOS ist, aber es könnte sich dennoch lohnen, es zu untersuchen.
Ich habe ein ähnliches Problem festgestellt, das unter iOS 9 aufgetreten ist, aber auf anderen Geräten funktioniert.
Ich habe dieses Problem mit dem gleichen Code reproduziert, der von santaslow auf 1.4.1 / ios 9 bereitgestellt wurde:
<!DOCTYPE html>
<html>
<head>
<script src="../static/js/angular/angular.1.4.1.js"></script>
<script src="../static/js/angular-route/angular-route.1.4.1.js"></script>
<script>
angular.module('fail', ['ngRoute'])
.config(function ($routeProvider) {
$routeProvider
.when('/a', {
template: '<a ng-href="#/b">a</a>'
})
.when('/b', {
template: '<a ng-href="#/a">b</a>'
})
.otherwise({
redirectTo: '/a'
});
}).factory('$exceptionHandler', ['$log', function($log) {
return function(exception, cause) {
var message = 'angularjs exception: '+exception.message+': caused by "' + cause+ '\njs stack:\n'+exception.stack;
$log.error(message);
};
}]);
</script>
</head>
<body ng-app="fail">
<div ng-view></div>
</body>
</html>
Der obige Code wird normalerweise im Desktop-Browser, Android und iOS 8 Webview ausgeführt, aber unter iOS 9 wird eine Ausnahme ausgelöst, wenn ich auf den Link klicke
2015-07-02 11:00:09 ... angularjs exception: [$rootScope:infdig] 10 $digest() iterations reached. Aborting!
Watchers fired in the last 5 iterations: []
http://errors.angularjs.org/1.4.1/$rootScope/infdig?p0=10&p1=%5B%5D: caused by "undefined
js stack:
file:///.../static/js/angular/angular.js:68:32
$digest<strong i="10">@file</strong>:///.../static/js/angular/angular.js:15705:35
$apply<strong i="11">@file</strong>:///.../static/js/angular/angular.js:15935:31
file:///.../static/js/angular/angular.js:12070:30
eventHandler<strong i="12">@file</strong>:///.../static/js/angular/angular.js:3264:25
Ich kann in iOS 9 Beta 3 nicht mehr reproduzieren.
Ich erhalte den gleichen Fehler mit der öffentlichen Beta von ios9 (13A4293g)
Ich habe den obigen Code auf iOS 9 Beta 3 (13A4293g) überprüft, keine Ausnahme mehr. Aber die App mit der Verwendung von ng-view löst immer noch infdig-Ausnahmen auf iOS 9 Beta 3 aus.
Ich erhalte den gleichen Fehler mit der öffentlichen Beta von ios9 (13A4293g)
Fehler: [$ rootScope:infdig ] 10 $digest() Iterationen erreicht. Abbruch!
Beobachter, die in den letzten 5 Iterationen gefeuert wurden: []
http://errors.angularjs.org/1.3.13/ $rootScope/infdig?p0=10&p1=%5B%5D
file:///Users/mac5/Library/Developer/CoreSimulator/Devices/749DE7E3-D93F-47F9-A1FC-E3D54A1CCEEE/data/Containers/Bundle/Application/9B5EE368-F2A0-4C99-807B-EA17B2479E58/BAShops.app/www /lib/ionic/js/ionic.bundle.js:8762:32
$digest@file :///Users/mac5/Library/Developer/CoreSimulator/Devices/749DE7E3-D93F-47F9-A1FC-E3D54A1CCEEE/data/Containers/Bundle/Application/9B5EE368-F2A0-4C99-807B-EA17B2479E58/BA app/www/lib/ionic/js/ionic.bundle.js:22980:35
$apply@file :///Users/mac5/Library/Developer/CoreSimulator/Devices/749DE7E3-D93F-47F9-A1FC-E3D54A1CCEEE/data/Containers/Bundle/Application/9B5EE368-F2A0-4C99-807B-EA17B2479E58/BA app/www/lib/ionic/js/ionic.bundle.js:23205:31
file:///Users/mac5/Library/Developer/CoreSimulator/Devices/749DE7E3-D93F-47F9-A1FC-E3D54A1CCEEE/data/Containers/Bundle/Application/9B5EE368-F2A0-4C99-807B-EA17B2479E58/BAShops.app/www /lib/ionic/js/ionic.bundle.js:54879:24
eventHandler@file :/// 47F9- A1FC- EA17B2479E58 /BA /www/lib/ionic/js/ionic.bundle.js:11713:25
DispatchEvent@[nativer Code]
triggerMouseEvent@file :/// 47F9- A1FC- F2A0-4C99-807B- EA17B2479E58/ /www/lib/ionic/js/ionic.bundle.js:2863:20
tapClick@file :/// 47F9- A1FC- EA17B2479E58 /BA /www/lib/ionic/js/ionic.bundle.js:2852:20
tapTouchEnd@file :/// 47F9- A1FC- EA17B2479E58 /BA /www/lib/ionic/js/ionic.bundle.js:2975:13
Wir erhalten diesen Fehler auch in der öffentlichen Beta 3 von iOS 9 mit unserer eigenen Angular-Anwendung. Es tritt nicht in iOS 8 auf.
Als Workaround habe ich eine einfache Direktive geschrieben, um ng-view und angle-route.js zu ersetzen. Die Lösung hat in unserer eigenen Anwendung gut funktioniert, alle Infdig-Ausnahmen sind in iOS 9 Beta/Beta 3 verschwunden. Unten ist der vereinfachte Code, der nur für unsere eigene Anwendung gedacht ist, allgemeine Anwendungsfälle werden nicht berücksichtigt. Ich empfehle anderen Leuten NICHT, dies zu verwenden:
(function (window) {
'use strict';
var myApp = angular.module("myApp");
var $route = {};
// replace $routeProvider.when with the function below:
window.routeWhen = function(path, route) {
$route[path] = route;
};
myApp.directive("myView", ['$compile', '$controller', '$http', '$rootScope', function ($compile, $controller, $http, $rootScope) {
return {
priority: -400,
link: function (scope, element) {
var parentScope = scope;
scope = null;
window.updateView = function (path) {
location.hash = '#'+url;
if (scope) scope.$destroy();
scope = parentScope.$new();
var route = $route[path];
var linkView = function(html) {
element.html(html);
var link = $compile(element.contents());
var controller = $controller(route.controller, {$scope: scope});
element.data('$ngControllerController', controller);
element.children().data('$ngControllerController', controller);
link(scope);
scope.$emit('$viewContentLoaded');
if (!$rootScope.$$phase && !scope.$$phase) scope.$apply();
};
if (route.templateCache) linkView(route.templateCache)
else if (route.template) {
route.templateCache = document.getElementById(route.template).innerHTML;
linkView(route.templateCache)
}
else $http.get(route.templateUrl;).success(function(html) {
route.templateCache = html;
linkView(html);
});
};
//updateView(initialPath);
// call updateView(path) to set location at other places of the app
}
};
}]);
})(window)
Habe gerade iOS 9 Beta 4 installiert und habe immer noch das gleiche Problem. Irgendjemand anderes?
Ich habe es in iOS 9 Beta 3 gesehen und sehe es immer noch in iOS 9 Beta 4.
+1
Ja, wir sehen das gleiche Problem auch bei einem eckigen UI-Router. Hat in der Zwischenzeit jemand eine gültige Lösung für dieses Problem?
Das gleiche Problem wird in uiWebView auf dem neuesten iOS9 angezeigt.
Hat jemand Updates zu diesem Thema?
Dies ist immer noch ein Thema. Wiedereröffnung
Es sieht nach einem iOS-Problem aus. Wird das irgendwo im Webkit nachverfolgt?
+1
+1
Hier gilt das gleiche. Unsere Cordova-App läuft gut, wenn sie als Web auf dem iPad Safari ausgeführt wird, aber der unendliche Digest tritt auf, wenn sie als Cordova-App (UIWebView) ausgeführt wird.
Genau die gleichen Probleme wie bei @borrull ! Habe schon mit WKWebView experimentiert und dann ist das Problem nicht mehr vorhanden. Aber wir können WKWebView nicht verwenden, da wir Local File Serving (und wir keinen lokalen Server in unserer Anwendung betreiben wollen) und Cookies benötigen. Es hat also etwas mit UIWebView in Kombination mit Cordova/Mobile Safari auf iOS 9 zu tun. Ich debugge derzeit die $locationWatch in Angular, weil ich sehe, dass unsere Anwendung mehrmals an einen anderen Ort wechseln möchte und dann (nach 10 Malen .) ) wird der Digest-Fehler geworfen.
gleiches Problem hier auf iOS9 beta4
Angular unendliche $digest-Schleife ;(
+1, nur in UIWebView, nicht in WKWebView, aber wir können UIWebView nur in unserer Cordova-App verwenden.
+1
Wenn es sich um ein iOS-spezifisches Problem handelt, öffnen Sie bitte ein Problem im Webkit-Problem-Tracker und stellen Sie eine Demo bereit! +1 hier wird wahrscheinlich nichts ändern, da es wirklich nach einem Browser-Bug klingt.
Hat jemand Apple diesen Fehler zur Untersuchung gemeldet?
Ich habe diesen Fehler an Apple gemeldet. Aber vielleicht sollten Sie alle dasselbe tun, um ihre Aufmerksamkeit auf den Fehler zu lenken.
Können Sie uns einen Link geben, damit wir +1 können?
Es ist in unserem persönlichen Apple-Konto über den Bug-Reporter .. also kein öffentlicher Link ;(
Könnten Sie es auf openradar posten und die rdar-ID teilen, damit wir es täuschen können!
Gleiches auf iOS9 Beta 5:
funktioniert auf mobiler Safari
funktioniert mit WKWebview, das wir nicht verwenden können, da es keine lokalen Dateien bereitstellen kann und NSProtocol nicht unterstützt
funktioniert NICHT auf UIWebView
das gleiche hier auf IOS 9 Beta 5
Ich habe auch einen Fehler bei Apple gemeldet. Der Open Radar-Link lautet: https://openradar.appspot.com/22186109 (Dies sollte denjenigen helfen, die faul sind, einen Fehler zu melden). Bitte hinterlassen Sie Kommentare, wenn Sie die Fehlerbeschreibung/Erklärung verbessern können ;-) Sie können das Xcode-Projekt herunterladen, um es mit der Fehlerdatei an das Open Radar-Ticket @santaslow für das JS im OP)
Ich habe eine Version desselben Xcode-Projekts (von @borrull) erstellt, jedoch mit ui-router anstelle von ng-route. Genau das gleiche Problem. Für Interessierte findet ihr das Projekt hier: http://s000.tinyupload.com/index.php?file_id=87281871603760127355
Wir sehen auch dieses Problem. Ich konnte dem Problem nachgehen, dass die location.*-Eigenschaften nicht sofort aktualisiert werden, wenn eckig in der Mischung ist. Wenn Sie versuchen, location.hash einen Wert zuzuweisen (wie das, was hinter dem Ortungsdienst getan wird), dann sofort wieder einlesen, der Wert hat sich nicht geändert. Es scheint einige Nebenwirkungen zu geben, die als Ergebnis der jqlite-Handler auftreten, die an popstate- und hashchanged-Ereignisse angehängt sind.
Ich werde versuchen, ein Beispiel hochzuladen, wenn ich an einem Computer bin.
+1
@CleverCoder Irgendwelche Updates zum Beispiel?
Ich muss den Repro-Fall morgen früh fertigstellen, da der Code da ich das ganze Wochenende gefesselt habe. Danke für den Anstoß! Da iOS 9 herunterzählt, haben wir ein berechtigtes Interesse daran, dass dies behoben wird. Ich werde so schnell wie möglich etwas hochladen.
+1
Ich habe reproduziert, was meiner Meinung nach die Hauptursache ist, bei der das Festlegen der Hash- oder Href-Eigenschaften für den Standort nicht sofort "zutreffen".
Hier ist ein Link zum XCode-Projekt:
https://www.dropbox.com/s/2jkwv2thhm86nly/iOS%209%20Location%20Bug.zip?dl=0
Lassen Sie es mich wissen, wenn Sie nicht auf die Datei zugreifen können.
Beobachten Sie den resultierenden Wert in location.hash und hängen Sie Safari an Debug an. Es scheint etwas zu geben, das die Änderung aufgrund einiger Ereignisinstallationen auf der Grundlage der Ereignisse "Popstate" und "Hashchange" verzögert.
Ich hoffe, das ist hilfreich.
Wir verwenden window.location.href anstelle von state.go und es scheint vorerst zu funktionieren. Weniger Buggy.
Der Wert von location.hash ist nach einer Drehung des Runloop korrekt. Angular kann dieses Problem leicht umgehen, indem das Abrufen von location.hash in einem setTimeout(..., 0) verzögert wird. Ich denke, das wären ~ 2 Änderungen an angle.js/src/ng/location.js.
@hober Habe das Timeout mit
// update $location when $browser url changes
$browser.onUrlChange(function(newUrl, newState) {
$rootScope.$evalAsync(function() {
var oldUrl = $location.absUrl();
var oldState = $location.$$state;
var defaultPrevented;
$location.$$parse(newUrl);
$location.$$state = newState;
defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,
newState, oldState).defaultPrevented;
// if the location was changed by a `$locationChangeStart` handler then stop
// processing this location change
if ($location.absUrl() !== newUrl) return;
if (defaultPrevented) {
$location.$$parse(oldUrl);
$location.$$state = oldState;
setTimeout(function(){ setBrowserUrlWithFallback(oldUrl, false, oldState) }, 0);
} else {
initializing = false;
afterLocationChange(oldUrl, oldState);
}
});
if (!$rootScope.$$phase) $rootScope.$digest();
});
und
// update browser
$rootScope.$watch(function $locationWatch() {
var oldUrl = trimEmptyHash($browser.url());
var newUrl = trimEmptyHash($location.absUrl());
var oldState = $browser.state();
var currentReplace = $location.$$replace;
var urlOrStateChanged = oldUrl !== newUrl ||
($location.$$html5 && $sniffer.history && oldState !== $location.$$state);
if (initializing || urlOrStateChanged) {
initializing = false;
$rootScope.$evalAsync(function() {
var newUrl = $location.absUrl();
var defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,
$location.$$state, oldState).defaultPrevented;
// if the location was changed by a `$locationChangeStart` handler then stop
// processing this location change
if ($location.absUrl() !== newUrl) return;
if (defaultPrevented) {
$location.$$parse(oldUrl);
$location.$$state = oldState;
} else {
if (urlOrStateChanged) {
setTimeout(function(){ setBrowserUrlWithFallback(newUrl, currentReplace,
oldState === $location.$$state ? null : $location.$$state) }, 0);
}
afterLocationChange(oldUrl, oldState);
}
});
}
$location.$$replace = false;
// we don't need to return anything because $evalAsync will make the digest loop dirty when
// there is a change
});
Also habe ich ein setTimout um die setBrowserUrlWithFallback-Methode hinzugefügt, aber es behebt das Problem nicht.
Hier ist ein reduzierter Testfall, der nicht auf Angular basiert und die Problemumgehung demonstriert. Wie man den Workaround in Angular tatsächlich umsetzt, ist mir unklar. https://gist.github.com/hober/a29b6c28ac1744c800dd
Bin in dieser Sache ein bisschen weiter gekommen. Ich habe in Angular eine Änderung bezüglich des Standorts vorgenommen.
Im Teil "Browser aktualisieren" habe ich $rootScope.$evalAsync in $rootScope.$applyAsync geändert.
Die beiden Methoden scheinen genau das gleiche zu tun. Der Unterschied wird erst deutlich, wenn Sie sich die tatsächliche Ausführung von $digest ansehen. Wenn AngularJS einen Digest ausführt, durchläuft es den Scope-Baum und führt $watch()-Bindungen aus, bis keine schmutzigen Daten mehr erzeugt werden. Während dieses Lebenszyklus werden sowohl die Warteschlange $applyAsync() als auch die Warteschlange $evalAsync() geleert; Dies geschieht jedoch an zwei sehr unterschiedlichen Orten.
Die $applyAsync()-Warteschlange wird nur oben im $digest geleert, bevor AngularJS mit der Überprüfung auf schmutzige Daten beginnt. Daher wird die $applyAsync()-Warteschlange höchstens einmal während eines $digest geleert und wird nur geleert, wenn die Warteschlange bereits gefüllt war, bevor der $digest gestartet wurde.
Die $evalAsync()-Warteschlange hingegen wird am Anfang der while-Schleife geleert, die den "dirty check" in $digest implementiert. Dies bedeutet, dass jeder Ausdruck, der während eines Digests zur $evalAsync()-Warteschlange hinzugefügt wird, zu einem späteren Zeitpunkt innerhalb desselben Digests ausgeführt wird.
Um diesen Unterschied konkreter zu machen, bedeutet dies, dass asynchrone Ausdrücke, die von $evalAsync() aus einer $watch()-Bindung hinzugefügt werden, im selben Digest ausgeführt werden. Asynchrone Ausdrücke, die von $applyAsync() innerhalb einer $watch()-Bindung hinzugefügt werden, werden zu einem späteren Zeitpunkt (~10 ms) ausgeführt.
Hoffe das hilft schon einigen von euch :-).
// update browser
$rootScope.$watch(function $locationWatch() {
var oldUrl = trimEmptyHash($browser.url());
var newUrl = trimEmptyHash($location.absUrl());
var oldState = $browser.state();
var currentReplace = $location.$$replace;
var urlOrStateChanged = oldUrl !== newUrl ||
($location.$$html5 && $sniffer.history && oldState !== $location.$$state);
if (initializing || urlOrStateChanged) {
initializing = false;
$rootScope.$applyAsync(function() {
var newUrl = $location.absUrl();
var defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,
$location.$$state, oldState).defaultPrevented;
// if the location was changed by a `$locationChangeStart` handler then stop
// processing this location change
if ($location.absUrl() !== newUrl) return;
if (defaultPrevented) {
$location.$$parse(oldUrl);
$location.$$state = oldState;
} else {
if (urlOrStateChanged) {
setBrowserUrlWithFallback(newUrl, currentReplace,
oldState === $location.$$state ? null : $location.$$state);
}
afterLocationChange(oldUrl, oldState);
}
});
}
$location.$$replace = false;
// we don't need to return anything because $evalAsync will make the digest loop dirty when
// there is a change
});
Hier ist ein anderer Ansatz. Ich bin mit der Angular-Codebasis nicht so vertraut, aber die Logik scheint rational zu sein. Die Browser-URL(...)-Funktion hängt derzeit davon ab, dass location.href sofort die richtige URL zurückgibt. Da diese Methode innerhalb des Stabilisierungszyklus $digest in derselben Ausführungsschleife aufgerufen wird, wird weiterhin die alte URL abgerufen. Dieser Patch nutzt ein 'pendingHref', um die Zuweisung zu verfolgen, und gibt stattdessen diesen Wert zurück, falls er gesetzt ist. Sobald der Wert mit location.href abgeglichen ist, wird der ausstehende Wert gelöscht. Während eines Satzes der URL wird ein Timer mit 0ms gesetzt, um den Fall abzufangen, in dem ein url() get nicht aufgerufen wird. Es ist nicht perfekt, aber die Logik scheint zu funktionieren. Dies dient hauptsächlich der Betrachtung eines alternativen Ansatzes, der keine Leistungsverzögerungen verursacht. Dies basiert auf dem Angular-Tag v1.4.3.
diff --git a/src/ng/browser.js b/src/ng/browser.js
index 928de95..3b9957e 100644
--- a/src/ng/browser.js
+++ b/src/ng/browser.js
@@ -87,7 +87,9 @@ function Browser(window, document, $log, $sniffer) {
var cachedState, lastHistoryState,
lastBrowserUrl = location.href,
baseElement = document.find('base'),
- reloadLocation = null;
+ reloadLocation = null,
+ pendingHref = null,
+ pendingHrefTimer = null;
cacheState();
lastHistoryState = cachedState;
@@ -124,6 +126,18 @@ function Browser(window, document, $log, $sniffer) {
if (location !== window.location) location = window.location;
if (history !== window.history) history = window.history;
+ // Schedule cleaning up pendingHref on the next run loop for setting URL. This is to handle
+ // the case where the browser doesn't update the location.* properties immediately
+ if (!pendingHrefTimer && pendingHref && url) {
+ pendingHrefTimer = setTimeout(function () {
+ if (location.href == pendingHref) {
+ console.log('Actual href updated... setting pendingHref to null from setTimeout');
+ pendingHref = null;
+ }
+ pendingHrefTimer = null;
+ }, 0);
+ }
+
// setter
if (url) {
var sameState = lastHistoryState === state;
@@ -147,6 +161,7 @@ function Browser(window, document, $log, $sniffer) {
// Do the assignment again so that those two variables are referentially identical.
lastHistoryState = cachedState;
} else {
+ pendingHref = url;
if (!sameBase || reloadLocation) {
reloadLocation = url;
}
@@ -161,10 +176,22 @@ function Browser(window, document, $log, $sniffer) {
return self;
// getter
} else {
+ var href = location.href.replace(/%27/g, "'");
+ if (pendingHref) {
+ //console.log('.. using pendingHref for url() return value');
+ href = pendingHref;
+ }
+
+ if (location.href == pendingHref) {
+ console.log('Actual href updated... setting pendingHref to null in getter');
+ pendingHref = null;
+ }
+
+ //var href = location.href.replace(/%27/g,"'");
// - reloadLocation is needed as browsers don't allow to read out
// the new location.href if a reload happened.
// - the replacement is a workaround for https://bugzilla.mozilla.org/show_bug.cgi?id=407172
- return reloadLocation || location.href.replace(/%27/g,"'");
+ return reloadLocation || href;
}
};
Danke @CleverCoder für die Lösung! Scheint wie ein Zauber zu funktionieren! :+1:
@CleverCoder
Wäre toll, wenn du mit diesem einen Pull-Request an das eckige Team machst.
@viattik Ich würde mich irgendwie überraschen, wenn das Angular-Team eine Problemumgehung für UIWebView unter iOS9 übernehmen würde, da der Fehler in UIWebView (Apple) selbst liegt. Aber du kannst es immer versuchen...
@raftheunis87
Es gibt viele Fehler in verschiedenen Browsern und viele Problemumgehungen für diese Fehler in eckigem Code.
Obwohl sie UIWebView nicht offiziell unterstützen, werden viele Hybrid-Apps kaputt gehen und die Verwendung von Angular wird in Hybrid-Apps im neuesten iOS unmöglich sein, bis Apple diesen Fehler behoben hat. Und das ist ein ziemlich großes Problem, würde ich sagen.
Also ich würde es versuchen.
@viattik Ich stimme
Leute, wenn Sie dies als Webkit-Bug posten könnten, idealerweise mit einem Repro-Fall, werde ich einige unserer Kontakte auf der WebKit-Seite nachfassen. https://bugs.webkit.org/
@naomiblack
Ich bin mir nicht sicher, ob es sich um einen Webkit-Fehler handelt. Weil es nur in UIWebView auf iOS9 passiert. Safari unter iOS9 funktioniert einwandfrei.
@raftheunis87 danke für deine
@raftheunis87 @CleverCoder ist eine Möglichkeit, mit
@abrahamrkj Ich habe keine Erfahrung mit ionisch. Aber sind ihre Anpassungen bei der Verwendung von ionisch eckig? Ansonsten würde ich sagen, dass der gleiche Fix mit Ionenwinkel funktionieren würde ...
@raftheunis87 https://github.com/driftyco/ionic/tree/master/js Dies ist der Winkel, den sie verwenden.
@CleverCoder +1 für den Pull-Request. Ich stimme @viattik zu, dass dies ein wichtiges Thema ist, da es viele Hybrid-Apps
Eine Pull-Anfrage könnte in naher Zukunft folgen, obwohl ich zögere, da ich nicht so nah an der Angular-Codebasis bin wie andere. Ich werde die Lösung bald wieder aufgreifen und versuchen, sie kugelsicher zu machen. Es erscheint seltsam, dass sich eine Eigenschaft des window.location-Objekts nicht „sofort“ ändert. In den Tests, die ich durchgeführt habe, habe ich festgestellt, dass die Änderung bestehen blieb, solange die Ereignis-Hooks 'popstate' und 'hashchange' nicht vorhanden waren, was mich zu der Annahme veranlasste, dass die Ursache für die verzögerte Änderung tatsächlich darin besteht, etwas zu tun sonst... Vielleicht hat sich der Zeitpunkt dieser Ereignisse geändert (ich glaube, das habe ich beobachtet).
Ich werde mir das in den nächsten Tagen ansehen, und wenn nichts Besseres auftaucht, werde ich ein wenig tiefer graben, um zu bestätigen, was ich bisher weiß und dass es keinen besseren Ort gibt, um die Verhaltensänderung anzugehen. Tut mir leid, wenn das verwirrend ist. Es passiert viel unter der Haube, was ich in Bezug auf diese Ereignisse immer noch nicht ganz verstehe.
Prost!
... und ja, @borrull , da stimme ich zu. Wenn Apple keine Änderungen mehr vornimmt, dann ist dies eine ernsthafte tickende Zeitbombe, die wirklich zu schlechter Presse und Fingerzeigen führen wird. Ich bin kein Fan von Timern als Problemumgehung (ich hätte lieber einen verbesserten Logikfluss um diese integrierten Eigenschaften), aber wenn wir uns nicht darauf verlassen können, dass sich der Wert ändert, sobald er festgelegt ist, wo ziehen wir dann die? Linie? Welchen anderen Eigenschaften können wir nicht vertrauen? Es ist ein seltsames.
@CleverCoder Ich wollte bedanken , Ihr Patch hat wirklich den Tag gerettet!
@CleverCoder Danke für die gegebene Problemumgehung.
Ich habe eine Lösung abgeleitet, die das Dekorator-Feature von Angular verwendet und ohne Patchen der Angular-Quelle kommt.
Mit cssua kann dieses Setup so konfiguriert werden, dass es nur in bestimmten Umgebungen verwendet wird.
app.config(['$provide', ($provide) => {
$provide.decorator('$browser', ['$delegate', ($delegate) => {
var origUrl = $delegate.url;
var pendingHref = null;
var pendingHrefTimer = null;
var newUrl = function (url, replace, state) {
if (url) {
// setter
var result = origUrl(url, replace, state);
if (window.location.href != url) {
if (pendingHref != url) {
pendingHref = url;
if (pendingHrefTimer) clearTimeout(pendingHrefTimer);
pendingHrefTimer = setTimeout(function () {
if (window.location.href == pendingHref) {
pendingHref = null;
}
pendingHrefTimer = null;
}, 0);
}
}
return result;
} else {
// getter
if (pendingHref == window.location.href) {
pendingHref = null;
}
return pendingHref || origUrl(url, replace, state);
}
};
$delegate.url = newUrl;
return $delegate;
}]);
}]);
@CleverCoder Siehe #12635
@jd-carroll: Das ist wirklich interessant. Ich werde das vielleicht heute etwas später wiederholen, wenn ich Zeit habe. Ziemlich vollgestopft mit Sachen. Das schafft nur noch mehr Mysterium, da dies wie ein separates Problem zu sein scheint, das keine Verzögerung bei der Ortung verursachen sollte.
@realityfilter : Lustig, dass Sie den Dekorateur erwähnen ... Ich habe gerade etwas mit der Angular-Dekoratorfunktion implementiert. Nett!
Hallo zusammen,
Ich wollte nur hinzufügen, dass dieser Fix einen Fehler in unserem Code einführte, der einfach zu beheben war.
Unsere Vorlagen hatten Anker-Tags, die href="#" und ng-click="someCall()" verwendeten. Das href führte dazu, dass die Site mit diesem Fix zu index.html wechselte. Das Entfernen der href hat das Problem behoben.
Unsere App bricht während der Navigation mit der Zurück-Taste in Ionic ab. Sie wechselt zuerst zur neuen Ansicht, dann teilweise zur alten Ansicht und wechselt dann wieder zur neuen Ansicht auf IOS9 Beta alle Auflösungen für Ionic
Gleiches Problem mit iOS 9 Beta 5 13A4325c, Angular 1.4.0 (mit Cordova-ios 3.9.1). Hoffentlich wird der zugrunde liegende UIWebView-Fehler behoben!
Das gleiche Problem tritt bei Angular v1.2.27 auf
Ich habe es bis zur Version 1.2.27 zurückverfolgt, der Fehler ist nicht in der vorherigen Version 1.2.26 enthalten.
Insbesondere dieser Commit ist der Schuldige.
@damrbaby Sieht so aus, als könnte ich etwas damit zu tun haben.
Aber die Tatsache, dass es mit der neuesten Version von Angular in Mobile Safari arbeitet, macht deutlich, dass es etwas mit uiWebView auf iOS 9 zu tun hat. Die Änderung, die sie im Angular-Quellcode vorgenommen haben, ist also nicht unbedingt schlecht.
@CleverCoder @realityfilter @jyc66 Ich wollte mich nur bedanken, du hast mir gerade den Tag gerettet.
Das Problem ist immer noch auf iOS9 GM Seed vorhanden, also aktualisieren Sie Ihre Apps!
Ich kann bestätigen, dass das Problem in iOS9 GM (13A340) immer noch vorhanden ist.
Das bedeutet also, dass Apple etwas kaputt gemacht hat und wir unsere Apps (von denen sich einige seit Monaten oder sogar über einem Jahr nicht geändert haben) erneut aktualisieren müssen, damit sie nicht abstürzen. Macht Sinn :( . Ich möchte lieber, dass Apple es für iOS9-Starts repariert. Wenn Sie in einer alten App zur neuesten Angular-Version wechseln, werden auch andere Dinge kaputt gehen.
Ich bezweifle stark, dass Angular das einzige Framework ist, das Probleme mit iOS9 hat?
Also haben @adamdbradley , @perrygovier und @mhartington vom Ionic Team den ganzen Tag an einem Fix gearbeitet, der sowohl für Ionic als auch für einfache Angular-Apps funktioniert. Das Ziel ist ein Drop-In-Fix, der keine Änderung von Angular erfordert und (hoffentlich) in den meisten Angular-Versionen ab 1.2 funktioniert.
Hier ist unsere aktuelle gebündelte Lösung, die $browser
durch Anwenden dieses Patches dekoriert und repariert. Hinweis: Dies basiert auf Angular 1.4.3 und ist eine Art "Klon mit Fixes" von browser.js
von Angular: https://github.com/driftyco/ionic/blob/ios9-patch/js /angular/service/decorators/ios9-browser-fix.js
Wir haben den Patch auch auf unserem CDN platziert. Ich empfehle nicht, die CDN-Datei für die Produktion zu verwenden, sie ist nur vorhanden, damit sie jetzt einfacher getestet werden kann.
Um es zu testen, platzieren Sie dieses Skript-Tag unter Ihrer Datei angle oder ionic.bundle.js:
<script src="https://code.ionicframework.com/patch/ios9-$browser-patch.js"></script>
Außerdem wird der Patch im Moment angewendet, unabhängig davon, ob Sie iOS9 ausführen oder nicht. Das wird bald behoben, so dass es nur auf dem iOS 9 UIWebView läuft.
Folgen Sie dem entsprechenden Ionic-Problem hier: https://github.com/driftyco/ionic/issues/4082#issuecomment -139079725
Hi an alle,
UI-sref funktioniert wie ein Zauber, aber $state.go unterbricht die Animation der Zurück-Schaltfläche
und die Seite flackert stark, selbst nachdem dieser Fix angewendet wurde.
Grüße,
Ajay Singh
Am Do, 10. September 2015 um 6:23 Uhr schrieb Max Lynch [email protected] :
Also, @adamdbradley https://github.com/adamdbradley , @perrygovier
https://github.com/perrygovier und @mhartington
https://github.com/mhartington vom Ionic Team haben gearbeitet
den ganzen Tag an einem Fix, der für Ionic und für einfache Angular-Apps funktioniert wie
Gut. Das Ziel ist ein Drop-In-Fix, der nicht geändert werden muss
Angular und wird (hoffentlich) mit den meisten 1.2+ Angular-Versionen funktionieren.Hier ist unsere aktuelle gebündelte Lösung, die $browser dekoriert und repariert von
diesen Patch anwenden
https://github.com/angular/angular.js/issues/12241#issuecomment -130744518.
Hinweis: Dies basiert auf Angular 1.4.3 und ist eine Art "Klon mit Korrekturen" von
browser.js von Angular selbst:
https://github.com/driftyco/ionic/blob/ios9-patch/js/angular/service/decorators/ios9-browser-fix.jsWir haben den Patch auch auf unserem CDN platziert. Ich empfehle nicht, die CDN-Datei zu verwenden
für die Produktion ist es nur da, damit es jetzt einfacher zu testen ist.Bitte testen Sie es und lassen Sie uns wissen, wie es gelaufen ist, danke.
Um es auszuprobieren, platzieren Sie dieses Skript-Tag unter Ihrem eckigen oder
ionic.bundle.js-Datei:Also, right now it applies the patch whether you're running on iOS9 or
not. That will soon be fixed such that it runs only on the iOS 9 UIWebView.—
Reply to this email directly or view it on GitHub
https://github.com/angular/angular.js/issues/12241#issuecomment-139082474
.
Ich kann bestätigen, dass dieser Fehler in iOS 9.1 Beta 1 noch vorhanden ist
Wir verwenden $state.go
viel und es flackert immer noch zwischen den Zuständen / wechselt nicht richtig.
Es tut uns leid, dass der Fix für unsere App jetzt funktioniert, nur müssen wir https einschließen
CND-Link anstelle von http CDN sieht so aus, als ob ios9 nur https innerhalb des
app, also nach der Verwendung von https funktionierte unsere App.
https://code.ionicframework.com/patch/ios9- $browser-patch.js
Am Do, 10. September 2015 um 15:22 Uhr, Tyler Crammond notifications@github.com
schrieb:
Wir verwenden $state.go viel und es flackert immer noch zwischen den Zuständen / nicht
richtig übergehen.—
Antworten Sie direkt auf diese E-Mail oder zeigen Sie sie auf GitHub an
https://github.com/angular/angular.js/issues/12241#issuecomment -139189216
.
ios9-$browser-patch.js funktioniert bei mir auch. Aber es generiert einige jshint-Fehler. Gibt es eine Möglichkeit, zum Patch beizutragen, um die Fehler zu beheben?
Ich glaube nicht, dass dieser Patch ganz in Ordnung ist, da Sie den Standort nicht von außerhalb von Angular aktualisieren können. Dies ist wahrscheinlich für die meisten Anwendungen kein Problem, aber wir arbeiten daran, zu sehen, ob es eine bessere Lösung gibt...
ios9-$browser-patch.js hat bei mir nicht funktioniert. Wenn ich von meiner Listenansicht zu einer Detailansicht gehe, benutze ich $state.go(), um zwischen den Seiten zu wechseln. Das erste Mal, wenn ich dies tue, gleitet es rüber und dann direkt zurück, ich klicke dann erneut und es funktioniert. UI-sref funktioniert wie gewünscht, aber ich kann nicht die bedingte Logik ausführen, die ich tun muss.
Leider hat das Herunterladen des Patches und das Speichern und Laden von ./lib/ (ich habe überprüft, ob es geladen ist), nichts für mich geändert:
Error: [$rootScope:infdig] 10 $digest() iterations reached. Aborting!
Watchers fired in the last 5 iterations: []
http://errors.angularjs.org/1.3.13/$rootScope/infdig?p0=10&p1=%5B%5D
iOS 9 GM, ionisch 1.0.0.
Jorisw, versuchen Sie, den ios9-Erkennungscode zu deaktivieren und sehen Sie, ob er funktioniert:
var isIOS9 = (navigator.userAgent.indexOf('Version/9.') != -1) && (navigator.appVersion.indexOf('9_0') != -1);
if (!isIOS9) {
// nicht patchen, wenn nicht iOS9 UIWebView
geben $browser zurück;
}
@ jyc66 Das funktioniert, danke. Wie stelle ich sicher, dass iOS < 9 nicht beschädigt wird?
Die Methode isIOS9
ist fehlerhaft. Es sollte geprüft werden gegen:
> navigator.userAgent
< "Mozilla/5.0 (iPhone; CPU iPhone OS 9_0 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Mobile/13A340 (2065230368)" = $1
> navigator.appVersion
< "5.0 (iPhone; CPU iPhone OS 9_0 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Mobile/13A340 (2065230368)" = $2
Ja, alternativ können Sie auf Betriebssysteme unter 9 testen und den Fix in diesen Fällen deaktivieren. Die aktuelle Überprüfung wird auf iOS 9.1 unterbrochen, das ebenfalls bald veröffentlicht wird.
Ich mache das jetzt, bis mir oder jemand ein besseres einfällt:
// only provide the patch for iOS9 on UIWebView
var isIOS9 = (navigator.userAgent.indexOf(' OS 9') != -1) && (navigator.appVersion.indexOf(' OS 9') != -1);
if (!isIOS9) {
// do not patch if not iOS9 UIWebView
return $browser;
}
Ja, das ist ähnlich wie bei mir.
Weiß jemand, ob das Anwenden des Patches auf iOS-Versionen >= 9.0 Probleme verursacht, wenn/wenn Apple das Problem in einer späteren Version von iOS behebt?
@JeremyPlease ich ausprobieren
Hat bei mir funktioniert, als ich die Überprüfung des Benutzeragenten deaktiviert habe und den Patch als Teil des minimierten Pakets bereitgestellt habe. Es ist eine nichtionische, eckige App. Werde später heute Abend weiter untersuchen und sicherstellen, dass alles wie erwartet funktioniert.
Danke an das ionic-Team für die Mühe!
9.1beta one hat also noch keinen Fix. Nicht überrascht.
Dies mag seltsam erscheinen - aber jemand sieht, dass die Funktion String.split() nicht richtig funktioniert, wenn der Patch auf iOS 9 angewendet wird? (bisher nur am Simulator getestet). Hier ist ein Screenshot aus dem Debugger von Safari: https://www.dropbox.com/s/hxgct9y0f9z6yci/Screenshot%202015-09-11%2000.40.26.png?dl=0
Ich bin ratlos! Funktioniert gut auf iOS8.4 und natürlich Chrome.
Update : String.split scheint im iOS 9 iPhone 6 und 6s Simulator für mich nicht zu funktionieren, hat nichts mit dem Patch zu tun.
Übrigens - Folgendes habe ich für die Überprüfung des Benutzeragenten verwendet:
var isIOS9WebView = (navigator.userAgent.indexOf('Safari') === -1) && (navigator.appVersion.indexOf('OS 9') !== -1);
if (!isIOS9WebView) {
// do not patch if not iOS9 UIWebView
return $browser;
}
Ich glaube, die beste Lösung ist vielleicht in Igors Pull-Request, aber das funktioniert für mich, während ich den Patch nicht auf iOS 9 Safari anwende, sondern nur auf UIWebView.
@dac09 Ich möchte Ihren Kommet testen, weiß aber nicht, welche Datei geändert werden muss ...
Kannst du mir sagen, welche Datei geändert werden muss?
Ich verwende den Patch von @CleverCoder , auf dem der Patch von ionic basiert, ohne Einschränkung, dass er nur in iOS9 UIWebView ausgeführt werden sollte, und es hat keine Auswirkungen auf UIWebView iOS8, Safari oder Android.
Hallo Leute, könnt ihr bitte diesen Patch testen: https://gist.github.com/IgorMinar/863acd413e3925bf282c
Es sollte mit Angular 1.2 – 1.4.5 funktionieren und benötigt keine Angular-Updates. Anweisungen, wie Sie dies auf Ihre App anwenden, finden Sie im Wesentlichen.
Wir werden in 1.4.6 einen richtigen Fix haben, aber in der Zwischenzeit soll dieser eigenständige Patch die Implementierung und Bereitstellung eines Fixes erleichtern, damit Sie ihn schnell ausrollen können.
Hallo @IgorMinar - Ich
Uncaught TypeError: angle.module(...).decorator ist keine Funktion (anonyme Funktion) @ angle-ios9-uiwebview.patch.js:33
@rajatrocks uhh.. guter Punkt. module.decorator ist nur eine 1.4-Funktion. Lass mich den Patch ändern.
@rajatrocks Ich habe das Wesentliche aktualisiert
Danke @IgorMinar , "installiert" jetzt gut. Werde meine Kommentare im Ionic-Thread hinterlassen, da sie mehr damit zu tun haben.
@IgorMinar Ich habe Ihre js-Datei eingebunden und folgendes in meine app.js eingefügt. Es behebt mein Problem nicht.
@IgorMinar Dein Patch hat mein Problem nicht @mlynch hat es getan.
Um sicherzustellen, dass es nur auf die iOS-Plattform angewendet wird, habe ich einen einfachen Cordova-Hook erstellt:
https://gist.github.com/DURK/f2acd6bca4759e719801
Update : Ah, ich sehe, dass der Patch jetzt eine Überprüfung enthält, sodass er nur auf iOS9 angewendet wird.
@IgorMinar Im Anschluss an das, was @DURK und @jprangenberg berichtet haben, scheint es beim Testen auf einem iPad Air 2 ein Problem mit der Funktion "isIOS9UIWebView" zu geben. Wenn ich erzwinge, dass das Shim immer angewendet wird, funktioniert der Patch.
Aus meinem Kommentar unter: https://github.com/driftyco/ionic/issues/4082#issuecomment -139567128
@IgorMinar , Ihr Patch funktioniert hervorragend auf iOS 9 iPhone UIWebView, aber es gibt einige Probleme mit der User-Agent-Erkennung für das iPad.
iOS 9 iPhone-Benutzeragent in UIWebView:
Mozilla/5.0 (iPhone; CPU iPhone OS 9_0 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Mobile/13A340
iOS 9 iPad-Benutzeragent in UIWebView:
Mozilla/5.0 (iPad; CPU OS 9_0 like Mac OS X) AppleWebKit/601.1.46 (KHTML, like Gecko) Mobile/13A340
Die Regex, die all dies zuverlässig abgleicht, ist:
function isIOS9UIWebView(userAgent) {
return /(iPhone|iPad|iPod);.*OS 9_\d/.test(userAgent) && !/Version\/9\./.test(userAgent);
}
Ich habe den Kern von @IgorMinar gegabelt und die Änderungen hier vorgenommen: https://gist.github.com/JeremyPlease/72cb3bf98279fefed4e3
@DURK Cordova-Haken ist nicht erforderlich. Der Patch macht auf Plattformen, die ihn nicht benötigen, nichts.
@JeremyPlease Safari unter iOS9 ist nicht betroffen. Wir möchten den Patch wirklich nur in UIWebView anwenden.
@JeremyPlease Safari iOS 9 ist nicht das Problem, daher ist die Überprüfung von
Funktioniert bei mir super.
Ich habe festgestellt, dass dies nur ein Problem in UIWebView ist, daher habe ich mein Wesentliches aktualisiert, um in Safari nicht zu gelten:
function isIOS9UIWebView(userAgent) {
return /(iPhone|iPad|iPod);.*OS 9_\d/.test(userAgent) && !/Version\/9\./.test(userAgent);
}
Ich habe v1.0.3 des Patches veröffentlicht
@IgorMinar Funktioniert dieser Fix nur, wenn Sie ngRoute verwenden? Bei mir funktioniert der Fix nicht... :-(
@jprangenberg ja. meine app mit ngroute funktioniert auf iphone/ipad einwandfrei. kannst du nähere Angaben machen? Stellen Sie außerdem sicher, dass Sie Version 1.0.3 oder höher des Patches verwenden
@IgorMinar Version 1.0.3 des Patches funktioniert in meiner Umgebung korrekt.
index.html:
<script src="lib/ionic/js/ionic.bundle.js"></script>
<script src="lib/ngCordova/dist/ng-cordova.min.js"></script>
<script src="js/libs/angular-ios9-uiwebview.patch.js"></script>
app.js:
angular.module('starter', [
'ionic',
'ngCordova',
'ngIOS9UIWebViewPatch',
'ionic.service.core',
'ionic.service.push',
'angular-loading-bar',
'starter.services',
'starter.controllers'
])
app.js (Route):
$stateProvider.state('app.regions', {
cache: false,
url: "/states/:state_id/regions",
views: {
'menuContent': {
templateUrl: "templates/regions.html",
controller: 'RegionsCtrl'
}
}
})
Es ist nicht möglich, durch die App zu navigieren. Wenn Sie auf einen Listeneintrag klicken, sehen Sie die aktuelle Ansicht. Die Schaltfläche Verlauf ändert sich. Wenn Sie auf die Schaltfläche Verlauf klicken, können Sie die Ansicht des Klicks auf das Listenelement sehen.
<ion-list>
<ion-item ng-repeat="state in states" href="#/app/states/{{state.id}}/regions">
{{state.name}}
</ion-item>
</ion-list>
@IgorMinar Bei mir funktioniert es nicht. Hat jemand Ideen?
@jprangenberg verwendest du die gepatchte Version des Ionic-Bundles oder ein Release?
@perrygovier Ich verwende die Version 1.0.3 von @IgorMinar
@jprangenberg richtig, aber das ionic.bundle.js. Welche Version ist das?
Version meines ionic.bundle.js:
window.ionic.version = '1.0.0';
@perrygovier Danke für deine Hilfe!
Aus Neugier, hilft die Verwendung der Version 1.1.0 des Bundles?
http://code.ionicframework.com/1.1.0/js/ionic.bundle.min.js
Du wirst wahrscheinlich auch das aktualisierte CSS brauchen
http://code.ionicframework.com/1.1.0/css/ionic.min.css
Hey @jprangenberg , während wir alle zusammen daran arbeiten, lasst uns diese ionische Diskussion zum ionischen Problem fortsetzen, damit wir normale eckige Benutzer nicht spammen driftyco/ionic#4082
Dieser Fehler wirkt sich also nicht auf WKWEBVIEW aus, wenn https://github.com/Telerik-Verified-Plugins/WKWebView verwendet wird ?
Der Fehler ist nur in UIWebView von iOS 9 vorhanden. Es ist nicht vorhanden, wenn WKWebView verwendet wird.
Danke für deine Arbeit an diesen Jungs, aber bei mir funktioniert es leider nicht. Ich bekomme kaputte Animationen, Seiten werden überhaupt nicht geladen, Seiten werden nicht richtig geladen, im Grunde ist der Router völlig wackelig.
Ich verwende Ionic Bundle 1.1.0 und iOS 9.1 auf einem iPhone 6 zusammen mit der Patch-Datei unter https://code.ionicframework.com/patch/ios9- $browser-patch.js. Ich sehe Fehler wie diese:
Fehler: [$ rootScope:infdig ] 10 $digest() Iterationen erreicht. Abbruch!
Beobachter, die in den letzten 5 Iterationen gefeuert wurden: []
Irgendwelche Vorschläge?
Vielen Dank!
@scottopolis hast du Igors Patch ausprobiert: https://gist.github.com/IgorMinar/863acd413e3925bf282c
@petebacondarwin ya danke, Igors Patch funktioniert bei mir. Meine Seitenübergangsanimationen sind abgehackt, aber der Router scheint repariert zu sein. Ich werde dieses Thema im Auge behalten.
Einige Tests hier und der Patch von @IgorMinar verursacht Probleme mit den Animationen der Zurück-Taste und den Controllern. Ich sehe den Controller für den Bildschirm, bei dem ich mich davor zurückziehe, erneut erstellt zu werden, wenn ich auf "Zurück" klicke. Dies führt dazu, dass Animationen in dieser Ansicht ausgeführt werden, wenn sie vom Bildschirm weg navigiert wird, alle Arten von seltsamen.
Bisher sehe ich keine Probleme bei der Verwendung des Nightly von ionic, aber beim Aktualisieren der iOS9-Erkennung.
var userAgent = navigator.userAgent,
isIOS9 = /(iPhone|iPad|iPod).* OS 9_\d/.test(userAgent) && !/Version\/9\./.test(userAgent);
Ich habe gerade v1.1.0 des Patches gepusht: https://gist.github.com/IgorMinar/863acd413e3925bf282c
Zusammen mit dem ionischen Team können wir mit dieser Version des Patches kein Flimmern mehr reproduzieren.
Bitte aktualisieren Sie und teilen Sie uns mit, wenn Sie weitere Probleme sehen. (Stellen Sie außerdem sicher, dass Sie neben der Version 1.1.0 des Patches keine anderen Patches für dieses Problem verwenden).
Wir werden nächste Woche einen Fix im Master landen, damit Angular v1.4.6 nicht mehr gepatcht werden muss.
Diese neue Version des Patches funktioniert perfekt für mich. Danke @IgorMinar!
Behebt die Version 1.4.6 dieses Problem endgültig?
@alexislg2 - Ja, diese Version sollte das Problem beheben, sodass Sie den Patch nicht anwenden müssen.
Bestätigt, funktioniert bei mir auf dem Simulator und Gerät, meine Benutzer müssen nur 2 Wochen auf die Apple-Genehmigung warten ;-(
@dbroadhurst Ich habe gehört, dass Sie möglicherweise den Fehlerbericht https://openradar.appspot.com/22186109 zitieren können, um Ihre Aktualisierung Ihrer App zu beschleunigen .
Sie können diesen WebKit-Fehler für Updates verfolgen.
Hallo, Sie scheinen das Problem des asynchronen iOS9-Aufrufs bei der Hash-Änderung auf Angular.js gelöst zu haben.
Ich habe Nachforschungen angestellt und auch auf Stackoverflow gepostet, aber die einzige Lösung, die ich bisher gefunden habe, ist Ihr eckiger browser.js-Patch.
Ich bin mit Angular nicht wirklich vertraut und würde gerne verstehen, was du dir zur Verfügung gestellt hast in
jede Webanwendung basierend auf Hash Routing
Würden Sie erklären, wie Sie das Problem identifiziert und behoben haben?
@lchenneberg - der Commit, der das Problem in AngularJS behebt, ist hier https://github.com/angular/angular.js/commit/8d39bd8abf423517b5bff70137c2a29e32bff76d
Das Problem besteht darin, dass dieser spezielle Browser den Wert für window.location.href
erst beim nächsten Lauf der JavaScript-Ereignisschleife aktualisiert. Das heißt, wenn Sie in diesen Wert schreiben und ihn sofort zurücklesen, erhalten Sie einen anderen Wert:
console.log(window.location.href) // -> http://my.domain.com/path/to/page
window.location.href = 'http://my.domain.com/path/to/other/page';
console.log(window.location.href) // -> http://my.domain.com/path/to/page
// next tick of the event loop
console.log(window.location.href) // -> http://my.domain.com/path/to/other/page
Beachten Sie, dass das zweite console.log
den alten Wert zurückgibt, nicht den neuen Wert. Nachdem die aktuelle Ereignisschleife abgeschlossen ist, wird der Wert aktualisiert, wie im dritten console.log
Die Lösung, die wir gefunden haben, besteht darin, den von uns geschriebenen Wert zwischenzuspeichern, wenn der Browser nicht synchron aktualisiert, und diesen Wert von da an anstelle des von window.location.href
Werts zu verwenden, bis es gibt ein hashchange
Ereignis, das uns mitteilt, dass sich der Browser endlich selbst aussortiert hat.
Ich hoffe, das hilft.
Der Patch von
window.ionic.version "1.0.1"
angular.version
Object {full: "1.3.13", major: 1, minor: 3, dot: 13, codeName: "meticulous-riffleshuffle"}
Der Patch von
Aber ich habe noch eine Frage, die einer von euch vielleicht beantworten kann:
Oder, was noch wichtiger ist, nutzt der Zugriff auf eine Webanwendung auf diese Weise die Nitro-Rendering-Engine?
@tpeiffer würden sie wkwebview verwenden, da es sich nur um Safari ohne Adressleiste handelt.
Hallo, ich habe genau das gleiche Problem mit einer alten Version von Angular: 1.0.6
Ich sehe, dass alle Fixes für neuere Versionen sind. Wissen Sie, wo ich suchen sollte, um zu sehen, ob ich dieses Problem beheben kann? Vielen Dank.
@tzamora Haben Sie versucht, den Patch von @IgorMinar anzuwenden? Vielleicht ist 1.0.6 zu früh, um zu funktionieren.
@petebacondarwin der Patch von @IgorMinar verweist auf eine Datei namens browser.js. Ich habe keine Datei namens browser.js
Zu Ihrer Information, neulich ist ein Fix für das zugrunde liegende Problem in WebKit gelandet:
http://trac.webkit.org/changeset/19092
http://trac.webkit.org/changeset/190100
Ich habe das mit dem js-Patch zum Laufen gebracht, aber nicht sofort. Neu hier (angularjs und Ionic), also wenn jemand dies überprüfen und mich wissen lassen könnte, wenn ich etwas Wichtiges verpasst habe, würde ich es wirklich schätzen! (zB ist das Plattformobjekt sehr ineffizient usw.)
Hinweis:
function isIOS9UIWebView(userAgent) {
return (/9\.[0-9]\.[0-9]/.test(ionic.Platform.version()) && /iOS/.test(ionic.Platform.device() ));
//return true;
//return (navigator.userAgent.indexOf(' OS 9') != -1) && (navigator.appVersion.indexOf(' OS 9') != -1);
//return /(iPhone|iPad|iPod).* OS 9_\d/.test(userAgent) && !/Version\/9\./.test(userAgent);
// only provide the patch for iOS9 on UIWebView
}
Ich stieß auf dieses Problem auf 8.4 auf dem Simulator; Daher glaube ich nicht, dass es nur auf iOS 9 beschränkt ist. Ich habe gerade die Agent-String-Überprüfung aktualisiert, um die Versionen iOS 8 und 9 einzuschließen. Hier ist die Agent-Zeichenfolge.
"Mozilla/5.0 (iPhone; CPU iPhone OS 8_4 wie Mac OS X) AppleWebKit/600.1.4 (KHTML, wie Gecko) Mobile/12H141 (140307121489296)"
+1
Hallo
Kann jemand bestätigen, ob dies unter iOS 9.2 gelöst wurde? (Beta)
Vielen Dank :)
Ich kann das Problem mit dem heutigen Update auf iOS 9.2 (13C75) auf dem iPhone 6 nicht reproduzieren. Sieht bisher gut aus. Dieser Fehler ist jedoch noch offen - https://openradar.appspot.com/22186109
Könnte dieser Patch negative Auswirkungen auf iOS 9.2 und höher haben? Ich werde dies mit unserer eigenen App testen, aber ich möchte sicherstellen, dass ich keine Probleme einführe, die beim Testen unserer speziellen Situation nicht auftauchen.
Soweit ich sehen kann, verwenden alle Patches eine Regex, die iOS 9 und höher filtert, aber nicht speziell 9.x bis einschließlich 9.1.
Hey Leute, dieses Problem tritt derzeit in iPhone 6 mit iOS 9 auf. Kann mir jemand sagen, warum?
https://forum.ionicframework.com/t/ios-9-beta-slide-menu-app-transition-issue/30768
ist ein weiterer Patch, den ich anwenden muss? Bitte lassen Sie es mich wissen, ich muss dieses Problem mit der Bildschirmüberlappung wirklich beheben.
Das Update auf iOS 9.2 scheint es auch für mich zu lösen.
@bruno-serfe Dies ist ein Problem, wie iOS mit window.location
umgeht, das nur in iOS 9.0.x vorhanden ist. Wenn Sie auf Angular 1.4.6 oder höher aktualisieren können, müssen Sie nichts weiter tun, da diese Version den Fix enthält. Wenn Sie kein Upgrade durchführen können, enthält der Patch unter https://github.com/angular/angular.js/issues/12241#issuecomment -139446288 denselben Fix.
Wie bereits erwähnt, tritt dieses Problem nur in iOS 9.0.x auf, da dies in iOS 9.1.0 behoben wurde.
Das auf ionic gepostete Problem sieht aus wie das gleiche Problem, daher sollte der gleiche Fix in beide Richtungen funktionieren.
@lgalfaso danke für die Antwort, ich werde versuchen, einen Digest-Fehler zu beheben, den ich gefunden habe. Wenn das das Problem nicht löst, werde ich versuchen, die Winkel zu aktualisieren, danke für die Antwort!.
Danke @lgalfaso :+1:
Ich hatte dieses Problem, als ich die Web-App zum Startbildschirm hinzugefügt und als Standalone verwendet habe, aber ein Upgrade von AngularJS 1.4.5 auf 1.5 hat das Problem vollständig gelöst und die Navigation verdammt beschleunigt!
@volgwfang Das Problem, das Sie haben, hat nichts mit diesem Thema zu tun?
Hilfreichster Kommentar
Bin in dieser Sache ein bisschen weiter gekommen. Ich habe in Angular eine Änderung bezüglich des Standorts vorgenommen.
Im Teil "Browser aktualisieren" habe ich $rootScope.$evalAsync in $rootScope.$applyAsync geändert.
Die beiden Methoden scheinen genau das gleiche zu tun. Der Unterschied wird erst deutlich, wenn Sie sich die tatsächliche Ausführung von $digest ansehen. Wenn AngularJS einen Digest ausführt, durchläuft es den Scope-Baum und führt $watch()-Bindungen aus, bis keine schmutzigen Daten mehr erzeugt werden. Während dieses Lebenszyklus werden sowohl die Warteschlange $applyAsync() als auch die Warteschlange $evalAsync() geleert; Dies geschieht jedoch an zwei sehr unterschiedlichen Orten.
Die $applyAsync()-Warteschlange wird nur oben im $digest geleert, bevor AngularJS mit der Überprüfung auf schmutzige Daten beginnt. Daher wird die $applyAsync()-Warteschlange höchstens einmal während eines $digest geleert und wird nur geleert, wenn die Warteschlange bereits gefüllt war, bevor der $digest gestartet wurde.
Die $evalAsync()-Warteschlange hingegen wird am Anfang der while-Schleife geleert, die den "dirty check" in $digest implementiert. Dies bedeutet, dass jeder Ausdruck, der während eines Digests zur $evalAsync()-Warteschlange hinzugefügt wird, zu einem späteren Zeitpunkt innerhalb desselben Digests ausgeführt wird.
Um diesen Unterschied konkreter zu machen, bedeutet dies, dass asynchrone Ausdrücke, die von $evalAsync() aus einer $watch()-Bindung hinzugefügt werden, im selben Digest ausgeführt werden. Asynchrone Ausdrücke, die von $applyAsync() innerhalb einer $watch()-Bindung hinzugefügt werden, werden zu einem späteren Zeitpunkt (~10 ms) ausgeführt.
Hoffe das hilft schon einigen von euch :-).