# JavaScript
1、前端知识体系
前端三要素
HTML(结构)
- 负责网页的内容和结构
CSS(表现)
- 网页的表现样式
- 是一门标记语言,并不是编程语言,不可以自定义变量,不可以引用(不具备任何语法支持)
- CSS预处理器:“用一种专门的编程语言,进行Web页面样式设计,再通过编译器转化为正常的CSS文件,以供项目使用”
- LESS:基于NodeJS,通过客户端处理,使用简单。功能比SASS简单,解析效率也低于SASS,但在实际开发中足够了,所以如果我们后台人员如果需要的话,建议使用LESS
JavaScript(行为)
- 一种弱类型脚本语言(最流行),其源码不需经过编译,而是由浏览器解释运行,用于控制网页的行为,即其源代码在发往客户端运行之前不需要经过编译,而是将文本格式的字符代码发送给浏览器,由浏览器解释运行
2、JS概述
javaScript是一门世界上最流行的脚本语言,一个合格的后端人员,必须精通JavaScript
3、JS快速入门
3.1引入
3.1.1、内部标签
<script>
//....
<script>
3.1.2、外部引入
test.js
alert("hello,world");
test.html
<!--外部引入
注意:script必须成对出现
-->
<script src="js/test.js"></script>
<!--不用显示定义type,也默认就是javaScript-->
<script type="text/javascript"></script>
测试代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<!--script标签内,写Javascript代码-->
<!--<script>
alert("hello,world");
</script>-->
<!--外部引入
注意:script必须成对出现
-->
<script src="js/hj.js"></script>
<!--不用显示定义type,也默认就是javaScript-->
<script type="text/javascript"></script>
</head>
<body>
<!--这里也可以存放-->
</body>
</html>
3.2、基本语法入门
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<!--JavaScript严格区分大小写-->
<script>
// 1. 定义变量 变量类型 变量名 = 变量值
var score = 1 ;
//alert(num)
// 2. 条件控制
if (score > 60 && score < 70){
alert("60~70");
}else if(score > 70 && score < 80){
alert("70~80");
}else{
alert("other")
}
</script>
</head>
<body>
</body>
</html>
- 浏览器必备调试须知
3.3、数据类型
数值,文本,图形,音频,视频
- 变量
var name;
3.3.1、number
js不区分小数和整数,Number
123//整数123
123.1//浮点数123.1
1.123e3//科学计数法
-99//负数
NaN //not a number
Infinity // 表示无限大
3.3.2、字符串
‘abc’ “abc”
3.3.3、布尔值
true,false
3.3.4、逻辑运算
&& 两个都为真,结果为真
|| 一个为真,结果为真
! 真即假,假即真
3.3.5、==比较运算符(重要) ==
=
1,"1"
== 等于(类型不一样,值一样,也会判断为true)
=== 绝对等于(类型一样,值一样,结果为true)
这是一个JS的缺陷,坚持不要使用 == 比较
须知:
- NaN === NaN,这个与所有的数值都不相等,包括自己
- 只能通过isNaN(NaN)来判断这个数是否是NaN
3.3.6、浮点数问题
尽量避免使用浮点数进行运算,存在精度问题
3.3.7、null 和 undefined
- null:null 空
- undefined:undefined 未定义
3.3.7、数组
Java的数组必须是相同类型的对象~,JS中不需要这样
//保证代码的可读性,尽量使用[]
var arr = [1,2,3,4,5,'hello',null,true];
//第二种定义方法
new Array(1,2,3,4,5,'hello');
注意:取数字下标:如果越界了,就会 报undefined
3.3.8、对象
对象是大括号,数组是中括号
每个属性之间使用逗号隔开,最后一个属性不需要逗号
// Person person = new Person(1,2,3,4,5);
var person = {
name:'Tom',
age:3,
tags:['js','java','web','...']
}
取对象值
person.name
> "Tom"
person.age
> 3
3.3.9 use strict(严格检查格式)
- 局部变量建议使用let去定义
4、数据类型
4.1、字符串
4.1.1、正常字符串我们使用 单引号,或者双引号包裹
4.1.2、注意转义字符 \
\'
\n
\t
\u4e2d \u##### Unicode字符
\x41 Ascall字符
4.1.3、 多行字符串编写
//tab 上面 esc下面
var msg =
`hello
world
你好呀
nihao
`
4.1.4、 模板字符串
//tab 上面 esc下面
'use strict'
let name='zs';
let age=15;
let msg=`你哈呀${name},你的年龄是${age}`
4.1.5、 字符串长度
str.length
4.1.6、大小写转换
//注意,这里是方法,不是属性了
student.toUpperCase();
student.toLowerCase();
4.1.7、student.indexof(‘t’)
4.1.8、substring,从0开始
[)
student.substring(1)//从第一个字符串截取到最后一个字符串
student.substring(1,3)//[1,3)
4.2、数组
Array可以包含任意的数据类型
var arr = [1,'a',3,'ccasd',5,6];//通过下标取值和赋值
4.2.1、长度 arr.length
注意:假如给arr.lennth赋值,数组大小就会发生变化~,如果赋值过小,元素就会丢失
4.2.2、indexOf
通过元素获得下标索引
arr.indexOf(3)
2
字符串的"2"和数字2是不同的
4.2.3、slice()
截取Array的一部分,返回的一个新数组,类似于String中substring
4.2.4、push(),pop() 尾部
push:压入到尾部
pop:弹出尾部的一个元素
4.2.5、unshift(),shift() 头部
unshift:压入到头部
shift:弹出头部的一个元素
4.2.6、排序sort()
(3)["B","C","A"]
arr.sort()
(3)["A","B","C"]
4.2.7、元素反转reverse()
(3)["A","B","C"]
arr.reverse()
(3)["C","B","A"]
4.2.8、concat()
注意:concat()并没有修改数组,只是会返回一个新的数组
4.2.9、连接符join
打印拼接数组,使用特定的字符串连接
4.2.10、多维数组
4.3、对象
若干个键值对
var 对象名 = {
属性名:属性值,
属性名:属性值,
属性名:属性值
}
//定义了一个person对象,它有四个属性
var person = {
name:"Tom",
age:3,
email:"123456798@QQ.com",
score:66
}
Js中对象,{…}表示一个对象,建制对描述属性xxx:xxx,多个属性之间用逗号隔开,最后一个属性不加逗号!
JavaScript中的所有的键都是字符串,值是任意对象!
4.3.1、对象赋值
使用一个不存在的对象属性,不会报错!undefined
4.3.2、动态的删减属性,通过delete删除对象的属性
4.3.3、动态的添加,直接给新的属性添加值即可
4.3.4、判断属性值是否在这个对象中!
xxx in xxx
4.3.5、判断一个属性是否是这个对象自身拥有的
hasOwnProperty()
4.4、流程控制
4.4.1、if判断
4.4.2、while循环,避免程序死循环
4.4.3、for循环![在这里插入图片描述](https://i-blog.csdnimg.cn/blog_migrate/099f030ea792ddf25f83fe98868eb3b5.png)
4.4.4、forEach循环(ES5.1特性)
4.4.5、for …in-------下标
4.4.5、for …of-------值
4.5、Map和Set(ES6)
4.5.1、Map
4.5.2、Set 无序不重复的集合
4.6、iterator
4.6.1、遍历数组
<script>
var arr=[2,5,0,1,3,8,6,5];
for (let number of arr) {
console.log(number);
}
</script>
4.6.2、遍历Map
let map=new Map([['zs',18],['ls',20],['ww',20]])
for (let mapElement of map) {
console.log(mapElement)
}
4.6.3、遍历Set
let set=new Set([1,3,6,9])
for (let setElement of set) {
console.log(setElement)
}
5、函数
5.1、定义函数
5.1.1、方式一
<script>
function abc(x){
if(x>0){
return x;
}else{
return -x;
}
}
</script>
5.1.2、方式二
function(x){…}这是一个匿名函数。但是可以把结果赋值给abs,通过abs就可以调用函数
<script>
let abc=function (x) {
if(x>0){
return x;
}else{
return -x
}
}
</script>
注:
- 一旦执行到return代表函数结束,返回结果!
- 如果没有执行return,函数执行完也会返回结果,结果就是undefined/NaN
5.1.3、参数
- JS可以传任意个参数,也可以不传递参数
- 参数规避:手动判断
<script>
let abc=function (x) {
if(typeof x!=='number'){
throw 'Not a Number!'
}
if(x>0){
return x;
}else{
return -x
}
}
</script>
- 多参数问题
arguments
是JS免费赠送的关键字,是一个数组,代表传进方法的所有参数
<script>
let abc=function (x) {
console.log('x==>'+x)
for(let i=0;i<arguments.length;i++){
console.log(arguments[i])
}
if(x>0){
return x;
}else{
return -x
}
}
</script>
rest
获取除了已经定义的参数之外的所有参数 …
不使用rest
使用rest
<script>
let aaa=function (x,y,...rest) {
console.log(x)
console.log(y)
console.log(rest)
}
</script>
注:rest参数只能写在最后面,必须用…标识。
5.2、变量作用域
5.2.1 在函数体重声明,则在函数体外不可以使用~(如果非要用,闭包)
<script>
function f() {
let x=1;
console.log(x)
}
console.log(x)
</script>
5.2.2 如果两个函数使用了相同的变量名,只要在函数内部就不冲突
function f() {
let x=1;
console.log(x)
}
function f1() {
let x='a';
console.log(x)
}
f();
f1();
</script>
5.2.3内部函数可以访问外部函数的成员,反之则不行
<script>
function f() {
let x=1;
console.log(x)
f1()
function f1() {
console.log(x)
}
}
</script>
5.2.4内部函数变量和外部函数变量,重名()就近原则
假设在JavaScript中,函数查找变量从自身函数开始~, 由“内”向“外”查找,假设外部存在这个同名的函数变量,则内部函数会屏蔽外部函数的变量。
<script>
function f() {
let x=1;
console.log('outer'+x)
f1()
function f1() {
x='a'
console.log('inner'+x)
}
}
</script>
5.2.5 提示变量作用域
<script>
function f() {
var x="x"+y;
console.log(x);
var y="y";
console.log(x);
}
</script>
说明:js执行引擎,自动提升了y的声明,但是不会提升变量y的赋值
等价
<script>
function f() {
var y;
var x="x"+y;
console.log(x);
y="y";
console.log(x);
}
</script>
这个是在javascript建立之初就存在的特性。 养成规范:所有 的变量定义都放在函数的头部,不要乱放,便于代码维护;
5.2.6全局变量
<script>
var x=1;
function f() {
console.log(x);
}
function f2() {
console.log(x);
}
f();
f2();
console.log(x);
</script>
5.2.7全局对象window
<script>
var x='1231412';
alert(x)
alert(window.x)//默认所有的全局变量都会绑定在windows对象下
</script>
alert() 这个函数本身也是一个window的变量;
javascript实际上只有一个全局作用域,任何变量(函数也可以视为变量),假设没有在函数作用范围内找到,就会向外查找,如果在全局作用域都没有找到,就会报错 Refrence
5.2.8规范
- 问题:由于我们的所有变量都会绑定到window上,。如果不同的js文件,使用了相同的全局变量,就会产生冲突—>如何减少这样的冲突?
- 方案:定义唯一全局变量
把自己的代码全部放入自己定义的唯一空间名字中,降低全局命名冲突问题~
jQuery中就是使用的该方法:jQuery.name,简便写法:$()
5.2.9局部作用域
<script>
function a(){
for (var i = 0; i < 10; i++) {
console.log(i)
}
console.log(i+1)//存在问题:i出了这个作用域还可以使用
}
</script>
ES6的let
关键字,解决了局部作用域冲突的问题!
<script>
function a(){
for (let i = 0; i < 10; i++) {
console.log(i)
}
console.log(i+1)//存在问题:i出了这个作用域还可以使用
}
</script>
建议大家都用let去定义局部作用域的变量;
5.2.10常量
- 在ES6之前,只要用全部大写字母命名的变量就是常量;建议不要修改这样的值(约定)。
- 在ES6引入了常量关键字 const
6、内部对象
6.1、标准对象和包装对象
6.1.1、 标准对象
注:
1、null的类型是object,Array的类型也是object,如果我们用typeof将无法区分出null、Array和通常意义上的object——{}
2、typeof操作符可以判断出number
、boolean
、string
、function
和undefined
;
3、判断Array
要使用Array.isArray(arr);
4、判断null
请使用myVar === null;
5、判断某个全局变量是否存在用typeof window.myVar === 'undefined'
6、函数内部判断某个变量是否存在用typeof myVar === 'undefined'
6.1.2、包装对象
number、boolean和string都有包装对象。没错,在JavaScript中,字符串也区分string类型和它的包装类型。包装对象用new创建
var n = new Number(123); // 123,生成了新的包装类型
var b = new Boolean(true); // true,生成了新的包装类型
var s = new String('str'); // 'str',生成了新的包装类型
特点:虽然包装对象看上去和原来的值一模一样,显示出来也是一模一样,但他们的类型已经变为object
了!所以,包装对象和原始值用=比较会返回false
typeof new Number(123); // 'object'
new Number(123) === 123; // false
typeof new Boolean(true); // 'object'
new Boolean(true) === true; // false
typeof new String('str'); // 'object'
new String('str') === 'str'; // false
6.2、Date
6.2.1、基本使用
6.2.2、转换
6.3、JSON
6.3.1、定义
在javascript中,一切皆为对象,任何js支持的类型都可以用JSON表示
6.3.2、格式
- 对象都用{}
- 数组都用[]
- 所有的键值对 都是用key:value
6.3.3、JSON字符串和js对象转化
JSON和JS对象的区别
- son本身是(格式化)字符串
- 对象是键值对
6.4、AJAX
- 原生的js写法 xhr异步请求
- jQuery封装好的方法$(#name).ajax("")
- axios请求
7、正则表达式
正则表达式是一种用来匹配字符串的强有力的武器。它的设计思想是用一种描述性的语言来给字符串定义一个规则,凡是符合规则的字符串,我们就认为它“匹配”了,否则,该字符串就是不合法的。
7.1、规则
7.1.1、精确匹配
在正则表达式中,如果直接给出字符,就是精确匹配
\d
:可以匹配一个数字00\d
可以匹配007
,但无法匹配00A
;\d\d\d
可以匹配010
;
\w
:可以匹配一个字母或数字\w\w
可以匹配js
;
.
:可以匹配任意字符js.
可以匹配jsp
、jss
、js!
等等
7.1.2、变长的字符
*
:表示任意个字符(包括0个)+
:表示至少一个字符?
:表示0个或1个字符{n}
:表示n个字符{n,m}
:表示n-m个字符
7.1.3、解析
\d{3}\s+\d{3,8}
\d{3}
表示匹配3个数字,例如’010’;\s
可以匹配一个空格(也包括Tab等空白符),所以\s+
表示至少有一个空格,例如匹配' '
,'\t\t'
等;\d{3,8}
表示3-8个数字,例如’1234567’
综合起来,上面的正则表达式可以匹配以任意个空格隔开的带区号的电话号码
如果要匹配’010-12345’这样的号码呢?由于'-'
是特殊字符,在正则表达式中,要用'\'
转义,所以,上面的正则是\d{3}\-\d{3,8}
7.1.4、更精确匹配(进阶)
[]
[0-9a-zA-Z\_]
可以匹配一个数字、字母或者下划线[0-9a-zA-Z\_]+
可以匹配至少由一个数字、字母或者下划线组成的字符串,比如a100
,0_Z
,js2015
等等;[a-zA-Z\_\$][0-9a-zA-Z\_\$]*
可以匹配由字母或下划线、$
开头,后接任意个由一个数字、字母或者下划线、$组成的字符串,也就是JavaScript允许的变量名;[a-zA-Z\_\$][0-9a-zA-Z\_\$]{0, 19}
更精确地限制了变量的长度是1-20个字符(前面1个字符+后面最多19个字符)
A|B
可以匹配A或B,所以(J|j)ava(S|s)cript可以匹配JavaScript
、Javascript
、javaScript
或者javascript
^
表示行的开头,^\d
表示必须以数字开头$
表示行的结束,\d$
表示必须以数字结束
8、面向对象编程
8.1、概念
8.1.1、Java中的类和实例
类
:类是对象的类型模板,例如,定义Student
类来表示学生,类本身是一种类型,Student
表示学生类型,但不表示任何具体的某个学生;实例
:实例是根据类创建的对象,例如,根据Student
类可以创建出xiaoming、xiaohong、xiaojun
等多个实例,每个实例表示一个具体的学生,他们全都属于Student类型
8.1.2、JavaScript中
JavaScript不区分类和实例的概念,而是通过原型
(prototype)来实现面向对象编程
- 原型是指当我们想要创建xiaoming这个具体的学生时,我们并没有一个Student类型可用。那怎么办?恰好有这么一个现成的对象:
var robot = {
name: 'Robot',
height: 1.6,
run: function () {
console.log(this.name + ' is running...');
}
};
- 我们看这个
robot
对象有名字,有身高,还会跑,有点像小明,干脆就根据它来“创建”小明得了!于是我们把它改名为Student
,然后创建出xiaoming
var Student = {
name: 'Robot',
height: 1.2,
run: function () {
console.log(this.name + ' is running...');
}
};
var xiaoming = {
name: '小明'
};
xiaoming.__proto__ = Student;
- 注意最后一行代码把
xiaoming
的原型指向了对象Student,看上去xiaoming
仿佛是从Student
继承下来的:
xiaoming.name; // '小明'
xiaoming.height;//1.2
xiaoming.run(); // 小明 is running...
-
xiaoming
有自己的name属性,但并没有定义run()方法。不过,由于小明是从Student继承而来,只要Student
有run()方法,xiaoming
也可以调用:
JavaScript的原型链和Java的Class区别就在,它没有“Class”的概念,所有对象都是实例,所谓继承关系不过是把一个对象的原型指向另一个对象而已。 -
如果你把
xiaoming
的原型指向其他对象:
var Bird = {
fly: function () {
console.log(this.name + ' is flying...');
}
};
xiaoming.__proto__ = Bird;
- 现在
xiaoming
已经无法run()了,他已经变成了一只鸟:
xiaoming.fly(); // 小明 is flying...
在JavaScrip代码运行时期,你可以把xiaoming
从Student
变成Bird
,或者变成任何对象。
- 注:上述代码仅用于演示目的。在编写JavaScript代码时,不要直接用obj.proto__去改变一个对象的原型,并且,低版本的IE也无法使用__proto。
Object.create()
方法可以传入一个原型对象,并创建一个基于该原型的新对象,但是新对象什么属性都没有,因此,我们可以编写一个函数来创建xiaoming:
// 原型对象:
var Student = {
name: 'Robot',
height: 1.2,
run: function () {
console.log(this.name + ' is running...');
}
};
function createStudent(name) {
// 基于Student原型创建一个新对象:
var s = Object.create(Student);
// 初始化新对象:
s.name = name;
return s;
}
var xiaoming = createStudent('小明');
xiaoming.run(); // 小明 is running...
xiaoming.__proto__ === Student; // true
8.2、创建对象
8.2.1、方式一
- JavaScript对每个创建的对象都会设置一个
原型
,指向它的原型对象
- 当我们用
obj.xxx
访问一个对象的属性时,JavaScript引擎先在当前对象上查找该属性,如果没有找到,就到其原型对象上找,如果还没有找到,就一直上溯到Object.prototype对象
,最后,如果还没有找到,就只能返回undefined。- 创建一个Array对象
var arr = [1, 2, 3];
- 其原型链
arr ----> Array.prototype ----> Object.prototype ----> null
Array.prototype
定义了indexOf()、shift()
等方法,因此你可以在所有的Array
对象上直接调用这些方法
很容易想到,如果原型链很长,那么访问一个对象的属性就会因为花更多的时间查找而变得更慢,因此要注意不要把原型链搞得太长
- 创建一个Array对象
8.2.2、方式二(构造函数)
- 先定义构造函数
function Student(name) {
this.name = name;
this.hello = function () {
alert('Hello, ' + this.name + '!');
}
}
- 用关键字new来调用这个函数,并返回一个对象
var xiaoming = new Student('小明');
xiaoming.name; // '小明'
xiaoming.hello(); // Hello, 小明!
注意,如果不写new
,这就是一个普通函数,它返回undefined
。但是,如果写了new,它就变成了一个构造函数,它绑定的this
指向新创建的对象,并默认返回this
,也就是说,不需要在最后写return this
;。
xiaoming
的原型链
xiaoming ----> Student.prototype ----> Object.prototype ----> null
- xiaoming的原型指向函数Student的原型。如果你又创建了xiaohong、xiaojun,那么这些对象的原型与xiaoming是一样的:
xiaoming ↘
xiaohong -→ Student.prototype ----> Object.prototype ----> null
xiaojun ↗
8.3、class集继承
8.3.1、class关键字
- 定义一个类、属性、方法
class Person{
constructor(name) {
this.name=name
}
run(){
alert(this.name+"can run")
}
}
var zz=new Person('zz');
zz.run();
8.3.2、继承
class Person{
constructor(name) {
this.name=name
}
run(){
alert(this.name+"can run")
}
}
var zz=new Person('zz');
zz.run();
class Children extends Person{
constructor(name,age) {
super(name);
this.age=age;
}
say(){
alert(this.name+"是个孩子")
}
}
var c=new Children('cc',20);
c.say()
本质:查看对象原型
8.3.3、原型链
9、操作BOM对象
BOM:浏览器对象模型
- JavaScript和浏览器的关系
JS的诞生就是为了让它能在浏览器中运行
JavaScript可以获取浏览器提供的很多对象,并进行操作
9.1、window
window
对象不但充当全局作用域,而且表示浏览器窗口
- 内部宽高是指除去菜单栏、工具栏、边框等占位元素后,用于显示网页的净宽高;
- outer~可以获取浏览器窗口的整个宽高
9.2、navigator(不建议使用)
navigator
对象表示浏览器的信息,最常用的属性包括- navigator.appName:浏览器名称;
- navigator.appVersion:浏览器版本;
- navigator.language:浏览器设置的语言;
- navigator.platform:操作系统类型;
- navigator.userAgent:浏览器设定的User-Agent字符串
注:大多数时候,我们不会使用navigator对象,因为会被人为修改!不建议使用这些属性来判断和编写代码
9.3、screen
screen对象表示屏幕的信息,常用的属性有
- screen.width:屏幕宽度,以像素为单位;
- screen.height:屏幕高度,以像素为单位;
- screen.colorDepth:返回颜色位数,如8、16、24。
9.4、location(重要)
- location对象表示当前页面的URL信息
- 可以用
location.href
获取。要获得URL各个部分的值
location.protocol; // 'http'
location.host; // 'www.example.com'
location.port; // '8080'
location.pathname; // '/path/index.html'
location.search; // '?a=1&b=2'
location.hash; // 'TOP'
要加载一个新页面,可以调用**location.assign()**。
如果要重新加载当前页面,调用**location.reload()**
9.5、document(内容DOM)
document
对象表示当前页面。由于HTML在浏览器中以DOM
形式表示为树形结构,document对象
就是整个DOM树的根节点。
document.title="phx132"
9.5.1、查找DOM树的某个节点
- 要查找DOM树的某个节点,需要从document对象开始查找。最常用的查找是根据ID和Tag Name
- .getElementById()可以按ID获得一个DOM节点
- .getElementsByTagName()可以按Tag名称获得一组DOM节点
<dl id="drink-menu" style="border:solid 1px #ccc;padding:6px;">
<dt>摩卡</dt>
<dd>热摩卡咖啡</dd>
<dt>酸奶</dt>
<dd>北京老酸奶</dd>
<dt>果汁</dt>
<dd>鲜榨苹果汁</dd>
</dl>
<script>
var menu = document.getElementById('drink-menu');
var drinks = document.getElementsByTagName('dt');
var i, s;
s = '提供的饮料有:';
for (i=0; i<drinks.length; i++) {
s = s + drinks[i].innerHTML + ',';
}
console.log(s);
</script>
9.5.2、获取cookie
- 劫持cookie原理 www.taobao.com
服务器端可以设置cookie为httpOnly
9.6、history(不建议使用)
history代表浏览器的历史记录
10、操作DOM对象(重点)
由于HTML文档被浏览器解析后就是一棵DOM树,要改变HTML的结构,就需要通过JavaScript来操作DOM。始终记住DOM是一个树形结构
10.1、DOM节点操作:
- 更新:更新该DOM节点的内容,相当于更新了该DOM节点表示的HTML的内容;
- 遍历:遍历该DOM节点下的子节点,以便进行进一步操作;
- 添加:在该DOM节点下新增一个子节点,相当于动态增加了一个HTML节点;
- 删除:将该节点从HTML中删除,相当于删掉了该DOM节点的内容以及它包含的所有子节点。
注:要操作一个Dom节点,就必须要先获得这个Dom节点
10.2、获得Dom节点
<div id="father">
<h1>h1</h1>
<p id="p1"> p1</p>
<p class="p2"> p2</p>
</div>
这是原生代码,之后我们尽量都使用jQuery();
10.3、更新节点
10.3.1、操作文本
- innerHTML:这个方式非常强大,不但可以修改一个DOM节点的文本内容,还可以直接通过HTML片段修改DOM节点内部的子
- innerText或textContent:可以自动对字符串进行HTML编码,保证无法设置任何HTML标签
10.3.2、操作css![在这里插入图片描述](https://i-blog.csdnimg.cn/blog_migrate/894560d73e6d7876b2f0c3fe5253d4ba.png)
10.3、删除节点
删除节点的步骤:先获取父节点,再通过父节点删除自己
// 拿到待删除节点:
var self = document.getElementById('to-be-removed');
// 拿到父节点:
var parent = self.parentElement;
// 删除:
var removed = parent.removeChild(self);
removed === self; // true
当你遍历一个父节点的子节点并进行删除操作时,要注意,children属性是一个只读属性,并且它在子节点变化时会实时更新。
<div id="parent">
<p>First</p>
<p>Second</p>
</div>
<script>
var parent = document.getElementById('parent');
parent.removeChild(parent.children[0]);
parent.removeChild(parent.children[1]); // <-- 浏览器报错
</script>
浏览器报错:parent.children[1]不是一个有效的节点。原因就在于,当<p>First</p>
节点被删除后,parent.children的节点数量已经从2变为了1,索引[1]已经不存在了。因此,删除多个节点时,要注意children属性时刻都在变化。
10.4、插入节点
10.4.1、innerHTML实现插入
我们获得了某个Dom节点,假设这个dom节点是空的,我们通过innerHTML就可以增加一个元素了
例如,<div></div>
,那么,直接使用innerHTML = 'child’就可以修改DOM节点的内容,,相当于“插入”了新的DOM节点
10.4.2、appendChild实现插入
<!-- HTML结构 -->
<div id="list">
<p id="java">Java</p>
<p id="python">Python</p>
<p id="scheme">Scheme</p>
<p id="js">JavaScript</p>
</div>
<script>
var list = document.getElementById('list'),
var haskell = document.createElement('p');
//haskell.setAttribute("id","haskell");
haskell.id = 'haskell';
//haskell.setAttribute("innerText ","Haskell");
haskell.innerText = 'Haskell';
list.appendChild(haskell);
</script>
10.4.2、insertBefore实现插入
<!-- HTML结构 -->
<div id="list">
<p id="java">Java</p>
<p id="python">Python</p>
<p id="scheme">Scheme</p>
</div>
<script>
var list = document.getElementById('list'),
var ref = document.getElementById('python'),
var haskell = document.createElement('p');
haskell.id = 'haskell';
haskell.innerText = 'Haskell';
list.insertBefore(haskell, ref);
</script>
10、操作表单(重点)
10.1、 表单
文本框----text
下拉框----select
单选框----radio
多选框----checkbox
隐藏域----hidden
密码框----password
...
10.2、 获取表单信息
<body>
<form action = "post">
<p>
<span>用户名:</span><input type="text" id = "username" />
</p>
<!--多选框的值就是定义好的value-->
<p>
<span>性别:</span>
<input type = "radio" name = "sex" value = "man" id = "boy"/>男
<input type = "radio" name = "sex" value = "woman" id = "girl"/>女
</p>
</form>
<script>
var input_text = document.getElementById("username");
var boy_radio = document.getElementById("boy");
var girl_radio = document.getElementById("girl");
//得到输入框的值
input_text.value
//修改输入框的值
input_text.value = "value";
//对于单选框,多选框等等固定的值,boy_radio.value只能取到当前的值
boy_radio.checked;//查看返回的结果,是否为true,如果为true,则被选中。
girl_radio.checked = true;//赋值
</script>
</body>
10.3、 提交表单
md5加密密码,表单优化
<!DOCTYPE html>
<html lang = "en">
<head>
<meta charset = "UTF-8">
<title>Title</title>
<!--MD5加密工具类-->
<script src = "https://cdn.bootcss.com/blueimp-md5/2.10.0/js/md5.min.js">
</script>
</head>
<body>
<!--表达绑定提交事件
οnsubmit= 绑定一个提交检测的函数,true,false
将这个结果返回给表单,使用onsubmit接收
-->
<form action = "https://www.baidu.com" method = "post" onsubmit = "return aaa()">
<p>
<span>用户名:</span><input type="text" id = "username" name = "username"/>
</p>
<p>
<span>密码:</span><input type="password" id = "password" />
</p>
<input type = "hidden" id = "md5-password" name = "password">
<!--绑定事件 onclick 被点击-->
<button type = "submit">提交</button>
</form>
<script>
function aaa(){
alert(1);
var username = document.getElementById("username");
var pwd = document.getElementById("password");
var md5pwd = document.getElementById("md5-password");
//pwd.value = md5(pwd,value);
md5pwd.value = mad5(pwd.value);
//可以校验判断表单内容,true就是通过提交,false就是阻止提交
return false;
}
</script>
</body>
</html>
11、jQuery
javaScript和jQuery的关系:jQuery库,里面存在大量的JavaScript函数
11.1、获取jQuery
公式:$(selector).action()
<!DOCTYPE html>
<html lang = "en">
<head>
<meta charset = "UTF-8">
<title>Title</title>
<script src="lib/jquery-3.4.1.js"></script>
</head>
<body>
<a href="" id = "test-jquery">点我</a>
<script>
//选择器就是css选择器
$('#test-jquery').click(function(){
alert('hello,jQuery!');
});
</script>
</body>
</html>
11.2、选择器
//原生js,选择器少,麻烦不好记
//标签
document.getElementByTagName();
//id
document.getElementById();
//class
document.getElementByClassName();
//jQuery css中的选择器它全部都能用!
$('p').click();//标签选择器
$('#id1').click();//id选择器
$('.class1').click;//class选择器
11.3、事件
mousedown()(jQuery)----按下
mouseenter()(jQuery)
mouseleave()(jQuery)
mousemove()(jQuery)----移动
mouseout()(jQuery)
mouseover()(jQuery)
mouseup()(jQuery)
<!DOCTYPE html>
<html lang = "en">
<head>
<meta charset = "UTF-8">
<title>Title</title>
<script src="lib/jquery-3.4.1.js"></script>
<style>
#divMove{
width:500px;
height:500px;
border:1px solid red;
}
</style>
</head>
<body>
<!--要求:获取鼠标当前的一个坐标-->
mouse:<span id = "mouseMove"></span>
<div id = "divMove">
在这里移动鼠标试试
</div>
<script>
//当网页元素加载完毕之后,响应事件
//$(document).ready(function(){})
$(function(){
$('#divMove').mousemove(function(e){
$('#mouseMove').text('x:'+e.pageX+"y:"+e.pageY)
})
});
</script>
</body>
</html>
11.4、操作DOM
11.4.1、节点文本操作
$('#test-ul li[name=python]').text();//获得值
$('#test-ul li[name=python]').text('设置值');//设置值
$('#test-ul').html();//获得值
$('#test-ul').html('<strong>123</strong>');//设置值
11.4.2、CSS的操作
$('#test-ul li[name=python]').css({"color","red"});
11.4.3、元素的显示和隐藏,:本质display:none
$('#test-ul li[name=python]').show();
$('#test-ul li[name=python]').hide();
11.4.4、娱乐测试
$(window).width()
$(window).height()
$('#test-ul li[name=python]').toggle();
11.4.5、ajax()
$('#form').ajax()
$.ajax({url:"test.html",context:document.body,success:function(){
$(this).addClass("done");
}})