У меня есть ссылки в шаблонах внутри модалов. Когда я нажимаю на них, текущая страница меняется, но наложение и модальное пребывание. Я мог бы добавить ng-click="dimiss()" к каждой ссылке во всех шаблонах в модалях, но есть ли лучший способ? Например. автоматически закрыть его при успешном изменении маршрута или добавить только один ng-click для каждого шаблона для обработки всех ссылок?
Есть ли способ автоматически закрыть Angular UI Bootstrap modal при изменении маршрута?
Ответ 1
Если вы хотите, чтобы все открытые модалы были закрыты всякий раз, когда маршрут был успешно изменен, вы можете сделать это в одном центральном месте, прослушивая событие $routeChangeSuccess, например, в блоке запуска вашего приложения:
var myApp = angular.module('app', []).run(function($rootScope, $uibModalStack) {
  $uibModalStack.dismissAll();
}); 
Здесь вы можете увидеть, что служба $uibModalStack получает инъекцию, по которой вы можете вызвать метод dismissAll - этот вызов закроет все текущие открытые модальности.
Итак, да, вы можете обрабатывать модалы, закрывающиеся централизованно, в одном месте, с одной строкой кода:-)
Ответ 2
Лучше всего увидеть, что всякий раз, когда всплывающее окно (модальное) открыто, на кнопке "Назад браузера" (или "Клавиатура назад" ) мы останавливаем изменение URL-адреса и просто закрываем всплывающее окно. Это работает для лучшего пользовательского опыта в моем проекте.
Кнопка "Назад браузера" работает нормально, если нет открытого модального режима.
использование:
$uibModalStack.dismiss(openedModal.key);
или
$uibModalStack.dismissAll;
Пример кода:
.run(['$rootScope', '$uibModalStack',
    function ($rootScope,  $uibModalStack) {       
        // close the opened modal on location change.
        $rootScope.$on('$locationChangeStart', function ($event) {
            var openedModal = $uibModalStack.getTop();
            if (openedModal) {
                if (!!$event.preventDefault) {
                    $event.preventDefault();
                }
                if (!!$event.stopPropagation) {
                    $event.stopPropagation();
                }
                $uibModalStack.dismiss(openedModal.key);
            }
        });
    }]);
Ответ 3
Я действительно не использую Angular UI Bootstrap, но, глядя на docs, похоже, что есть close() метод объекта $modalInstance.
Поэтому, взяв пример из docs, это должно работать:
var ModalInstanceCtrl = function ($scope, $modalInstance, items) {
    $scope.items = items;
    $scope.selected = {
        item: $scope.items[0]
    };
    $scope.ok = function () {
        $modalInstance.close($scope.selected.item);
    };
    $scope.cancel = function () {
        $modalInstance.dismiss('cancel');
    };
    // this will listen for route changes and call the callback
    $scope.$on('$routeChangeStart', function(){
        $modalInstance.close();
    });
};
Надеюсь, что это поможет.
Ответ 4
Я решил эту проблему, выполнив что-то вроде этого:
$rootScope.$on('$stateChangeSuccess',
function(event, toState, toParams, fromState, fromParams){
$modalStack.dismissAll();
});
Ответ 5
Я сохраняю эту логику в модальном контроллере. Вы можете прослушать $locationChangeStart событие и закрыть там мода. Также полезно удалить слушателя после, особенно если вы зарегистрировали прослушиватель на $rootScope:
angular.module('MainApp').controller('ModalCtrl',['$scope','$uibModalInstance',
function ($scope, $uibModalInstance) {
  var dismissModalListener = $scope.$on('$locationChangeStart', function () {
    $uibModalInstance.close();
  });
  $scope.$on('$destroy', function() {
    dismissModalListener();
  });
}]);
Ответ 6
 проверьте наличие соответствующего условия маршрута в событии $stateChangeSuccess и затем глобально закройте открытые модальности начальной загрузки, используя следующий класс:
$rootScope.$on('$stateChangeSuccess',
function(event, toState, toParams, fromState, fromParams){
//hide any open bootstrap modals
  angular.element('.inmodal').hide();
});
 Если вы хотите скрыть любые другие модалы, такие как диалог угловых материалов ($mdDialog) и диалог сладких оповещений, используйте angular.element('.modal-dialog').hide(); & angular.element('.sweet-alert').hide();
Ответ 7
Добавление этого альтернативного ответа.
 В зависимости от вашего проекта использование $uibModalStack.dismissAll() может вызвать сообщение об ошибке.
 Как объяснил JB Nizet в этом ответе, это вызвано тем, что dismissAll() отклонил обещание, что привело к dismissAll() ", в отличие от обратного вызова "success", вызванного close().
Отказ от обещания может привести к нежелательной процедуре обработки ошибок.
 Учитывая, что в $uibModalStack нет closeAll(), я использовал это:
    var modal = $uibModalStack.getTop();
    while (modal && this.close(modal.key)) {
      modal = this.getTop();
    }
 Это то же поведение, что и $uibModalStack.dismissAll() но использует .close() вместо .dismiss().
 Я не смог найти никакой документации, описывающей публичные методы для $uibModalStack, таким образом, на случай, если кто-то заинтересован в использовании/просмотре других методов, доступных в $uibModalStack.
 Скорее всего, он будет расположен в \node-modules\angular-ui-boostrap\dist\ui-boostrap-tpls.js а dismissAll() - @line 4349
Мне понадобилось время, чтобы найти его.
