一:开发环境准备
下载安装angular
,webpack,脚手架搭建
查看node版本:node –v
Angular8只支持node10以上版本
查看npm版本:npm –v
删除已安装的旧版本的angular:cnpm uninstall –g @angular/cli
删除angular安装包
清除缓存:npm cache clean --force
全局安装angular最新版本:cnpm install –g @angular/cli@latest
查看是否安装成功:ng version
gnvm管理node
下载放在安装node的路径下,双击运行
以管理员身份运行:gnvm version
- 使用gnvm下载node:gnvm install 6.13
- 下载最新版本的node:gnvm update latest
- 查看安装了那些node版本:gnvm ls
- 使用某个版本:gnvm use 6.11.3
创建项目:ng new demo
报错:npm ERR code ERR_STREAM_WRITE_AFTER_END
解决方法:降低npm版本:npm i –g npm@5.6.0(会有不支持node10.16.3的警告)
再重新创建:ng new demo(cmd下)
切换到目录:cd demo
运行项目:ng serve –open(angular6需node10以上)
二:基础
组件/指令
模块/路由
依赖注入
rxjs/Http
组件及组件树:
1.创建组件
在component目录下创建header组件:ng g component comments/header
2.组件内容
组件内包含:html和css和ts
文件构成
class组件类和装饰器@Component构成
装饰器:赋予类更丰富的元数据,里面可以定义组件的模板template
@Component({
selector:’hello’, //匹配hello标签
template:’<p>{{greeting}}</p>’//这个模板会被插入到hello标签里
})
export class HelloComponent{
private greeting:string; //属性声明
constructor(){
=’Hello Angular 2’} //属性赋值
}
4.属性和对象的声明和使用(ts里)
数据类型 | 声明 | 使用 |
属性 | public name:any=’张三’ | <div [title]=”name”> |
public name:string; | ||
constructor(){ =’张三’ } | ||
对象 | public userinfo:object={ name:’张三’, age:’20’ } |
{{}} |
5.数据的使用(html里)
插值:{{greeting}}
数据绑定:属性绑定,事件绑定,双向绑定
绑定的类型 | 包含内容 | 例子 |
Html绑定 | public contant=’<div>123</div>’ <div [innerHTML]=’contant’> |
|
Class绑定 | <div [ngClass]=”{ ‘box1’:ture }”> <li *ngFor=”let item of data1;let key=index” [ngClass]=”{red:key==0}”></li> |
|
Style绑定 | <li [ngStyle]=”{‘color’:licolor}”></li> private licolor:ang=”red”; |
|
属性绑定 | value | <input [value]=”myData”/> |
src | pubilc picUrl:string=”../../../assets/”; <img [src]=”picUrl”> |
|
事件绑定 | 键盘事件 keydown |
keyDown(e){ console.log(e); (); (); } <input type=”text” (keydown)=”kayDown($event)”> |
键盘事件 keyup |
keyUp(e){()} <input type=”text” (keyup)=”kayUp($event)”> |
|
鼠标点击事件 click |
//点击后获取数据 public title:any=”原始标题”; getData(){alert()} <button (click)=”getData”>点击</button> |
|
//点击后设置数据 public title:any=”原始标题”; setData(){=”标题被改变”} <button (click)=”setData”>点击</button> | ||
//点击后获取对象 getDom(e){var dom=;=”red”} <button (click)=”getDom($event)” >点击</button> | ||
双向绑定 | <input [(ngModel)]=”myData”/> |
双向绑定
1.导入模块
import {FormsModule} from ‘@angular/forms’
2.模块注册
@NgModule({
imports:[FormsModule]
})
3.使用:
public keywords:any;
<input type=”text” [(ngModle)]=”keywords”>
{{keywords}}
指令和命令
包括属性指令和结构指令,组件也是指令的一种
属性指令:改变组件外观或行为,如样式
结构指令:改变模板的Dom结构
指令 |
例子 |
解释 |
ng-app |
|
初始化应用程序 |
ng-init |
|
初始化数据 |
ng-module |
|
把元素绑定到应用程序 |
ng-repeat |
|
重复HTML元素 |
ng-module |
<form name=’myForm’> <input type=’email’ ng-module=’myText’ name=’myAddress’> <p>点击</p> {{.$valid}} {{ .$dirty}} </form> |
将输入域的值与变量绑定,可以为应用数据提供状态值 Invalid:输入值合法时为ture dirty:值改变时为 touched:通过触屏点击为ture error: |
*ngFor |
//数据
|
ngFor用作循环 |
ngSwitch | //定义数据 public score:ang=”1” //使用: <ul [ngSwitch]=”score”> <li *ngSwitchCase=”1”>已支付</li> <li *ngSwitchCase=”2”>未支付</li> <li *ngSwitchCase=”false”>支付失败</li> </ul> |
|
*ngIf | //定义数据: public flag:boolean=true; //使用 <div *ngIf=”flag”><div> |
用处 |
命令 |
解释 |
查看angular版本 |
ng version |
|
创建项目 |
ng new demo |
|
运行项目 |
ng serve –open |
|
创建有哪些参数 |
ng g |
|
创建组件 |
ng g component comments/header |
|
服务与依赖注入
依赖注入providers:组件引入外部构建(如服务)的一种机制
服务:实现单一目的的逻辑单元,如日志服务
服务→实例化→依赖注入→注入→组件
@component({
selector:’hello’,
template:’<p>greeting</p>’,
providers:[loggerService],
})
export class HelloCom1{
private greeting:string;
constructor(logger: loggerService){
=’hello angular’;
(‘构造函数执行完毕’)
}}
模块
包括文件模块和应用模块
文件模块:框架代码以模块形式组织,包括core核心模块(变换检测,依赖注入Component,Directive,ElementRef,Renderer等),comment通用模块(常用内置指令),forms表单模块(表单相关组件和指令),http网络模块(处理网络请求)及其他
应用模块:功能单元以模块形式主旨,即将组件,指令,服务进行包装
1.导入
import {Http} from ‘@angular/http’
2.模块定义
@NgModule({ //模块声明
declarations:[AppComponent,SomeDiretive], //包装指令或组件等
providers:[loggerService], //依赖注入
imports:[OtherModule], //导入其他模块
bootstrap:[ AppComponent], //设置根组件
exports:[SomeDirective], //导出组件或指令
})
export class AppModule {}
数据处理
pipe管道
类型 | 例子 |
日期转换 | 定义:public today:any=new Date() 使用:{{today | date : ‘yyyy-MM-dd HH-mm-ss‘}} |
大小写转换 | 转换成大写:{{data1 | uppercase}} 转换成小写:{{data1 | lowercase}} |
小数位数 | 格式:最少整数位数.最少小数位数-最多整数位数 {{data2 | number:1.2-4}} |
对象序列化 | {{ {name:’jennifer’}| json}} |
字符串截取 | {{ ‘jennifer’|slice:0:3}} |
管道链 | {{‘jennifer’ | slice:0:3 | uppercase}} |
表单
表单类型 | 关键词 | 例子 |
输入框 | text | <input type=’text’ /> |
单选 | radio | <input type='radio' value="男" name="sex" [(ngModel)]=""><label for='sex1'>男</label> <input type='radio' value="女" name="sex" [(ngModel)]=""><label for='sex1'>女</label> ngModle 绑定Value值,当ngModel值和value值相同,默认被选中 |
多选 | checkbox | <span *ngFor=’item of ’> <input type=’checkbox’ [(ngModel)]=’’ /> </span> 双向绑定的是check的value,被选中则为true |
下拉列表 | select option |
<select name=’’ [(ngModel)]=’item’> <option [value]=’item’ *ngFor=’item of ’>{{item}}</option> </select> Select里双向绑定的是被选中的option的value |
P6(搜索记录和todolist)
输出 |
增 | 删 | |
搜索缓存 | <input type=”text” [(ngModel)]=”keyword”/> <button (click)=”zengjia()”></button> <ul> <li *ngFor=”let item of arr; let key=index”>{{item}} <button (click)=”delete(key)”>删除</button></li> </ul> |
public arr:any[]=[]; public keyword:any; zengjia(){//检测是否存在相同值 if(()==-1){ () } } |
delete(key){ (key,1) } |
Todolist | |||
P7数据缓存
服务 | 根模块 | 组件 | ||||||
1.1创建服务 ng g service services/storage |
2.1引入服务import {StorageService} from './services/'; | 3.1组件中引入服务 import {StorageService} from '../../services/'; |
||||||
1.2服务类中的内容 set(key:any,value:any){ (key,(value)); } //从localstorage取出 get(key:any){ return ((key)) } //从localstorage移除 remove(key:any){ (key) } |
2.2注册 @NgModule({ providers: [StorageService], }) |
3.2组件中注册constructor(public storage:StorageService) { } 3.3组件中使用服务类中的方法 ('todolist',); ngOnInit() { var localList=('todolist'); =localList; } |
Dom操作
获取Document对象:
import { DOCUMENT } from '@angular/common';
constructor(@Inject(DOCUMENT) private doc: Document) { }
P8ViewChild用于Dom操作和组件方法调用
html:<div #wySlide></div> //
ts:
class里{
private sliderDom: HTMLDivElement; //3.类型声明
@ViewChild('wySlider', { static: true }) private wySlider: ElementRef; //2.获取ElementRef
ngOnInit(){
= ; //4.获取Dom
}}
P9父子组件通信
通信方式 | 父组件中内容 | 子组件中内容 |
子获取父数据@Input | public msgFromFather:any=”我是父组件传给子组件的值” <app-header [childMsg]=”msgFromFather”></app-header> |
import {Import} from ‘@angular/core’; @imprrt() childMsg:any; getMsg(){ () } |
子执行父方法@Input | funFromFather(){alert(“父组件方法”)} <app-header [run]=”funFromFather”></app-header> |
import {Import} from ‘@angular/core’; @Input run:any getRun(){ () } |
子获取整个父组件 | public msg:any=”首页” <app-header [home]=”this”></app-header> |
import {Input} from ‘@angular/core’ @Input home:any; getFatherMag(){ alert() } |
父获取子数据/方法@ViewChild | <app-header #header></app-header> import {ViewChild} from ‘@angular/core’ @ViewChild(“header”) box2 getChildMsg(){ return this.; } getChildFunc(){ return () } |
public msg:any=”子组件的数据” run(){alert(“子组件的方法”)} |
子触发父方法并传值(父被动获取子数据) | <app-header (outer)=”runParent($event)”></app-header> runParent(e){alert(outer)} |
<button (click)="setParent('传入值')"></button> import {Output,EventEmitter} from ‘@angular/core’ @Output() private outer=new EventEmitter<string>(); //实例化 setParent(data){(data)} |
P10生命周期
异步,响应式
异步编程方法 | 服务内容(RequestService) | 组件里调用 | 解释 |
回调函数 | getCallbackData(cb){ setTimeout(() => { var username = "jennifer"; cb(username); },1000); } |
construct(p){public request:RequestService} ngOnInit(){ ( (data) => {(data)} ) } |
cb函数作为getCallbackData的参数被传进,然后被异步函数setTimeOut调用 回调函数:将一个函数作为参数传入到另一函数 |
Promise | getPromiseData(){ return new Promise((resolve,reject) => { setTimeout(() => { var username = "jennifer"; resolve(username); },1000); }) } |
construct(p){public request:RequestService} ngOnInit(){ ().then( (data) => {(data)} ) } |
getPromiseData里的异步函数setTimeOut执行成功后就调用resolve函数 ()设置resolve()和reject()内容 |
Rxjs | import {Observable} from 'rxjs'; getRxjsData(){ let steam = new Obervable(observer =>{ setTimeout(() => { var username = "jennifer"; (username); ("失败") },1000); }) }
|
construct(p){public request:RequestService} ngOnInit(){ var rxjs = (); ( (data) => {(data)} ) } |
subscript()设置 |
Rxjs取消订阅 | import {Observable} from 'rxjs'; getRxjsData(){ let steam = new Obervable(observer =>{ setTimeout(() => { var username = "jennifer"; (username); ("失败") },3000); }) } |
construct(p){public request:RequestService} ngOnInit(){ var rxjs = (); var d = ( (data) => {(data)} ) setTimeOut(() => {()},1000) } |
|
Rxjs多次执行 | import {Observable} from 'rxjs'; getRxjsData(){ let steam = new Obervable(observer =>{ setInterval(() => { var username = "jennifer"; (username); ("失败") },1000); }) } |
construct(p){public request:RequestService} ngOnInit(){ var rxjs = (); ( (data) => {(data)} ) } |
P12请求数据
方式 | 根模块中 | 组件中 | 组件中发出请求 |
get | import {HttpClientModule} from ‘@angular/common/http’; | import {HttpClient} from ‘@angular/common/http’;(get请求) import
constructor(public http:HttpClient){} |
var api=http://xxx; (api).subscribe(response => {(response); }); |
post | import {HttpClientModule} from ‘@angular/common/http’; | constructor(public http:HttpClient){} | const httpOptions = { headers:new HttpHeaders({‘Content-type’:’application/json’}) } var api=http://xxx/doLogin; (api,{username:”张三”,age:”20”},httpOptions).subscribe( response => {(response)}; ); |
jsonp | import {HttpClientModule, httpClientJsonpModule} from ‘@angular/common/http’; | import {HttpClient} from ‘@angular/common/http’; constructor(public http:HttpClient){} |
var api=http://xxx/doLogin; (api,’callback’).subscribe(response =>{(response)}) |
方法 | 内容 | 步骤 | ||
axios | 服务HttpService中使用axios | 1.1安装 cnpm install axios --save |
1.2新建服务 ng g service services/httpservice 服务中引入axios import axios from ‘axios’ |
1.3服务类中使用axios axiosGet(api){ return new Promise((resolve,reject) => { (api) .then(function(response){ resolve(response); }) }) } |
根模块 | 2.1引入服务类 import {HttpService} from ‘./services/’; |
2.2注册 @NgModule({ providers:[ HttpService], }) |
||
组件中 | 3.1引入服务类 import {HttpService} from ‘../../services/’; |
3.2实例化 constructor(public httpService: HttpService,){} |
3.3发出请求 var api=http://xxx/doLogin; this. httpService. axiosGet(api).then((data) => { (data) }) |
P13路由
配置理由
根路由模块中由引入组件 | 根路由模块中配置路由 | 使用路由 |
import {HomeComponent} from ‘./home/’; import {newsComponent} from ‘./news/’; import {newsContentComponent} from ‘./newsContent/’; |
const routes:Routes = [ {path:’home’,component:HomeComponent}, { path:’news’,component: newsComponent },//静态路由 { path:’newsContent/:aid’,component: newsContentComponent },//动态路由 {path:’**’,redirectTo:’home’} //默认路由
] |
<h1> <a [routerLink]=”[’/home’]”>首页</a> <a [routerLink]=”[’/news’]”>新闻</a> </h1> <router-outlet></router-outlet> |
路由传值(组件切换+传值)
传出数据的组件 | 接受数据组件 | ||
get传值 | 引入组件 import {HomeComponent} from ‘./home/’; import {newsComponent} from ‘./news/’; import {newsContentComponent} from ‘./newsContent/’; 路由配置(静态) const routes:Routes = [ {path:’home’,component:HomeComponent}, { path:’news’,component: newsComponent }, { path:’newsContent’,component: newsContentComponent }, {path:’**’,redirectTo:’home’} //默认路由 ] |
通过queryParams传值 <li *ngFor=”let item of list;let key =index”> <a [routerLink]=”[‘/newsContent’]” [queryParams]=”{aid:key}”>{{item}}</a> </li> |
引入ActivityRoute import {ActivatedRoute} from ‘@angular/router’; 声明 constructor(public route: ActivatedRoute){} 获取数据 ngOnInit(){ ((data) => { (data) }) } |
动态路由传值 | 引入组件(同上) 路由配置(动态) const routes:Routes = [ {path:’home’,component:HomeComponent}, //普通路由 { path:’news’,component: newsComponent },//普通路由 { path:’newsContent/:aid’,component: newsContentComponent }, //动态路由 path:’**’,redirectTo:’home’} ] |
<li *ngFor=”let item of list;let key =index”> <a [routerLink]=”[‘/newsContent/’,key]”>{{item}}</a> </li> |
引入ActivityRoute import {ActivatedRoute} from ‘@angular/router’; 声明 constructor(public route:ActivitedRoute){} 获取数据 ngOnInit(){ ((data) => {data}) } |
路由跳转(页面跳转+传值)
方法 | 跳转前页面 | 接收数据页面 |
路由get传值js跳转 | 触发跳转 <button (click)=” goNewsContent()”></button> |
接受数据组件newsContent引入ActivityRoute并声明 import {ActivatedRoute} from ‘@angular/router’; constructor(public route: ActivatedRoute){} ngOnInit(){ ((data) => { (data) }) |
引入NavigationExtras import{Router, NavigationExtras} from ‘@angular/router’ construct中初始化 constructor(public router:Router){} 执行跳转,用NavigationExtras配置传参 goNewsContent(){ //定义数据 let msg: NavigationExtras = { queryParams:{‘userId’:’123’}, fragment:’anchor’ }; ([‘/news’], msg) } | ||
动态路由的js跳转 | 触发跳转 <button (click)=”goNewsContent()”>js路由跳转(动态路由)<button> <button (click)=”goHome ()”>js路由跳转(普通路由)<button> |
接收数据的组件 import {ActivatedRoute} from ‘@angular/router’; constructor(public route:ActivitedRoute){} ngOnInit(){ ((data) => {data}) } |
引入 import {Router} from ‘@angular/router’; 初始化 constructor(public router:Router){} navigate跳转 goNewsContent(){ ([‘/newsContent/’ ,’1234’]) } goHome(){ ([‘/Home’]) } |
P15嵌套路由(父子路由)
场景:页面存在父子组件,点击时加载不同子组件
根路由模块配置路由 | 父组件home | |
创建home的子组件news ng g component component components/home/news 引入组件(缩进) import {HomeComponent} from ‘./home/’; import {newsComponent} from ‘./news/’; 配置嵌套路由 const routes:Routes = [ {path:’home’,component:HomeComponent children:[ { path:’news’,component: newsComponent }, {path:'**',redirectTo:'news'} //默认加载 ] ] |
<a [routerLink]=“['/home/welcome']">加载新闻组件</a> <a [routerLink]=”['/home/welcome']">加载通知组件</a> <div> <router-outlet></router-outlet> </div> |
|
- 创建home的子组件
ng g component component components/home/welcome