TypeScript笔记

TypeScript 笔记

参考

官方文档:https://www.typescriptlang.org
参考作者:https://www.yuque.com/zyzhao/as2bfc


TypeScript 优点

  • 程序更容易理解
  • 效率更高
  • 更少的错误
  • 非常好的兼容性

一些缺点

  • 增加了一些学习成本
  • 短期内会增加开发成本

使用到的工具

  1. 下载Node
    nodejs官网地址:https://nodejs.cn
  2. 安装TypeScript
    npm install -g typescript
  3. npm install -g typescript
    tsc -v
  4. 下载VSCode
    vscode官网 https://code.visualstudio.com/

Basic Types

boolean

let isBool: Boolean = true;
isBool = false;
console.log(isBool)

number

let num1: number = 123;
let num2:number = 0xffff;
let num3: number = 0b10010100;

string

let str1: string = "abc";
let str2: string = `hello ${str1}`;
console.log(str1)
console.log(str2)

any

但是用第三方的类库的时候,不确定参数的类型可以使用any类型

let noSure: any = 1;
noSure = "abc";
noSure = true;

使用any类型的时候,变量不会有代码智能提示。

联合类型

当一个变量可能为多种类型时可以使用联合类型

let numOrStr: number | string = 'abc';
numOrStr = 123

enum

enum Dirction{
    Up,
    Down,
    Left,
    Right = "RIGHT"
}

let dirc: Dirction = Dirction.Right
if (dirc == Dirction.Right){
    console.log("right: ", Dirction.Right)
}

array

let nums: number[] = [1, 2, 3];
nums.push(4)
console.log(nums[3])		// 输入:4

let strarray: string[] = ['abc', 'ijk'];
strarray.push('uvw')
console.log(strarray[2])	// 输入:vuw

let bools: Array<boolean> = [false, true]
bools.push(true)
console.log(bools[1]) 		// 输入:true

Tuple

元组中的数类类型时被定义的

let numTuple: [number, string] = [123, "abc"];
// numTuple.push([456, 'ijk']);     // 元组不能使用push方法
numTuple = [0, "456"];
console.log(numTuple[0], numTuple[1]);      // 输出结果为:0 456
numTuple[0] = 133;
console.log(numTuple[0], numTuple[1]);      // 输出结果为:133 456

void

void通常用在定义一个函数或方法的时候使用void,使用void表示这个函数或方法没有返回值。

function say_hello(name:string):void{
    console.log(`hello ${name}`)
}

say_hello("xiaoming")

Null and Undefine

let u: undefined = undefined
let n: null = null
// 方法1 需要将tsconfig.json文件中:"strictNullChecks": false
let n1: number = 0;
n1 = undefined;
console.log(n1)

n1 = null
console.log(n1)

// 方法2 使用联合类型
let n2: string | undefined | null;
n2 = "123";
n2 = undefined;
n2 = null;

类型断言

类型断言通常使用在你不知TypeScript变量数据的是时候,类实数据类型转换

let anystr: any = "hello wrold"
let strLength: number = (anystr as string).length
// (anystr as string)  解释:将变量anystr的数据类型转为string类型
console.log("len", strLength)

let strLen: number = (<string>anystr).length
// (<string>anystr)  解释:将变量anystr的数据类型转为string类型
console.log("strLen", strLen)

Interface

接口类型时声明对象类型的一种方法。

作为函数参数

interface Point{
    x: number;
    y: number;
}

function printCoord(pt: Point){
    console.log("The coordinate's x value is " + pt.x);
    console.log("The coordinate's y value is " + pt.y);
    console.log("The coordinate object value is " , pt);
}

printCoord({x: 100, y: 200});

调用可选参数

可选参数使用 ?

// interface

interface Point{
    x: number;
    y: number;
    absX?: number;       // 可选参数使用  ?
    absY?: number;       // 可选参数使用  ?
}

function printCoord(pt: Point){
    console.log("The coordinate's x value is " + pt.x);
    console.log("The coordinate's y value is " + pt.y);
    if(pt.absX != undefined){
        console.log("The coordinate's absX value is " + pt.absX);
    }
    if(pt.absY != undefined){
        console.log("The coordinate's absY value is " + pt.absY);
    }
    console.log("The coordinate object value is " , pt);
}

printCoord({x: 100, y: 200});
console.log("-----------------------分界线------------------------")
printCoord({x: 100, y: 200, absX: 300, absY: 400});

Readonly properties

// interface

interface Point {
    readonly x: number;
    y: number;
}

let pt: Point = {x: 100, y: 200};
console.log(pt.x)
console.log(pt.y)

// pt.x = 300;   // readonly类型在定义时设置好之后是不可修改的
pt.y = 400;
console.log(pt.y)

Function Types

// interface

interface searchFunc {
    (source: string, substr?: string): boolean;
    // () :小括号表示传入函数的参数
    // : :冒号后面boolean表示函数返回的类型
}

let sf: searchFunc = function(sr: string, sb?: string){
    return sr.length > (sb.length || 0);
}

let sf2: searchFunc = function(sr: string, sb: string){
    return sr.length > sb.length;
}

Indexable Types

数组数据类型

// interface

interface StringArray {
    [index: number]: string | number;
    // [] :中括号来表示索引
    // string | number :表示数组内可以string类型和number类型的变量
}

let strarray: StringArray = ['a', 'b', 'v', 1, 2];

class Types

// 对类进行创建interface
interface ClockInterface {
    currentDate: Date
    tick(): void
}

// 对构造器进行创建interface
interface ClockContructor {
    new (hour: number, minute: number): any;
}

let Clock: ClockContructor = class Colck implements ClockInterface {
    currentDate: Date;
    currentHour: number;
    currentMinute: number;

    constructor(h:number, m:number){
        this.currentDate = new Date;
        this.currentHour = h;
        this.currentMinute = m;
    }
    tick(): void {
        console.log(`${this.currentDate} ${this.currentHour} ${this.currentMinute}`)
    }
}

let clock = new Clock(10, 0);
clock.tick()

Extending Interface

单继承

interface Shape {
    color: string;
}

interface Square extends Shape {
    sideLength: number
}

let quare = {} as Square;
quare.color = "red";
quare.sideLength = 3;

多继承

多继承是使用 逗号(,)

interface Shape {
    color: string;
}

interface PenStroke {
    penWdith: number;
}

interface Square extends Shape, PenStroke {
    sideLength: number;
}

let quare = {} as Square;
quare.color = "red";
quare.sideLength = 3;
quare.penWdith = 4;

Generics

interface identifyFn<T> {
    (arg: T): T;
}

let fn1: identifyFn<number> = (arg:number) => {
    return arg + 100;
}

console.log(fn1(100))

let fn2:identifyFn<string> = (srg: string) => {
    return "test" + srg;
}

console.log(fn2("hello world"))

Function

函数定义

函数声明法

function add(x: number, y: number): number {
    return x+y;
}

let num = add(1, 2);
console.log(num);

函数声明法定义函数解释器会首先在代码解释阶段执行函数声明,即函数声明法可以在本文件的所有位置可调用。

函数直接量表达式

let add = function(x: number, y: number): number {
    return x+y;
}

let num = add(1, 2);
console.log(num);
let greetUnnamed: (name: string) => string;

greetUnnamed = function(name: string): string {
    return 'Hi ' + name;
}

箭头函数

箭头函数常用写法

let add2 = (x: number, y: number): number => {
    return x+y
}

let num2 = add2(1, 2);
console.log(num2);

箭头函数应用扩展

  • 在Typescript中,我们可以使用function表达式或箭头函数定义一个函数。箭头函数是function表达式的缩写,箭头函数这种词法会在作用域绑定this操作
    举例:
class Person {
    name: string;
    constructor(name: string) {
        this.name = name;
    }
    greet() {
        console.log(`Hi! My name is ${this.name}`);
    }

    greetDelay(time: number) {
        // 使用 function定义函数就不能使用 this 关键字
        // setTimeout(function () {
        //     console.log(`Hi! My name is ${this.name}`);
        // }, time)

        // 
        setTimeout(() => {
            console.log(`Hi! My name is ${this.name}`);
        }, time)
    }
}

let remo = new Person("Remo");
remo.greet();           // ""
remo.greetDelay(3333)

通过箭头函数,我们可以保证 this 操作符指向的 Person 的示例而不是 setTimeout 的回调函数。

立即调用函数

立即调用函数表达式(IIFE)是一种设计模式,使用函数作用域作为一个词法作用域。IIFE 可以被用于防止全局作用域中的变量提升导致污染。

let bar = 0;

(function() {
  var foo: number = 0;    // 在函数作用域中
  bar = 1;                // 在全局作用域中
  console.log(foo);       // 0
  console.log(bar);       // 1
})();

console.log(bar);
console.log(foo);         // 错误

Optional and Default Parameter


function printUserInfo(name: string, sex: string="男", age?: number): void {
	// sex 为默认参数
	// age 为可选参数, 可选参数后面加 ?
    console.log(`${name}, ${age}, ${sex}`)
}

printUserInfo("xiaoming", "man")
printUserInfo("xiaoming", "man", 22)

Rest Parameters

function buildName(firstName: string, ...restOfName: string[]): string {
    return firstName + " " + restOfName.join(" ")
}

let fullName:string = buildName("xiaoming", "xiaoming", "xiaoming")
console.log(fullName)

生成器

如果在Typescript 中调用一个函数,我们可以可定一旦这个函数开始运行,在它运行完成之间其他代码都不能运行。然而,一种新的函数可能会在函数执行过程中将这个函数暂停一次或多次,并在随后回复它的运行,而且可以让其它代码暂停的过程中运行,在Typescript和ES6中即实现了该功能。这种新型函数被称为生成器
一个生成器代表一个值的序列。生成器对象的接口是一个迭代器,可以使用 next() 函数使它产出结果。
可以使用function 关键字后面跟着一个(*)定义一个生成器的构造函数。yield关键字被用来暂停函数的执行和返回值。以下举个例子:

function *foo() {
    yield 1;
    yield 2;
    yield 3;
    yield 4;
    return 5;
}

let bar = foo();
console.log(bar.next())
console.log(bar.next())
console.log(bar.next())
console.log(bar.next())
console.log(bar.next())

异步函数 async 和 await

一个异步函数是在异步操作中被调用的函数。开发者可以使用 await 关键字等待异步结束的到来而不会阻塞程序的执行。
示例:

async function fn() {
    await console.log("执行结束");
}

fn();

Clssses

readonly

字段前缀加上readonly关键字表示只读,放置在创建对象修改字段

class Greeter {
    readonly name: string = "world";
    
    constructor(otherName?: string){
        if(otherName !== undefined) {
            this.name = otherName       // 如果 执行到该语句 将会报错
        }
    }
    err() {
        // this.name = "not ok";
    // Cannot assign to 'name' because it is a read-only property.
      }
}

const g = new Greeter();
// g.name = "also not ok";  Cannot assign to 'name' because it is a read-only property.

constructor

// 创建类
class Point {
    x: number;
    y: number;
    absX: number;
    absY: number;

    // 创建构造方法
    constructor(x = 0, y = 0, absX?: number, absY?: number) {
        this.x = x;
        this.y = y;
        this.absX = absX;
        this.absY = absY;
    }
    // 创建类方法
    printCoord(){
        console.log("The coordinate's x value is " + this.x);
        console.log("The coordinate's y value is " + this.y);
        if(this.absX != undefined){
            console.log("The coordinate's absX value is " + this.absX);
        }
        if(this.absX != undefined){
            console.log("The coordinate's absX value is " + this.absX);
        }
    }
}
// 创建类对象并实例化对象
let point = new Point(10, 20);
point.printCoord();
console.log("-----------------------分界线------------------------")
let point2 = new Point(100, 200, 300);
point.printCoord();

extends Classes

使用extends实现类的显示继承
Typeccript不支持类的多继承

class Animal {
    move() {
      console.log("Moving along!");
    }
  }
// 使用关键字extends实现继承
  class Dog extends Animal {
    woof(times: number) {
      for (let i = 0; i < times; i++) {
        console.log("woof!");
      }
    }
  }
   
  const d = new Dog();
  // 使用基类下的方法
  d.move();
  // 使用衍生类下的方法
  d.woof(3);

调用父类中的属性和方法;

class Father {
    protected name: string = "Father";
    getName() {
        return this.name
    }
}

class Son extends Father {
    name: string = "Son";   //  将name设置为public
    getName() {     //重写父类中的属性
        return this.name    
    }
    fatherName() {
        return super.getName()
    }
}

const person1 = new Father();
console.log(person1.getName);
// console.log(person1.name);       // Father类中不能直接访问 name属性


const person2 = new Son();
console.log(person2.getName())
console.log(person2.fatherName())
console.log(person2.name)           // Son类中可以直接访问 name属性

public

Typescript 类中默认访问权限是public

class Animal {
    name: string;
    constructor(theName: string){
        this.name = theName
    }

    run() {
        console.log(`${this.name} is running...`);
    }
}

const dog = new Animal("wangcai");
dog.run()
console.log(dog.name)       // 访问name属性

private

private修饰的变量方法只能在类中访问

class Animal {
    private name: string;
    constructor(theName: string){
        this.name = theName
    }

    run() {
        console.log(`${this.name} is running...`);
    }
}

const dog = new Animal("wangcai");
dog.run()
// console.log(dog.name)       // 只能在类中访问

protected

类中的变量或方法前添加protected关键字,在外部是不可以访问的,只能在衍生类或自身内部访问。

class Animal {
    protected name: string;
    constructor(theName: string){
        this.name = theName
    }

    run() {
        console.log(`${this.name} is running...`);
    }
}

class Dog extends Animal {
    constructor(dogName: string) {
        super(dogName);      // 调用父类的构造器
    }

    wangwang() {
        console.log(`${this.name} is wangwang...`);
    }
}

const dog = new Dog("wangcai");
dog.wangwang()
// console.log(dog.name)       
// Property 'name' is protected and only accessible through an instance of class 'Derived2'. This is an instance of class 'Base'.

类的多态

class Iphone {
    password:string;

    constructor(thePassword: string) {
        this.password = thePassword;
    }

    unlock(...resstParameter: string[]) {
        console.log(`using the password ${this.password} unlock`);
    }
}

class Iphone5s extends Iphone {
    constructor(thePasswrod: string) {
        super(thePasswrod);
    }

    unlockByFinger(fingerPrin?: string) {
        if(fingerPrin){
            console.log(`iphone5s using ${fingerPrin} finger unlock`);
            return true;
        }
    }
    unlock(fingerPrin?: string) {
        if(fingerPrin) {
            return this.unlockByFinger(fingerPrin);
        }
        super.unlock();
    }
}

class Iphonex extends Iphone {
    constructor(faceId: string) {
        super(faceId);
    }

    unlockByFaceID(faceID?: string) {
        if(faceID){
            console.log(`iphone5s using ${faceID} fingerPrint unlock`);
            return true;
        }
    }

    unlock(faceID?: string) {
        if(faceID) {
            return this.unlockByFaceID(faceID);
        }
        super.unlock();
    }
}

function testUnlock(iphone: Iphone, arg?: string) {
    arg ? iphone.unlock(arg) : iphone.unlock(arg);
}

const iphone5s = new Iphone5s("555555");
testUnlock(iphone5s);
testUnlock(iphone5s, "666666");
console.log("-----------------------分界线------------------------");
const iphonex = new Iphone5s("xxxxxx");
testUnlock(iphonex);
testUnlock(iphonex, "222222");

输出结果:

using the password 555555 unlock
iphone5s using 666666 finger unlock
-----------------------分界线------------------------
using the password xxxxxx unlock
iphone5s using 222222 finger unlock

Abstract Classes

抽象类不能通过new的方法创建实例,抽象类智能被继承。
抽象类中的抽象方法不需要在父类中实现,抽象方法需要在子类中实现。

abstract class Base {
    abstract getName(): string;

    printName() {
        console.log("Hello, " + this.getName());
    }
}

class Derived extends Base {
    getName() {         // 实现父类中的抽象方法
        return "world";
    }
}

const a = new Derived()
a.printName()       // 输出 Hello, world

Generic Classes

使用泛型在class 后用 来表示

class Box<T> {
    contents: T;
    constructor(value: T) {
        this.contents = value;
    }
}

const b = new Box("hello!")
// b.contents.length

const c = new Box(123)
// c.contents.toString()

类的单例模式

class Demo {
    private static instace: Demo;
    private constructor() {

    }

    static getInstance() {
        if(!this.instace) {
            return this.instace = new Demo()
        }
        return this.instace;
    }
}

const demo1 = Demo.getInstance();
const demo2 = Demo.getInstance();

if (demo1 === demo2) {
    console.log("相同对象")
}
else {
    console.log("不相同对象")
}


For 语句

以下通过一个加法函数来了解for循环和遍历列表

for

function add1(...list: number[]) :number {
    let result = 0;
    // 遍历列表方法 1
    let len = list.length;
    for(let i=0; i<len; i++) {
        result += list[i];
    }
    return result;
}

console.log(add1(1, 2, 3, 4, 5))	// 输出 15

for in

对于普通对象,没有部署原生的 iterator 接口,直接使用 for…of 会报错

遍历列表

for…in 循环:只能获得对象的键名,不能获得键值

function add2(...list: number[]) :number {
    let result = 0;

    // 遍历列表方法 2
    for(let index in list){
        result += list[index];
    }

    return result;
}

console.log(add2(1, 2, 3, 4, 5))	// 输出 15

遍历字典

for…of 循环:允许遍历获得键值

let dict:{[key: string]: string| number} = {
    "a": "1",
    "b": 2,
    "c": 3
}

for(let k in dict){
    console.log(dict[k]);
}

for of

function add3(...list: number[]) :number {
    let result = 0;

    // 遍历列表方法 3
    for(let value of list){
        result += value;
    }

    return result;
}

console.log(add3(1, 2, 3, 4, 5))	// 输出 15

forEach

forEach 循环无法中途跳出,break 命令或 return 命令都不能奏效

function add4(...list: number[]) :number {
    let result = 0;

    // 遍历列表方法 4
    list.forEach((val, index, array) => {
    	// val: list 中的值 val = list[index] 
    	// index: 列表索引
    	// 第二个列表是一个可选参数
        result += val;
        console.log(index + ":",  val)
        console.log(array)
    })

    return result;
}

console.log(add4(1, 2, 3, 4, 5))	// 输出 15

CSS的使用方式:

使用style属性

使用style属性:在HTML标签中,通过style属性来添加样式。

<p style="color: blue; font-size: 40px;">越走越漫长的道路</p>

使用style标签

在head标签中创建style标签

    <style>
        p {
            color: chartreuse;
            font-size: 80px;
            background-color: darkslateblue;
        }
    </style>

CSS文件

CSS文件:创建css文件,将样式放在文件中,然后在head中通过link标签引入该文件。
index.cs文件

p {
    color: chartreuse;
    font-size: 20px;
    background-color:darkslateblue;
}
.cls {
    color: chartreuse;
    font-size: 80px;
    background-color:darkslateblue;
}
#myid {
    color: chartreuse;
    font-size: 40px;
    background-color:darkslateblue;
}

html文件

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>display title</title>
    <link rel="stylesheet" href="./index.css">
</head>
<body>
    <H1 class="cls">html</H1>
    <p id="myid">路灯下黄昏的剪影</p>
    <p class="cls">越走越漫长的道路</p>
</body>
</html>

浏览器中使用Javascript

Javascript(简称js),负责让页面"动"起来,为页面添加动态效果。

使用JS的两种方式

script标签

script标签:在body标签的最后面,创建script标签。

<body>
    <H1 class="cls">在浏览器中使用 JS</H1>
    
    <script>
        // js代码
        let age = 18
        console.log(age)
    </script>
</body>

注意:html文件中的console.log()语句输出内容需要在浏览器控制台的console面板查看

独立js文件

独立js文件:创建index.js文件,在body标签的最后面,通过script标签引入

  1. 创建index.js文件
let person = {
    name: 'xiaoming000',
    age: 20
}

console.log(person)
  1. 在html文件中引入index.js文件
<body>
    <H1 class="cls">在浏览器中使用 JS</H1>

    <script src="./index.js"></script>
</body>

自动刷新浏览器

使用CSCode的Live Server插件,实现自动刷线浏览器。
作用:监视html或引入的css、js的变化,在保存文件时,该插件就会帮助我们自动刷新浏览器。
打开监视方式:在html文件上右键使用 Open with Live Server 方式打开
在这里插入图片描述

浏览器中运行Typescript

注意:浏览器中智能运行JS,无法直接运行TS,因此需要将TS转化为JS然后才能运行。

DOM操作

概述

DOM(Document Object Modal):文档对象模型。
DOM是浏览器提供的(浏览器特有),专门用来操作网页对象内容的一些JS对象。
目的:让我们可以使用JS/TS代码来操作页面(HTML)内容,让页面”动“起来,从而实现Web开发。
HTML:超文本标记语言,用来创建网页结构。
两者关系:浏览器根据HTML内容创建响应的DOM对象,也就是:每个HTML标签都应对应的DOM对象。

学习常用的DOM操作:

  1. 获取DOM元素(DOM对象)
  2. 设置样式
  3. 设置内容
  4. 绑定(解绑)事件

DOM操作的套路(技巧):先找人 后做事。
找人:获取DOM元素。
做事:设置样式、内容、绑定(解绑)实践。

获取元素

常用方法有两个:

  1. querySelect(selector)
    作用:获取某一个DOM元素。
  2. querySelectAll(selector)
    作用:同时获取多个DOM元素。

获取一个DOM元素:

document.querySelector(selector)

document对象:文档对象(整个页面),是操作页面内容的入口对象。
selector参数:是一个CSS选择器(标签、类、ID选择器等)。
作用:查询(获取)与选择器参数匹配的DOM元素,但是,只能获取第一个

示例:

let title = document.querySelector('#title')
// 解释:获取页面中id为title的DOM元素

index.html文件

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>浏览器中运行Ts</title>
</head>
<body>
    <h1 id="title">青花瓷</h1>

    <p class="c1">天青色等烟雨</p>
    <p class="c1">而我在等你</p>

    <script src="./index.js"></script>
</body>
</html>

index.ts文件

// 实例: 获取id为title的DOM元素
let title = document.querySelector('#title')
console.log(title)

let title1 = document.querySelector('.c1')
console.log(title1)

输出结果:
在这里插入图片描述

类型断言

问题:调用querySelector() 通过id选择器获取DOM元素时,拿到的元素类型都是Element.
因为无法确定id来去顶元素的类型,所以,该方法就返回了一个宽泛的类型:元素(Element)类型。不管是h1还是img都是元素。
导致问题:无法访问img元素的src属性。
原因:因为Element类型只是包含所有元素共有的属性和方法(比如:id属性、class属性等)。
解决方式:使用类型断言,来手动指定更加具体的类型(比如,此处应该比Element类型更加具体)。
语法

as 更加具体的类型

index.ts文件

// 实例: 获取id为title的DOM元素
let title = document.querySelector('#title')
console.log(title)

let img = document.querySelector('#image') as HTMLImageElement;
img.src = "./image2.png"

总结:
类型断言:手动指定**更加具体(精确)**的类型.
使用场景:当你比TS更加了解某个值的类型,并且需要执行具体的类型时。
技巧:通过 console.dir() 打印DOM对象,来查看该元素的类型。

获取多个元素

获取多个元素语法:

document.querySelectorAll(select);

作用:获取所有与选择器参数匹配的DOM元素,返回值时一个列表。
推荐:使用class选择器。
实例:

let list = document.querySelectorAll('.a');

解释:获取页面中所有class元素包含 a 的元素。


操作文本内容

读取:

dom.innerText

设置:

dom.innerText = "设置DOM文本"

注意:需要通过类型断言来指定DOM元素的具体类型,才可以使用innerText属性
注意:设置内容时,会覆盖原来的内容。如何实现追加内容?

dom.innerText += 'append text';

操作样式

DOM操作样式有两种操作方式:

  1. dom.sytle 属性:行内样式操作,可设置每个样式属性(比如:字体大小、文本颜色等)。
  2. dom。classList 属性:样式操作,也就是操作类名,比如,添加类名、移除类名等。

行内样式操作 style 属性

  • 读取:
dom.style.样式名称;
  • 设置:
dom.style.样式名称 = 样式值;
  • 示例:
dom.style.color= read;
dom.style.fontSize = 40px;
dom.style.display = "None";       	// 隐藏元素
dom.style.display = "block";      	// 显示元素
console.log(dom.style.fontSize); 	// 读取dom元素字体大小属性

类样式操作 classList 属性

类样式操作包含三种方法添加类名、移除类名、判断类名是否存在。

  • 添加类名:
dom.classList.add(类名1, 类名2, ...);
  • 移除类样式:
dom.classList.remove(类名1, 类名2, ...);
  • 判断类名是否存在:
    如果当前DOM元素中存在指定的类名返回true,反之则返回false

  • 示例:

title.classList.add("a", "b");          // 添加类样式

if(title.classList.contains("a")) {     // 判断dom元素中是否存在类样式 "a"
    title.classList.remove("a");            // 移除类样式
}

事件操作

在浏览器页面我们经常会通过鼠标悬停、点击或敲击键盘等操作,来操作元素提供的功能。
如果让我们自己实现这样的功能,就需要通过事件操作来实现。
实际上,移入鼠标、敲击键盘等,都是常见的DOM操作事件。
操作事件的两种方法:

  • addEventListener 添加(绑定)事件。
  • removeEventListener 移除(绑定)事件。

添加事件

作用:给DOM元素添加事件。

dom.addEventListener(事件名称, 事件处理程序)

事件名称:字符串,比如 ‘click’ (鼠标点击事件)、 ‘mouseenter’ (鼠标进入事件)。
时间处理程序:回调函数,指定要实现的功能,该函数会在出发时间时调用。

示例:

  • index.html 文件
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>浏览器中运行Ts</title>
</head>
<body>
    <button name="btn">来打我呀!</button>

    <script src="./index.js"></script>
</body>
</html>
  • index.ts 文件
// 实例: 实现鼠标点击操作
let myBtn = document.querySelector("[name=btn]") as HTMLButtonElement

myBtn.addEventListener('click', function () {
    console.log("打不着打不着...");
})

myBtn.addEventListener('mouseenter', function () {
    console.log("你来啦")
})

事件对象

事件对象(event),是事件处理程序(回调函数)的参数。
表示:与当前事件相关的信息。
比如:事件类型(type)、出发事件的DOM元素(target)等。

示例:

// 实例: 实现鼠标点击操作来操作事件对象
let myBtn = document.querySelector("[name=btn]") as HTMLButtonElement

myBtn.addEventListener('click', function (event) {
    console.log(event.type)
    let btn = event.target as HTMLButtonElement
    btn.style.fontSize = "40px";	// 修改btn按钮字体大小
})

移除事件

removeEventListener 移除事件
作用移除给DOM元素添加的事件,移除后事件就不会再出发了。

dom.removeEventListener(事件名称, 事件处理程序)

事件名称:同添加事件的第一参数。
事件处理程序:必须要跟添加事件的事件处理程序是同一个,否则无法移除
示例:

// 实例: 实现除click事件
let myBtn = document.querySelector("[name=btn]") as HTMLButtonElement

function handleClick(event: MouseEvent) {
    console.log(event.type)
    let btn = event.target as HTMLButtonElement
    btn.style.fontSize = "40px";
}

myBtn.addEventListener('click', handleClick)            // 添加 click 事件
myBtn.removeEventListener('click', handleClick)         // 移除 click 事件

单次出发事件

如果事件只需要出发一次,可以添加事件处理。
处理方式:传入第三个参数,将once属性设置为true。

btn.addEventListener('click', function () {}, { once: true})

once: 如果值为true, 会出发时间后自动将事件移除,达到只出发一次的目的。

示例:

// 实例: 实现单次出发事件
let myBtn = document.querySelector("[name=btn]") as HTMLButtonElement

function handleClick(event: MouseEvent) {
    console.log(event.type)
    let btn = event.target as HTMLButtonElement
    btn.style.fontSize = "40px";
}

myBtn.addEventListener('click', handleClick, {once: true})            // 添加 click 事件
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值