Wie kann ich eine Funktion starten, nachdem die Ansicht gerendert wurde? Ich muss zum Beispiel gemessene Breite einer Komponente erhalten, aber alles ist 0 oder NaN zumindest wenn auf die Ereignisse navigatedTo
und loaded
zugegriffen wird.Ereignis, wenn die Ansicht auf NativeScript gerendert wird
Antwort
Sind Sie sicher, dass Sie "onNavigatedTo", nicht "onNavigatingTo" verwenden?
Dies sind alle page events.
Überprüft und ja ich benutze das. – Terhoraj
Tun Sie zu dem Zeitpunkt, wenn Dinge gebaut und gezeichnet werden; die einzige Methode, die ich zuverlässig gefunden habe, zu arbeiten ist eigentlich so etwas wie:
exports.onNavigatingTo = function() {
setTimeout(codeAfterRender, 1);
}
function codeAfterRender() {
/* do something cool */
}
Der Grund, warum denn gerade wie eine normale Anwendung ist die UI ist immer noch nur ein einzelner Thread; also während JS läuft; Die Benutzeroberfläche kann nicht wirklich aktualisiert werden.
Der Trick besteht also darin, den Code so lange auszugeben, bis die JS-Engine wieder in den systemeigenen Code zurückkehrt. Der native Code rendert den Bildschirm und gibt die JS-Engine erneut ein.
Die einfachste Methode, Ihren Code zu verzögern, ist die Verwendung von setTimeout, da setTimeout in systemeigenem Code geplant ist. (Dies ist sehr ähnlich wie process.nextTick in Knoten verwenden.)
Ereignisschleife:
- JavaScript-Code
- JavaScript-Code -> Sie Schedule Timeout (die eigentlich in der india geplant ist)
- JavaScript-Code Beendet die Ausführung
- JavaScript-Laufzeit kehrt zurück zum systemeigenen Code
- Nativer Code Rendert und verarbeitet alle verbleibenden Nachrichten.
- systemeigenen Code Timer Feuer beginnt JS Motor Ihre SetTimeout Funktion
- JavaScript-Code vorbei startet Ihre SetTimeout Routine
- JavaScript-Code abgeschlossen ist, zu Nativeindia
- -Code tritt zurück macht und verarbeitet alle Nachrichten
- Rest Der systemeigene Code wird inaktiv.
Nur für etwas zusätzliche Klarheit; wie die Ereignisschleife funktioniert, ein echtes Beispiel; Eine Hilfsroutine, die ich für eine meiner Apps geschrieben habe, ist wie folgt:
Also würde ich diese Art von Code tun.
UpdateProgress("Processing 1/3")
.then(function() {
/* do some work, work freezes UI, so break it up */
return UpdateProgress("Processing 2/3");
})
.then(function() {
/* do some more work, again work freezes UI */
return UpdateProgress("Processing 3/3");
})
.then(function() {
/* do some more work, again work freezes UI */
return ...
});
Der Grund dafür ist, weil während NativeScript noch im JavaScript-Teil der Ereignisschleife die Anzeige nicht aktualisiert wird; Wenn Sie also viel zu tun haben und die Anzeige immer noch reaktionsschnell sein soll, müssen Sie den JavaScript-Teil der Ereignisschleife verlassen. Lassen Sie den nativen Teil alle ausstehenden Nachrichten behandeln, und fahren Sie dann im JS-Teil für den nächsten Teil der Verarbeitung fort. (Dies beseitigt auch ANRs auf Android) - Der Trick ist also, dass der Resolve
Aufruf über ein setTimeout abgewickelt wird.
Ich habe auch einige Leute gesehen, die die On-Idle-Benachrichtigung verwenden; Es ist jedoch etwas komplizierter, die Ereignisse auf beiden Plattformen einzurichten. mit setTimeout
ist einfacher und funktioniert genauso gut.
Vielen Dank für die ausführliche Antwort! Bedeutet dies, dass 'setTimeout (codeAfterRender, 0);' genauso effektiv wäre? –
Ja, 0 funktioniert auch. Es wird keinen Unterschied geben, 0 oder 1 Millisekunde sind identisch, wenn Sie die Arbeit abwerfen; zu dem Zeitpunkt, zu dem die JS-Engine beendet wird und zu nativ wechselt; Du hast mindestens 1 ms benutzt. ;-) Der einzige Grund, warum ich 1 über 0 bevorzuge, ist nur für den Fall, dass jemand einen Falsy-Test in einem setTimeout-Monkey oder in den Laufzeiten verwendet; Mein Code wird weiterhin ausgeführt. Wahrscheinlich eine sehr sehr sehr entfernte Möglichkeit; aber ich hedge immer meine Wetten ... ;-) – Nathanael
Ich denke persönlich werde ich 'setTimeout (codeAfterRender, 0);' bevorzugen, damit die Absicht des Codes dem Leser klarer wird - dass dies nicht benutzt wird eine absichtliche Verzögerung einführen. Vielen Dank für Ihre tolle Antwort! –
- 1. mit mvc.net gibt es ein Ereignis, das ausgelöst wird, nachdem die Ansicht gerendert wird
- 2. Ermitteln, welche Ansicht in @RenderBody gerendert wird()
- 3. Angular - URL wird auf state.go aktualisiert, aber die Ansicht wird nicht gerendert
- 4. Backbone.js: Keine Ansicht gerendert
- 5. Zugriff auf die Android-Ansicht eines nativescript-Layouts
- 6. Wenn Benutzer die URL ändert und die falsche Ansicht gerendert wird
- 7. Ereignisse werden nicht ausgelöst, wenn die Backbone-Ansicht mit jquery gerendert wird
- 8. Wird ein Ereignis ausgelöst, wenn die Android-Ansicht in der App sichtbar wird?
- 9. Wie überprüft man, ob eine Backbone-Ansicht gerendert wird?
- 10. Ereignis, wenn die Position: sticky ausgelöst wird
- 11. Cytoscape js Ereignis, wenn alle Elemente gerendert werden?
- 12. Eingang Platzhalter eingestellt wird, wenn die Ansicht
- 13. UIWebView wird nicht korrekt gerendert
- 14. Touch-Ereignis in einer Ansicht erkennen, wenn aus einer anderen Ansicht gezogen wird
- 15. Nativescript - gebundene Eigenschaft in der Ansicht wird nicht aktualisiert, wenn das Modell in promise.then() eingestellt ist
- 16. ListView wird nicht nach einer SegmentiertenBar-Route gerendert
- 17. Welches Ereignis wird ausgelöst, wenn ein UserControl angezeigt wird?
- 18. ViewDidAppear wird nicht aufgerufen, wenn die modale Ansicht gelöscht wird
- 19. WPF wird nicht auf Remote-Desktop gerendert
- 20. Pass Click-Ereignis durch die Ansicht android
- 21. NativeScript, in ListView, ItemTap-Ereignis funktioniert nicht
- 22. benutzerdefinierte Android-Ansicht in nativescript mit Typoskript
- 23. Swift - warum NSColor heller wird, wenn es gerendert wird
- 24. Objekt wird nicht gerendert
- 25. BindingList.ListChanged Ereignis wird nicht ausgelöst, wenn die Eigenschaft geändert wird
- 26. React.js wird nicht gerendert?
- 27. Welches Ereignis wird aufgerufen, wenn wir auf UISearchBar
- 28. UIView - Wie wird benachrichtigt, wenn die Ansicht geladen wird?
- 29. Rendern einer neuen Ansicht, wenn auf eine Schaltfläche geklickt wird
- 30. Komponente wird nicht gerendert
proiva tatsächlichen Code von dem, was Sie versuchen zu erreichen –
Sie könnten einen Timer mit einem setTimeout von 1 Millisekunde verwenden. Dieser Code wird ausgeführt, nachdem der gesamte Code ausgeführt wurde. –
Ich versuche, Dimensionen zu sehen, nicht viel Code dort noch. Ich werde versuchen, diese Zeitverzögerung Idee auszuprobieren. – Terhoraj