Angular 是一个单页面的应用所有的页面展示都在本页面内完成。
我们实现页面局部刷新 展示一个班级的学生信息时,
1. 通过sql的 limit 语句加载固定数目的数据
2. 异步加载sql查询的数据(ajax实现)
3. jQuery替换当前页面的内容
即可实现简单的页面刷新。
由于 angular 中所有操作均在本页完成,因此页面的切换需要使用一定的方式才能实现。通过路由配置,描述当前页面的某一个局部(可以指某一个部分,也可以指当前整个页面)被哪一个局部替换最后表现出类似页面“跳转”的效果。
当路由器导航到一个新的组件视图时(替换当前页面的某一个部分或者替换整个页面),它会用该视图的 URL 来更新浏览器的当前地址以及历史。 严格来说,这个 URL 其实是本地的,浏览器不会把该 URL 发给服务器,并且不会重新加载此页面。
把界面比作某一个目的地,路由比作地图
那么去往每一个地方的路线就都需要进行配置。这就是路由的作用,描述去往某一个目的地的路径。(页面切换,由于是单页面应用所以不称之为页面跳转)
Angular 的路由器是一个可选的服务,它用来呈现指定的 URL 所对应的视图。 它并不是 Angular 核心库的一部分,而是在它自己的 @angular/router 包中。
所谓目的地,就是将当前页面的某一部分替换,或者将当前整个页面替换,而形成的新界面。
src/app/app.module.ts
const appRoutes: Routes = [
{ path: 'crisis-center', component: CrisisListComponent },
{ path: 'hero/:id', component: HeroDetailComponent },
{
path: 'heroes',
component: HeroListComponent,
data: { title: 'Heroes List' }
},
{ path: '',
redirectTo: '/heroes',
pathMatch: 'full'
},
{ path: '**', component: PageNotFoundComponent }
];
@NgModule({
imports: [
RouterModule.forRoot(
appRoutes,
{ enableTracing: true } // <-- debugging purposes only
)
// other imports here
],
...
})
export class AppModule { }
来自官网配置的一个路由 路由配置
path 指行走的路线,每一个路线只能走向一个目的地。component 指目的地。
当应用在浏览器中的 URL 变为 /heroes 时,路由器就会匹配到 path 为 heroes 的 Route,并在宿主视图中的RouterOutlet之后显示 HeroListComponent 组件。
那么path: ''
和 path: '**'
是什么意思?
对于空,就是指没有说要走到哪一个目的地时,应该走向那个目的地。redirect
说明没有指明该如何走时,此处将走向 heroes 对应的目的地 HeroListComponent 。
此处将该路由描述为重定向路由, 重定向路由需要一个 pathMatch 属性,来告诉路由器如何用 URL 去匹配路由的路径,否则路由器就会报错。 在本应用中,路由器应该只有在完整的 URL等于 ” 时才选择 HeroListComponent 组件,因此要把 pathMatch 设置为 ‘full’。
对于 **
的意思是,当 URL 描述的是一个我们没有声明的地址时,应该如何处理。他会走向 PageNotFoundComponent
在使用配置手册时,我们要注意是替换哪一部分。
上图是应该是编写路由配置的基础。也就是先画出页面的路径图,然后根据图去编码配置手册。
<h1>Angular Routerh1>
<nav>
<a routerLink="/crisis-center" routerLinkActive="active">Crisis Centera>
<a routerLink="/heroes" routerLinkActive="active">Heroesa>
nav>
<router-outlet>router-outlet>
我们可以见到,上面的代码中有
这么一句话,这就是指明,可以放置不同局部的替换,可以理解成默认里面放置一个页面或者一个部分内容,然后根据配置项可以替换里面的内容。
上图 【2】 中由 导航
和 router-outlet
页面组成,其实就是上面代码的布局。同时 上图中所有界面的起点是一个 router-outlet
在默认情况,它会默认显示 登录
模块。登录后会将当前的 router-outlet
中的内容替换成首页里的内容。
仅依靠页面导航是不够的
如点击事件,登录成功事件,我们做出的响应中有页面的刷新,此时通过动态的导航到指定的目的地。
constructor(
private router: Router
) {}
this.router.navigate(['/heroes']);
为什么参数是数组?
数组内可以携带参数
传递单一参数
html中传递参数,hero 是配合项中的path
, id 是要传递的参数。
params
{path:"hero/:id",component: HeroDetailComponent}
"/hero",id] routerLinkActive="active">
this.stockID = this.routeInfo.snapshot.params["id"];
queryParams
{path:"hero/:id",component: HeroDetailComponent}
"['/hero']" queryParams= "{id:1}" routerLinkActive="active">
this.routeInfo.snapshot.queryParams["id"];
2. 传递多个参数
"/hero",{queryParams:object}] routerLinkActive="active">
this.router.navigate(['/hero'],{queryParams:{'name':'小明'}});
3. 标签激活样式
每个 A 标签还有一个到 RouterLinkActive 指令的属性绑定,就像 routerLinkActive=”…”。
等号(=)右侧的模板表达式包含用空格分隔的一些 CSS 类。当路由激活时路由器就会把它们添加到此链接上(反之则移除)。你还可以把 RouterLinkActive 指令绑定到一个 CSS 类组成的数组,如 [routerLinkActive]=”[‘…’]”。
RouterLinkActive 指令会基于当前的 RouterState 对象来为激活的 RouterLink 切换 CSS 类。 这会一直沿着路由树往下进行级联处理,所以父路由链接和子路由链接可能会同时激活。 要改变这种行为,可以把 [routerLinkActiveOptions] 绑定到 {exact: true} 表达式。 如果使用了 { exact: true },那么只有在其 URL 与当前 URL 精确匹配时才会激活指定的 RouterLink。
import { ActivateRoute } from '@angular/router';
public id: number;
public name: string;
constructor( public route: ActivateRoute ) {
// 接收单一参数
this.data = this.route.snapshot.params['id'];
// 接收对象
this.route.queryParams.subscribe(params => {
this.name = params['name'];
};
你还可以通过提供查询字符串参数为 RouterLink 提供更多情境信息,或提供一个 URL 片段(Fragment 或 hash)来跳转到本页面中的其它区域。
查询字符串可以由 [queryParams] 绑定来提供,它需要一个对象型参数(如 { name: ‘value’ }),而 URL 片段需要一个绑定到 [fragment] 的单一值。