javascript总结

#初识 javascript

一、JS组成:ECMA   BOM  DOM

  • js 是一种基于 对象模型 和 事件驱动 的脚本语言
  • 组成:
    • ECMAScript由ECMA-262定义,提供核心语言功能;
    • 文档对象模型(DOM),提供访问和操作网页内容的方法和接口;
    • 浏览器对象模型(BOM),提供与浏览器交互的方法和接口;

二、html 中使用 javascript

  • html是从上往下瀑布式加载,<script>包裹的 js 代码也是从上往下依次加载的;
  • 一般应该把<script>元素放在页面最后(body的最后面),越晚加载越好,有利于提升网页的响应速度;
  • 关于 script 标签的 async 和 defer 属性:
    • 通过 src 引用外部的脚本时,script 标签的 async 和 defer 属性都会让脚本的加载不会阻塞 dom 的渲染;
    • async 是异步加载和执行脚本,不能保证脚本执行的顺序和执行时机(不一定在 dom 渲染完成后),所以 async 适用于脚本对 dom 和其他脚本没有依赖的情况使用;
    • defer 属性能够保证脚本执行的时机是在 dom 渲染完成后,还能保证脚本的执行顺序是正常的从上往下执行,所以这种模式是比较可靠的,用 defer 比 async 更稳;

 

#基本概念

一、js 的基本特点

  • 区分大小写;
  • 标识符字母、数字、下划线和美元符组成,数字不能开头;
  • 单行和多行注和 java 一样;
  • 语句的分号不是必须的,但是最好写一下;

二、变量

  • 常用数据类型:string、number、boolean、array、object
  • typeof 运算符(单目运算符):不是函数;可以用来判断 function;function 是一个特殊的对象;
  • js中的字面量类似于其他语言的常量:12,'java' 都是字面量

三、基本数据类型

1、布尔 Boolean:

  • 其他类型通过Boolean()函数可以转换为 boolean 值;
  • 空串、0、NAN、null、undefined 都为 false;

2、数值 Number:

  • JS数值始终是 64 位的浮点数
  • 浮点数计算产生舍入误差
    var x = 0.2 + 0.1;                     // x 将是 0.30000000000000004
    var x = (0.2 * 10 + 0.1 * 10) / 10;    //结果将是0.3
  • 关于NAN:nan不等于nan;可以用 isNaN()函数判断,用 typeof 判断 NAN 会得到 number;
  • toString 用来进制转换
    var myNumber = 128;
    myNumber.toString(16);     // 返回 80
    myNumber.toString(8);      // 返回 200
    myNumber.toString(2);      // 返回 10000000
  • 转换为数值:三个方法是全局方法,非数字的方法
  • Number(支持十六进制);parseInt(str,rule):rule 参数可以指定进制;parseFloat()
  • 空串、null 和 undefined:Number函数的结果是0、0、nan;parseFloat 和 parseInt 都是 nan;
  • 数值处理:toFixed() 方法
    var x = 9.656;
    x.toFixed(0);           // 返回 10
    x.toFixed(2);           // 返回 9.66
    x.toFixed(4);           // 返回 9.6560
    x.toFixed(6);           // 返回 9.656000

*****************************tips*******************************

  • 关于Math 对象的Floor 和 ceil 方法:这两个方法都是取离目标数字最近的整数,前者是比目标数字小,后者是比目标数字大
  • Math.random() 一定范围的随机数获取方法
    function getRndInteger(min, max) {
        return Math.floor(Math.random() * (max - min + 1) ) + min;
    }

****************************************************************

3、字符串 String:

  • 基本特点:实质是字符序列,字符串常量概念
  • 常用方法:
    • 查找:indexOf、search
    • 截取:slice(b,e)、substring(b,e)、substr(b,l)
    • 其他:replace(不会改变原有的,返回的是新串)、toUpperCase、toLowerCase、trim、split

4、对象 Object:

  • BOM和DOM中的对象由宿主实现提供,不一定会继承 js 中的 Object;
  • object 使用字面量表示法(json),不会调用构造函数;

5、数组 Array

  • 特点:
    • 可以保存不同类型的值,大小也可以动态调整;
    • 创建数组最好不要用 new Array 方法;
    • 包含 index 和 length,伪数组也有这两个属性;
      var arr = [1,2];
      arr[arr.length] = 3;
      arr[arr.length] = 4;
      arr[10] = 10;
      console.log(arr.length);
      console.log(arr[8]);
  • 常用方法:join、push (返回操作后的数组的长度)、 pop(后面)、shift(前面)、unshift、reverse、indexOf、lastIndexOf、concat、slice(切片)
  • sort (默认比较字符串,其他类型比较依赖于比较函数)

  • splice(可以新增、删除和替换)
    var fruits = ["Banana", "Orange", "Apple", "Mango"];
    //insert
    fruits.splice(2, 0, "Lemon", "Kiwi");
    alert(fruits);
    //delete
    fruits.splice(2, 1);
    alert(fruits);
    //replace
    fruits.splice(2, 2, "Lemon", "Kiwi");
    alert(fruits);
  • 迭代方法:
    //forEach方法
    var haha =[12,13,14];
    haha.forEach(function(value,index,array){
       alert(value);
    })
    
    //map建新数组,不会改变原来的
    var numbers1 = [45, 4, 9, 16, 25];
    var numbers2 = numbers1.map(myFunction);
    function myFunction(value, index, array) {
      return value * 2;
    }
    
    //filter条件过滤
    var numbers = [45, 4, 9, 16, 25];
    var over18 = numbers.filter(myFunction);
    function myFunction(value, index, array) {
      return value > 18;
    }
    
    //reduce total总是保存上一次返回的值
    var numbers1 = [45, 4, 9, 16, 25];
    var sum = numbers1.reduce(myFunction);
    function myFunction(total, value, index, array) {
      return total + value;
    }
    
    //every() 方法检查所有数组值是否通过测试
    var numbers = [45, 4, 9, 16, 25];
    var allOver18 = numbers.every(myFunction);
    function myFunction(value, index, array) {
      return value > 18;
    }
    
    //some() 方法检查某些数组值是否通过了测试
    var numbers = [45, 4, 9, 16, 25];
    var someOver18 = numbers.some(myFunction);
    function myFunction(value, index, array) {
      return value > 18;
    }
    
    //find() 方法返回通过测试函数的第一个数组元素的值
    //findIndex() 方法返回通过测试函数的第一个数组元素的索引
  • 数组判断
    Array.isArray(fruits);  
    fruits instanceof Array 

**************************************************tips***********************************************

  • 关于 null 和 undefined
    • null 是空对象,undefined 是未初始化的变量或者未声明变量;
    • null==undefined 判断结果为 true,null===undefined 判断结果为 false;
    • 空对象的判断先要看是否未定义
      //如果要测试对象是否为空,则必须先测试它是否未定义
      typeof myObj !== "undefined" && myObj !== null;
  • 关于函数闭包:子函数可以使用父函数的局部变量
    var add = function (a) {
        return function (b) {
            return a + b;
        };
    };
    var addFive = add(5);
    alert(addFive(10));

*******************************************************************************************************

四、数据类型 & 变量(补充)

1、基本类型 & 引用类型

  • 基本类型
    • 保存在栈中;复制值的副本;
    • 可以用 typeof 区分类型;函数传参是按值传递;
  • 引用类型
    • 值为对象保存在堆中;复制的时候复制的是指针;
    • 用 instanceof 区分具体类型;函数传参是按值传递(传递的是引用的副本);
    • 对象可以动态添加属性;

2、作用域(执行环境)

  • 全局变量(全局执行环境):尽量少用,全局变量的频繁使用可能会导致安全问题并使代码变得难以维护;
  • 局部变量(函数执行环境):变量的作用域是靠函数来限制的,而不是用像 if 后面的{}来进行界定的;
  • 在HTML中,全局作用域是window,所有全局变量均属于window对象;
  • 函数也是变量;尽量不要创建全局变量,全局变量(函数)容易发生相互覆盖;

3、内存问题(垃圾回收)

  • js 自动垃圾回收机制基于标记清除法(基于变量的作用域);
  • 另外一种回收机制是引用计数法,用的少,因为相互引用会导致无法垃圾回收引发内存泄漏;
  • 解除变量的引用有利于垃圾回收:全局变量、全局变量属性和循环引用在不用的时候最好及时解除引用(null);

4、变量声明提升

  • 将变量声明移至顶部的默认行为,变量初始化不会被提升
  • 用 let 或 const 声明的变量和常量不会被提升
  • 为了避免 bug和提高程序的易读性,在每个作用域的开头声明所有变量

五、运算符 | 流程控制 | JSON

1、运算符

  • 相等(==)和不相等(!=)操作符仅能用于判断二者的值是否相等;
  • 推荐使用全等(===)和不全等(!==)判断二者的值和类型是否都相等;
  • 三目运算符:(condition?value1:value2);
  • JS 将数字存储为 64 位浮点数,但所有按位运算都以 32 位二进制数执行【负数二进制码(补码)=绝对值反码+1】

2、流程控制 -- if、switch、for、for-in、while、do-while(break和continue)

  • 基本和java一样的用法;
  • 循环也支持 label:statement 方式的命名,以便在break等中使用;
  • switch语句在比较值时使用的是全等操作符,因此不会发生类型转换,同时js的switch不加break的话也具有穿透性;
  • for(var  i  in  json)来进行遍历对象的属性(json 可以理解为 js 对象的简化表示);
  • 关于 if 和 for:js没有块级作用域

3、JSON(js 对象的字面量表示)

  • JSON 是一种数据传输的格式,用于前后端的数据传输,正逐渐取代 xml 成为主流;
  • JSON 串和 js 对象的相互转换:stringify 和 parse 方法
var jsonString = JSON.stringify({
    make: "McLaren",
    model: "MP4-12C",
    miles: 5023
});
var car = JSON.parse(jsonString);
console.log(jsonString);
console.log(car);

**********************************tips**************************************

  • with语句:作用和vb里的with类似,使用一个对象的多个属性,不用多次写对象名
    function Lakers() {  
           this.name = "kobe bryant";  
           this.age = "28";  
           this.gender = "boy";  
    }  
    var people=new Lakers();  
    with(people)  
    {  
           var str = "姓名: " + name;  
           str += "年龄:" + age;  
           str += "性别:" + gender;  
           document.write(str);  
    }  

****************************************************************************

 

#引用类型

一、对象(Object)

  • 后面的Array、Date、RegExp都是Object
  • 对象具体类型判断的通用方法示例
//通过检查 constructor 属性来确定某个对象的具体类型
//这里是检查date类型的实例
function isDate(myDate) {
    return myDate.constructor.toString().indexOf("Date") > -1;
}

二、数组(Array)

三、时间(Date)

1、构造函数和三个方法

//构造器和几个方法
var d = new Date();
var d = new Date(454545545);
var d = new Date(2018, 11, 24, 10, 33, 30, 0);
var d = new Date("October 13, 2014 11:13:00");
var d = Date.parse('2018-01-01'); //返回毫秒值
var d = Date.UTC(2005,4,5); //返回毫秒值
var d = Date.now(); //返回毫秒值

2、四种日期格式

//时间格式
var d = new Date("2018-02-19T12:00:00-08:30"); //标准日期格式
var d = new Date("02/19/2018"); // 短日期 最好不要省略0
var d = new Date("Feb 19 2018");//长日期
var d  = new Date("Mon Feb 19 2018 06:55:23 GMT+0200 (W. Europe Standard Time)");//完整格式,括号里的错误会被自动忽略

3、几个toString方法

//几个toString 方法
var d = new Date();
document.getElementById("p1").innerHTML = d.toLocaleString();//完整本地时间
document.getElementById("p3").innerHTML = d.toUTCString();//完整标准时间
document.getElementById("p2").innerHTML = d.toDateString();//年月日
document.getElementById("p4").innerHTML = d.toTimeString();//时分秒

4、时间获取和设置方法

//时间获取方法分别对应几个相应的时间设置方法
getDate()    //以数值返回天(1-31)
getDay()    //以数值获取周名(0-6)
getFullYear()    //获取四位的年(yyyy)
getHours()    //获取小时(0-23)
getMilliseconds()    //获取毫秒(0-999)
getMinutes()    //获取分(0-59)
getMonth()    //获取月(0-11)
getSeconds()    //获取秒(0-59)
getTime()    //获取时间(从 1970 年 1 月 1 日至今)和 valueOf都是返回毫秒值

**********************tips***************************

  • 外国的月份是0到11月,分别对应我们的1到12;

*****************************************************

四、正则(RegExp)

1、正则基础

  • 修饰符
    g(全局匹配)、i(忽略大小写)、m(多行模式)
  • 括号
    [abc]    查找方括号之间的任何字符。
    [^abc]    查找任何不在方括号之间的字符。
    [0-9]    查找任何从 0 至 9 的数字。
    (red|blue|green)    查找任何指定的选项。
  • 元字符
    .    查找单个字符,除了换行和行结束符。
    w    查找单词字符。
    W    查找非单词字符。
    d    查找数字。
    s    查找空白字符。
        匹配单词边界。
  • 量词
    n+    匹配任何包含至少一个 n 的字符串。
    n*    匹配任何包含零个或多个 n 的字符串。
    n?    匹配任何包含零个或一个 n 的字符串。
    n{X}    匹配包含 X 个 n 的序列的字符串。
    n{X,Y}    匹配包含 X 至 Y 个 n 的序列的字符串。
    n{X,}    匹配包含至少 X 个 n 的序列的字符串。
  • 首尾匹配
    n$    匹配任何结尾为 n 的字符串。
    ^n    匹配任何开头为 n 的字符串。
  • string支持正则的方法:search、replace、match、split

2、正则对象

  • 字面量的元字符转义只要一个    而构造函数要 \
var pattern1 = /at/g;
var pattern2 = new RegExp("[bc]at", "i");

3、对象属性

  • global          RegExp 对象是否具有标志 g
  • ignoreCase RegExp 对象是否具有标志 i
  • lastIndex     标示开始下一次匹配的字符位置
  • multiline      RegExp 对象是否具有标志 m
  • source         正则表达式的源文本

4、对象方法

  • 方法:test方法、exec方法、compile方法
  • exec 方法返回的是数组,其中含两个额外属性,index 表示匹配项在字符串中的位置,input表示测试的字符串
var text = "mom and dad and baby"; 
var pattern = /mom( and dad( and baby)?)?/gi; 
var matches = pattern.exec(text); 
alert(matches.index);     // 0 
alert(matches.input);     // "mom and dad and baby" 
alert(matches[0]);        // "mom and dad and baby" 
alert(matches[1]);        // " and dad and baby" 
alert(matches[2]);        // " and baby" 

5、构造函数属性?

  • RegExp.$1、RegExp.$2...RegExp.$9,分别用于存储第一、第二......第九个匹配的捕获组;
var text = "this has been a short summer";
var pattern = /(.)hort/g;
if (pattern.test(text)){
    alert(RegExp.input);            // this has been a short summer
    alert(RegExp.leftContext);      // this has been a
    alert(RegExp.rightContext);     // summer
    alert(RegExp.lastMatch);        // short
    alert(RegExp.lastParen);        // s
    alert(RegExp.multiline);        // false IE不支持
}

五、函数(funtion)

1、函数参数(声明、调用和返回略)

  • arguments(可变参):伪数组(有 index 和 length),存的传入的参数,可以用for 遍历;
  • 函数的参数在声明的时候写不写都可以,写多少个也没有规定,底层是用数组实现的,函数声明的括号里写上形参只是为了函数内部使用的方便;函数在调用的时候要传几个实参都是可以的,反正是传几个接受几个;
  • 由于 js 函数参数的以上特点,所以 js 的函数没有真正意义上的重载;
  • 函数的参数最好的做法是对那些必需值使用命名参数,而使用对象字面量(json)来封装多个可选参数;
  • es2015支持 函数参数默认值 的设置;

2、function 类型

  • js 是没有方法重载导致同名函数是覆盖的效果;function 不是 object 类型的;
  • 函数声明随意写在什么位置都不影响函数的调用,但是函数表达式必须写在调用之前才不会出错;
    //函数表达式
    var run = function (v1) {
      alert(v1);
    };
    //函数声明
    function run() {}

 

#DOM应用

一、dom基础

1、节点获取

  • 通过 id、标签名、类名和选择器获取:
    • getElementById 和 getElementsByTagname;
    • getElementsByClassName 通过类名获取元素列表;
    • querySelector(通过 css 选择器获取一个元素) 和 querySelectorAll(通过 css 选择器获取元素列表);
    • 用 className 来获取元素,封装函数 getByClass(oParent,sClass);
  • 父子兄弟节点获取:
    • 父节点的获取:parentNode、offsetParent(获取有定位的父节点);
    • 子节点的获取:childNodes和nodeType(也可以用children);
    • 首尾子节点:firstChild(firstElementChild 不会获取到文本节点,IE9以下不可用)、lastChild(lastElementChild);
    • 兄弟子节点:nextSibling(nextElementSibling)、previousSibling(previousElementSibling);

2、属性操作

  • 基本方法:obj.value(不可以传参) 和 obj["value"](可以传参);setAttribute | getAttribute | removeAttribute
  • 相关细节:
    • 属性基本 html 怎么写 js 就怎么写,除了 class 外:div.className=" ";
    • style 属性无论是增加还是获取都是取行间,行间没有的话,取值的时候取不到;
    • style 的优先级高于 className;
    • 获取非行间样式的兼容性写法:
function getStyle(obj, attr) {
    if(obj.currentStyle){
        return obj.currentStyle[attr];
    }else{
        return getComputedStyle(obj,null)[attr];
    }
}

3、节点操作(创建-插入-删除)

  • createElement | appendChild(加在末尾,也是先删后加)| insertBefore(节点,指定节点)--加在前面 | removeChild
var div = document.createElement('div');
div.textContent = "Sup, y'all?";
div.setAttribute('class', 'note');
document.body.appendChild(div);
var span = document.createElement('span');
span.textContent = "Hello!";
div.appendChild(span);
div.parentNode.removeChild(div);

4、关于 innerText、innerHTML 和 textContent

  • innerText 和 textContent 都只能设置文本;innerHTML既能设置文本也能设置标签;
  • innerText基本的浏览器都支持,textContent 低版本的 IE 不支持;
  • textContent 相对于 innerText 保留了一定的格式信息;

二、dom进阶

1、表格应用

  • 表格的便捷操作:tHead、tFoot、tBodies、rows、cells;
  • 练习:表格的隔行变色;添加和删除一行;搜索和排序;

2、表单应用(表单验证)

  • input 添加属性进行输入约束:disabled、required、pattern、max和min
  • css 伪选择器选择相应约束的元素:disabled、invalid、valid、optional、required
  • input约束验证相关方法
    • checkValidity() :input 的数据有效则返回 true
    • setCustomValidity() :设置input元素的 validationMessage(校验提示信息)
  • input约束验证相关属性
    • validity   包含一系列和input元素的合法性相关的布尔属性
    • validationMessage   错误提示信息
    • willValidate   是否会进行校验
  • validity包含的属性:customError、patternMismatch、rangeOverflow、rangeUnderflow、stepMismatch、tooLong、typeMismatch、、valueMissing、valid
  • 注意:以上基于html的约束及其验证在IE浏览器不太好使!!!

 

#BOM应用

一、基础

  • window.open(url,'_self'):打开一个窗口;
  • window.close():关闭一个窗口,最好是脚本打开,脚本关闭,不然会有一些问题;
  • window.navigator.userAgent
  • window.location:就是html文件的地址,不仅可以取值,也可以赋值;

二、尺寸坐标

1、可视区宽高

  • document.documentElement.clientWidth
  • document.documentElement.clientHeight

2、滚动距离

  • document.body.scrollTop
  • document.documentElement.scrollTop

三、常用方法事件

  • 对话框:alert(警告框)、confirm(确认框)、prompt(输入框)
  • 事件:onload、onscroll、onresize

 

#JS运动技术

1、运动基础

(1)offsetWidth 和 offsetHeight:只和自身相关,与周围的元素无关

  • offsetWidth = border-left + border-right + padding-left+padding-right+元素本身的宽度;
  • offsetHeight = border-top + border-bottom + padding-top+padding-bottom+元素本身的高度;

(2)offsetLeft和offsetTop

  • offsetTop = 上级定位元素的padding + 元素本身的margin;
  • 如果二者中间还有其他元素,还要加上该元素的 margin padding 和 border;
  • offsetLeft同理;

(3)scrollTop和scrollLeft:与滚动条相关的属性

  • scrollTop:滚动条当前位置显示的最上面和真正的最上面的距离,scrollLeft同理;

(4)clientHeight和clientWidth

  • clientHeight包括padding但不包括border、水平滚动条、margin的元素的高度,clientWidth同理;

(5)定时器

  • 开启:setInterval(函数,时间)---循环执行;setTimeout()---只执行一次;
  • 关闭:clearInterval;clearTimeOut;
  • 应用:数码时钟,延时提示框、无缝滚动;

2、运动框架

(1)开始运动前先关闭已有的定时器;

(2)将运动和停止的状态用 if else 隔开;

(3)练习:侧边栏、图片的淡入淡出;

3、缓冲运动

(1)速度越来越慢,最后停止;

(2)速度=(目标值-当前值)/缩放系数;

(3)缓冲菜单:速度取整(向上和向下取整);目标值取整;

4、匀速运动的停止条件

(1)距离小于速度就停止;

(2)再手动将元素移到目标点;

(3)匀速和缓冲运动代码的差异:速度表达式不同,最后的停止条件和处理方法也不同

5、多物体运动框架

(1)多物体运动框架很多东西都不能公用,定时器和透明度的变量等,解决方法就是给每个元素设置自定义属性;

6、任意值的运动框架

(1)offset 属性 bug 和 opacity 的小数问题;

(2)练习:图片轮换的播放器;

7、运动中级

(1)链式运动

  • 在原有框架的基础上加一个回调函数,在运动结束关闭定时器之后加

(2)完美运动框架

  • 多个属性同时变化;
  • 等所有的条件都满足再停止;

 

#JS事件应用

1、基础

(1)event对象

  • 用来获取事件的详细信息:鼠标位置,键盘键位
  • 鼠标的位置:clientX 和 clientY
  • document的本质:可以看作一个最高级的节点,包含html 的所有内容,全局事件加在 document 上
  • 事件对象的兼容性写法:var oEvent = ev || event
var handleClick = function (event) {
    console.log('offsetX:'+event.offsetX);
    console.log('offsetY:'+event.offsetY);
    console.log('pageX:'+event.pageX);
    console.log('pageY:'+event.pageY);
    console.log('screenX:'+event.screenX);
    console.log('screenY:'+event.screenY);
    console.log('X:'+event.x);
    console.log('Y:'+event.y);
    console.log('target:'+event.target);
    console.log('timestamp:'+event.timeStamp);
    console.log('type:'+event.type);
    console.log(event);
};
var but1 = document.querySelector('#but1');
but1.addEventListener('click',handleClick);

(2)事件冒泡

  • 父级和子级的元素假如都有 onclick 事件,子级元素的被点击,则会触发父级元素的点击事件
  • 阻止事件的冒泡:event.cancelBubble = true;

(3)鼠标事件

  • onmousemove事件
  • clientX 和 clientY 实际是可视区域的坐标,如果要获取相对与 document 的绝对坐标,需要和 scrolltop 等配合使用,封装相应的方法;
  • 应用:div 跟随鼠标的移动

(4)键盘事件

  • keycode :可以用来判断键盘的按键;应用:键盘控制 div 的移动;
  • ctrlkey、altkey、shiftkey:应用提交留言;

2、中级

(1)默认行为

  • 默认行为就是浏览器自发产生的行为,不用人为写代码触发;
  • document.onContextMenu(右键菜单弹出);
  • 阻止默认行为,直接在事件的方法里 return false;
  • 练习:阻止右键默认菜单,弹出自定义菜单;只能输入数字的文本框(keycode 和 onKeydown);

(2)拖拽

   1、基本原理:

  • 元素位置的确定依靠鼠标位置和鼠标距离元素左上边界的长度来确定;
  • onmousedown计算鼠标和元素边界的距离,onmousemove重新定位元素,onmouseup停止事件;

   2、拖拽的改进:

  • 快速拖动鼠标会移出 div :直接给 document 加事件;
  • 火狐浏览器下空 div 的拖拽 bug:阻止默认行为;
  • 防止 div 脱出页面:进行位置的修正;

3、应用

(1)事件绑定

  • 老方法给同一个元素相同事件绑定不同的函数,会出现后面的把前面的覆盖了的问题;
  • 解决以上问题需要用到新的事件的绑定方法
function myAddEvent(obj, ev, fn)
{
    if(obj.attachEvent)
    {
        obj.attachEvent('on'+ev, fn);
    }
    else
    {
        obj.addEventListener(ev, fn, false);
    }
}
  • 事件的解绑:IE(detachEvent);CHROME(removeEventListener); 

(2)高级拖拽

  • 练习:不能脱出指定的元素;
  • 练习:磁性吸附功能(靠近边界的时候把距离设置为0即可);
  • 练习:带框的拖拽;
  • 事件捕获:将所有元素的事件集中到某一个元素上,解决IE下拖拽引起的其他元素的选中问题(setCapture()、releaseCapture());

(3)自定义滚动条

  • 原理:横向拖拽;限制范围;计算比例;
  • 应用:控制元素大小;控制透明度;控制文字的滚动;

 

#AJAX技术

1、概念

  • Ajax 即 Asynchronous Javascript And XML(异步 JavaScript 和 XML);
  • 可以用来获取 html、xml、json 和纯文本等,实现网页的局部刷新;

------- tips ---------

  • eval(str)可以将 str 解析为 js 执行;
  • 浏览器缓存是根据 url 进行缓存的,变更 url 可以阻止浏览器的缓存;
  • js 的变量与属性:使用未定义的变量会报错;使用未定义的属性仅仅是 undefine,不会报错;

2、原理

(1)AJAX 原理

/**
 * ajax 的简单封装
 */

function myAjax(method,url,data,async,sucFn,faiFn){
    //get ajax obj
    if(window.XMLHttpRequest)
    {
        var oAjax=new XMLHttpRequest();
    }
    else
    {
        var oAjax=new ActiveXObject("Microsoft.XMLHTTP");
    }
    //connection check method
    if(method.toUpperCase() == "GET"){
        oAjax.open(method, url+(data ? '?'+data : ''), async);
        oAjax.send(data);
    }else if(method.toUpperCase() == "POST"){
        oAjax.open(method, url, async);
        oAjax.setRequestHeader("Content-type","application/x-www-form-urlencoded");  
        oAjax.send(data);
    }
    //state listener
    oAjax.onreadystatechange=function ()
    {
        if(oAjax.readyState==4)    
        {
            if(oAjax.status==200)
            {
                if(sucFn){
                    sucFn(oAjax);
                }
            }
            else
            {
                if(faiFn){
                    faiFn(oAjax);
                }
            }
        }
    };
};

(2)AJAX请求的几种状态说明:

  • 0:未初始化,还未调用 open 方法;
  • 1:载入,已调用 send 方法,正在发送去请求;
  • 2:载入完成,send 方法完成,收到所有的响应内容;
  • 3:解析,解析响应内容;
  • 4:完成,解析完成,可以在客户端使用了;

 

#面向对象

1、概述

  • js 中没有类的概念,可以通过构造函数直接创建对象;
  • 对象之间的继承极大的提高了 js 代码的可扩展性;
  • js 对象无法进行对比,比较两个对象将始终返回 false,不管使用 == 还是使用 === 判断;

2、JS 对象构建

  • 最佳实践:构造函数加属性(特有);原型(prototype)加方法(共有);
function CreatePerson(name, qq)        //构造函数
{
    this.name=name;
    this.qq=qq;
}

CreatePerson.prototype.showName=function ()    //原型
{
    alert('我的名字叫:'+this.name);
};

CreatePerson.prototype.showQQ=function ()
{
    alert('我的QQ号:'+this.qq);
};

var obj=new CreatePerson('blue', '258248832');
var obj2=new CreatePerson('张三', '45648979879');

3、添加方法和属性

(1)this 的本质:函数属于谁 this 就是谁,全局函数属于 window 对象;

(2)Object 对象:不能随意给系统的对象添加属性和方法,可能会造成方法和属性的覆盖;Object 是一个空的对象,可以用来改造;

4、面向对象的选项卡(练习)

(1)面向对象原则:不能有函数套函数、但可以有全局变量

(2)过程:onload  →  构造函数;全局变量  →  属性;函数  →  方法

(3)注意 this 在面向对象的用法

window.onload=function(){
    new Tar('div1');
};

function Tar(id) {
    var _this = this;
    this.oDiv = document.getElementById(id);
    this.aInput = this.oDiv.getElementsByTagName('input');
    this.aDiv = this.oDiv.getElementsByTagName('div');

    for(var i = 0;i < this.aInput.length;i ++){
        this.aInput[i].index = i;
        this.aInput[i].onclick=function () {
            _this.fnClick(this);
        };
    }
}

Tar.prototype.fnClick = function (aInput) {
    for(var j = 0;j < this.aInput.length;j ++){
        this.aDiv[j].style.display = "none";
        this.aInput[j].className = '';
    }
    this.aDiv[aInput.index].style.display = 'block';
    aInput.className = 'active';
};

5、面向对象高级

(1)JSON方式的面向对象(字面量):适合单例模式(复用性差);

var obj = {
    name:'allen',
    age:24,
    show:function () {
        alert(this.name+':'+this.age);
    }
};
obj.show();

(2)继承(以拖拽为例):普通拖拽和限制范围的拖拽

//1、构造函数内用 call 继承属性;
//2、遍历原型链复制继承方法;

/*普通拖拽*/
function Drag(id) {
    var _this = this;
    this.oDiv = document.getElementById(id);
    this.oDiv.onmousedown = function (ev) {
        _this.down(ev);
    }
}

Drag.prototype.down = function (ev) {
    var _this = this;
    var oEvent = ev || event;
    this.disX = oEvent.clientX - this.oDiv.offsetLeft;
    this.disY = oEvent.clientY - this.oDiv.offsetTop;
    document.onmousemove = function (ev) {
        _this.move(ev);
    };
    document.onmouseup = function () {
        _this.up();
    };
};

Drag.prototype.move = function (ev){
    var oEvent = ev || event;
    this.oDiv.style.left = oEvent.clientX - this.disX + "px";
    this.oDiv.style.top = oEvent.clientY - this.disY + "px";
};

Drag.prototype.up = function () {
    document.onmousemove = null;
    document.onmouseup = null;
};


/*限制拖拽*/
function LimitDrag(id) {
    Drag.call(this,id);
}

for(var i in Drag.prototype){
    LimitDrag.prototype[i] = Drag.prototype[i];
}

LimitDrag.prototype.move = function (ev) {
    var oEvent = ev || event;
    var l = oEvent.clientX - this.disX;
    var t = oEvent.clientY - this.disY;
    if(l < 0){
        l = 0;
    }
    if(t < 0){
        t = 0;
    }
    this.oDiv.style.left = l + "px";
    this.oDiv.style.top = t + "px";
}

(3)系统对象

  • 本地对象(非静态):Object、Function、Array、Number、String 等
  • 内置对象(静态):Math、Global
  • 宿主对象(浏览器提供):BOM、DOM
原文地址:https://www.cnblogs.com/stanwuc/p/10600063.html