angular11源码探索二十[路由ActivatedRoute]
ActivatedRoute
拿到路由的信息
interface ActivatedRoute {
// 下面有介绍
snapshot: ActivatedRouteSnapshot
url: Observable<UrlSegment[]>
params: Observable<Params> //动态参数
queryParams: Observable<Params> //问号传参
fragment: Observable<string> // #
data: Observable<Data> // route里面的data
outlet: string // 路由出口名称
component: Type<any> | string | null // 拿到当前组件
//拿到当前的route信息 {path: "c/d", component: ƒ}
routeConfig: Route | null
//根route AppComponent
root: ActivatedRoute
//父路由,感觉这个挺有用的,拿到父路由的信息
parent: ActivatedRoute | null
//第一个子孩子
firstChild: ActivatedRoute | null
//多个子孩子
children: ActivatedRoute[]
//从路由器状态树的根到此路由的路径的数组集合
pathFromRoot: ActivatedRoute[]
// 动态id ParamMap方法查找
paramMap: Observable<ParamMap>
// 问号传参 ParamMap方法查找
queryParamMap: Observable<ParamMap>
toString(): string
}
toString
toString(): string {
const url = this.url.map(segment => segment.toString()).join('/');
const matched = this.routeConfig ? this.routeConfig.path : '';
return `Route(url:'${url}', path:'${matched}')`;
}+
// 例如 Route(url:'c;name=xxx/d;age=12', path:'c/d')
UrlSegment
'/team;id=33'
s[0].path // team
s[0].parameters // {id: 33}
当前的url路段
当前路由的参数,为啥是[],因为当为'a/b'为拆成两个数组
UrlSegment[]
path: string
// ;name=xxx
parameters: {...}
// 给parameters 封装一些查询的方法
parameterMap
//当前字段的url信息
toString()
// serializePath(this);
带s 就是整个字段连接起来
export function serializePaths(segment: UrlSegmentGroup): string {
return segment.segments.map(p => serializePath(p)).join('/');
}
不带`serializePath`就是当前的路段
例如: {path: 'c/d', component: CComponent}
那么就是这个最后的信息
<a [routerLink]="['/home','a','c',{name:'xxx'},'d',{age:12}]" [queryParams]="{age:12}">aaa</a>
/home/a/c;name=xxx/d;age=12?age=12
console.log(this.router.snapshot.url.toString());
// c;name=xxx,d;age=12
是url路段信息不会带有其他
案例
<a [routerLink]="['/home','a','c',{name:'xxx'},'d',{age:12}]">aaa</a>
{
path: 'a', component: AComponent,children: [
{path: 'c/d', component: CComponent}
]
}
export class CComponent implements OnInit {
constructor(private router:ActivatedRoute) { }
ngOnInit(): void {
console.log(this.router.snapshot.url);
// [UrlSegment, UrlSegment]
// [
// {parameters: {name: "xxx"},path: "c",parameterMap: ParamsAsMap}
// {parameters: {age: "12"}, path: "d",parameterMap: ParamsAsMap}
// ]
this.router.snapshot.url[0].parameterMap.keys // 列举下面ParamsAsMap的用法
}
}
ParamMap
export interface ParamMap {
// 查询是否有这个属性
has(name: string): boolean;
/**
根据属性查询值
**/
get(name: string): string|null;
// 返回数组的属性值 Array.isArray(v) ? v : [v];
getAll(name: string): string[];
//查询所有的属性名 Object.keys
readonly keys: string[];
}
ParamsAsMap
class ParamsAsMap implements ParamMap {
private params: Params;
constructor(params: Params) {
this.params = params || {};
}
has(name: string): boolean {
return Object.prototype.hasOwnProperty.call(this.params, name);
}
get(name: string): string|null {
if (this.has(name)) {
const v = this.params[name];
return Array.isArray(v) ? v[0] : v;
}
return null;
}
getAll(name: string): string[] {
if (this.has(name)) {
const v = this.params[name];
return Array.isArray(v) ? v : [v];
}
return [];
}
get keys(): string[] {
return Object.keys(this.params);
}
}
ActivatedRouteSnapshot
路线的信息,可以用于遍历怎么路由器状态树,跟ActivatedRoute
相同,只是返回的类型不同
本质应该差不多,使用ActivatedRoute
的好处就是返回的是Observable
我们使用pipe
使用特定的操作
interface ActivatedRouteSnapshot {
routeConfig: Route | null
url: UrlSegment[]
params: Params
queryParams: Params
fragment: string
data: Data
outlet: string
component: Type<any> | string | null
root: ActivatedRouteSnapshot
parent: ActivatedRouteSnapshot | null
firstChild: ActivatedRouteSnapshot | null
children: ActivatedRouteSnapshot[]
pathFromRoot: ActivatedRouteSnapshot[]
paramMap: ParamMap
queryParamMap: ParamMap
toString(): string
}
constructor(private router: Router, private route: ActivatedRoute) {
this.route.snapshot.toString();
// 拿到问号传参
this.route.snapshot.queryParams
// 问好传参 map格式,可以通过 get('') 进行查询需要的值
this.route.snapshot.queryParamMap
}
案例
激活的路由
// {path: 'b/:id#name', component: BComponent,data:{name:'xxx'}},
export class BComponent implements OnInit {
constructor(private route:ActivatedRoute) {
// 拿到当前节点路由
console.log(route.snapshot.url.join(''));
// b, 如果本来是/a/b,也是拿到的当前树的节点
// 拿到绑定的数据
console.log(route.snapshot.data);
// {name: "xxx"}
// 查询动态路由的参数,3种方法
console.log(this.route.snapshot.paramMap.get('id'));
console.log(this.route.snapshot.params['id']);
this.route.params.subscribe(val=>{
console.log(val.id);
})
//
console.log(this.route.snapshot.fragment);
// name
}
ngOnInit(): void {
}
}
参数查询的问题
constructor( private route: ActivatedRoute) {
console.log(this.route.snapshot.queryParams);
}
?a=&b=
// {a: '', b: ''}
?a=foo&a=bar&a=swaz
// {a: ['foo', 'bar', 'swaz']}
.queryParamMap.get('a')
// 查询的是第一个 foo
.queryParamMap.getAll('a')
// ['foo', 'bar', 'swaz']
/one/(two//left:three//right:four)
/one/(left:three//right:four)
{
path: 'one', component: OneComponent, // 三个路由接口写在这里
children: [
{path: '', component: FourComponent},
{path: 'two', component: TwoComponent },
{path: 'three', outlet: 'left', component: EComponent},
{path: 'four', outlet: 'right', component: FourComponent},
],
},
决定自己的高度的是你的态度,而不是你的才能
记得我们是终身初学者和学习者
总有一天我也能成为大佬