简体   繁体   English

angular 4中如何防止页面刷新

[英]How to prevent page refresh in angular 4

I want to prevent page refresh by everywhere.我想防止到处刷新页面。

I tried the code below我尝试了下面的代码

import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router';
import { CommonServices } from '../services/common.service'; 

@Component({
  selector: 'app-review-prescription',
  templateUrl: './review-prescription.component.html',
  styleUrls: ['../../assets/css/prescriptionView.css'],
  providers:[
    CommonServices
  ]
})
export class ReviewPrescriptionComponent implements OnInit {
    constructor(
        private commonServices:CommonServices,
        private router:Router
        ){}
    ngOnInit(){
      window.onbeforeunload = function(event) {
        return 'By refreshing this page you may lost all data.';
      }
  }

}

Tried this on ngOnChanges() , ngOnInit() , ngOnDestroy() even outside the component class(sorry illogical) but nothing works?ngOnChanges()ngOnInit()ngOnDestroy()上尝试过这个,甚至在组件类之外(抱歉不合逻辑)但没有任何效果?

I need solution in Angular or JavaScript not in jQuery.我需要 Angular 或 JavaScript 中的解决方案,而不是 jQuery 中的解决方案。

Thanks.谢谢。

Try the below subscription to throw alert window on page refresh.尝试以下订阅以在页面刷新时抛出警报窗口。 do some user events like click over the page before trying to refresh or close the window.在尝试刷新或关闭窗口之前执行一些用户事件,例如单击页面。 check the working version here在此处检查工作版本

see the official documentation on beforeunload 请参阅 beforeunload 的官方文档

ngOnInit() {
    window.addEventListener("beforeunload", function (e) {
        var confirmationMessage = "\o/";
        console.log("cond");
        e.returnValue = confirmationMessage;     // Gecko, Trident, Chrome 34+
        return confirmationMessage;              // Gecko, WebKit, Chrome <34
    });
}
@HostListener("window:beforeunload", ["$event"]) unloadHandler(event: Event) {
      event.returnValue = false;
  }

The solution depends on why you want to prevent the page reload.解决方案取决于您为什么要阻止页面重新加载。 If you want to prevent it because there can be unsaved changes you have actually to prevent two different behaviours:如果您想阻止它,因为可能存在未保存的更改,您实际上必须阻止两种不同的行为:

  1. Browser page reload.浏览器页面重新加载。 You can achieve this by creating an HostListener on the beforeunload event (similar to your attempt) like:您可以通过在 beforeunload 事件(类似于您的尝试)上创建一个 HostListener 来实现这一点,例如:
    @HostListener('window:beforeunload', ['$event'])
    beforeUnloadHander() {
        // or directly false
        this.allowRedirect;
    }
  1. Angular routing change (if you have routing): to do that you have to use a Deactivation guard on the route you want to lock, there are many ways but the most appreciated is the one that uses an interface implementation:角度路由更改(如果您有路由):要做到这一点,您必须在要锁定的路由上使用 Deactivation 保护,有很多方法,但最受赞赏的是使用接口实现的方法:

I. The interface sets up a couple of fields used in the angular guard to check if the we can change the router path: I. 接口设置了 angular guard 中使用的几个字段来检查我们是否可以更改路由器路径:


    import { Observable } from "rxjs";
    import { HostListener } from "@angular/core";

    // see https://scotch.io/courses/routing-angular-2-applications/candeactivate
    // implementing this interface with a component in angular you can implement a candeactivate
    // guard that automatically checks if there is the canDeactivate function and
    // it allows to navigate out of the route or not
    export default interface LockableComponent {
      allowRedirect: boolean;
      canDeactivate(): boolean;
    }

II.二、 Each component has to implement this interface with the method canDeactivate or the allowRedirect field (reusable in the HostListener for the problem #1) and must returning a boolean that indicates if navigation is allowed or not.每个组件都必须使用方法 canDeactivate 或 allowRedirect 字段(可在问题 #1 的 HostListener 中重用)实现此接口,并且必须返回一个布尔值,指示是否允许导航。

III.三、 Create a router guard that checks this component fields for the deactivation:创建一个路由器守卫,检查此组件字段是否停用:

  canDeactivate(
    component: LockableComponent,
    currentRoute: ActivatedRouteSnapshot,
    currentState: RouterStateSnapshot
  ): Observable<boolean> | Promise<boolean> | boolean {
    if (
      (component.allowRedirect === false ||
        (component.canDeactivate && !component.canDeactivate()))
    ) {
      // Angular bug! The stack navigation with candeactivate guard
      // messes up all the navigation stack...
      // see here: https://github.com/angular/angular/issues/13586#issuecomment-402250031
      this.location.go(currentState.url);

      if (
        window.confirm("Sure man?")
      ) {
        return true;
      } else {
        return false;
      }
    } else {
      return true;
    }
  }

III.三、 Set the canDeactivate router guard in your module.routing.ts file:在你的 module.routing.ts 文件中设置 canDeactivate 路由器保护:

const myRoutes: Routes = [
      {
        path: "locked-route-path",
        component: ComponentThatImplementsLockedInterface,
        canDeactivate: [TheCanDeactivateGuardJustMade]
      }
      //...
]

You can try this.你可以试试这个。

@HostListener('window:beforeunload', ['$event'])
beforeunloadHandler(event) {
    alert('By refreshing this page you may lost all data.');
}

Please be sure to include this inside the class.请务必将其包含在课程中。

I have done it using both RouteGuard and pure Javascript code to prevent browser close tab/back/close window.我已经使用RouteGuard和纯Javascript代码来防止浏览器关闭选项卡/返回/关闭窗口。

Component:零件:

profileForm = this.fb.group({
  ClientName: ['', [Validators.required]]
});

@HostListener('window:beforeunload', ['$event']) beforeUnloadHander(event: any) {
     debugger
     var isFormDirty = document.getElementById('profileformStatus').innerText;
     console.log(isFormDirty);
     if(isFormDirty == 'true'){
       return false;
     }
     else{
       return true;
     }
   }

Component HTML:组件 HTML:

<div id="profileformStatus">{{profileForm.dirty ? true:false}}</div>

Your Component Guard Service File(Optional):您的组件保护服务文件(可选):

import { CanDeactivate } from "@angular/router";
import { Injectable } from "@angular/core";
import { YourComponent } from "./projects/your-component";
@Injectable()

export class YourComponentCanDeactivateGuardService
    implements CanDeactivate<YourComponent> {

    canDeactivate(component: YourComponent): boolean {
        if (component.profileForm.dirty) {
            return confirm('Are you sure you want to discard your changes?');
        }
        return true;
    }
}

Your Module: add The Above Guard(Optional)你的模块:添加上面的警卫(可选)

@NgModule({
    providers: [YourComponentCanDeactivateGuardService]
})

Finally最后

Update your routing module(Optional):更新您的路由模块(可选):

const routes: Routes = [
    {
        path: 'detail/:id',
        component: YourComponent,
        canDeactivate: [YourComponentCanDeactivateGuardService]
    }
];

Done.完毕。 Now it will prevent reload/back navigation both.现在它将阻止重新加载/返回导航。

All the previous answers contains this code, but we need to add a statement to prevent the default behaviour.之前的所有答案都包含此代码,但我们需要添加一条语句来防止默认行为。

event.preventDefault() event.preventDefault()

@HostListener("window:beforeunload", ["$event"])
unloadHandler(event) {
    event.preventDefault();
    return event.returnValue = "Are you sure you want to exit?";
}

I have been looking for a perfect solution for this but there was none of them was perfect.我一直在为此寻找完美的解决方案,但没有一个是完美的。

I have created a solution for this and you can see the full code here.我为此创建了一个解决方案,您可以在此处查看完整代码。 Prevent reload without saving 防止重新加载而不保存

Code example: https://github.com/mukeshsalaria01/angular-show-alert-on-page-reload-without-saving-example代码示例: https://github.com/mukeshsalaria01/angular-show-alert-on-page-reload-without-saving-example

For this, you should create a Guard.为此,您应该创建一个 Guard。

in your routing configuration file:在您的路由配置文件中:

const routes: Routes = [
    {
        path: '',
        redirectTo: '/homePage',
        pathMatch: 'full'
    },
    {
        path: 'accueil',
        component: AccueilComponent,
        canDeactivate: [GuardName]
    }]

By doing this you're calling your guard on the selected component通过这样做,您正在对选定的组件进行警戒

More informations Here更多信息在这里

In your guard:在你的保护下:

@Injectable()
export class CanDeactivateGuard implements CanDeactivate<CanComponentDeactivate> {
  canDeactivate(component: CanComponentDeactivate) {
    return true/false;
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM