1.JS概述 window.sessionStorage.setItem("flag", flag);原生JS也可以存SessionStorage 尚硅谷的视频教程: 不用在服务端,在客户端就验证了。 解释型VS编译型;事件驱动;客户端的脚本语言;脚本语言(对环境依赖不强); 加强用户体验; JavaScript:雷锋、雷锋塔;周杰、周杰伦 (1)语言的介绍: ◆ 计算机是一个有人的机器,人下达什么指令,它来执行什么。 ◆ 目的就是人与计算机交流,人通过语言来操作计算机。 ◆ 编程语言中英文本质上没有区别,只是语法上的不同。 ◆ 语言的发展:机器语言-符号语言-高级语言。(2)起源: JS诞生与1995年,做网页中的前端验证,用户名长度,密码,邮箱是否正确… 时代需要验证的语言存在,但是当时没有。 除了验证,还有页面的动态效果、游戏等多种实际的应用。 (3)简历史 ECMAScript与JavaScript一般是一个概念。实际上JS含义更大点,一个完整的JS由ECMAScript、DOM、BOM三部分构成。 (4)语言特点: ①解释型语言 ②类似于C和Java的语法结构 ③动态语言 ④基于原型的面向对象 2.使用JS <!DOCTYPE html><html lang="cn"><head><meta charset="UTF-8"><title>Title</title></head><body><!--页面部分--></body><!--外部js的引入--><script type="text/javascript">/* JS代码部分*/alert("欢迎来到JS的世界~");</script><style type="text/css">/* 样式表*/</style></html> 要分离的统一维护。 (1)简单的入门打印: (2)页面中输出内容: document.writeln("Hello JS"); (3)控制台输出内容: console.log("Hello JS"); (4)JS的编写位置 <button οnclick="alert('讨厌,点我干什么?')">点我一下</button><a href="javascript:alert('我去...超链接')">也点击我吧</a> 一般不用这种的写法。 下面这种才是常用的: <script>//JS部分alert("我是script里的标签的提示");console.log("Hello JS");</script>或者编写到外部文件,然后script来引入XXX.js。推荐这种方式。 3.语法、关键字保留及变量 (1)注释,分为多行与单行注释,养成良好的编写注释的习惯。 (2)JS中完全区分大小写。使用方法的时候需要注意。 (3)每条语句以分号结尾,如果不写浏览器会自动资源,但是会消耗一部分资源。性能降低。而且还可能给你加错,在开发中分号必须写。 (4)JS会自动忽略多个空格和换行,可以利用空格和换行对代码进行格式化操作。 (5)字面量:1、2、3这些固定的值。 (6)变量:X、Y、Z,变量可以用来保存字面量,变量的值可以任意改变。变量更加方便我们使用。 var x="13703619524"alert(x);(7)可以由我们自主命名的都可以叫做标识符。如变量名、函数名、属性名。命名标识符的时候需要遵守如下规则:标识符中可以有字母、数字、下划线、$符号。标识符不能以数字开头。标识符不能为JS中的保留、关键字。一般采用驼峰命名法(首字母小写,每个单词的开头字母大写,其余小写)。JS底层保存标识符采用的是Unicode编码,所以中文可以作为名字,但是没有直接用中文的,除非神经病。 4.数据类型 (1)类型介绍 值类型(基本类型):字符串(String)、数字(Number)、布尔(Boolean)、对空(Null)、未定义(Undefined)、Symbol。 引用数据类型:对象(Object)、数组(Array)、函数(Function)。 var a=123;//numberconsole.log(typeof a);var b='helloWorld';//Stringconsole.log(typeof b);var c=true;//booleanconsole.log(typeof c);var d=null;//nullconsole.log(typeof d);//这里仍是返回object类型var e=undefined;//undefinedconsole.log(typeof e);var f={};//对象console.log(typeof f); (2)强制数据类型转换 //其他类型转换为Stringvar a=123;console.log(typeof a);console.log(a);//调用toString()方法var b=a.toString();console.log(typeof b);console.log(b);注意:但是toString对于null与undefined如果调用转换会报错的,他俩就没有toString的方法,调用会报错。 (3)String()函数 //调用String()函数var a=456;console.log(typeof a);console.log(a);a=String(a);console.log(typeof a);console.log(a);var a=null;console.log(typeof a);console.log(a);a=String(a);console.log(typeof a);console.log(a); 这种方式对null与undefined也是可以使用的。对于number和boolean就是调用了toString。但是对于null与undefined就不同了,它会将null转换为“null”,将undefined转换为“undefined”。 (4)数据类型转换为number //转换为number,使用Number()函数var a="123";console.log(typeof a);console.log(a);a=Number(a);console.log(typeof a);console.log(a); 但是对于123A这种情况,使用Number会变成NaN。如果字符串为空或者多个空格,会转化为0。如果是false转成0,true转成1。Null会转为0。 //第二种方式parseInt()方法,把字符串转换为整数//parseFloat()方法,把字符串转换为浮点数var a="123px";//这里只会去有效的整数内容,从左往右,遇到非数字就停止a=parseInt(a);console.log(typeof a);console.log(a);var a="123.567px";a=parseFloat(a);console.log(typeof a);console.log(a); 但是这种适合有数字的转换,如果是布尔值,转换后就是NaN。 (5)进制的转换: 十六进制:0x开头的,八进制以0开头,二进制以ob开头(不是所有的浏览器都支持)。主要还是使用十进制。 var a="070"//IE浏览器会当成八进制解析,谷歌是当成十进制的a=parseInt(a,10);//可以指定十进制来转换console.log(typeof a);console.log(a); (6)转换为boolean //转换为boolean,只有一种方式Boolean()函数var a=123;a=Boolean(a);console.log(typeof a);console.log(a);var a=0;a=Boolean(a);console.log(typeof a);console.log(a);var a=NaN;a=Boolean(a);console.log(typeof a);console.log(a);var a=-123;a=Boolean(a);console.log(typeof a);console.log(a); 除了0与NaN,其他的都是true。字符串转布尔值,除了空字符串、undfined与null,其余的都是true。 5.运算符 (1)也叫作操作符,可以对一个或多个值进行运算。 //运算符可以对一个或多个值进行运算//比如typeof也是运算符//运算符都是会返回结果的//typeof的返回值是字符串var a=123;var result=typeof a;console.log(result);console.log(typeof result); (2)算术运算符 //算术运算符//加减乘除//任何值与NaN做运算,最后结果都是NaN//两个字符串相加,则会做拼接字符串操作var result=2+null;console.log(result);result=2+NaN;console.log(result);result=true+1;console.log(result);result="123"+"456"+"陈翔";console.log(result);//任何的值与字符串做+运算,都会先转换为字符串,然后再拼串//转成字符串技巧:直接+""空串就可以了var result=123+"1";console.log(typeof result);console.log(result);result=true+"陈翔";console.log(typeof result);console.log(result);//从左往右运算,结果为"33"var result=1+2+"3";console.log(result);result="1"+2+3;console.log(result);//这个结果是"123"//减法,都是转换为Numbervar a=100-"1";console.log(typeof a);console.log(a);a=2*undefined;console.log(typeof a);console.log(a);a=2*null;console.log(typeof a);console.log(a);//转换为Number类型的技巧,可以通过-0 /1 *1var a="123";a=a-0;console.log(typeof a);console.log(a);//% 取模运算(求余数)var a=9 % 2;console.log(a);//余数为1(3)一元运算符 //一元运算符,只需要一个操作符//+好不影响//-能取反var a=123;a= +a;console.log(a);(4)自增和自减 //自增与自减var a=1;/*a=a+1;console.log(a);*/a++;console.log(a);(5)逻辑运算符 //逻辑运算符 与或非//!非运算var a=false;a=!a;console.log(a);//truevar b=10;b=!b;console.log(typeof b);console.log(b);//&&与 对两侧进行与运算var a=true && false;console.log(a);a=true && true;console.log(a);a=false && false;console.log(a);//||或 对两侧进行或运算var a=true || false;console.log(a);a=true || true;console.log(a);a=false || false;console.log(a);//逻辑运算符 与或非//对非布尔值,会先转换为布尔值,然后再运算,//但是返回的是非布尔值,谁在后面返回谁//如果有0,则会返回0var a=2 && 1;console.log(typeof a);console.log(a);a=0 && 1;console.log(typeof a);console.log(a);(6)赋值运算符 //赋值运算符,将右侧的值赋给左侧的变量//=、+=var a=123;a=a+5;console.log(a);(7)关系运算符 //关系运算符,比较两个值的大小关系//关系成立则返回true,否则返回false//>、>=、<、<=、==var a=1>2;console.log(a);a=1<2;console.log(a);a=2==2;console.log(a);a=1>"陈翔";console.log(a);a=1>"0";console.log(a);//true(8)unicode编码表 UTF-8就是对这里面的一个实现,但是UTF-8只是实现其中的一部分。 //unicode编码//输出u支持unidoce编码//在body里是&#(注意这里后面是十进制)2620对应十进制就是9760console.log("u2660");console.log("u2620");(9)相等运算符 //相等运算符,用来比较两个值是否相等//使用==比较,如果类型不同,将会自动转换相同的来进行比较console.log(1==1);var a=10;console.log(a==4);console.log("1"==1);//undefined衍生自nullconsole.log(undefined===null);//NaN不和任何值相等,包括他自身//!=与==是相反的//===全等,!==不全等console.log("1"===1);console.log("1"!==1); (10)条件运算符 //条件运算符//条件表达式?语句一:语句二;//感觉没有比较函数来的直接,麻烦(1>0)?console.log('真的'):console.log('假的');(1>2)?console.log('真的'):console.log('假的');(11)运算符的优先级 //运算符的优先级//使用,可以划分多个语句//就和数学中的优先级一样//用括号感觉挺好的var result =1+2*3;console.log(result);//如果优先级一样,则从左往右算 6.流程控制语句 通常在写代码时,您总是需要为不同的决定来执行不同的动作。您可以在代码中使用条件语句来完成该任务。 在 JavaScript 中,我们可使用以下条件语句: if 语句 - 只有当指定条件为 true 时,使用该语句来执行代码 if...else 语句 - 当条件为 true 时执行代码,当条件为 false 时执行其他代码 if...else if....else 语句- 使用该语句来选择多个代码块之一来执行 switch 语句 - 使用该语句来选择多个代码块之一来执行。 (1)代码块 //代码块//语句是按照自上而下的顺序一条条执行的//可以使用大括号对语句进行分组,每一个都是代码块//要么都执行,要么都不执行//只有分组的作用,没有其他作用{var a=10;alert('Hello');console.log('你好');document.write('Hi');}console.log(a);//也可以执行(2)流程控制语句 //流程控制语句//条件判断语句、条件分支语句、循环语句//if语句只能控制其后的一条语句,所以想控制多条要用到代码块var a=98;if(a>60){console.log("及格");}else{console.log("不及格");}//下面的语句中只会有一个语句被执行,一旦执行了则下面的都不执行了//这个写的时候要注意,避免有的代码一直不被执行var age=200;if(30>=age>17){console.log('你成年了');}else if(60>=age>30){console.log('你中年了');}else if(80>=age>60){console.log('你已经退休了');}else{console.log('你岁数挺大的');}//流程控制语句//条件判断语句、条件分支语句、循环语句//prompt()提示框,会带有可输入的文本框//用户输入的内容,将会作为此函数的返回值var score=prompt("请输入成绩");alert('您的成绩为:'+score);(3)条件分支语句 //流程控制语句//条件分支语句、循环语句//执行将case的值与switch的值进行'全等'比较,比较结果为true,则从当前case开始执行代码 如果所有的都false则执行default语句var num=4;//根据num的值输出中文switch (num) {case 1:console.log("一");break;case 2:console.log("二");break;case 3:console.log("三");break;default:console.log("其他情况");break;}(4)循环语句 //循环语句//向页面中输出连续的数字for(var n=0;n<30;n++){document.write(n+'<br/>');}//循环语句//while循环 {}里的叫做循环体//while在执行时,先对表达式进行判断,如果true执行循环体,继续判断执行...//如果表达式为false则终止执行//如果一直为true则为死循环//使用'break'可以退出循环var n=0;while(n<30){document.write(n+'<br/>');n++;}var m=0;while(m<30){document.write(m+'<br/>');m++;if(m>10){break;}}//循环语句//do...while循环//循环语句//for循环for(var i=0;i<=100;i++){if(i%2!=0){console.log(i+'是奇数')}}//循环语句//嵌套for循环for(var m=0;m<30;m++){for(var n=0;n<20;n++){document.write(n+'<br/>');}}(5)break与continue的使用 //break关键字可以退出switch或循环语句//break会立刻终止距离他最近的循环语句//使用break语句,可以在后面跟lable,可以结束指定的循环outer:for(var a=0;a<5;a++){console.log(a);for(var b=0;b<5;b++){console.log(b);if(b==3){break outer;}}}//测试程序性能计时console.time('myTime');for(var a=0;a<5;a++){if(a==3){continue;//跳过当次,继续下一次循环}console.log(a+'------');}console.timeEnd('myTime');7.函数 (1)函数的简介 //函数的简介//函数也是一个对象,一切皆对象//函数中可以封装一些功能(代码),在需要的时候调用//创建一个函数对象var myFunction=new Function();console.log(typeof myFunction);console.log(myFunction);//可以将要封装的代码一字符串的形式传递给构造函数var myFunction=new Function("console.log('我的第一个函数');");console.log(myFunction);//但是函数里封装的代码不会立刻执行,会在函数调用时执行//调用函数语法,函数对象(),函数中封装的代码会按照顺序执行myFunction();myFunction();myFunction();//所以函数对象比普通对象强大//但是在实际开发中很少使用构造函数的方法来创建函数//使用函数声明来创建函数/* function 函数名([参数,参数...]){语句...}*///函数名不要与构造函数重名...function myFunction2(){console.log("我的正规方法定义的函数...");}myFunction2();//函数表达式的方式/* var 函数名=function(){}*/var myFunction3=function(){console.log('匿名函数赋值给变量的方式三...');};myFunction3();(2)函数的参数 //函数的参数//定义一个用来求和的函数function mySumFunction(a,b){console.log(a+b);}mySumFunction(4,9);//形参,就是形式上的参数,多个形参之间使用逗号隔开//在调用函数时,可以在()中指定实参(实际参数)mySumFunction(12,98);//浏览器不会检查实参的类型mySumFunction('Hello','World');//所以需要检查下实参是否合法,从而导致程序异常//解析器也不会检查实参的数量,多余的实参不用被程序考虑mySumFunction('Hello','World',789);//如果实参数量,则没有实参的形参将是undefined//实参可以是任意的数据类型(3)返回值 //函数的返回值//计算三个数的和function myFunctionSum(a,b,c){//alert(a+b+c);return a+b+c;//return 执行以后的语句都不会执行}alert(myFunctionSum(1,2,3));//往往执行函数时,结果是需要返回的//如果return不跟着或者不写,函数都会返回undefined//return可以跟任意类型的值(4)实参可以是任意类型值 //函数的实参function myFunctionIsEvenNum(num){/* if(num % 2==0){return true;}else{return false;}*/return num % 2==0;}var result=myFunctionIsEvenNum(3);console.log(result);function myFunctionSayHello(name,age){console.log('我是'+name,'今年'+age);}myFunctionSayHello('陈翔',26);//如果参数特别多,我写起来就有点麻烦,甚至搞不清顺序//创建一个对象var myObject={name:'陈翔',age:26,sex:'男',site:'广州'};//如果参数过多,可以封装到对象中,通过对象传递function myFunctionSayHi(myObject){console.log('我是'+myObject.name,'今年'+myObject.age+" 我的性别是"+myObject.sex);}myFunctionSayHi(myObject);//实参也可以是一个函数function myFunctionTemp(a){console.log('a='+a);//如果传函数,a就变成了那个函数a(myObject);}//实参也可以传'函数'myFunctionTemp(myFunctionSayHi);//如果里面加 调用函数//myFunctionTemp(myFunctionSayHi());//这种相当于传了括号内函数的返回值,这里要注意(5)返回值的类型 //返回值的类型function myFunction(){alert("函数要执行了...");for(var i=0;i<10;i++){console.log(i);if(i==2){//break可以退出当前循环//break;//continue用户跳过当次循环//return可以结束整个函数return;}}alert("函数执行完了...");}myFunction();//函数的返回值可以是任意的数据类型//可以返回对象也可以返回函数function myFunctionReturn(){/*return null;*/function myFunctionInner(){alert('我是myFunctionInner');}//函数本身return myFunctionInner;//函数的调用返回值undefinedreturn myFunctionInner();}var temp=myFunctionReturn();console.log(temp);(6)立刻执行函数 //立即执行函数,定义完毕马上被调用//立即执行函数往往只会执行一次/* (function(){alert('我是匿名函数...');})();*/(function(a,b){console.log(a+':'+b);})(1,2);(7)方法 //方法var myObject=new Object();myObject.name='陈翔';myObject.age=18;//对象的属性值可以是任何的数据类型//可以是对象也可是函数myObject.sayNameFunction=function(){console.log(myObject.name);};console.log(myObject.sayNameFunction);myObject.sayNameFunction();//所以函数也可以作为对象属性//这种情况我们称此类函数为对象的方法//调用函数就是就是调用对象的方法//但是他只是名称上的区别,没有其他的区别//所以方法与函数本质是相同的,只是名称上有点不同var myObject2={name:'陈翔',age:18,//方法的定义是一样的sayNameFunction:function(){console.log(myObject2.name);}};myObject2.sayNameFunction();(8)枚举 //枚举var myObject={name:'陈翔',age:19,sex:'男'};//怎么知道myObject里有哪些属性,所以要枚举这些属性//使用for...in语句for(var temp in myObject){//console.log('Hello');//属性名就可以全部取出来console.log(temp+'对应的值'+myObject[temp]);}(9)全局作用域 //全局作用域scope//两种作用域:全局作用域、局部作用域//全局作用域在打开时创建,在页面关闭是销毁//全局作用域中有一个全局对象window(代表的是浏览器的窗口),我们可以直接使用//创建的变量都会作为window对象的属性保存,创建的函数都会作为window对象的方法保存//所以a与window.a是一样的作用console.log(window);var temp=456;//全局function myFunction(){//局部的var a=123;}//这里无法直接饮用console.log(window.temp);//变量的声明提前//var关键字声明的变量,会在所有的代码执行之前被声明//如果不使用var,则不会被声明提前var c=123;console.log('c='+c);function myFunction(){console.log('我是一个函数...');}var myFunctionTwo=function(){console.log('我是第二个函数...');}//函数的声明提前 function 函数(){},会在所有的代码执行之前被创建//所以这种方法,可以在函数声明前被调用。//但是 var myFunctionTwo=function(){}就不能声明提前,所以不能在声明前调用。//全局作用中的变量都是全局变量。在页面的任意部位都可以访问到。(10)函数作用域 //函数作用域,也就是局部变量//调用函数时创建作用域,函数执行完毕后,作用域销毁//没调用一个函数都会创建一个新的函数作用域,他们之间互相独立。//在函数作用域中可以访问到全局作用域的变量。var a=10;function myFunction1(){var a='我是函数作用域的a';var b=20;console.log('内部输出a='+a);}myFunction1();console.log('外部输出a='+a);//在全局作用域中,无法访问到函数作用域的变量//console.log('b='+b);//会报错//当在函数作用域中操作一个变量时,会先在自身寻找,如果有则直接使用,如果没有则去上一级作用域去找//上一级不一定就是全局作用域,也可能是上一级的函数作用域//原则是从内往外找,直到找到全局作用域,如果还是没有则会报错XXX is not defined//如果在函数里想访问全局变量,可以在前面加上window.//函数作用域中也存在var提前声明与函数的提前创建var c=33;function myFunction5(){console.log('c='+c);c=35;}myFunction5();console.log('外部的c='+c);//在函数中不声明的变量都会成为全局变量//形参就相当于在函数作用域中声明了变量(11)DEBUG //Debugalert(d);var a=10;var b='Hello';c=true;function myFunction(){alert('Hi');}var d=35;//谷歌浏览器调出开发者模式//Sources-打断点-然后添加Watch里想监控的变量//一步步执行就可以看执行顺序了 (12)this的说明 //this的说明//调用myFunction的时候实际上是由隐藏参数this传递的//this指向的是一个对象,是函数执行的上下文对象//根据函数调用方式的不同,this会指向不同的对象//1.以函数的形式调用,this永远指向的是window//2.以方法的形式调用,this指向的是调用方法所在的对象。function myFunction(a,b){//console.log(a+';'+b);console.log(this);}myFunction(123,456);var myObject={name:'孙悟空',sayName:myFunction}console.log(myObject.sayName==myFunction);myFunction();myObject.sayName();var myObject1={name:'陈翔',sayName:myFunction}myObject1.sayName();8.对象与数组 (1)概述 //对象Object//基本数据类型:String、Number、Boolean、null、Undefined。不是基本类型:Object//如果在JS中表示人的信息//如果使用基本数据类型,会发现创建的变量都是独立的。//对象属于一种复合的数据类型,在对象中可以保存多个不同数据类型的属性。//对象的分类:1.内建对象 比如Math String Number...// 2.宿主对象 BOM DOM中的对象// 3.自定义对象,开发者自己创建的对象(2)对象的创建与增删改查 //对象Object的创建//new调用的函数是构造函数constructor,是专门创建对象的函数var myObject=new Object();//向对象中添加属性,在对象中保存的值叫做属性myObject.name='陈翔';myObject.age=26;myObject.sex='男';console.log(typeof myObject);console.log(myObject);//读取对象中的属性console.log(myObject.name);//修改属性值myObject.name='蘑菇头';console.log(myObject);//删除属性delete 对象.属性名delete myObject.sex;console.log(myObject);(3)属性名与属性值 //属性名与属性值//属性名可以随意定义,尽量注意规范即可//如果是123这种特殊的名字,要用myObject['123'],当然取的时候也是myObject['123']//中括号的形式可以更加灵活/*var myObject=new Object();myObject.name='陈翔';console.log(myObject);*/var myObject=new Object();myObject['name']='陈翔';for(var m=0;m<5;m++){myObject[m]=m+"->";}console.log(myObject);//属性名与属性值//属性值var myObject=new Object();myObject.name=true;console.log(myObject.name);myObject.name=null;console.log(myObject.name);var myObject2=new Object();myObject2.age=26;myObject.name=myObject2;//值也可以是对象console.log(myObject);//检查对象是否包含某个属性//in 运算符,检查对象中是否含有指定的属性console.log('test2' in myObject);console.log('name' in myObject);(4)基本数据类型与引用数据类型 //基本数据类型String Number Boolean Null Undefined//引用数据类型Objectvar a=123;var b=a;a=a+1console.log('a的值:'+a);console.log('b的值:'+b);//说明a的值变化,不影响b的值var myObject=new Object();myObject.name='陈翔';var myObject2=myObject;myObject.name='蘑菇头';//这里的改变,却影响了myObject2.name的值console.log('myObject的名字:'+myObject.name);console.log('myObject2的名字:'+myObject2.name);//这就是最基本的区别基本数据类型:引用数据类型:比较引用数据类型,它是比较的是对象的内存地址。如果两个对象一样,但是地址不同,也是会返回false的。所以这两个对象相比较相等则需要myObject.name与myObject2.name拿出来比较才可以。(5)对象字面量 //对象字面量var myObject={};myObject.name='陈翔';console.log(typeof myObject);console.log(myObject);//使用对象字面量,可以在创建对象时指定对象中的属性//对象字面量的属性名可以加引号,也可以不加,建议不加//如果是特殊的名字需要加引号//属性名与属性值是一组一组的名值对结构//多个名值之间用逗号隔开,如果是最后一对则不用写逗号了var myObject2={name:'陈翔',age:26,sex:'男',dog:{name:'小黑',age:2}};console.log(typeof myObject2);console.log(myObject2);(6)使用工厂方法创建对象 //使用工厂方法创建对象//比如需要创建10个类似的对象,如果更简单点function myFunctionCreatePerson(name,age,sex){//通过该方法大批量创建对象var myObject=new Object();//向对象中添加属性myObject.name=name;myObject.age=age;myObject.sex=sex;myObject.sayName=function(){console.log('你好,我是'+this.name)}//将新对象返回return myObject;}var myObject1=myFunctionCreatePerson('陈翔',26,'男');var myObject2=myFunctionCreatePerson('球球',28,'女');var myObject3=myFunctionCreatePerson('冷萌',23,'女');console.log(myObject1);console.log(myObject2);console.log(myObject3);(7)构造函数的形式创建类 //使用工厂方法创建对象,使用的构造函数都是Object//类型都是Object就导致我们无法区分出多种不同类型的对象//所以我们要用构造函数的方式//创建一个构造函数,专门来创建person对象//不同的是,构造函数是首字母大写。//普通函数直接调用,new关键字就是构造函数的调用。//构造函数的执行流程/**1.立刻创建一个新的对象2.将新建的对象设置为函数中的this,在构造函数中可以使用this来引用新建的对象3.逐行执行函数中的代码4.将新的对象作为返回值返回*///这样我们就可以更好的区分Person与Dog了function Person(name,age,sex){this.name=name;this.age=age;this.sex=sex;}var myPerson=new Person('陈翔',26,'男');var myPerson1=new Person('蘑菇头',27,'男');var myPerson2=new Person('闰土',28,'男');console.log(myPerson);console.log(myPerson1);console.log(myPerson2);function Dog(name,age){this.name=name;this.age=age;}var myDog=new Dog('小黄',2);console.log(myDog);//instanceof可以检查一个对象是否是一个类的实例console.log(myDog instanceof Person); Object是所有对象的祖先,比如例子中的Person与Dog,如果用instaceof检查是否属于Object都会返回true。、 A. This当以函数的形式调用时,this是window B. This当以方法的形式调用时,谁调用方法this就是谁 C. This当以构造函数的形式调用时,this就是新创建的那个对象 (8)构造函数的修改 /**1.创建一个Person构造函数* 2.但是构造函数创建方法,每个对象都有sayName方法* 3.这样就导致构造函数每执行一次,就创建了一次sayName方法,而这样的方法都是一样的* 是完全没有必要的,完全可以是所有的对象共享同一个方法。*///这样我们就可以更好的区分Person与Dog了function Person(name,age,sex){this.name=name;this.age=age;this.sex=sex;this.sayName=myFunction;}//将sayName方法在全局作用域中定义//这个在性能上有很大的提升function myFunction(){console.log(this.name);}var myPerson=new Person('陈翔',26,'男');myPerson.sayName();(9)forEach()遍历方法 //提供的遍历方法forEach()//仅支持IE8以上的浏览器var myArray=['陈翔','蘑菇','球球','冷萌'];//需要一个函数作为参数//像这种函数,由我们创建,但是不由我们调用的,我们称之为回调函数。//数组中有几个元素,函数就回执行几次//每次遍历到元素会以实参的形式传递进来,我们可以定义形参来读取这些内容。//浏览器会在回调函数中传递三个参数//第三个参数就是正在遍历的数组myArray.forEach(function(value,index){console.log('-----');console.log(index+':'+value);});(10)原型对象 //原型对象//全局作用域污染了全局作用的命令空间//原型prototype//我们所创建的每一个函数,我们的解析器都会向函数中添加一个属性prototype//这个属性对应一个对象,这个对象就是我们所说的原型对象//如果函数作为普通函数调用,prototype没有任何作用//当以构造函数的形式调用时,他所创建的对象中会有一个隐含的属性//原型对象就相当于一个公共的区域,所有同一个类的实例都可以访问到这个原型对象,//所以我们可以将对象中的共有内容,统一设置到原型对象中function Person(){}/*console.log(Person.prototype);var myPerson=new Person();console.log(myPerson.__proto__==Person.prototype);var myPerson2=new Person();console.log(myPerson2.__proto__==Person.prototype);*///myPerson.myNum='我是myPerson中的...';var myPerson=new Person();Person.prototype.myNum=123;//当我们访问对象按给你属性或方法时,会先在对象自身寻找,如果有则直接使用//如果没有则去原型对象找,如果有则使用var myPerson=new Person();console.log(myPerson.myNum);Person.prototype.sayName=function(){console.log('原型里的方法调用ing...');}myPerson.sayName();//以后创建构造函数时,可以统一添加到构造函数的原型对象中,这样可以不用分别//为每一个对象添加,也不会影响到全局作用域,就可以使每个对象都具有属性和方法//原型对象function Person(){}var myPerson=new Person();//向原型对象中添加一个name属性Person.prototype.name='我是原型中的名字';console.log(myPerson.name);//使用in检查对象中是否含有某个属性时,如果对象中没有但是原型中有,也会返回trueconsole.log('name' in myPerson);//可以用hasOwnProperty检查对象自身是否含有该尚需经console.log(myPerson.hasOwnProperty('name'));myPerson.age=18;console.log(myPerson.hasOwnProperty('age'));//原型对象里还有原型,因为原型对象也是对象//当使用对象的属性或方法时,会在自身中寻找,//如果有,则直接使用//如果没有则去原型对象中寻找,如果原型对象中有,则使用//如果没有则去原型的原型中寻找,看是否有...//从下面的代码,可以看到是在原型的原型里。//知道找到Object对象的原型,Object对象的原型没有原型//如果仍然没有找到,则返回undefinedconsole.log(myPerson.__proto__.__proto__.hasOwnProperty('hasOwnProperty'));(11)toString()方法 //toString()function Person(name,age){this.name=name;this.age=age;}var myPerson=new Person('陈翔',26);//之类实际输出的是对象的toString()方法的返回值//console.log(myPerson);console.log(myPerson.__proto__.__proto__.hasOwnProperty('toString'));//如果我们希望在输出对象时不输出默认样式,可以自行添加toString()方法/* myPerson.toString=function(){return '我自定的toString返回值';};*/Person.prototype.toString=function(){return this.name+': '+this.age;};console.log(myPerson.toString());(12)垃圾回收 //1.垃圾回收GC//就想人生活时间长会产生垃圾一样,程序运行过程中也会产生垃圾//所以我们需要一个垃圾回收极致,来处理程序运行过程中产生的垃圾var myObject=new Object();//对对象进行各种操作...//2.当一个对象没有任何的变量或者属性对它进行引用,此时我们无法操作//该对象,此时这种对象就是一个垃圾,这种对象过多会占用大量的内存空间,//导致程序变慢,必须进行清理//3.JS中有用自动的垃圾回收机制,会自动将这些垃圾对象从内存中销毁,//我们不需要也不能进行垃圾回收的操作,我们需要做的是将不再用的对象//设置为nullmyObject=null;(13)数组 //1.内建对象、宿主对象、自定义对象//2.数组Array,数组也是一个对象,它和我们普通的对象功能类似,//不同的是普通对象是使用字符串作为属性名的,而数组是用数字//作为索引来操作元素的。//索引是从0开始的,可以使用数组来存储一些数据//3.创建数组对象var myArray=new Array();console.log(myArray);console.log(typeof myArray);//向数组中添加元素myArray[0]=10;myArray[1]=33;console.log(myArray);//读取数组中的元素console.log(myArray[0]);//读取不存在的索引会返回undefinedconsole.log(myArray[3]);//获取数组的长度,也就是元素的个数console.log(myArray.length);//对于非连续的数组,使用length会获取到数组的最大索引+1myArray[10]=1010;console.log(myArray.length);console.log(myArray);//如果修改的length大于原长度,则会空出来多出的部分//如果修改的length小于原长度,则多出的元素会被删除//永远都像数字的最后以为添加//则可以用下面的方式,这是一个技巧myArray[myArray.length]=70;console.log(myArray);(14)数组字面量 //数组字面量//使用字面量来创建数组var myArray=[1,2,3,4,5];console.log(myArray);console.log(myArray.length);var myArray1=new Array(1,2,3,4,5);//这种方式是一样的console.log(myArray1);console.log(myArray1.length);//数组的元素可以是任意的数据类型var myArray2=['Hello',true,1,null,undefined];console.log(myArray2);console.log(myArray2.length);//也可以放对象var myObject={name:'陈翔'};myArray2[myArray2.length]=myObject;console.log(myArray2);console.log(myArray2.length);console.log(myArray2[5]);//JSONvar myArray3=[{name:'陈翔'},{name:'陈翔'}];console.log(myArray3);//也可以放函数myArray3=[function(){console.log('Hi')},function(){console.log('Hi')}];console.log(myArray3);//数组里也可以放数组,这种叫做二维数组myArray3=[[1,2],[1,2],[1,2]];(15)数组的四个方法 //数组的方法var myArray=['孙悟空','猪八戒','沙和尚'];//push()向数组末尾添加一个元素,并返回数组的新长度var myPushReturn=myArray.push('唐僧','白骨精');console.log(myArray);//返回的是数组的新长度console.log(myPushReturn);//pop()删除并返回数组的最后一个元素//返回的是被删除的元素var myPopReturn=myArray.pop();console.log(myArray);console.log(myPopReturn);//unshift()向数组的开头添加一个或多个元素//并返回新的长度var unshiftReturn= myArray.unshift('牛魔王','红孩儿');console.log(myArray);console.log(unshiftReturn);//shift()是删除之前的元素//返回的也是删除的元素var shiftReturn= myArray.shift();console.log(myArray);console.log(shiftReturn);(16)数组的遍历 //数组的遍历var myArray=['孙悟空','猪八戒','沙和尚','唐僧'];for(var i=0;i<myArray.length;i++){console.log(myArray[i]);}(17)slice和splice方法 //slice()var myArray=['关羽','赵云','诸葛亮','马超'];console.log(myArray);//可以从数组中提取元素,包含开始不包含结束var sliceArray=myArray.slice(0,2);console.log(sliceArray);//下标也可以用负数,但是不推荐使用//splice()可以用于删除数组的指定元素//后面的是表示删除几个console.log(myArray);var spliceArray=myArray.splice(0,2);//这里myArray就回被删除两个元素//返回的是删除的元素console.log(myArray);console.log(spliceArray);//第三个参数及以后可以传递一些新的元素,这些元素//将会自动插入到开始位置的前边。spliceArray=myArray.splice(0,1,'典韦');console.log(myArray);console.log(spliceArray);//数组去重var myArray=[1,2,3,3,3,3,3,3,3,3,4,5,6,1,2,3,4];for(var i=0;i<myArray.length;i++){for(var j=i+1;j<myArray.length;j++){if(myArray[i]==myArray[j]){myArray.splice(j,1);//当删除当前j对应的元素后,后边的元素//会自动补位,此时将不会再比较这个//元素,所以我需要再比较一次j所在的元素j--;}}}console.log(myArray);(18)关于数组的其他方法 //数组相关的方法var myArray=['陈翔','球球','蘑菇头'];var myArray2=['闰土','冷檬','妹大爷'];//concat()可以连接两个或多个数组,并将新的数组返回var concatReturn=myArray.concat(myArray2);console.log(concatReturn);//join()该方法可以将数组转换为字符串//不会对原数组产生影响//可以指定连接符,不指定是逗号,可以使用空格连接符var joinReturn=myArray.join();console.log(joinReturn);var joinReturn=myArray.join('--');console.log(joinReturn);var joinReturn=myArray.join('@');console.log(joinReturn);//reverse()该方法用来反转数组(前边的去后面,//后面的去前面)//该方法会直接修改原数组myArray.reverse();console.log(myArray);//sort()对数组的元素进行排序//也会影响原数组//按照unicode编码进行排序var myArray2=['a','d','e','b','f'];console.log(myArray2);myArray2.sort();console.log(myArray2);//这种根据unicode编码排序就会出现问题var myArray3=[1,2,3,4,11,5,6,12,23,22];myArray3.sort();console.log(myArray3);//所以要自定义排序myArray3.sort(function(a,b){/* if(a>b){return 1;}else{return -1;}*/return a-b;//代码的优化,降序就是b-a});console.log(myArray3);(19)函数的方法call()与apply() //函数的方法function myFunction(){alert(this);}//call与apply都是函数对象的方法 ,需要通过函数对象来调用/* myFunction.call();myFunction.apply();myFunction();*///上面三个是同一个效果//不同的是,在调用call与apply可以将一个对象指定为第一个参数//此时这个对象将会成为函数执行时的thismyFunction();var myObject={};myFunction.call(myObject);//所以这两个函数的主要作用是修改上下文对象this//apply方法需要将实参封装到数组中统一传递//call可以一个个传//this情况总结://1.以函数的形式调用,this永远是window//2.以方法的形式调用,this是调用方法的那个对象//3.使用call与apply调用时,this是指定的那个对象//4.以构造函数调用时,this是创建的那个对象(20)arguments //函数的argumentsfunction myFunction() {console.log(arguments);console.log(arguments instanceof Array);console.log(arguments.length);console.log(arguments.callee);}//调用函数时,浏览器每次都会传递进来两个隐藏的参数//1.函数上线文对象this//2.封装实参的对象argumentsmyFunction();//arguments是一个类数组对象//也可以通过索引来操作数据,也可以获取长度//在调用函数时,我们所传递的实参都会在arguments中保存myFunction('Hi','Say');//arguments[0]、arguments[1]表示第N+1个实参//callee属性,这个属性对应一个函数对象//就是当前正在执行的函数的对象(21)Date对象 //Date对象//直接使用构造函数创建一个Date对象,则会封装当前代码执行的时间var myDate=new Date();console.log(myDate);//创建指定时间的对象//日期的格式 月份/日/年 时:分:秒var myDate1=new Date("12/05/2021 11:10:30");console.log(myDate1);//获取当前对象是几号var tempDate=myDate1.getDate();console.log("几号tempDate: "+tempDate);//获取当前日期对象是周几//0-6分别表示周日-周六tempDate=myDate1.getDay();console.log("星期tempDate: "+tempDate);//获取当前对象的月份//0-11表示1-12月,0表示1月份tempDate=myDate1.getMonth();console.log("月份tempDate: "+tempDate);//获取当前日期对象的年份tempDate=myDate1.getFullYear();console.log("年份tempDate: "+tempDate);//时间戳,从格林威治标准时间1970年1月1日,0分0秒//到当前日期所耗费的毫秒数//计算机底层在保存时间使用的都是时间戳tempDate=myDate1.getTime();console.log("时间戳毫秒tempDate: "+tempDate);//来看下特例,这里默认的是中八区的时间//所以改成8:0:0就相当于格林威治的0:0:0myDate1=new Date("1/1/1970 8:0:0");tempDate=myDate1.getTime();console.log("时间戳毫秒tempDate: "+tempDate);var startTime=Date.now();for(var i=0;i<100;i++){console.log(i);}var endTime=Date.now();console.log("共计耗时毫秒 "+(endTime-startTime));(22)Math对象 //Math对象console.log(Math);//Math和其他函数不同,它不是一个构造函数//他属于一个工具类,不用创建对象,它里面封装了数学//运算的属性与方法console.log("圆周率 "+Math.PI);//abs()可以计算一个数的绝对值console.log("-36的绝对值 "+Math.abs(-36));//向上取整console.log("1.2的向上取整 "+Math.ceil(1.2));//向下取整console.log("1.9的向下取整 "+Math.floor(1.9));//四舍五入取整console.log("1.4四舍五入取整 "+Math.round(1.4));console.log("1.6四舍五入取整 "+Math.round(1.6));//随机数console.log("0-1之间的随机数 "+Math.random());console.log("0-10之间的随机数 "+Math.round(Math.random()*10));//生成X-Y之间的随机数//Math.round((Math.random()*y-x)+x)//max()获取多个数中的最大值console.log("找最大值 "+Math.max(10,1,2,45,100));console.log("找最小值 "+Math.min(10,1,2,45,100));//Math.pow(x,y) x的y次方console.log(Math.pow(2,4));//开方console.log(Math.sqrt(2));9.类与正则表达式 (1)包装类 //数据类型//1.基本数据类型、引用数据类型//2.JS中提供了三个包装类,可以将基本的数据类型转换为对象//String()变成String对象//Number()变成Number对象//Boolean()编程Boolean对象var a=123;console.log(typeof a);var num=new Number(3);//这是是Object对象类型console.log(typeof num);num.name="陈翔";//对象更强大,可以添加属性console.log(num.name);var str=new String('Hello');console.log(typeof str);var myFlag=new Boolean(true);console.log(typeof myFlag);//实际中不会使用基本数据类型的对象//如果使用基本数据类型对象,进行比较时可能会带来//与预期不同的后果。//→当我们对一些基本数据类型的值去调用属性和方法时//浏览器会"临时"使用包装类将其转换为对象,然后再调用//对象的属性和方法。调用完毕后再转换为基本数据类型。var s=123;s=s.toString();console.log(s);console.log(typeof s);s.name='蘑菇头';//这里将打印undefined,因为原s被销毁了//新的s读是没有这个属性的,所以会undefinedconsole.log(s.name);(2)字符串方法 //创建一个字符串var str="Hello,HIT";//底层字符串是以字符数组的形式保存的//['H','e','l'....]console.log(str.length);for(var i=0;i<str.length;i++){//console.log(str[i]);}//length可以获取字符串的长度//charAt()可以返回字符串中指定位置的字符console.log(str.charAt(6));//charCodeAt()//获取指定位置字符的编码(unicode编码)console.log(str.charCodeAt(0));//fromCharCode()可以根据字符编码取字符//unicode对照表是16进制可以用0x...来表示console.log(String.fromCharCode(20013));//concat()可以连接两个或多个字符串var result=str.concat('你好');console.log(result);//indexOf()该方法可以检索一个字符串是否包含指定//内容,返回字符串所在的位置。//如果没有找到则返回-1//也可以从指定位置查找result=str.indexOf('H');console.log('str中是否包含H,位置为 '+result);result=str.indexOf('T');console.log('str中是否包含H,位置为 '+result);result=str.indexOf('0');console.log('str中是否包含H,位置为 '+result);//lastIndexOf//1.与indexOf(从前往后找)一样,lastIndexOf是从后往前找//2.也可以指定开始查找的位置result=str.lastIndexOf('H');console.log('str中是否包含H,位置为 '+result);//slice()//1.可以从字符串中截取指定的内容//2.不会影响原字符串(包括开始)//3.第一个参数开始位置,第二个是结束位置(不包括结束)//4.如果省略第二个参数,则会截取到后面所有的//5.如果第二个传负值,则从后面开始截取console.log(str.slice(0,2));//substring()//1.可以用来截取一个字符串,与slice()类似//2.参数开始位置、结束位置(不包括结束位置)//3.不同的是substring不能传负的参数//4.而且会自动调整参数位置,如果第二个参数小于第一个//参数,则自动调整参数位置。console.log(str.substring(0,2));//split()//1.可以将字符串拆分为一个数组//2.需要字符串作为参数//3.如果传递一个空串作为参数,则将每个字符都拆分为//数组中的一个元素str='1,2,34,6,9';result=str.split(',');console.log(result);console.log(Array.isArray(result));//toLocaleLowerCase()、toLocaleUpperCase()str='Hello';console.log(str.toLocaleUpperCase());(3)正则表达式 //正则表达式//1.如邮件的校验//(1)前面可以是XXX//(2)跟着一个@//(3)后边是XXX.com//2.正则表达式就是一定字符串的规则//计算机来根据正则表达式来检查一个字符串是否符合//规则,或者将字符串中符合规则的内容提取出来//3.创建正则表达式对象//(1)RegExp('正则表达式','匹配模式');var myRegExp=new RegExp('a');console.log(myRegExp);console.log(typeof myRegExp);var checkStr='Abc';//(2)正则表达式的方法test()//单独new RegExp('a');可以检查字符串中是否含有avar checkFlag=myRegExp.test(checkStr);console.log(checkFlag);//checkStr必须包含小a才可以返回true//是严格区分大小写的//(3)RegExp('正则表达式','匹配模式');//匹配模式i 忽略大小写;g 全局匹配模式myRegExp=new RegExp('a','i');checkFlag=myRegExp.test(checkStr);console.log(checkFlag);(4)正则语法 //正则语法//1.var myRegExp=new RegExp();//2.也可以使用字面量来创建正则表达式//语法:var 变量=/正则表达式/匹配模式var myRegExp=/a/i;console.log(myRegExp.test('abc'));console.log(typeof myRegExp);//3.使用字面量的方式更加简单,使用构造函数的创建//更加灵活。//4.创建一个正则表达式,检查字符中是否有a或bmyRegExp=/a|b/;console.log(myRegExp.test('cd'));console.log(myRegExp.test('a'));console.log(myRegExp.test('b'));//5.创建字符串中检查是否包含字母//[]里的内容也是或的关系//[ab]==a|b//[a-z]表示a到z,表示任意的小写字母都可以//[A-z]表示任意字母,不区分大小写myRegExp=/[a-z]/;console.log(myRegExp.test('b'));//6.是否包含abc或adc或aecmyRegExp=/a[bde]c/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('afc'));//7.[^]除了myRegExp=/[^ab]/;console.log(myRegExp.test('a'));console.log(myRegExp.test('c'));//8.[0-9]任意数字myRegExp=/[0-9]/;console.log(myRegExp.test('1'));console.log(myRegExp.test('c'));(5)字符串与正则相关的方法 //字符串与正则相关的方法var checkStr='1ab2c3d4e5';//split()//1.将字符串拆分为数组var myArray=checkStr.split('c');console.log(myArray);//2.实现根据任意字母拆分//需要在方法中传递正则表达式//这种拆分方法更加灵活myArray=checkStr.split(/[A-z]/);console.log(myArray);//search()//1.可以搜索字符串是否包含指定内容//2.如果搜索到指定内容,则会返回第一次出现的索引//如果没有搜索到返回-1。//它可以接受一个正则表达式作为参数,然后根据正则//表达式去检索字符串var str='Hello abc';var myResult=str.search('abc');console.log(myResult);//如想搜索abc或aec或afcstr='Hello abc aec afc';myResult=str.search(/a[bef]c/);console.log(myResult);//match()//1.可以根据正则表达式,从一个字符串中将符合条件的//提取出来,比如找出所有的字母//2.默认情况下match只会找到第一个,可以让正则表达式//开启全局模式g,可以全部匹配。//当然可以为一个正则表达式设置多个匹配模式,//顺序不重要如/XXXX/ig /XXX/gi//匹配到多个返回的是一个数组。str='1a2b3c4d5af6ea7agABC';myResult=str.match(/[A-z]/g);console.log(myResult);//replace()//1.可以将字符串中指定的内容替换为新的内容//2.两个参数,第一个是被替换的内容,第二个是新的内容myResult=str.replace(/a/ig,'X');console.log(myResult);myResult=str.replace(/[A-z]/ig,'X');console.log(myResult);(6)正则表达式语法 //语法//创建一个正则表达式检查字符串是否有aaavar myRegExp=/aaa/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('aaa'));//如果检测3000个a怎么写呢?//量词//1.所以就有量词的表达//2.a{3}代表a连续出现3次myRegExp=/a{3}/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('aaa'));//3.量词只对它前边的一个内容起作用//如果ab连续出现几次需要(ab){3}来表达myRegExp=/(ab){3}/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('ababab'));//4.一个字母出现1-N次//b{1,3}myRegExp=/ab{1,3}c/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('abbbc'));console.log(myRegExp.test('abbbbc'));//5.一个字母至少出现1次//b+,相当于{1,}myRegExp=/ab+c/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('ac'));//* 表示一个或多个,相当于{0,}//? 表示0个或1个{0,1}//6.检查一个字符串是否以a开头// ^表示开头myRegExp=/^a/;console.log(myRegExp.test('bac'));console.log(myRegExp.test('ac'));//7. a$ 表示以a结尾myRegExp=/a$/;console.log(myRegExp.test('abc'));console.log(myRegExp.test('cba'));//8.^a$ 表示以此a为开头,又要以此a结尾//也就是只能有一个amyRegExp=/^a$/;console.log(myRegExp.test('a'));//9.以a开头以a结尾myRegExp=/^a[A-z]{1,}a$/;console.log(myRegExp.test('abcdafdsafa'));//10.用正则表达式检查是否为合法的手机号//手机号的规则://(1)第一位以1开头//(2)第二位3-9任意数字//(3)三位任意数字9个//(4)分开写^1 [3-9] [0-9]{9}$myRegExp=/^1[3-9][0-9]{9}$/;console.log(myRegExp.test('13703619524'));console.log(myRegExp.test('11703619524'));console.log(myRegExp.test('117-3619524'));//语法二//检查字符串中是否含义.//1.点.表示任意字符//2.如何检测点呢? 需要用转义字符// .即可//3.其他的也是同样的道理,如检查等也需要转义//4.注意使用构造函数时候,由于他的参数是字符串//必须使用来代替转义var myRegExp=/./;console.log(myRegExp.test('avc.daf'));console.log(myRegExp.test('121212'));// w W d...// w表示任意字母、数字// W表示除了字母、数字// d表示任意的数字[0-9]// D除了数字[^0-9]// s空格// S除了空格// 单词边界// B除了单词边界myRegExp=/child/;//非child单词不匹配console.log(myRegExp.test('children'));console.log(myRegExp.test('child'));//接受一个用户的输入,去除掉其中的空格//只去两遍的,不去中间的空格var userInput=prompt('请输入你的用户名: ');userInput=userInput.replace(/^s{0,}|s{0,}$/g,'');console.log(userInput);(7)电子邮件的正则 //电子邮件//1.任意的字母数字下划线.任意的字母数字下划线//2.@符//3.任意字母数字//4. .任意字母(2-5位)//5.预写w{3,} (.w{1,}){0,} @ [A-z0-9]{0,} (.[A-z]{2,5}){1,2}var myRegExp=/^w{3,}(.w{1,}){0,}@[A-z0-9]{0,}(.[A-z]{2,5}){1,2}$/;console.log(myRegExp.test('wdfgdzx@163.com'));console.log(myRegExp.test('weffadfadf'));10.关于DOM (1)概述 //宿主对象DOM与BOM//Document Object Model文档对象模型//1.文档 整个HTML网页文档//2.对象 对象表示将网页中的每一个部分都转换为一个对象//3.模型 使用模型来表示对象之间的关系,这样方便我们获取对象//就是体现节点与节点之间的关系的//4.节点:Node是构成网页的最基本的组成部分//常用节点:文档节点(HTML文档)、元素节点(HTML标签)、属性节点(元素的属性)、文本节点(HTML中的文本内容)//5.节点的属性//(1)nodeName//(2)nodeType//(3)nodeValue//6.一句话DOM就是用来操作网页的//浏览器已经为我们提供了文档节点,这个对象是window属性//可以在页面中直接使用,文档节点代表的是整个网页console.log(document);//获取到button对象var myButton=document.getElementById('myButton');console.log(myButton);//修改按钮的文字myButton.innerHTML='修改后的按钮...';(2)事件 //事件//1.就是文档或浏览器窗口中发生的一些特定的交互瞬间//2.比如按钮的点击、窗口大小的改变、窗口的关闭...//3.最重要的是处理事件,需要设置对应的JS代码//4.这种在Html中写结构与行为耦合了,不推荐使用//5.使用下面的方法var myButton=document.getElementById('myButton');//绑定一个单击事件,而且进行了代码分离/* myButton.οnclick=function(){alert('不要点我...');};*///绑定双击事件myButton.οndblclick=function(){alert('你还双击我');};(3)文档的加载 //文档的加载var myButton=document.getElementById('myButton');myButton.οnclick=function(){alert('点我干什么呀');};//为什么JS不写在body的上面呢?//1.因为文档的加载是一行行按顺序加载的//2.如果JS写在上面,代码执行时页面还没有加载,所以会报错//3.所以JS代码一定要写在body的下面//4.如果非要写在上面有什么办法吗?//也就是等页面加载完毕后再执行JS//onload//会在整个页面加载完毕后再执行//为window绑定onload事件//这样可以确保代码执行时所有的DOM对象已经加载完毕window.οnlοad=function(){//这里就可以保证alert('Hello');};//最优化的方式还是把JS写在下面(4)DOM查询 //DOM查询//1.通过Id//2.通过TagName//3.通过Name//查看#bj节点var bj=document.getElementById('bj');console.log(bj.innerHTML);//查找所有的li节点var allLi=document.getElementsByTagName('li');for(var i=0;i<allLi.length;i++){console.log(allLi[i].innerHTML);}//即是查询到的只有一个元素也会封装到数组中返回//查找name=gender的所有节点var allGender=document.getElementsByName('gender');for(var i=0;i<allGender.length;i++){//innerHTML获取标签内部的HTML代码的//像这种没有内部的,自结束标签没有意义//读取的时候直接.就可以了//读取class(因为是保留字)时需要用classNameconsole.log(allGender[i].value);}(5)图片切换 //图片切换//点击按钮切换图片var up=document.getElementById('up');var down=document.getElementById('down');var img=document.getElementsByTagName('img');//因为是数组,就一个所以直接img[0]赋值img=img[0];//创建一个数组用来保存图片路径var imgArray=['siteJsCssTool/1.jpg','siteJsCssTool/2.jpg','siteJsCssTool/3.jpg'];//创建一个变量,来保存当前正在显示图片的索引var imgIndex=0;var imgInfo=document.getElementById('imgInfo');imgInfo.innerHTML="共"+imgArray.length+"图片,当前第"+(imgIndex+1)+"张";//切换图片其实就是修改src的属性up.οnclick=function(){if(imgIndex>0){imgIndex=imgIndex-1;}else{imgIndex=2;}imgInfo.innerHTML="共"+imgArray.length+"图片,当前第"+(imgIndex+1)+"张";img.src=imgArray[imgIndex];};down.οnclick=function(){if(imgIndex<2){imgIndex=imgIndex+1;}else{imgIndex=0;}imgInfo.innerHTML="共"+imgArray.length+"图片,当前第"+(imgIndex+1)+"张";img.src=imgArray[imgIndex];};CSS *{margin:0;padding:0;}#outer{width: 550px;margin:50px auto;padding:10px;background-color:yellowgreen;/*文本居中*/text-align: center;}HTML <div id="outer"><p id="imgInfo">一共3张图片,当前第1张</p><img src="siteJsCssTool/1.jpg" alt="美女" width="530px"/><button id="up">上一张</button><button id="down">下一张</button></div>(6)获取子节点 //获取子节点//childNodes表示当前节点的所有子节点//firstChild表示当前节点的第一个子节点//lastChild表示当前节点的最后一个子节点//查找#city下所有li节点var city=document.getElementById('city');//注意这里是city. 不是document. !!!var cityLi=city.getElementsByTagName('li');for(var i=0;i<cityLi.length;i++){//console.log(cityLi[i].innerHTML);}//返回#city的所有子节点var cityAllChild=city.childNodes;for(var i=0;i<cityAllChild.length;i++){//一共9个,有4个li对象,5个文本Text对象//DOM文档中间的空白,也会被当成文本对象console.log(cityAllChild[i].innerHTML);}var cityChildren=city.children;//这里获取的是所有的子元素for(var i=0;i<cityChildren.length;i++){console.log(cityChildren[i].innerHTML);}(7)父节点与兄弟节点 //父节点与兄弟节点//定义一个函数,为指定元素绑定单击响应函数//fun表示事件的回调函数function myFunctionClick(idStr,myFunction){var myButton=document.getElementById(idStr);myButton.οnclick=myFunction;}myFunctionClick('myButton',function(){console.log("我是第0个按钮...");});/*myFunctionClick('myButton1',function(){console.log("我是第1个按钮...");});*/myFunctionClick('myButton1',function(){var bj=document.getElementById('bj');var parentNode=bj.parentNode;console.log(parentNode.innerHTML);console.log(parentNode.innerText);});//innerText会自动讲html标签去除//previousSibling前一个兄弟节点(也可能获取到空白文本)//previousElementsSibling获取前一个兄弟元素(不会获取到空白文本)//读取指定id的value属性值var myText=document.getElementById('myText');console.log(myText.value);(7)全选实现 //全选//1.点击全选按钮,四个多选框全都被选中//2.要熟练的使用文档查属性var allOrNo=document.getElementById('allOrNo');var allButton=document.getElementById('allButton');allButton.οnclick=function(){//设置四个多选框为选中状态//获取这四个多选框var chooseItems=document.getElementsByName('chooseItems');for(var i=0;i<chooseItems.length;i++){chooseItems[i].checked=true;}allOrNo.checked=true;};var noButton=document.getElementById('noButton');noButton.οnclick=function(){//设置四个多选框为选中状态//获取这四个多选框var chooseItems=document.getElementsByName('chooseItems');for(var i=0;i<chooseItems.length;i++){chooseItems[i].checked=false;}allOrNo.checked=false;};var reverseButton=document.getElementById('reverseButton');reverseButton.οnclick=function(){//设置四个多选框为选中状态//获取这四个多选框var chooseItems=document.getElementsByName('chooseItems');allOrNo.checked=true;for(var i=0;i<chooseItems.length;i++){/*if(chooseItems[i].checked==true){chooseItems[i].checked=false;}else if(chooseItems[i].checked==false){chooseItems[i].checked=true;}*///可以进一步的优化为下面代码chooseItems[i].checked=!chooseItems[i].checked;if(!chooseItems[i].checked){allOrNo.checked=false;}}};//提交按钮//点击按钮以后,讲所有选中的多选框的value属性值弹出var sendButton=document.getElementById('sendButton');sendButton.οnclick=function(){var chooseItems=document.getElementsByName('chooseItems');for(var i=0;i<chooseItems.length;i++){if(chooseItems[i].checked){console.log(chooseItems[i].value);}}};//全选全部选多选框//为allOrNo绑定单击事件allOrNo.οnclick=function(){var chooseItems=document.getElementsByName('chooseItems');for(var i=0;i<chooseItems.length;i++){//在事件响应函数中,事件是给谁绑定的//this就是谁chooseItems[i].checked=this.checked;}}//四个多选框与allOrNo状态实现同步var chooseItems=document.getElementsByName('chooseItems');for(var i=0;i<chooseItems.length;i++){chooseItems[i].οnclick=function(){//上来就是全选allOrNo.checked=true;//判断四个多选框是否全选for(var j=0;j<chooseItems.length;j++){//只要有一个没选中则不是全选if(!chooseItems[j].checked){allOrNo.checked=false;}}};}(8)DOM查询剩余方法 //获取body标签var body=document.getElementsByTagName('body')[0];console.log(body);//也可以使用document直接获取body=document.body;console.log(body);//document.documentElement HTML页面//document.all 所有元素//document.getElementsByClassName() 也是数组,不支持IE8//document.querySelector('') 单个的//document.querySelectorAll('') 这个返回的是数组//可以用来选择class为''的元素或元素集合(9)DOM增删改查 //DOM增删改的操作//appendChild() 把新节点添加到指定的节点//1.创建一个广州节点,添加到#city下//创建广州节点<li>广州</li>//创建<li>元素节点//document.createElement()可以创建元素节点对象//他需要一个标签名作为参数,会根据该标签名创建元素节点对象//并将创建好的对象作为返回值返回/* var myLi=document.createElement('li');//创建文本节点//需要一个文本内容作为参数var myText=document.createTextNode('广州');//将广州text设置为li的节点//appendChild()可以向父节点中添加新的子节点myLi.appendChild(myText);//添加到city下面var city=document.getElementById('city');city.appendChild(myLi);*///2.将广州节点插入到#bj前面//一样的步骤/*var myLi=document.createElement('li');var myText=document.createTextNode('广州');myLi.appendChild(myText);var bj=document.getElementById('bj');//insertBefore()在指定的子节点前面插入新的子节点//父节点.insertBefore(新节点,旧节点)var city=document.getElementById('city');city.insertBefore(myLi,bj);*///3.使用广州节点替换北京节点/* var myLi=document.createElement('li');var myText=document.createTextNode('广州');myLi.appendChild(myText);var bj=document.getElementById('bj');var city=document.getElementById('city');//replaceChild()使用指定的子节点替换已有的子节点city.replaceChild(myLi,bj);*///4.删除北京节点/*var bj=document.getElementById('bj');var city=document.getElementById('city');//removeChild()可以删除一个子节点city.removeChild(bj);*///如果通过北京子节点自己删也可以/*var bj=document.getElementById('bj');bj.parentNode.removeChild(bj);*///5.修改#bj内的HTML代码/*var bj=document.getElementById('bj');bj.innerHTML='西安';*///6.在原来的基础上加上广州var city=document.getElementById('city');//city.innerHTML=city.innerHTML+"<li>广州</li>";//city.innerHTML="<li>广州</li>"+city.innerHTML;//这种方式更简单,更直接,缺点是原来绑定的方法可能//被删除,所以"强烈建议"使用如下方式var myLi=document.createElement('li');myLi.innerHTML='广州';city.appendChild(myLi);(10)DOM增删改训练 //添加删除记录练习//获取所有的超链接,删除功能var allHref=document.getElementsByTagName('a');//为每个超链接绑定一个单击响应函数for(var i=0;i<allHref.length;i++){allHref[i].οnclick=function(){//点击超链接后需要删除对应行//这里点击哪个超链接 this就是哪个var myTr=this.parentNode.parentNode;var name=myTr.getElementsByTagName('td')[0].innerHTML;//优化个提示var flag=confirm("确定要删除"+name+"吗?");if(flag){//自删除myTr.parentNode.removeChild(myTr);}//默认是跳转的,我们不希望它跳转//return false可以取消默认跳转return false;}}//添加功能var addEmployee=document.getElementById('addEmployee');addEmployee.οnclick=function(){//获取用户填写的信息var tempName=document.getElementById('Name');var tempEmail=document.getElementById('Email');var tempSalary=document.getElementById('Salary');//需要将获取到信息保存到tr中//比较麻烦的方法var tr=document.createElement('tr');var tdName=document.createElement('td');var tdEmail=document.createElement('td');var tdSalary=document.createElement('td');var tdHref=document.createElement('td');//创建一个a元素var a=document.createElement('a');var nameText=document.createTextNode(tempName.value);var emailText=document.createTextNode(tempEmail.value);var salaryText=document.createTextNode(tempSalary.value);var deleteText=document.createTextNode("Delete");//拼接子节点tdName.appendChild(nameText);tdEmail.appendChild(emailText);tdSalary.appendChild(salaryText);a.appendChild(deleteText);a.href='#';//还可以把这段函数提出来,放到外面共用a.οnclick=function(){var myTr=this.parentNode.parentNode;var name=myTr.getElementsByTagName('td')[0].innerHTML;var flag=confirm("确定要删除"+name+"吗?");if(flag){myTr.parentNode.removeChild(myTr);}return false;};tdHref.appendChild(a);//将td添加到tr中tr.appendChild(tdName);tr.appendChild(tdEmail);tr.appendChild(tdSalary);tr.appendChild(tdHref);//把tr添加到table中var employeeTable=document.getElementById('employeeTable');//获取tbodyvar tbody=employeeTable.getElementsByTagName('tbody')[0];tbody.appendChild(tr);}使用简化的方法操作: //添加删除记录练习//获取所有的超链接,删除功能var allHref=document.getElementsByTagName('a');//为每个超链接绑定一个单击响应函数for(var i=0;i<allHref.length;i++){allHref[i].οnclick=function(){//点击超链接后需要删除对应行//这里点击哪个超链接 this就是哪个var myTr=this.parentNode.parentNode;var name=myTr.getElementsByTagName('td')[0].innerHTML;//优化个提示var flag=confirm("确定要删除"+name+"吗?");if(flag){//自删除myTr.parentNode.removeChild(myTr);}//默认是跳转的,我们不希望它跳转//return false可以取消默认跳转return false;}}//添加功能var addEmployee=document.getElementById('addEmployee');addEmployee.οnclick=function(){//获取用户填写的信息var tempName=document.getElementById('Name');var tempEmail=document.getElementById('Email');var tempSalary=document.getElementById('Salary');var tr=document.createElement('tr');//设置tr中的内容tr.innerHTML="<td>"+tempName.value+"</td>"+"<td>"+tempEmail.value+"</td>"+"<td>"+tempSalary.value+"</td>"+"<td><a href='#'>Delete</a></td>";//获取a元素,为其绑定单击事件var a=tr.getElementsByTagName('a')[0];a.οnclick=function(){var myTr=this.parentNode.parentNode;var name=myTr.getElementsByTagName('td')[0].innerHTML;var flag=confirm("确定要删除"+name+"吗?");if(flag){myTr.parentNode.removeChild(myTr);}return false;};//把tr添加到table中var employeeTable=document.getElementById('employeeTable');//获取tbodyvar tbody=employeeTable.getElementsByTagName('tbody')[0];tbody.appendChild(tr);}(11)a的索引问题 //a的索引问题var allHref=document.getElementsByTagName('a');//为每个超链接绑定一个单击响应函数for(var i=0;i<allHref.length;i++){alert('for循环正在执行...'+i);allHref[i].οnclick=function(){//这里为什么不相等呢?//因为i的值 i的值已经恒定为2了//因为for循环会先执行//而响应函数会在超链接点击时才执行,所以for//循环早已经执行完毕了//所以i一直为最大值了alert(i);alert(allHref[i]==this);}}(12)操作内联样式 //操作内联样式//点击按钮后,修改box1的大小var myButton=document.getElementById('myButton');var box1=document.getElementById('box1');myButton.οnclick=function(){//修改box1的样式box1.style.width='500px';box1.style.height='500px';//如果样式名中含有-,这种是不合法的//需要将这种样式修改为驼峰命名法//如果实在忘记了,去看文档即可box1.style.backgroundColor='yellow';//通过这种方法修改的是内联样式//所以修改了立刻就生效了//但是千万不要写!important,则此时是最高的优先级//JS修改也无法改变。所以尽量不要这么使用};var myButton1=document.getElementById('myButton1');myButton1.οnclick=function(){//通过style属性读取的也是内联样式//所以如果上来默认点击会获取到打印出空//那么如何读取非内联样式呢?看后面的知识alert(box1.style.width);alert(box1.style.height);alert(box1.style.backgroundColor);};(13)操作元素样式 //操作元素样式var myButton=document.getElementById('myButton');var box1=document.getElementById('box1');myButton.οnclick=function(){//读取当前样式//语法 元素.currentStyle.样式名,它可以用来读取当前显示的样式如果但前样式没有设置样式,则获取它的默认值//currentStyle只有IE浏览器支持,其他浏览器都不支持//alert(box.currentStyle.width);//在其他浏览器中可以使用getComputedStyle()这个方法来获取当前的样式,这个方法是window方法可以直接使用需要有两个参数第一个,需获取样式的元素。第二个,可以传递一个伪元素,一般都是null//需要两个参数1.获取样式的元素2.传递一个伪元素,一般传null//返回的对象封装了当前元素对应的样式//但是该方法不支持IE8及以下浏览器//var box1Style=getComputedStyle(box1,null);//alert(box1Style.width+"---"+box1Style.color);//通过以上两种方式都是只读的,如果要修改必须通过style属性alert(getStyle(box1,'width'));};//定义一个函数,用来获取指定元素的当前样式//元素,样式名function getStyle(myObject,name){//正常浏览器if(window.getComputedStyle){var myObjectStyle=getComputedStyle(myObject,null);return myObjectStyle[name];}else{//IE8的方式return myObject.currentStyle[name];}}(14)其他样式相关的属性 JS部分 ------------------------------ //其他样式属性操作var box1=document.getElementById('box1');var box2=document.getElementById('box2');var myButton=document.getElementById('myButton');myButton.οnclick=function(){//clientWidth//clientHeight//包括宽度/高度+内外边距padding//这些属性都是不带px,返回都是一个数字,可以直接进行计算//获取元素的宽度与高度,包括内容区和内边距//只能读取不能修改//alert("可见宽度:"+box1.clientWidth);//alert("可见高度:"+box1.clientHeight);//下面的这两个属性包括了内容区的高度/宽度//alert("元素宽度:"+box1.offsetWidth);//alert("元素高度:"+box1.offsetHeight);//offsetParent//获取当前元素的定位父元素//主要看外层元素是否开启相对定位relative//style="position:'relative';"//var myOffsetParent=box1.offsetParent;//alert("定位的父元素:"+myOffsetParent);//offsetLeft//相对于定位元素的水平偏移量//offsetTop//相对于定位元素的垂直偏移量//alert("水平偏移:"+box1.offsetLeft);//alert("垂直偏移:"+box1.offsetTop);//scrollHeight/scrollWidth//滚动高度,不现实的部分也计算//alert("滚动高度:"+box2.scrollHeight);//alert("滚动宽度:"+box2.scrollWidth);//scrollTop/scrollLeftalert("滚动条左边偏移量:"+box1.scrollLeft);alert("滚动条上下偏移量:"+box1.scrollTop);alert(box1.clientHeight);}//当垂直滚动条滚动到底时表单项可用//获取info的p元素var myInfo=document.getElementById('info');//为info绑定一个滚动条动态的事件var myInputArray=document.getElementsByTagName('input');myInfo.οnscrοll=function(){//检查是否垂直滚动条滚动到底if(myInfo.scrollHeight-myInfo.scrollTop==myInfo.clientHeight){//设置禁用的表单项可用//disabled属性可以设置一个元素是否禁用//如果设置为true则元素禁用,如果设置为false则元素可用myInputArray[0].disabled=false;myInputArray[1].disabled=false;}}CSS部分 ------------------------------- #box1{width: 280px;height: 200px;background-color: red;/* 自适应,会出现滚动条*/overflow: auto;}#box2{width: 460px;height: 500px;background-color: #b7eb8f;}#info{width: 280px;height: 100px;background-color: darkolivegreen;overflow: auto;}HTML部分 --------------------------- <h1>JS</h1><!--主题部分--><button id="myButton">点我一下</button><hr/><div id="box1"><div id="box2"></div></div><h1>亲爱的用户,欢迎注册</h1><p id="info">必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/>必须仔细阅读<br/></p><!--如果为表单项添加disabled="disabled" 则表单项将变成不可用的--><input type="checkbox" disabled="disabled"/>我已经仔细阅读,同意遵守!<input type="submit" value="注册" disabled="disabled"/>11.事件部分 (1)事件对象 JS: //事件对象var areaDiv=document.getElementById('areaDiv');var showMsg=document.getElementById('showMsg');//onmousemove//该事件在 鼠标在元素中移动时被触发//事件对象//1、当事件的响应函数被触发时,浏览器每次都会将一个事件对象//作为实参传递进响应函数。//2、这个对象封装了当前时间的一切信息,比如鼠标的坐标,//键盘的那个按键被按下,鼠标滚轮的移动方向...areaDiv.οnmοusemοve=function(myEvent){//myEvent=event||window.event//alert('想屁吃');//在showMsg中显示鼠标的坐标if(myEvent){var tempX=myEvent.clientX;var tempX=myEvent.clientY;}else{//在IE8及以下浏览器中要用var tempX=window.event.clientX;var tempY=window.event.clientY;}showMsg.innerHTML="X坐标:"+tempX+",Y坐标:"+tempX;};CSS: #areaDiv{width: 500px;height: 100px;border: solid 1px;}#showMsg{width: 500px;height: 50px;border: solid 1px;}HTML部分两个DIV,比较简单。 (2)DIV与鼠标同动 //事件的冒泡var mySpan=document.getElementById('mySpan');var box1=document.getElementById('box1');mySpan.οnclick=function(myEvent){alert('我是span的单击响应函数...');//取消冒泡myEvent.cancelBubble=true;//同时可以联想到移动DIV时,可以不让移动到其他DIV的内部};box1.οnclick=function(){alert('我是box1的单击响应函数...');};document.body.οnclick=function(){alert('我是body的单击响应函数...');};//1、点击mySpan//其余的box1与document的点击也都被触发了//所谓"冒泡"就是后代元素事件被触发时,祖先元素//的相同事件也会被触发。//2、"冒泡的事件"//3、大部分冒泡都是有用的,如果不需要可以用时间对象取消(3)事件的委派 //事件的委派//为每个超链接绑定一个单击响应函数/* var aArray=document.getElementsByTagName('a');//遍历for(var i=0;i<aArray.length;i++){aArray[i].οnclick=function(){alert('我是a的单击响应函数');};}*/var myButton=document.getElementById('myButton');var myUl=document.getElementById('myUl');myButton.οnclick=function(){var li=document.createElement('li');li.innerHTML="<a href="#" class="myLink">新建的超链接</a>";myUl.appendChild(li);};//1、为每个超链接都绑定一个单击响应函数//这种操作比较麻烦,而且这些操作只能为已有的超链接设置事件//新添加的时间必须重新绑定//2、我们希望只绑定一次时间,即可应用到多个元素上//即是元素是动态的//这就是事件的"委派"//3、绑定给祖先元素单击事件,这样子元素就可以冒泡到//祖先元素,利用冒泡可以减少事件绑定。myUl.οnclick=function(myEvent){//1、如果触发事件对象是我们期望的元素则我们执行//否则不执行。//2、target返回触发事件对象的元素myEvent=myEvent||window.event;if(myEvent.target.className=='myLink'){alert('我是ul的单击绑定函数');}};HTML部分: <button id="myButton">添加超链接</button><ul id="myUl"><li><a href="#" class="myLink">超链接1</a></li><li><a href="#" class="myLink">超链接2</a></li><li><a href="#" class="myLink">超链接3</a></li></ul>CSS部分: #myUl{background-color: #4d5669;}(4)事件的绑定 //事件的绑定var myButton=document.getElementById('myButton');myButton.οnclick=function(){alert("第一个函数...");};//如果绑定第二个函数//1、使用对象.事件=函数的形式//只能同时为一个元素的事件绑定一个相应函数//不能绑定多个,如果绑定了多个,则后边会覆盖掉前面的//2、addEventListener()//这个方法也可以为元素绑定响应函数//参数//(1)事件的字符串,不要on//(2)回调函数,当事件触发时该函数会被调用//(3)是否在捕获阶段触发事件,需要一个布尔值,一般都传false//可以为一个元素的相同事件同时绑定多个响应函数,//当事件被触发时,会按照绑定顺序依次执行//3、当时这种方法不支持IE8及以下浏览器myButton.addEventListener('click',function(){alert('第二种方式绑定的函数1...')},false);myButton.addEventListener('click',function(){alert('第二种方式绑定的函数2...')},false);//IE8中要使用attachEvent()来进行绑定//myButton.attachEvent('onclick',function(){});//4、写个通用的绑定函数//addEventListener对应的this,是绑定事件的对象//attachEvent中的this,是windowfunction bind(myObject,myEventStr,myCallback){//如果有这个方法则用,没有则用别的if(myObject.addEventListener){//谷歌等浏览器myObject.addEventListener(myEventStr,myCallback,false);}else{//IE8及以下myObject.attachEvent('on'+myEventStr,function(){//在匿名函数中调用回调函数myCallback.call(myObject);//这样做的目的就是统一this指向button对象});}}(5)事件的传播 JS:---- //事件的传播var myDiv=document.getElementById('myDiv');var myDiv1=document.getElementById('myDiv1');var myDiv2=document.getElementById('myDiv2');//事件的传播网景和微软公司有不同的理解//1、微软公司认为事件应该是由内向外传播,也就是当前事件//触发时,应该先触发当前元素上的事件,然后再向祖先事件传播//,也就是从内向外,按照冒泡事件执行。//2、网景公司认为事件应该是由外向内传播的,也就是先触发//祖先元素事件,然后再向内传播给后代元素。//3、最后w3c综合两个公司的方案,将事件传播分为三个阶段//(1)捕获阶段,由祖先到目标元素进行事件的捕获,默认此时不会触发事件//(2)目标阶段,事件捕获到目标元素,开始在目标元素上执行事件//(3)冒泡阶段,事件从目标元素向他的祖先元素传递,依次触发祖先元素上的事件//4、如果希望在捕获阶段就触发事件,可以将addEventListener()第三个参数//设置为true。刚好和目前的执行相反。一般我们不会使用。//所以此参数一般都设置为false。bind(myDiv,'click',function(){alert('我是myDiv的响应函数');});bind(myDiv1,'click',function(){alert('我是myDiv1的响应函数');});bind(myDiv2,'click',function(){alert('我是myDiv2的响应函数');});function bind(myObject,myEventStr,myCallback){//如果有这个方法则用,没有则用别的if(myObject.addEventListener){//谷歌等浏览器myObject.addEventListener(myEventStr,myCallback,false);//设置为true执行相反,一般都设置为false}else{//IE8及以下myObject.attachEvent('on'+myEventStr,function(){//在匿名函数中调用回调函数myCallback.call(myObject);//这样做的目的就是统一this指向button对象});}}HTML------ <div id="myDiv"><div id="myDiv1"><div id="myDiv2"></div></div></div>CSS---- #myDiv{width: 300px;height: 300px;background-color: #b7eb8f;}#myDiv1{width: 200px;height: 200px;background-color: #13c2c2;}#myDiv2{width: 100px;height: 100px;background-color: #2baee9;}(6)拖拽 JS---- //拖拽//1.当鼠标在元素上按下时开始拖拽onmousedown//2.当鼠标移动时,被拖拽元素跟随鼠标移动onmousemove//3.当鼠标松开时,被拖拽元素固定在当前位置onmouseupvar myDiv1=document.getElementById('myDiv1');myDiv1.οnmοusedοwn=function(){//当鼠标移动时document.οnmοusemοve=function(myEvent){//当鼠标移动时,被拖拽元素跟随鼠标移动myEvent=myEvent||window.event;//获取坐标var leftX=myEvent.clientX;var topY=myEvent.clientY;//修改myDiv1的位置myDiv1.style.left=leftX+'px';myDiv1.style.top=topY+'px';};//当鼠标松开时document.οnmοuseup=function(){//松开时//取消移动函数document.οnmοusemοve=null;//但是这个时候,如果有个myDiv2,当两个div//重叠时会有问题,所以鼠标松开也是要给//document绑定document.οnmοuseup=null;};};HTML----- <div id="myDiv1"></div><div id="myDiv2"></div>CSS---- #myDiv1{width: 100px;height: 100px;background-color: #2baee9;position: absolute;}#myDiv2{width: 100px;height: 100px;background-color: red;position: absolute;left: 200px;top: 200px;}鼠标所在位置的优化JS------- //拖拽(2)//1.当鼠标在元素上按下时开始拖拽onmousedown//2.当鼠标移动时,被拖拽元素跟随鼠标移动onmousemove//3.当鼠标松开时,被拖拽元素固定在当前位置onmouseupvar myDiv1=document.getElementById('myDiv1');myDiv1.οnmοusedοwn=function(myEventTop){//div的偏移量鼠标.clientX-元素.offsetLeft//div的偏移量鼠标.clientY-元素.offsetTopvar myOffsetLeft=myEventTop.clientX-myDiv1.offsetLeft;var myOffsetTop=myEventTop.clientY-myDiv1.offsetTop;//当鼠标移动时document.οnmοusemοve=function(myEvent){//当鼠标移动时,被拖拽元素跟随鼠标移动myEvent=myEvent||window.event;//获取坐标var leftX=myEvent.clientX-myOffsetLeft;var topY=myEvent.clientY-myOffsetTop;//修改myDiv1的位置myDiv1.style.left=leftX+'px';myDiv1.style.top=topY+'px';};//当鼠标松开时document.οnmοuseup=function(){//松开时//取消移动函数document.οnmοusemοve=null;//但是这个时候,如果有个myDiv2,当两个div//重叠时会有问题,所以鼠标松开也是要给//document绑定document.οnmοuseup=null;};};拖拽封装成函数(myObject)----------- //拖拽(3) 拖消失问题的解决//1.当鼠标在元素上按下时开始拖拽onmousedown//2.当鼠标移动时,被拖拽元素跟随鼠标移动onmousemove//3.当鼠标松开时,被拖拽元素固定在当前位置onmouseupvar myDiv1=document.getElementById('myDiv1');myDiv1.οnmοusedοwn=function(myEventTop){//div的偏移量鼠标.clientX-元素.offsetLeft//div的偏移量鼠标.clientY-元素.offsetTopvar myOffsetLeft=myEventTop.clientX-myDiv1.offsetLeft;var myOffsetTop=myEventTop.clientY-myDiv1.offsetTop;//当鼠标移动时document.οnmοusemοve=function(myEvent){//当鼠标移动时,被拖拽元素跟随鼠标移动myEvent=myEvent||window.event;//获取坐标var leftX=myEvent.clientX-myOffsetLeft;var topY=myEvent.clientY-myOffsetTop;//修改myDiv1的位置myDiv1.style.left=leftX+'px';myDiv1.style.top=topY+'px';};//当鼠标松开时document.οnmοuseup=function(){//松开时//取消移动函数document.οnmοusemοve=null;//但是这个时候,如果有个myDiv2,当两个div//重叠时会有问题,所以鼠标松开也是要给//document绑定document.οnmοuseup=null;};//1.当我们拖拽网页中的内容时,浏览器会默认去搜索引擎中搜索内容//此时会导致拖拽功能的异常,这个是浏览器提供的默认行为//可以通过return false来取消这个行为//2.但是这个方法对IE8不起作用//方法setCapture(),土匪把下次所有的事件都揽到自己身上//myDiv1.setCapture();//只有IE支持,在谷歌中会报错//当鼠标松开时取消这个函数//所以需要加判断if(myDiv1.setCapture)...//myDiv1.releaseCapture(),这里也要加判断才执行return false;};//可以提炼为函数方法,专门绑定拖拽使用//不仅可以拖拽div也可以拖拽img只需要传对象就可以了(7)滚轮的事件 //滚轮事件//滚轮可以改变div的高度var myDiv1=document.getElementById('myDiv1');//绑定滚轮事件onmousewheel//但是火狐不支持该属性//DOMMouseScroll来绑定该事件,而且必须通过//addEventListener()函数来绑定myDiv1.onmousewheel=function(myEvent){//判断鼠标滚轮滚动的方向//向上滚120 向下滚是-120//wheelDelta只看正负就可以了//wheelDelta这个属性火狐中也不支持//在火狐中是myEvent.detailif(myEvent.wheelDelta>0||myEvent.detail<0){//alert('向上滚');//box1变短if(myDiv1.clientHeight>10){myDiv1.style.height=myDiv1.clientHeight-10+'px';}}else{//alert('向下滚');myDiv1.style.height=myDiv1.clientHeight+10+'px';}//1.当滚轮滚动时,浏览器有滚动条,滚动条也会随之滚动//这是浏览器的默认行为,如果不希望发生,则可以取消默认行为//2.使用addEventListener()方法绑定响应函数,取消默认行为时//不能使用return false//需要使用event来取消默认行为,火狐就是这样//IE8不支持,所以这里要加个判断if(myEvent.preventDefault){myEvent.preventDefault();}//if判断也可以用这种写法myEvent.preventDefault &&myEvent.preventDefault();return false;};//为火狐绑定bind(myDiv1,'DOMMouseScroll', myDiv1.onmousewheel);function bind(myObject,myEventStr,myCallback){//如果有这个方法则用,没有则用别的if(myObject.addEventListener){//谷歌等浏览器myObject.addEventListener(myEventStr,myCallback,false);//设置为true执行相反,一般都设置为false}else{//IE8及以下myObject.attachEvent('on'+myEventStr,function(){//在匿名函数中调用回调函数myCallback.call(myObject);//这样做的目的就是统一this指向button对象});}}(8)键盘事件 //键盘事件//onkeydown按下 onkeyup松开//1.onkeydown如果一直按着某个键,会连续触发//2.当其连续触发时,第一次与第二次间隔稍微长点//其他的会非常快,这里是为了防止误操作。//这种设计是浏览器的设计。//3.onkeyup只会触发一次//键盘事件一般会绑定给获取到焦点的对象//或者是documentvar inputArray=document.getElementsByTagName('input');/*document.οnkeydοwn=function(myEvent){myEvent=myEvent||window.event;//可以通过keyCode获取按键编码console.log(myEvent.keyCode);//通过keyCode可以判断哪个键被按了if(myEvent.keyCode===13){console.log('你按的是回车键');}//判断ctrl/shift/alt+某个字母被按下//ctrlKey//shiftKey//altKeyif(myEvent.keyCode===89&&event.ctrlKey){console.log('你按的是ctrl+y');}console.log('键盘被按下...');};document.οnkeyup=function(myEvent){myEvent=myEvent||window.event;console.log('键盘被松开...');};*/inputArray[0].οnkeydοwn=function(myEvent){myEvent=myEvent||window.event;//可以通过keyCode获取按键编码console.log(myEvent.keyCode);//通过keyCode可以判断哪个键被按了if(myEvent.keyCode===13){console.log('你按的是回车键');}//判断ctrl/shift/alt+某个字母被按下//ctrlKey//shiftKey//altKeyif(myEvent.keyCode===89&&event.ctrlKey){console.log('你按的是ctrl+y');}console.log('键盘被按下...');//如果加上return false,则输出的内容不会到文本框中//可以使文本框中不能输入数字if(myEvent.keyCode>=48 && myEvent.keyCode<=57){return false;}};inputArray[0].οnkeyup=function(myEvent){myEvent=myEvent||window.event;console.log('键盘被松开...');};//让div根据按键方向移动上下左右键盘(9)键盘移动DIV //键盘移动DIVvar myDiv1=document.getElementById('myDiv1');//定义速度var speed=10;document.οnkeydοwn=function(myEvent){myEvent=myEvent||window.event;console.log(myEvent.keyCode);//当用户按了ctrl以后速度加快if(myEvent.ctrlKey){speed=500;console.log('按下了加速'+speed);}switch (myEvent.keyCode) {case 37:console.log("左"+speed);myDiv1.style.left=myDiv1.offsetLeft-speed+'px';break;case 38:console.log("上"+speed);myDiv1.style.top=myDiv1.offsetTop-speed+'px';break;case 39:console.log("右"+speed);myDiv1.style.left=myDiv1.offsetLeft+speed+'px';break;case 40:console.log("下"+speed);myDiv1.style.top=myDiv1.offsetTop+speed+'px';break;}}12.关于BOM (1)Navigator //BOM Navigator//提供了一组对象,用来完成对浏览器的操作//BOM对象有哪些//1.Window//代表的是整个浏览器的窗口,同时window也是网页中的全局对象//2.Navigator//代表当前浏览器的信息,通过该对象可以识别不同的浏览器//3.Location//代表浏览器的当前地址栏信息,通过它可以获取地址栏信息,//或者操作浏览器跳转页面//4.History//代表浏览器的历史记录,可以通过该对象来操作浏览器的历史记录,//由于隐私原因,该对象不能获取到具体的历史记录,只能操作浏览器//向前或者向后翻页,而且该操作只在当次访问时有效。//5.Screen//代表用户的屏幕的信息,通过该对象可以获取到用户显示器的相关//信息。//6.这些BOM对象都是在浏览器中作为Window对象属性保存的,//可以通过Windows对象来使用,也可以直接使用。/*console.log(window);console.log(navigator);console.log(location);console.log(history);*///1.我们先看navigator//(1)由于历史原因,navigator对象中大部分属性都已经不能帮我识别浏览器了//一般我们只会使用userAgent(用户代理)来判断浏览器的信息。//userAgent是一个字符串,包含用来描述浏览器的信息的内容。//不同的浏览器会有不同的userAgent//谷歌:Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.82 Safari/537.36//2345:Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3947.100 Safari/537.36console.log("浏览器名称:"+navigator.userAgent);var myUserAgent=navigator.userAgent;if(/chrome/i.test(myUserAgent)){alert("你用的是谷歌浏览器...");}else if(/msie/i.test(myUserAgent)){alert("你用的是IE浏览器...");//IE11已经将微软和IE相关的标识去除了//所以我们基本不能通过userAgent来识别是否为IE了}//2.如果不能通过userAgent判断,可以通过一些浏览器中//特有的对象,来判断浏览器的信息。//比如ActiveXObject//只有IE里能打印出来//3."ActiveXObject" in window 这是检查一个对象里是否//包含某个属性。if("ActiveXObject" in window){alert("是IE浏览器");}else{alert("不是IE浏览器");}(2)History //History//1.可以用来操作浏览器向前或者向后翻页//2.length可以获取到当成访问的链接数量alert(history.length);var myButton=document.getElementById('myButton');myButton.οnclick=function(){//和浏览器的后退按钮一样history.back();//可以跳转到下一个页面,与前进按钮一样history.forward();//可以跳转到指定页面//1表示向前跳转一个页面,相当于forward//2表示向前跳转两个页面//-1是向后跳转一个页面,相当于back//-2是向后跳转两个页面history.go();}(3)Location //Location//1.该对象封装了浏览器的地址栏信息//2.可以获取当前页面的完整路径alert(location);var myButton=document.getElementById('myButton');myButton.οnclick=function(){location='https://www.baidu.com';//1.如果直接将location修改为一个相对路径或完整路径。//则页面直接跳转到该路径,而且会生成响应的历史记录//2.location还能获取端口号、服务器相关的方法//3.assign()跳转其他页面,与直接修改location一样//location.assign('https://www.baidu.com');//reload()重新加载当前页面,与刷新按钮一样//location.reload();//ctrl+F5可以强制清空页面缓存,与location.reload(true)效果一样//用新页面替换当前页面,只是不会生成历史记录。location.replace('https://www.baidu.com');};(4)定时器 //定时器 Window对象//1.setInterval()定时调用//2.但是循环太快了//3.如果希望每间隔一段时间执行一次,可以使用定时调用//setInterval()var myCount=document.getElementById("myCount");//开启定时器,可以将函数每隔一段时间执行一次//参数(1)回调函数(2)每次调用间隔的时间msvar tempNum=1;var mySetInterval=setInterval(function(){myCount.innerHTML=tempNum++;//在达到11时就关闭定时执行器if(tempNum==11){clearInterval(mySetInterval);}},1000);//setInterval这个方法会返回一个Number类型的数据//1.clearInterval()用来关闭一个定时器//2.方法中需要一个定时器的标识作为参数,这样将关闭//标识对应的定时器。(5)自动切换图片 var myImg=document.getElementById("myImg");var myButton=document.getElementById("myButton");var myButton1=document.getElementById("myButton1");var mySetInterval;myButton.οnclick=function(){//1.每点击一次按钮,就回开启一个定时器//如果点击十次,就回开启10个定时器了//这就导致图片切换速度切换过快,并且只能关闭//最后一个定时器。//2.所以在开启之前就把上一个关闭了clearInterval(mySetInterval);var tempNum=1;mySetInterval=setInterval(function(){myImg.src="siteJsCssTool/"+(tempNum++)+".jpg";if(tempNum==4){tempNum=1;//clearInterval(mySetInterval);}},1000);};myButton1.οnclick=function(){clearInterval(mySetInterval);};//1.clearInterval()可以接受任意参数//如果参数有效,则停止对应的定时器//如果不是有效标识,则什么都不做。(6)通过定时器解决方块移动卡顿 //键盘移动DIVvar myDiv1=document.getElementById('myDiv1');//定义速度var speed=10;var direction=0;//开启一个定时器,来控制div的移动setInterval(function(){switch (direction) {case 37:console.log("左"+speed);myDiv1.style.left=myDiv1.offsetLeft-speed+'px';break;case 38:console.log("上"+speed);myDiv1.style.top=myDiv1.offsetTop-speed+'px';break;case 39:console.log("右"+speed);myDiv1.style.left=myDiv1.offsetLeft+speed+'px';break;case 40:console.log("下"+speed);myDiv1.style.top=myDiv1.offsetTop+speed+'px';break;}},30)document.οnkeydοwn=function(myEvent){myEvent=myEvent||window.event;direction=myEvent.keyCode;console.log(myEvent.keyCode);//当用户按了ctrl以后速度加快if(myEvent.ctrlKey){speed=500;console.log('按下了加速'+speed);}else{speed=10;}}document.οnkeyup=function(){//设置方向为0direction=0;} (7)延时调用 //1.延时调用var num=1;//定时调用/* setInterval(function(){console.log(num++);},3000);*///延时调用//隔3秒以后再执行,"只会执行一次"var mySetTimeout=setTimeout(function(){console.log(num++);clearTimeout(mySetTimeout);},3000);//关闭延时调用//clearTimeout(mySetTimeout);//2.延时调用与定时调用实际上是可以互相代替的,//在开发者用的多的是定时调用。(8)定时器的应用 //定时器的应用var myDiv1=document.getElementById("myDiv1");var myDiv2=document.getElementById("myDiv2");var myButton=document.getElementById("myButton");var myButton1=document.getElementById("myButton1");var myButton2=document.getElementById("myButton2");var myButton3=document.getElementById("myButton3");//1.点击按钮后,使box1向右移动(left值增大)//当两个div都在这个变量中保存setInterval就会出现//问题。//所以保存在各自的对象中//全局变量要慎用//var mySetInterval;myButton.οnclick=function(){move(myDiv1,'left',800,10,function(){move(myDiv1,'height',500,10,function(){move(myDiv1,'top',1500,10,function(){move(myDiv1,'top',0,10,function(){});});});});};myButton1.οnclick=function(){move(myDiv1,'width',500,10);};myButton2.οnclick=function(){move(myDiv2,800,10);};//提取一个可以执行简单动画的函数//正数向右移动,负数向左移动//attr执行动画的样式//callback,这个函数将会在我们的动画执行完毕以后执行//1.也可以直接把这两个函数放到JS文件中//2.然后在要引用的地方引用,直接把库拷贝过去就可以了function move(myObject,attr,target,speed,callback){//防止多次点击开启多个定时器的问题clearInterval(myObject.mySetInterval);//获取当前值var currentValue=parseInt(getStyle(myObject,attr));if(currentValue>target){//此时speed为负值speed=-speed;}//开启定时器,用来执行动画效果myObject.mySetInterval=setInterval(function(){//获取div1原理left值var oldValue=parseInt(getStyle(myObject,attr));//判断速度的正负值//在旧的基础上增加var newValue=oldValue+speed;//向左移动是否小于target//向右移动是否大于targetif((speed<0&&newValue<target) || (speed>0&&newValue>target)){newValue=target;}//新值设置给div1myObject.style[attr]=newValue+'px';//到达目标关闭定时器if(newValue==target){clearInterval(myObject.mySetInterval);//动画执行完毕,调用回调函数if(callback){callback();}}},30);}function getStyle(obj,name){if(window.getComputedStyle){return getComputedStyle(obj,null)[name];}else{return obj.currentStyle[name];}}(9)轮播图 HTML: <!--创建一个外部的div,来作为大的容器--><div id="divOuter"><!--创建一个ul,用于放置图片--><ul id="ulImageList"><li><img src="siteJsCssTool/1.jpg" /></li><li><img src="siteJsCssTool/2.jpg" /></li><li><img src="siteJsCssTool/3.jpg" /></li></ul><!--创建导航按钮--><div id="divNavigator"><a href="#"></a><a href="#"></a><a href="#"></a></div></div>CSS: <style>*{margin:0;padding:0;}#divOuter{width: 572px;height: 696px;/* 居中*/margin:50px auto;/*设置背景颜色*/background-color:yellowgreen;/*设置padding*/padding:10px 0;/*开启相对定位*/position: relative;/* 裁剪溢出的内容*/overflow: hidden;}#ulImageList{/*去除项目符号*/list-style: none;/* width: 1800px;*//*开启绝对定位*/position: absolute;/*每向左移动572px,就会显示到下一张图片*/left:-572px;}/*设置图片中的li*/#ulImageList li{/*设置浮动*/float:left;/*设置上下外边距*/margin:0 10px;}#ulImageList img{width: 552px;height: 696px;}/*设置导航按钮*/#divNavigator{/* 开启绝对定位*/position: absolute;bottom:105px;/*设置left的值outer宽度572divNavigator宽度 25*3=75572-75=497/2=248.5 *//*left:248.5px;写死不能适应所有情况,所以通过js*/}#divNavigator a{width: 15px;height: 15px;background-color: red;/*设置超链接浮动*/float:left;/*设置左右外边距*/margin: 0 5px;/*设置透明*/opacity:0.5;/*兼容IE8的透明*/filter:alpha(opacity=50);}#divNavigator a:hover{background-color: black;}</style>JS: <script>//轮播图//设置var ulImageList=document.getElementById('ulImageList');//设置ulImageList的宽度var imageArray=document.getElementsByTagName('img');ulImageList.style.width=imageArray.length*572+'px';var divNavigator=document.getElementById('divNavigator');var divOuter=document.getElementById('divOuter');//设置divNavigator的left的值/*console.log(divOuter.offsetWidth);console.log(divNavigator.clientWidth);*/divNavigator.style.left=(divOuter.offsetWidth -divNavigator.offsetWidth)/2+'px';//获取所有的a标签var aArray=document.getElementsByTagName('a');//设置第一张默认为黑色aArray[0].style.backgroundColor='black';</script>(10)点击切换图片 <!DOCTYPE html><html lang="cn" xmlns:th="http://www.thymeleaf.org" xmlns:v-bind="http://www.w3.org/1999/xhtml"xmlns:v-on="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="application/json; charset=UTF-8"><meta name="referrer" content="never"><title>JS</title></head><body><!--创建一个外部的div,来作为大的容器--><div id="divOuter"><!--创建一个ul,用于放置图片--><ul id="ulImageList"><li><img src="siteJsCssTool/1.jpg" /></li><li><img src="siteJsCssTool/2.jpg" /></li><li><img src="siteJsCssTool/3.jpg" /></li></ul><!--创建导航按钮--><div id="divNavigator"><a href="#"></a><a href="#"></a><a href="#"></a></div></div></body><style>*{margin:0;padding:0;}#divOuter{width: 572px;height: 696px;/* 居中*/margin:50px auto;/*设置背景颜色*/background-color:yellowgreen;/*设置padding*/padding:10px 0;/*开启相对定位*/position: relative;/* 裁剪溢出的内容*/overflow: hidden;}#ulImageList{/*去除项目符号*/list-style: none;/* width: 1800px;*//*开启绝对定位*/position: absolute;/*每向左移动572px,就会显示到下一张图片*/left:-572px;}/*设置图片中的li*/#ulImageList li{/*设置浮动*/float:left;/*设置上下外边距*/margin:0 10px;}#ulImageList img{width: 552px;height: 696px;}/*设置导航按钮*/#divNavigator{/* 开启绝对定位*/position: absolute;bottom:105px;/*设置left的值outer宽度572divNavigator宽度 25*3=75572-75=497/2=248.5 *//*left:248.5px;写死不能适应所有情况,所以通过js*/}#divNavigator a{width: 15px;height: 15px;background-color: red;/*设置超链接浮动*/float:left;/*设置左右外边距*/margin: 0 5px;/*设置透明*/opacity:0.5;/*兼容IE8的透明*/filter:alpha(opacity=50);}#divNavigator a:hover{background-color: black;}</style><script>//轮播图//设置var ulImageList=document.getElementById('ulImageList');//设置ulImageList的宽度var imageArray=document.getElementsByTagName('img');ulImageList.style.width=imageArray.length*572+'px';var divNavigator=document.getElementById('divNavigator');var divOuter=document.getElementById('divOuter');//设置divNavigator的left的值/*console.log(divOuter.offsetWidth);console.log(divNavigator.clientWidth);*/divNavigator.style.left=(divOuter.offsetWidth -divNavigator.offsetWidth)/2+'px';//获取所有的a标签var aArray=document.getElementsByTagName('a');//设置第一张默认为黑色aArray[0].style.backgroundColor='black';//点击超链接切换到指定的图片//1.点击第一个超链接,显示第一个图片...以此类推//2.为所有的超链接绑定单击响应函数var index=0;ulImageList.style.left=index*-572+'px';for(var i=0;i<aArray.length;i++){//为每一个超链接都添加一个onlyMark属性aArray[i].onlyMark=i;aArray[i].οnclick=function(){//获取点击超链接的索引,并将其设置为index//alert(this.onlyMark);index=this.onlyMark;//切换图片//1.第一张 0 0 第二张 1 -572 第三张2 -572*2//ulImageList.style.left=index*-572+'px';setA(aArray,index);move(ulImageList,"left",index*-572,20,function(){});};}//创建一个方法用来设置选中的afunction setA(myArray,myIndex){for(var i=0;i<myArray.length;i++){//myArray[i].style.backgroundColor='red';//让内联样式生效myArray[i].style.backgroundColor='';}myArray[myIndex].style.backgroundColor='black';}function move(myObject,attr,target,speed,callback){//防止多次点击开启多个定时器的问题clearInterval(myObject.mySetInterval);//获取当前值var currentValue=parseInt(getStyle(myObject,attr));if(currentValue>target){//此时speed为负值speed=-speed;}//开启定时器,用来执行动画效果myObject.mySetInterval=setInterval(function(){//获取div1原理left值var oldValue=parseInt(getStyle(myObject,attr));//判断速度的正负值//在旧的基础上增加var newValue=oldValue+speed;//向左移动是否小于target//向右移动是否大于targetif((speed<0&&newValue<target) || (speed>0&&newValue>target)){newValue=target;}//新值设置给div1myObject.style[attr]=newValue+'px';//到达目标关闭定时器if(newValue==target){clearInterval(myObject.mySetInterval);//动画执行完毕,调用回调函数if(callback){callback();}}},30);}function getStyle(obj,name){if(window.getComputedStyle){return getComputedStyle(obj,null)[name];}else{return obj.currentStyle[name];}}</script></html>(11)完成所有轮播图 <!DOCTYPE html><html lang="cn" xmlns:th="http://www.thymeleaf.org" xmlns:v-bind="http://www.w3.org/1999/xhtml"xmlns:v-on="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="application/json; charset=UTF-8"><meta name="referrer" content="never"><title>JS</title></head><body><!--创建一个外部的div,来作为大的容器--><div id="divOuter"><!--创建一个ul,用于放置图片--><ul id="ulImageList"><li><img src="siteJsCssTool/1.jpg" /></li><li><img src="siteJsCssTool/2.jpg" /></li><li><img src="siteJsCssTool/3.jpg" /></li><li><img src="siteJsCssTool/1.jpg" /></li></ul><!--创建导航按钮--><div id="divNavigator"><a href="#"></a><a href="#"></a><a href="#"></a></div></div></body><style>*{margin:0;padding:0;}#divOuter{width: 572px;height: 696px;/* 居中*/margin:50px auto;/*设置背景颜色*/background-color:yellowgreen;/*设置padding*/padding:10px 0;/*开启相对定位*/position: relative;/* 裁剪溢出的内容*/overflow: hidden;}#ulImageList{/*去除项目符号*/list-style: none;/* width: 1800px;*//*开启绝对定位*/position: absolute;/*每向左移动572px,就会显示到下一张图片*/left:-572px;}/*设置图片中的li*/#ulImageList li{/*设置浮动*/float:left;/*设置上下外边距*/margin:0 10px;}#ulImageList img{width: 552px;height: 696px;}/*设置导航按钮*/#divNavigator{/* 开启绝对定位*/position: absolute;bottom:105px;/*设置left的值outer宽度572divNavigator宽度 25*3=75572-75=497/2=248.5 *//*left:248.5px;写死不能适应所有情况,所以通过js*/}#divNavigator a{width: 15px;height: 15px;background-color: red;/*设置超链接浮动*/float:left;/*设置左右外边距*/margin: 0 5px;/*设置透明*/opacity:0.5;/*兼容IE8的透明*/filter:alpha(opacity=50);}#divNavigator a:hover{background-color: black;}</style><script>//轮播图//设置var ulImageList=document.getElementById('ulImageList');//设置ulImageList的宽度var imageArray=document.getElementsByTagName('img');ulImageList.style.width=imageArray.length*572+'px';var divNavigator=document.getElementById('divNavigator');var divOuter=document.getElementById('divOuter');//设置divNavigator的left的值/*console.log(divOuter.offsetWidth);console.log(divNavigator.clientWidth);*/divNavigator.style.left=(divOuter.offsetWidth -divNavigator.offsetWidth)/2+'px';//获取所有的a标签var aArray=document.getElementsByTagName('a');//设置第一张默认为黑色aArray[0].style.backgroundColor='black';//点击超链接切换到指定的图片//1.点击第一个超链接,显示第一个图片...以此类推//2.为所有的超链接绑定单击响应函数var index=0;ulImageList.style.left=index*-572+'px';for(var i=0;i<aArray.length;i++){//为每一个超链接都添加一个onlyMark属性aArray[i].onlyMark=i;aArray[i].οnclick=function(){//关闭自动切换的定时器clearInterval(mySetInterval);//获取点击超链接的索引,并将其设置为index//alert(this.onlyMark);index=this.onlyMark;//切换图片//1.第一张 0 0 第二张 1 -572 第三张2 -572*2//ulImageList.style.left=index*-572+'px';setA(aArray,index);move(ulImageList,"left",index*-572,20,function(){//动画执行完毕,再次开启自动切换autoChange();});};}//自动切换图片autoChange();var mySetInterval;function autoChange(){//开启一个定时器,定时切换图片mySetInterval=setInterval(function(){//使索引自增index++;//判断index的值index=index%(imageArray.length);//console.log(index);//执行动画move(ulImageList,"left",index*-572,20,function(){//修改导航按钮setA(aArray,index);});},3000);}//创建一个方法用来设置选中的afunction setA(myArray,myIndex){//判断当前索引是否为最后一张图片if(index>=imageArray.length-1){//则将index设置为0index=0;//此时显示的是最后一张图片,而最后一张与第一张是一样的//通过css将最后一张切换成第一张ulImageList.style.left=0+"px";}for(var i=0;i<myArray.length;i++){//myArray[i].style.backgroundColor='red';//让内联样式生效myArray[i].style.backgroundColor='';}myArray[index].style.backgroundColor='black';}function move(myObject,attr,target,speed,callback){//防止多次点击开启多个定时器的问题clearInterval(myObject.mySetInterval);//获取当前值var currentValue=parseInt(getStyle(myObject,attr));if(currentValue>target){//此时speed为负值speed=-speed;}//开启定时器,用来执行动画效果myObject.mySetInterval=setInterval(function(){//获取div1原理left值var oldValue=parseInt(getStyle(myObject,attr));//判断速度的正负值//在旧的基础上增加var newValue=oldValue+speed;//向左移动是否小于target//向右移动是否大于targetif((speed<0&&newValue<target) || (speed>0&&newValue>target)){newValue=target;}//新值设置给div1myObject.style[attr]=newValue+'px';//到达目标关闭定时器if(newValue==target){clearInterval(myObject.mySetInterval);//动画执行完毕,调用回调函数if(callback){callback();}}},30);}function getStyle(obj,name){if(window.getComputedStyle){return getComputedStyle(obj,null)[name];}else{return obj.currentStyle[name];}}</script></html>(12)类的操作 <!DOCTYPE html><html lang="cn" xmlns:th="http://www.thymeleaf.org" xmlns:v-bind="http://www.w3.org/1999/xhtml"xmlns:v-on="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="application/json; charset=UTF-8"><meta name="referrer" content="never"><title>JS</title></head><body><!--创建一个外部的div,来作为大的容器--><button id="myButton">点击按钮修改div的样式</button><div id="myDiv" class="myDivClass"></div></body><style>.myDivClass{width: 100px;height: 500px;background-color: red;}.myDivClass2{width: 200px;background-color: yellowgreen;}</style><script>//类的操作var myButton=document.getElementById('myButton');var myDiv=document.getElementById('myDiv');myButton.οnclick=function(){//修改div的样式//1.这样浏览器每次都需要渲染一次页面//2.执行性能差,而且修改多个样式也不太方便/*my_div.style.width='200px';my_div.style.height='200px';my_div.style.backgroundColor='yellow';*///我希望一行代码,可以同时修改多个样式//修改box的class属性//1.所以我们可以通过元素的class属性来简介的修改样式//2.这样一来,我们只需要修改一次,即可同时修改多个样式//3.浏览器只需要重新渲染页面一次,性能比较好//4.并且这种方式可以使表现和行为进一步的分离//5.也实现了进一步将JS与CSS的分离//myDiv.className='myDivClass2';//6.实现两个class叠加的效果/*if(!hasClass(myDiv,'myDivClass2')){addClass(myDiv,'myDivClass2');}alert('3秒后即将删除myDivClass2');setTimeout(function(){deleteClass(myDiv,'myDivClass2');},3000);*/toggleClass(myDiv,'myDivClass2');}//定义一个函数,用来向一个元素中添加指定的class的值//1.obj 要添加class属性的元素//2.cn 要添加的class的值function addClass(obj,cn){obj.className+=" "+cn;}//判断元素中是否含有指定的属性值function hasClass(obj,cn){//var myReg=/cn/;var myRegExp=new RegExp(""+cn+"");return myRegExp.test(obj.className);}//删除一个元素中指定的classfunction deleteClass(obj,cn){//创建一个正则表达式var myRegExp=new RegExp(""+cn+"");obj.className=obj.className.replace(myRegExp,"");}//切换一个类//1.如果元素中具有该类,则删除//2.如果元素中没有该类,则添加function toggleClass(obj,cn){if(hasClass(obj,cn)){//有则删除deleteClass(obj,cn);}else{addClass(obj,cn);}}</script></html>(13)二级菜单 <!DOCTYPE html><html lang="cn" xmlns:th="http://www.thymeleaf.org" xmlns:v-bind="http://www.w3.org/1999/xhtml"xmlns:v-on="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="application/json; charset=UTF-8"><meta name="referrer" content="never"><title>JS</title></head><body><!--创建一个外部的div,来作为大的容器--><div id="myDivMenu" class="myDivMenuClass"><div><span class="mySpanMenuClass">在线工具</span><a href="#">图像优化</a><a href="#">收藏夹图标生成器</a><a href="#">邮件</a><a href="#">htaccess密码</a><a href="#">梯度图像</a><a href="#">按钮生成器</a></div><div class="myDivCollapsedClass"><span class="mySpanMenuClass">支持我们</span><a href="#">推荐我们</a><a href="#">连接我们</a><a href="#">网络资源</a></div><div class="myDivCollapsedClass"><span class="mySpanMenuClass">合作伙伴</span><a href="#">工具包</a><a href="#">CSS驱动</a><a href="#">CSS例子</a></div></div></body><style>*{margin: 0;pading: 0;list-style-type: none;}a,img{border: 0;text-decoration: none;}body{font: 12px/180% Arial,Helvetica,sans-serif,'新宋体';}.myDivCollapsedClass{height: 25px;}.myDivMenuClass{width: 150px;margin: 0 auto;font-family: Arial,sans-serif;font-size:12px;padding-bottom: 10px;background: #4d5669;color: #fff;}.myDivMenuClass div{background: #2b85e4;overflow: hidden;}.myDivMenuClass div span{display:block;height:15px;line-height: 15px;overflow: hidden;padding:5px 25px;font-weight: bold;color:white;background:grey 10px center;cursor:pointer;border-bottom:1px solid #add;}</style><script>//二级菜单//1.每一个菜单都是一个div//2.当div具有myDivCollapsedClass这个类时,div就是折叠的//3.当div没有这个类就是展开的状态//点击菜单,切换菜单的显示状态//获取spanvar mySpanMenuArray=document.querySelectorAll(".mySpanMenuClass");console.log(mySpanMenuArray.length);//定义个变量,来保存当前打开的菜单var openDiv=mySpanMenuArray[0].parentNode;//为每个span绑定单击响应函数for(var i=0;i<mySpanMenuArray.length;i++){mySpanMenuArray[i].οnclick=function(){//this代表当前点击的spanvar parentDiv=this.parentNode;//来关闭parentDivtoggleClass(parentDiv,'myDivCollapsedClass');//打开关闭以后,应该关闭之前打开的菜单//判断openDiv和parentDiv是否相同if(openDiv!=parentDiv){//为了统一处理动画的过渡效果,希望将addClass改为toggleClass//addClass(openDiv,'myDivCollapsedClass');//此处toggleClass不需要移出,只需要加上if(!hasClass(openDiv,'myDivCollapsedClass')){toggleClass(openDiv,'myDivCollapsedClass');}}//修改openDiv为当前打开的菜单openDiv=parentDiv;};}function addClass(obj,cn){obj.className+=" "+cn;}//判断元素中是否含有指定的属性值function hasClass(obj,cn){//var myReg=/cn/;var myRegExp=new RegExp(""+cn+"");return myRegExp.test(obj.className);}//删除一个元素中指定的classfunction deleteClass(obj,cn){//创建一个正则表达式var myRegExp=new RegExp(""+cn+"");obj.className=obj.className.replace(myRegExp,"");}//切换一个类//1.如果元素中具有该类,则删除//2.如果元素中没有该类,则添加function toggleClass(obj,cn){if(hasClass(obj,cn)){//有则删除deleteClass(obj,cn);}else{addClass(obj,cn);}}</script></html>(14)二次菜单的过渡效果 <!DOCTYPE html><html lang="cn" xmlns:th="http://www.thymeleaf.org" xmlns:v-bind="http://www.w3.org/1999/xhtml"xmlns:v-on="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="application/json; charset=UTF-8"><meta name="referrer" content="never"><title>JS</title></head><body><!--创建一个外部的div,来作为大的容器--><div id="myDivMenu" class="myDivMenuClass"><div><span class="mySpanMenuClass">在线工具</span><a href="#">图像优化</a><a href="#">收藏夹图标生成器</a><a href="#">邮件</a><a href="#">htaccess密码</a><a href="#">梯度图像</a><a href="#">按钮生成器</a></div><div class="myDivCollapsedClass"><span class="mySpanMenuClass">支持我们</span><a href="#">推荐我们</a><a href="#">连接我们</a><a href="#">网络资源</a></div><div class="myDivCollapsedClass"><span class="mySpanMenuClass">合作伙伴</span><a href="#">工具包</a><a href="#">CSS驱动</a><a href="#">CSS例子</a></div></div></body><style>*{margin: 0;pading: 0;list-style-type: none;}a,img{border: 0;text-decoration: none;width: 120px;float: left;}body{font: 12px/180% Arial,Helvetica,sans-serif,'新宋体';}.myDivCollapsedClass{height: 25px;}.myDivMenuClass{width: 100px;margin: 0 auto;font-family: Arial,sans-serif;font-size:12px;padding-bottom: 10px;background: #4d5669;color: #fff;}.myDivMenuClass div{background: #2b85e4;overflow: hidden;}.myDivMenuClass div span{display:block;height:15px;line-height: 15px;overflow: hidden;padding:5px 25px;font-weight: bold;color:white;background:grey 10px center;cursor:pointer;border-bottom:1px solid #add;}</style><script>//二级菜单//1.每一个菜单都是一个div//2.当div具有myDivCollapsedClass这个类时,div就是折叠的//3.当div没有这个类就是展开的状态//点击菜单,切换菜单的显示状态//获取spanvar mySpanMenuArray=document.querySelectorAll(".mySpanMenuClass");console.log(mySpanMenuArray.length);//定义个变量,来保存当前打开的菜单var openDiv=mySpanMenuArray[0].parentNode;//为每个span绑定单击响应函数for(var i=0;i<mySpanMenuArray.length;i++){mySpanMenuArray[i].οnclick=function(){//this代表当前点击的spanvar parentDiv=this.parentNode;//在切换类之前,获取元素的高度var begin=parentDiv.offsetHeight;//来关闭parentDivtoggleClass(parentDiv,'myDivCollapsedClass');//切换类之后获取一个高度var end=parentDiv.offsetHeight;//动画效果就是将高度从begin向end过渡//将元素的高度重置为beginparentDiv.style.height=begin+'px';//执行动画move(parentDiv,'height',end,10,function(){//动画执行完毕,删除内联样式parentDiv.style.height="";});//打开关闭以后,应该关闭之前打开的菜单//判断openDiv和parentDiv是否相同if(openDiv!=parentDiv){//为了统一处理动画的过渡效果,希望将addClass改为toggleClass//addClass(openDiv,'myDivCollapsedClass');//此处toggleClass不需要移出,只需要加上if(!hasClass(openDiv,'myDivCollapsedClass')){//在切换类之前,获取元素的高度var begin1=parentDiv.offsetHeight;toggleClass(openDiv,'myDivCollapsedClass');//切换类之后获取一个高度var end1=parentDiv.offsetHeight;//动画效果就是将高度从begin向end过渡//将元素的高度重置为beginparentDiv.style.height=begin1+'px';//执行动画move(parentDiv,'height',end1,10,function(){//动画执行完毕,删除内联样式parentDiv.style.height="";});}}//修改openDiv为当前打开的菜单openDiv=parentDiv;};}function addClass(obj,cn){obj.className+=" "+cn;}//判断元素中是否含有指定的属性值function hasClass(obj,cn){//var myReg=/cn/;var myRegExp=new RegExp(""+cn+"");return myRegExp.test(obj.className);}//删除一个元素中指定的classfunction deleteClass(obj,cn){//创建一个正则表达式var myRegExp=new RegExp(""+cn+"");obj.className=obj.className.replace(myRegExp,"");}//切换一个类//1.如果元素中具有该类,则删除//2.如果元素中没有该类,则添加function toggleClass(obj,cn){if(hasClass(obj,cn)){//有则删除deleteClass(obj,cn);}else{addClass(obj,cn);}}function move(myObject,attr,target,speed,callback){//防止多次点击开启多个定时器的问题clearInterval(myObject.mySetInterval);//获取当前值var currentValue=parseInt(getStyle(myObject,attr));if(currentValue>target){//此时speed为负值speed=-speed;}//开启定时器,用来执行动画效果myObject.mySetInterval=setInterval(function(){//获取div1原理left值var oldValue=parseInt(getStyle(myObject,attr));//判断速度的正负值//在旧的基础上增加var newValue=oldValue+speed;//向左移动是否小于target//向右移动是否大于targetif((speed<0&&newValue<target) || (speed>0&&newValue>target)){newValue=target;}//新值设置给div1myObject.style[attr]=newValue+'px';//到达目标关闭定时器if(newValue==target){clearInterval(myObject.mySetInterval);//动画执行完毕,调用回调函数if(callback){callback();}}},30);}function getStyle(obj,name){if(window.getComputedStyle){return getComputedStyle(obj,null)[name];}else{return obj.currentStyle[name];}}</script></html>(15)JSON <!DOCTYPE html><html lang="cn" xmlns:th="http://www.thymeleaf.org" xmlns:v-bind="http://www.w3.org/1999/xhtml"xmlns:v-on="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="application/json; charset=UTF-8"><meta name="referrer" content="never"><title>JS</title></head><body><!--创建一个外部的div,来作为大的容器--></body><style></style><script>//JSON//1.JS中的对象只有JS自己认识,其他语言都不认识//2.所以要把它转换为大家都认识的。//创建一个对象var myObject={"name":"陈翔","age":18,"sex":"男"};console.log(myObject);console.log(typeof myObject);var myJson='{"name":"陈翔","age":18,"sex":"男"}';console.log(myJson);console.log(typeof myJson);//打印出String//3.所以Json就是特殊格式的字符串,它可以被任何的语言识别//4.而且可以转换为任意语言中的对象//5.所以JSON在开发中主要用于数据的交互//6.JSON JavaScript Object Notation JS对象表示法//7.Json的格式和JS对象的格式一样,只不过JSON字符串中的属性必须加双引号//8.其他的和JS语法一致//9.Json分类 (1)对象{} (2)数组[]//10.JSON中允许的值:字符串、数值、布尔值、null、对象、数组//11.Json转换为对象//12.JS中为我们提供了一个工具类,就叫JSON//这个对象可以帮助我们把JSON—>JS,也可以把JS—>JSON//13.因为JS直接myJson.属性取不到var tempObject=JSON.parse(myJson);console.log(tempObject.name);//14.JS对象转JSONvar tempJson=JSON.stringify(myObject);console.log(tempJson);console.log(typeof tempJson);//15.JSON这个对象在IE7及以下对象不支持,所以在这些浏览器中会报错var IE7Json='{"name":"陈翔","age":18,"sex":"男"}';//16.eval()这个函数可以执行一段字符串形式的JS代码,//并将执行结果返回。//17.如果执行的eval中含有{},它会将{}当成是代码块,//如果不希望将其当成代码块,则需要再字符串前后各加一个()//var tempStr="alert('Hello')";//eval(tempStr);var IE7Object=eval("("+IE7Json+")");console.log(IE7Object);//18.eval()虽然很强大,但是开发者尽量不要使用//应为是执行性能差,而且存在安全隐患。//19.也可以通过引入外部的JS文件来处理。json2.js</script></html>