Wie kann ich mein $scope
Objekt mit .$emit
und .$on
Methoden von einem Controller an einen anderen senden ?
function firstCtrl($scope) {
$scope.$emit('someEvent', [1,2,3]);
}
function secondCtrl($scope) {
$scope.$on('someEvent', function(mass) { console.log(mass); });
}
Es funktioniert nicht so, wie ich es mir vorstelle. Wie machen $emit
und $on
arbeiten?
javascript
angularjs
Paul Kononenko
quelle
quelle
$rootScope
für Broadcast / Emit verwenden, wenn dies vermieden werden kann.Antworten:
Zunächst spielt die Beziehung zwischen Eltern und Kind eine Rolle. Sie haben zwei Möglichkeiten, ein Ereignis auszusenden:
$broadcast
- schickt das Ereignis nach unten an alle untergeordneten Bereiche,$emit
- Versendet das Ereignis über die Bereichshierarchie nach oben.Ich weiß nichts über Ihre Controller-Beziehung (Scopes), aber es gibt verschiedene Möglichkeiten:
Wenn der Gültigkeitsbereich von
firstCtrl
demsecondCtrl
Gültigkeitsbereich übergeordnet ist , sollte Ihr Code durch Ersetzen$emit
durch$broadcast
infirstCtrl
:Falls zwischen Ihren Bereichen keine Eltern-Kind-Beziehung besteht, können Sie sie
$rootScope
in den Controller einfügen und das Ereignis an alle untergeordneten Bereiche (dh auchsecondCtrl
) senden .Wenn Sie das Ereignis vom untergeordneten Controller an Bereiche nach oben senden müssen, können Sie es schließlich verwenden
$scope.$emit
. Wenn der GültigkeitsbereichfirstCtrl
von demsecondCtrl
Gültigkeitsbereich übergeordnet ist :quelle
$rootScope
in Ihren Dienst einspeisen und das Ereignis vom Dienst aus senden.$rootScope
- aber ich möchte wissen$rootScope
, dass das Ereignis immer noch versickert , wenn ich ein Ereignis von einem Dienst (aus ) aussende$rootScope
. WEIL, wenn$broadcast
die Hierarchie nach unten sickert und nach oben$emit
sickert - was passiert ZWISCHEN "AUF" und "UNTEN" - da der Sender / Sender auch der Zuhörer ist (?). Was ist, wenn das Ereignis für ALLE "UPWARD" - und ALL "DOWNWARD" -Bereiche stumm sein soll, aber nur auf derselben Ebene wie der Dispatcher "hörbar" sein soll?Ich würde zusätzlich eine 4. Option als bessere Alternative zu den von @zbynour vorgeschlagenen Optionen vorschlagen.
Verwenden Sie
$rootScope.$emit
anstatt$rootScope.$broadcast
unabhängig von der Beziehung zwischen Sende- und Empfangscontroller. Auf diese Weise bleibt das Ereignis innerhalb des Satzes von,$rootScope.$$listeners
während sich$rootScope.$broadcast
das Ereignis auf alle untergeordneten Bereiche ausbreitet, von denen die meisten wahrscheinlich sowieso keine Zuhörer dieses Ereignisses sein werden. Und natürlich verwenden Sie am Ende des empfangenden Controllers nur$rootScope.$on
.Für diese Option müssen Sie daran denken, die rootScope-Listener des Controllers zu zerstören:
quelle
$rootScope
Injektion in Steuerungen (was im Allgemeinen nicht benötigt wird). Aber sicherlich eine andere Option, danke!Sie können jedes gewünschte Objekt innerhalb der Hierarchie Ihrer App senden, einschließlich $ scope .
Hier ist eine kurze Vorstellung davon, wie Broadcast und Emit funktionieren.
Beachten Sie die Knoten unten; Alle in Knoten 3 verschachtelt. In diesem Szenario verwenden Sie Broadcast und Emit .
Hinweis: Die Nummer jedes Knotens in diesem Beispiel ist beliebig. es könnte leicht die Nummer eins sein; die Nummer zwei; oder sogar die Nummer 1.348. Jede Nummer ist nur eine Kennung für dieses Beispiel. In diesem Beispiel soll die Verschachtelung von Angular-Controllern / Direktiven gezeigt werden.
Schauen Sie sich diesen Baum an. Wie beantworten Sie die folgenden Fragen?
Hinweis: Es gibt andere Möglichkeiten, diese Fragen zu beantworten. Hier werden jedoch die Übertragung und die Übertragung erläutert . Wenn Sie den folgenden Text lesen, nehmen Sie an, dass jede Nummer eine eigene Datei (Direktive, Controller) hat, z. B. one.js, two.js, three.js.
Wie spricht Knoten 1 mit Knoten 3 ?
In der Datei one.js
In Datei three.js - der oberste Knoten zu allen untergeordneten Knoten, die für die Kommunikation benötigt werden.
Wie spricht Knoten 2 mit Knoten 3?
In der Datei two.js
In Datei three.js - der oberste Knoten zu allen untergeordneten Knoten, die für die Kommunikation benötigt werden.
Wie spricht Knoten 3 mit Knoten 1 und / oder Knoten 2?
In Datei three.js - der oberste Knoten zu allen untergeordneten Knoten, die für die Kommunikation benötigt werden.
In der Datei one.js && two.js die Datei, in der Sie die Nachricht abfangen möchten, oder beides.
Wie spricht Knoten 2 mit Knoten 1?
In der Datei two.js
In Datei three.js - der oberste Knoten zu allen untergeordneten Knoten, die für die Kommunikation benötigt werden.
In der Datei one.js
JEDOCH
Folgendes mache ich gerne.
Im obersten ELTERNKNOTEN ( in diesem Fall 3 ...), der möglicherweise Ihr übergeordneter Controller ist ...
Also, in Datei drei.js
Jetzt müssen Sie in einem der untergeordneten Knoten nur noch $ die Nachricht ausgeben oder sie mit $ on abfangen .
HINWEIS: Normalerweise ist es recht einfach, in einem verschachtelten Pfad zu sprechen, ohne $ emit , $ Broadcast oder $ on zu verwenden . Dies bedeutet, dass die meisten Anwendungsfälle auftreten, wenn Sie versuchen, Knoten 1 zur Kommunikation mit Knoten 2 zu bewegen oder umgekehrt.
Wie spricht Knoten 2 mit Knoten 1?
In der Datei two.js
In Datei three.js - der oberste Knoten zu allen untergeordneten Knoten, die für die Kommunikation benötigt werden.
Wir haben das schon erledigt, erinnerst du dich?
In der Datei one.js
Sie müssen weiterhin $ on für jeden bestimmten Wert verwenden, den Sie abfangen möchten. Jetzt können Sie jedoch in jedem der Knoten beliebige Werte erstellen, ohne sich Gedanken darüber machen zu müssen, wie die Nachricht beim Abfangen und Senden über die Lücke des übergeordneten Knotens übertragen werden kann die generischen pushChangesToAllNodes .
Hoffe das hilft...
quelle
The event life cycle starts at the scope on which $broadcast was called. All listeners listening for name event on this scope get notified.
Sie (wie ich) daher eine Endlosschleife, wenn Sie Strg1 implementieren und mit Strg2 mit Strg3 sprechen$on('x', function(e, data) { $broadcast('x', data) })
. Sie benötigen diese Zeilen vor der Ausstrahlung.if (e.targetScope.$id === $scope.$id) { return; }
Um
$scope object
von einem Controller zu einem anderen zu senden , werde ich darüber$rootScope.$broadcast
und$rootScope.$emit
hier diskutieren , wie sie am häufigsten verwendet werden.Fall 1 :
$ rootScope. $ Broadcast: -
$rootScope
Listener werden nicht automatisch zerstört. Sie müssen es mit zerstören$destroy
. Es ist besser zu verwenden,$scope.$on
wenn Listener eingeschaltet$scope
werden, dh sobald $ scope zerstört wird.Oder,
Fall 2:
$ rootScope. $ emit:
Der Hauptunterschied zwischen $ emit und $ Broadcast besteht darin, dass das Ereignis $ rootScope. $ Emit mit $ rootScope. $ On abgehört werden muss, da das ausgegebene Ereignis niemals über den Bereichsbaum herunterkommt. .
In diesem Fall müssen Sie auch den Listener wie im Fall von $ Broadcast zerstören.
Bearbeiten:
Bearbeiten 2 :
quelle
Sie müssen $ rootScope verwenden, um Ereignisse zwischen Controllern in derselben App zu senden und zu erfassen. Fügen Sie Ihren Controllern die Abhängigkeit $ rootScope ein. Hier ist ein Arbeitsbeispiel.
Mit dem $ scope-Objekt verknüpfte Ereignisse funktionieren nur im Eigentümer-Controller. Die Kommunikation zwischen Controllern erfolgt über $ rootScope oder Services.
quelle
Sie können einen Dienst von Ihrem Controller aus anrufen, der ein Versprechen zurückgibt, und ihn dann in Ihrem Controller verwenden. Und weiter verwenden
$emit
oder$broadcast
andere Controller darüber informieren. In meinem Fall musste ich über meinen Dienst http-Anrufe tätigen, also habe ich so etwas gemacht:und mein Service sieht so aus
quelle
Das ist meine Funktion:
quelle
quelle
Bereiche können verwendet werden, um Ereignisse an die untergeordneten oder übergeordneten Bereiche des Bereichs weiterzugeben und zu versenden.
$ emit - gibt das Ereignis an das übergeordnete Ereignis weiter. $ Broadcast - gibt das Ereignis an Kinder weiter. $ on - Methode zum Abhören der Ereignisse, die von $ emit und $ Broadcast verbreitet werden.
Beispiel index.html :
Beispiel app.js :
Hier können Sie Code testen: http://jsfiddle.net/zp6v0rut/41/
quelle
Der folgende Code zeigt die beiden Subcontroller, von denen aus die Ereignisse nach oben an den übergeordneten Controller (rootScope) gesendet werden.
http://jsfiddle.net/shushanthp/zp6v0rut/
quelle
Gemäß den Angularjs-Ereignisdokumenten sollte das empfangende Ende Argumente mit einer Struktur wie enthalten
@params
- {Object} -Ereignis ist das Ereignisobjekt, das Informationen zum Ereignis enthält
- {Objekt} Argumente, die vom Angerufenen übergeben werden (Beachten Sie, dass dies nur eines sein kann, um ein Wörterbuchobjekt immer besser einzusenden)
$scope.$on('fooEvent', function (event, args) { console.log(args) });
Aus Ihrem CodeAuch wenn Sie versuchen, eine gemeinsam genutzte Information für verschiedene Controller verfügbar zu machen, gibt es eine andere Möglichkeit, dies zu erreichen, nämlich Winkel-Services. Da es sich bei den Services um Singletons handelt, können Informationen zwischen Controllern gespeichert und abgerufen werden. Erstellen Sie einfach Getter und Setter-Funktionen in diesem Dienst, machen diese Funktionen verfügbar, erstellen globale Variablen im Dienst und verwenden sie zum Speichern der Informationen
quelle
Der einfachste Weg :
quelle