Mostrando alerta em angularjs quando o usuário sai de uma página

Eu sou uma nova abelha angular. Estou tentando escrever uma validação que alerta o usuário quando ele tenta fechar a janela do navegador.

Eu tenho 2 links na minha página v1 e v2.Quando clicado nos links que leva para as páginas específicas. Aqui está o código para redirect para v1 e v2

angular.module('myApp', ['myApp.filters', 'myApp.services', 'myApp.directives']) .config(['$routeProvider', function($routeProvider) { $routeProvider.when('/v1', {templateUrl: 'pages/v_1.html', controller: MyCtrl1}); $routeProvider.when('/v2', {templateUrl: 'pages/v_2.html', controller: MyCtrl2}); $routeProvider.otherwise({redirectTo: '/v1'}); }]); 

Eu quero abrir uma mensagem quando o usuário clica na v1 que “ele está prestes a sair da v1, se ele quiser continuar” e mesmo ao clicar na v2. Quaisquer sugestões sobre como conseguir isso seriam apreciadas.

Eu tenho uma resposta aqui, mas aparece a mensagem após cada intervalo de tempo.

Código atualizado;

Controladores

 function MyCtrl1() { $scope.$on('$locationChangeStart', function (event, next, current) { if ('your condition') { event.preventDefault(); MessageService.showConfirmation( 'Are you sure?', MessageService.MessageOptions.YES_NO, { 'YES': function () { blockNavigation = false; $location.url($location.url(next).hash()); $rootScope.$apply(); }, 'NO': function () { MessageService.clear(); $log.log('NO Selected') } }); } }); } MyCtrl1.$inject = []; function MyCtrl2() {} MyCtrl2.$inject = []; 

O código para o diálogo de confirmação pode ser escrito mais curto desta maneira:

 $scope.$on('$locationChangeStart', function( event ) { var answer = confirm("Are you sure you want to leave this page?") if (!answer) { event.preventDefault(); } }); 

Vamos separar sua pergunta, você está perguntando sobre duas coisas diferentes:

1

Estou tentando escrever uma validação que alerta o usuário quando ele tenta fechar a janela do navegador.

2

Eu quero abrir uma mensagem quando o usuário clica na v1 que “ele está prestes a sair da v1, se ele quiser continuar” e mesmo ao clicar na v2.

Para a primeira pergunta, faça assim:

 window.onbeforeunload = function (event) { var message = 'Sure you want to leave?'; if (typeof event == 'undefined') { event = window.event; } if (event) { event.returnValue = message; } return message; } 

E para a segunda pergunta, faça assim:

Você deve manipular o evento $locationChangeStart para conectar-se para ver o evento de transição, portanto, use este código para manipular a validação de transição em seu controller / s:

 function MyCtrl1($scope) { $scope.$on('$locationChangeStart', function(event) { var answer = confirm("Are you sure you want to leave this page?") if (!answer) { event.preventDefault(); } }); } 

Aqui está a diretiva que eu uso. Ele se limpa automaticamente quando o formulário é descarregado. Se você quiser impedir que o prompt seja triggersdo (por exemplo, porque você salvou o formulário com êxito), chame $ scope.FORMNAME. $ SetPristine (), onde FORMNAME é o nome do formulário que você deseja impedir de solicitar.

 .directive('dirtyTracking', [function () { return { restrict: 'A', link: function ($scope, $element, $attrs) { function isDirty() { var formObj = $scope[$element.attr('name')]; return formObj && formObj.$pristine === false; } function areYouSurePrompt() { if (isDirty()) { return 'You have unsaved changes. Are you sure you want to leave this page?'; } } window.addEventListener('beforeunload', areYouSurePrompt); $element.bind("$destroy", function () { window.removeEventListener('beforeunload', areYouSurePrompt); }); $scope.$on('$locationChangeStart', function (event) { var prompt = areYouSurePrompt(); if (!event.defaultPrevented && prompt && !confirm(prompt)) { event.preventDefault(); } }); } }; }]); 

Como você descobriu acima, você pode usar uma combinação de window.onbeforeunload e $locationChangeStart para enviar uma mensagem ao usuário. Além disso, você pode utilizar o ngForm.$dirty para enviar mensagens apenas ao usuário quando fizer alterações.

Escrevi uma diretiva angularjs que você pode aplicar a qualquer formulário que observe automaticamente as alterações e envie uma mensagem ao usuário se ele recarregar a página ou sair. @see https://github.com/facultymatt/angular-unsavedChanges

Espero que você ache esta diretiva útil!

Os outros exemplos aqui funcionam bem para as versões antigas do ui-router (> = 0.3.x), mas todos os events de estado, como $stateChangeStart , estão obsoletos a partir de 1.0 . O novo código do roteador ui 1.0 usa o serviço $ transições . Então você precisa injetar $transitions em seu componente e então usar o método $ transições.onBefore como o código abaixo demonstra.

 $ transitionions.onBefore ({}, function (transition) {
   return confirm ("Tem certeza de que deseja sair desta página?");
 });

Este é apenas um exemplo super simples. O serviço $transitions pode aceitar respostas mais complicadas, como promises. Veja o tipo HookResult para mais informações.

 $scope.rtGo = function(){ $window.sessionStorage.removeItem('message'); $window.sessionStorage.removeItem('status'); } $scope.init = function () { $window.sessionStorage.removeItem('message'); $window.sessionStorage.removeItem('status'); }; 

Atualizar página: usando o init