Как я могу отправить свой $scope
объект из одного контроллера на другой , используя .$emit
и .$on
методы?
function firstCtrl($scope) {
$scope.$emit('someEvent', [1,2,3]);
}
function secondCtrl($scope) {
$scope.$on('someEvent', function(mass) { console.log(mass); });
}
Это не работает так, как я думаю. Как делать$emit
$on
работает и работает?
javascript
angularjs
Павел Кононенко
источник
источник
$rootScope
для трансляции / эмиссии, когда этого можно избежать.Ответы:
Прежде всего, имеет значение отношение области родитель-потомок. У вас есть две возможности для создания какого-либо события:
$broadcast
- отправляет событие вниз во все дочерние области,$emit
- отправляет событие вверх через иерархию области действия.Я ничего не знаю о вашем отношении контроллеров (областей), но есть несколько вариантов:
Если сфера
firstCtrl
является родителемsecondCtrl
сферы, ваш код должен работать, заменив$emit
на$broadcast
вfirstCtrl
:Если между вашими областями нет родительско-дочерних отношений, вы можете ввести
$rootScope
их в контроллер и передать событие всем дочерним областям (т. Е. ТакжеsecondCtrl
).Наконец, когда вам нужно отправить событие из дочернего контроллера в области вверх, вы можете использовать
$scope.$emit
. Если область действияfirstCtrl
является родительской для областиsecondCtrl
действия:источник
$rootScope
в ваш сервис и транслировать событие из сервиса.$rootScope
- но я хочу знать, что если я отправлю событие из службы (отключено$rootScope
), то событие все равно будет предоставлено$rootScope
; ПОТОМУ ЧТО, если$broadcast
просачивается ВНИЗ по иерархии и$emit
просачивается вверх - что происходит между «ВВЕРХ» и «ВНИЗ» - поскольку вещатель / излучатель также является слушателем (?). Что если я хочу, чтобы событие было бесшумным для ВСЕХ областей «Вверх» и «Вниз», но было бы «слышимым» только на том же уровне, что и диспетчер?Я бы дополнительно предложил 4-й вариант в качестве лучшей альтернативы предложенным @zbynour вариантам.
Используйте,
$rootScope.$emit
а не$rootScope.$broadcast
независимо от отношений между передающим и принимающим контроллером. Таким образом, событие остается в наборе,$rootScope.$$listeners
тогда$rootScope.$broadcast
как событие распространяется на все дочерние области, большинство из которых, вероятно, в любом случае не будут слушателями этого события. И, конечно, в конце принимающего контроллера вы просто используете$rootScope.$on
.Для этой опции вы должны не забыть уничтожить слушатели rootScope контроллера:
источник
$rootScope
внедрения в контроллеры (что вообще не требуется). Но, конечно, еще один вариант, спасибо!Вы можете отправить любой объект в иерархии вашего приложения, включая $ scope .
Вот краткое представление о том, как транслировать и излучать работают .
Обратите внимание на узлы ниже; все они вложены в узел 3. Вы используете широковещательную рассылку и передачу при наличии этого сценария.
Примечание: номер каждого узла в этом примере является произвольным; это может легко быть номер один; номер два; или даже число 1348. Каждый номер является просто идентификатором для этого примера. Смысл этого примера - показать вложение угловых контроллеров / директив.
Посмотри на это дерево. Как вы отвечаете на следующие вопросы?
Примечание: Есть другие способы , чтобы ответить на эти вопросы, но здесь мы будем обсуждать трансляцию и Emit . Кроме того, при чтении текста ниже предположим, что у каждого числа есть собственный файл (директива, контроллер), например, one.js, two.js, three.js.
Как узел 1 говорит с узлом 3 ?
В файле one.js
В файле three.js - самый верхний узел для всех дочерних узлов, необходимых для связи.
Как узел 2 говорит с узлом 3?
В файле two.js
В файле three.js - самый верхний узел для всех дочерних узлов, необходимых для связи.
Как узел 3 общается с узлом 1 и / или узлом 2?
В файле three.js - самый верхний узел для всех дочерних узлов, необходимых для связи.
В файле one.js && two.js, в зависимости от того, какой файл вы хотите перехватить, или оба.
Как узел 2 говорит с узлом 1?
В файле two.js
В файле three.js - самый верхний узел для всех дочерних узлов, необходимых для связи.
В файле one.js
ОДНАКО
Вот что мне нравится делать.
В самом верхнем РОДИТЕЛЬСКОМ УЗЛЕ ( 3 в данном случае ...), который может быть вашим родительским контроллером ...
Итак, в файле three.js
Теперь в любом из дочерних узлов вам нужно всего лишь отправить сообщение или перехватить его, используя $ on .
ПРИМЕЧАНИЕ. Обычно довольно просто пересечь разговор по одному вложенному пути, не используя $ emit , $ broadcast или $ on , что означает, что большинство случаев использования - это когда вы пытаетесь заставить узел 1 взаимодействовать с узлом 2 или наоборот.
Как узел 2 говорит с узлом 1?
В файле two.js
В файле three.js - самый верхний узел для всех дочерних узлов, необходимых для связи.
Мы уже справились с этим помните?
В файле one.js
Вам все еще нужно будет использовать $ on для каждого конкретного значения, которое вы хотите перехватить, но теперь вы можете создавать все, что вам нравится, в любом из узлов, не беспокоясь о том, как передать сообщение через пробел родительского узла, когда мы ловим и транслируем универсальные pushChangesToAllNodes .
Надеюсь это поможет...
источник
The event life cycle starts at the scope on which $broadcast was called. All listeners listening for name event on this scope get notified.
вы (как и я) получите бесконечный цикл, если вы реализуете ctrl1, общаясь с ctrl2 с помощью$on('x', function(e, data) { $broadcast('x', data) })
ctrl3. Вам понадобятся эти линии перед трансляцией;if (e.targetScope.$id === $scope.$id) { return; }
Для отправки
$scope object
с одного контроллера на другой я расскажу о том$rootScope.$broadcast
и$rootScope.$emit
здесь, как они используются чаще всего.Случай 1 :
. $ RootScope вещать $: -
$rootScope
слушатель не уничтожается автоматически. Вы должны уничтожить его, используя$destroy
. Лучше использовать, так$scope.$on
как слушатели$scope
уничтожаются автоматически, т. Е. Как только $ scope уничтожается.Или,
Случай 2:
. $ RootScope $ выделяют:
Основное различие в $ emit и $ broadcast заключается в том, что событие $ rootScope. $ Emit необходимо прослушивать с помощью $ rootScope. $ On, поскольку событие emitted никогда не проходит через дерево областей действия. ,
В этом случае вы также должны уничтожить слушателя, как в случае с $ broadcast.
Редактировать:
Изменить 2 :
источник
Вы должны использовать $ rootScope для отправки и захвата событий между контроллерами в одном приложении. Внедрите зависимость $ rootScope в свои контроллеры. Вот рабочий пример.
События, связанные с объектом $ scope, просто работают в контроллере владельца. Связь между контроллерами осуществляется через $ rootScope или Services.
источник
Вы можете вызвать сервис из вашего контроллера, который возвращает обещание, а затем использовать его в своем контроллере. И далее использовать
$emit
или$broadcast
сообщить об этом другим контролерам. В моем случае мне пришлось делать http-вызовы через мой сервис, поэтому я сделал что-то вроде этого:и мой сервис выглядит так
источник
Это моя функция:
источник
источник
Область (ы) могут быть использованы для распространения, отправки события в область потомков или родителей.
$ emit - передает событие родителю. $ broadcast - распространяет событие среди детей. $ on - метод для прослушивания событий, распространяемых с помощью $ emit и $ broadcast.
пример index.html :
пример app.js :
Здесь вы можете проверить код: http://jsfiddle.net/zp6v0rut/41/
источник
Код ниже показывает два субконтроллера, откуда события отправляются вверх на родительский контроллер (rootScope)
http://jsfiddle.net/shushanthp/zp6v0rut/
источник
Согласно документации событий angularjs, принимающая сторона должна содержать аргументы со структурой, подобной
@params
- Событие {Object} является объектом события, содержащим информацию о событии
- Аргументы {Object}, которые передаются вызываемым пользователем (обратите внимание, что это может быть только один, поэтому лучше всегда отправлять в объект словаря)
$scope.$on('fooEvent', function (event, args) { console.log(args) });
Из вашего кодаКроме того, если вы пытаетесь получить доступ к общему фрагменту информации на разных контроллерах, есть еще один способ добиться этого, и это угловые сервисы. Поскольку сервисы являются единичными, информация может храниться и выбираться через контроллеры. Просто создайте геттер и установочные функции в этом сервисе, предоставляют эти функции, создают глобальные переменные в сервисе и используют их для хранения информации
источник
Самый простой способ:
источник