angular--路由

生成一个跟angular路由相关的项目:ng new router --routing;
生成组件:ng g component xx;

跟路由相关的五个对象:

image.png

五个对象在整个应用中的位置:
image.png

路由传递参数:
1:在查询参数中传递参数:

app.component.html:
 第一种通过界面:<a [routerLink]="['/product']" [queryParams]="{id:1}">商品</a> 
第二种通过typeScript:<button  type="button" (click)="toProductDetails()">商品详情</button>

第二种:app.component.ts:
toProductDetails() {
     this.router.navigate(['/product']);
  }

product.component.ts:
// 快照的方式获取参数
import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { Params } from '@angular/router/src/shared';

@Component({
  selector: 'app-product',
  templateUrl: './product.component.html',
  styleUrls: ['./product.component.css']
})
export class ProductComponent implements OnInit {
  private productId: number;
  constructor(private routerInfo: ActivatedRoute) { }

  ngOnInit() {
    // 使用订阅方式 获取路由参数的时候,不确定是否从路由本身路由到本身,则使用订阅方式
    this.routerInfo.params.subscribe((param: Params) => this.productId = param['id']);
  }

}

2:在路由路径中传递参数:

app.component.html:
 第一种通过界面: <a [routerLink]="['/product', 2]">商品</a>
第二种通过typeScript:<button  type="button" (click)="toProductDetails()">商品详情</button>

第二种:app.component.ts:
toProductDetails() {
     this.router.navigate(['/product', 3]);
  }

// 在路由中配置
app-routing.module.ts:
{path: 'product/:id', component: ProductComponent}, // 带参数传递

product.component.ts:
 // 从URL中获取参数
this.productId = this.routerInfo.snapshot.params['id'];

路由获取参数方式:
有快照和订阅两种方式,一般使用订阅

import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { Params } from '@angular/router/src/shared';

@Component({
  selector: 'app-product',
  templateUrl: './product.component.html',
  styleUrls: ['./product.component.css']
})
export class ProductComponent implements OnInit {
  private productId: number;
  constructor(private routerInfo: ActivatedRoute) { }

  ngOnInit() {
    // 快照的方式获取参数:
    // this.productId = this.routerInfo.snapshot.queryParams['id'];
    // this.productId = this.routerInfo.snapshot.params['id']; // 从URL中获取参数

    // 使用订阅方式:
    // 使用订阅方式 获取路由参数的时候,不确定是否从路由本身路由到本身,则使用订阅方式
    this.routerInfo.params.subscribe((param: Params) => this.productId = param['id']);
  }

}

路由配置:
重定向路由、找不到路径的默认路由

app-routing.module.ts:

import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { HomeComponent } from './home/home.component';
import { ProductComponent } from './product/product.component';
import { Code404Component } from './code404/code404.component';

const routes: Routes = [
  // --- 这里注意,path路径上不能有斜杠 /
  // 重定向路由
  {path: '', redirectTo: '/home', pathMatch: 'full'}, 
  {path: 'home', component: HomeComponent},
  {path: 'product/:id', component: ProductComponent}, // 带参数传递
  {path: 'home', component: HomeComponent},
  // 找不到路径的默认路由
  {path: '**', component: Code404Component}
];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule]
})
export class AppRoutingModule { }

子路由:

在app-routing.module.ts中配置:
{path: 'product/:id', component: ProductComponent,
    children: [
      {path: '', component: ProductDetailComponent},
      {path: 'seller/:id', component: SellInfoComponent}
    ]
 },

在父界面product.component.html中的定义:
<!-- 这里注意:路径前面是有一个点的 . 表示在当前的路径下找其子路由 -->
<a [routerLink]="['./']">sell商品</a>
<a [routerLink]="['./seller', 66]">product详情商品</a>
<router-outlet></router-outlet>

辅助路由:

image.png

app.component.html:
<!-- 辅助路由 primary:'home',用来指定跳转到辅助路由的同时,跳转到主路由为home,可以不指定主路由primary-->
<a [routerLink]="[{outlets: {primary:'home' ,aux: 'chat'}}]">展示chat</a>
<a [routerLink]="[{outlets: {aux: null}}]">隐藏chat</a>
<router-outlet></router-outlet>
<!-- 在主路由router-outlet下添加一个带有name的 router-outlet-->
<router-outlet name="aux"></router-outlet>

app-routing.module.ts:
{path: 'chat', component: ChatComponent, outlet: 'aux'},

路由守卫:
CanActivate:处理导航到某路由的情况,满足某种情况才可以进入指定路由。
CanDeactivate:处理从当前路由离开的情况,只有满足某种情况,才能离开当前路由。
Resolve:在路由激活之前获取路由数据。

app-routing.module.ts:
import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { HomeComponent } from './home/home.component';
import { ProductComponent } from './product/product.component';
import { Code404Component } from './code404/code404.component';
import { ProductDetailComponent } from './product-detail/product-detail.component';
import { SellInfoComponent } from './sell-info/sell-info.component';
import { ChatComponent } from './chat/chat.component';
import { LoginGuard } from './guard/login.guard';
import { UnsaveGuard } from './guard/unsave.guard';
import { ProductResolve } from './guard/product.resolve';

const routes: Routes = [
  // 这里注意,path路径上不能有斜杠 /
  {path: '', redirectTo: '/home', pathMatch: 'full'}, // 重定向路由
  {path: 'home', component: HomeComponent},
  {path: 'chat', component: ChatComponent, outlet: 'aux'},
  {path: 'product/:id', component: ProductComponent,
    children: [
      {path: '', component: ProductDetailComponent},
      {path: 'seller/:id', component: SellInfoComponent}
    ],
    canActivate: [LoginGuard],
    canDeactivate: [UnsaveGuard],
    resolve: {
      product: ProductResolve
    }
},
  {path: 'home', component: HomeComponent},
  {path: '**', component: Code404Component}
];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule],
  providers: [LoginGuard, UnsaveGuard, ProductResolve]
})
export class AppRoutingModule { }

-----------------------------------------------------------

login.guard.ts:canActivate
import { CanActivate } from '@angular/router';
export class LoginGuard implements CanActivate {
    canActivate() {
        const loggedIn: boolean = Math.random() < 0.5;
        if (!loggedIn) {
            console.log('用户未登录');
        }
        return loggedIn; // 返回true的时候
    }
}

-----------------------------------------------------------

unsave.guard.ts:CanDeactivate 
import { CanDeactivate } from '@angular/router/src/interfaces';
import { ProductComponent } from '../product/product.component';
// 针对要离开ProductComponent这个路由,则做处理
export class UnsaveGuard implements CanDeactivate< ProductComponent> {
    canDeactivate(component: ProductComponent) {
        return window.confirm('确定要离开么?');
    }
}

-----------------------------------------------------------

product.resolve.ts:Resolve 
import { Resolve } from '@angular/router/src/interfaces';
import { Product } from '../product/product.component';
import { ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router';
import { Router } from '@angular/router';
import { Injectable } from '@angular/core';

@Injectable()
export class ProductResolve implements Resolve<Product> {
    constructor(private router: Router) {
    }
    resolve(route: ActivatedRouteSnapshot, state: RouterStateSnapshot) {
        const productId: string = route.params['id'];
        if (productId === '2') {
            return new Product(2, 'ssss');
        }else {
            this.router.navigate(['/home']);
        }
    }
}

-----------------------------------------------------------

product.component.ts:
import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';
import { Params } from '@angular/router/src/shared';
@Component({
  selector: 'app-product',
  templateUrl: './product.component.html',
  styleUrls: ['./product.component.css']
})
export class ProductComponent implements OnInit {
  private productId: number;
  private productName: string;
  constructor(private routerInfo: ActivatedRoute) { }

  ngOnInit() {
   // 使用另外一种获取参数的方式,data
    this.routerInfo.data.subscribe((data: {product: Product}) => {
      this.productId = data.product.id;
      this.productName = data.product.name;
    });
  }
}
export class Product {
  constructor(public id: number, public name: string) {}
}

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,547评论 6 477
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,399评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,428评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,599评论 1 274
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,612评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,577评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,941评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,603评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,852评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,605评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,693评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,375评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,955评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,936评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,172评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 43,970评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,414评论 2 342

推荐阅读更多精彩内容

  • 一:路由基础 什么是路由: 在web开发中,路由的概念由来已久,简而言之,就是利用URL的唯一性来指定特定的事物,...
    真的稻城阅读 6,005评论 2 7
  • 也许这是我最后一次写关于Angular的文章,但也不一定,如果有机会我可能会继续吧,但今天的主题很明确就是路由。 ...
    我是上帝可爱多阅读 3,377评论 0 6
  • 1.背景介绍 angular路由 angular路由可以实现多视图的单页Web应用。当请求一个url时,根据...
    xiaoyudesu阅读 486评论 0 1
  • 引言 在企业应用中权限、复杂页多路由数据处理、进入与离开路由数据处理这些是非常常见的需求。 当希望用户离开一个正常...
    cipchk阅读 5,629评论 6 23
  • A guide to our Swift style and conventions. This is an at...
    lxyz22zp阅读 872评论 0 1