JavaScript
-
什么是JavaScript
- “弱类型”的脚本语言
- 基于“原型”的脚本语言
-
JS可以干什么
- 主要用于Web 页面使用
- 被非浏览器环境中去使用(nodejs)
-
JS的构成
- ECMAScript:核心语言,基本对象
- DOM:文档对象模型
- BOM:浏览器对象模型
-
在html中如何使用js
-
本页面中使用
<script type="text/javascript"> #js代码</script>
-
外部引用
<script type="text/javascript" src = "***.js"></script>
-
-
js的输出语句
-
document.write() ===> 在文档中打印类型
-
consloe.log(). ===> 在控制台打印内容
注意: js的每一句代码要用 ; 分隔开
-
-
延迟加载 & 异步加载
-
如何延迟加载
<script type = "text/javascript" defer src = ""></script> defer : js脚本可以延迟到文档完全被解析和显示后执行
-
如何异步加载
async: 遇到则执行 ,同时执行
-
-
js中的变量
- 命名规则:
- 组成:数字,字母,下划线,$(不建议使用,有特殊含义)
- 不能使用关键字,不能以数字开头
- 采用小驼峰命名法
- 用 var 进行声明变量
- 命名规则:
-
js中的注释
-
单行 : //
-
多行 :/**/
-
企业级注释:
// 1 公共的js文件 /* * 文件用途说明 * 作者姓名,练习方式 * 制作日期 * * **/ // 2 大的模块注释 // ========== // 代码用途 // ==========
-
-
数据类型
-
基本数据类型
-
string : 字符串 单引号优先
-
number : 数值
-
boolean : true false
-
underfined : 只声明,未赋值
-
null ; 表示 “没有对象” ,特殊的object的类型
null & underfined 的区别:
null 表示赋值为 null ,转换为数值 是 0
underfined表示没有赋值,转换为数值 是NaN
-
-
引用数据类型
object
-
-
企业级命名规范
-
引号:单引号优先
-
变量名命名:
-
str ,num , bol ,fun,arr :作用域不大的情况
-
循环: i ,j ,k
-
变量名的前缀
-
数组 a
-
字符串 s
-
数值 n
-
逻辑 b
-
函数 f
-
对象 o
-
正则 r
-
-
-
-
类型转换
-
其他类型转换为字符串类型
- 数据.toString()
- String(数据)
-
其他类型转换为数字类型
- Number(数据)
- parseInt(数据) ==》整数
- parseFloat(数据)==》小数
注意:
布尔: true ==> 1 false ==> 0
字符串不是纯数字:NaN
NaN:代表非数字类型的特殊值
-
-
其他类型转换为布尔类型
Boolean(数据)
-
数值:
- 0 =>false
- NaN =>false
- 其他值 => true
-
字符串:
- 非空字符串 =>true
- 空字符串 =>false
null => false
undefined => false
-
-
变量的存储机制原理
-
变量存储于内存中
-
内存的生命周期(三个周期)
- 分配期:分配所需要的内存
- 使用期:读 写
- 释放期:不需要时将其释放
内存分配 ==> 内存使用 ==> 内存释放
-
js 内存的生命周期
- 内存分配:分配你所需要的暂时使用的内存大小
- 内存使用:读写,内存
- 内存回收:对于不需要使用的内存将其回收
-
栈内存 & 堆内存
- 栈内存
- 基本类型(string, number,boolean,undefined,null)
- 按值访问
- 存储的值大小固定
- 系统会自动分配内存空间
- 空间小,运行效率高
- 先进后出
- 堆内存
- 引用类型(object)
- 引用访问
- 存储的值,大小不固定
- 在堆内存中分配内存
- 空间大,运行效率相对较低
- 无序存储(根据引用直接取值)
- 栈内存
-
-
算数运算符
+ - * / %
数据类型隐式转换问题:
1.布尔 和 数字 或 布尔相加,布尔将会自动转换为数值类型
2.字符和任何数字相加,其他类型都会转换为字符串类型
注意: 除了 + 以外,其他都是按照数值进行运算
-
比较运算符:
==:等于(值相同,类型不一定相同)
===:完全等于(值相同,类型也相同)
!=:
!==:
>
<
>=
<=
比较运算符返回的结果是布尔类型:true false
-
一元运算符
- i++ ,++i 或 i–,--i
- 规则:
- 如果不参与运算,++在前 和 ++在后 都是一样的
- 参与运算(包括赋值):
- ++ 在前面(++i)则表示:先自身 + 1,再运算
- ++在后面(i–)则表示:先运算,再自身+1
-
二元运算符
- &&(与)
- 语法风格:表达式 && 表达式
- 规则:如果(左边表达式)判断是false,则返回(左边表达式)的值,否则返回(右边表达式)的值
- ||(或)
- 语法风格: 表达 式 || 表达式
- 规则: 如果(左边表达式)判断为true ,则返回(左边表达 式)的值,否则返回(右边表达式)的值
- !(非):取反
- &&(与)
-
三元运算符
语法风格:条件 ? 结果1:结果2
如果条件成立,返回结果1,否则 ,返回结果2
-
流程控制语句:顺序 ,分支,循环
-
if分支
-
语法格式:
if(条件){
}else if(){
}else{
}
***补充知识点:
弹出输入框: prompt()
isNaN (): 检测参数是否为非数字,返回布尔值
-
-
switch分支
-
语法格式
switch(表达式){
cash 值:
执行代码
break;
cash 值:
执行代码
break;
default:
执行代码
}
区别:if 和 switch 运行效率来看,switch 要更快一些
if 语句可以和多个条件表达式使用,switch 只能和一个表达式使用
-
-
for循环
语法格式:
for(var i = 0;i<10;i++){
# 代码块
}
跳出语句: break continue
-
while循环 & do while 循环
while 语法格式:
var i = 0
while(i < 10){
代码块
i++
}
do while 语法格式:
var i = 0
do{
代码块
i++
}while(i < 10)
区别: 不同点,do while 无论条件是否成立,至少执行一次
-
-
函数
-
好处:
- 复用性
- 封装性
-
函数的定义
-
函数声明
语法格式:
function 函数名(){函数体}
-
函数表达式
语法格式:
var 变量名 = function(){函数体}
区别:
函数表达式:函数只能在声明调用,因为这种方式的函数,是在函数运行的阶段赋值给变量的
函数声明:函数可以在声明函数所属的作用域任意位置进行调用,因为这种方式,是在函数解析 阶段赋值给函数的
-
-
函数的调用
函数表达式 或 函数声明 是不能自己执行的,需要调用才能执行
调用: 函数名( )
-
函数的参数
- function fun(形参1,形参2,…){}
- fun(实参1,实参2,…);
-
arguments对象
当形参个数 > 实参个数 时:多余的形参 为 undifined
当实参个数 > 形参个数时 : 多余的实参 存储于 arguments 数组对象中
arguments.length
arguments[0]
-
return : 返回值 并 跳出当前函数体
-
匿名函数: 没有名字的函数
(function(){})
-
自执行函数:
(function(){形参})(实参)
-
-
执行环境
-
什么是执行环境
-
执行环境又被称为:执行上下文
执行环境定义了 变量或者函数有权 或 无权 访问了其他数据,决定各自的行为
-
-
执行环境分类(共三种)
-
全局执行环境
全局执行环境 是 外围的执行环境
在页面中,全局执行环境就是window对象
当一打开页面时,会自动生成window对象,那么全局的变量或者函数都属于window 对象的内容,
那么 window 对象的内容,那么window 就是全局的
-
函数执行环境
当某个函数给调用时,首先会创建一个执行环境以及作用链,然后使用arguments和 其他参数来初始化这个执行环境
-
-
回收机制:
- 某个执行环境中的所有代码执行完毕,保存在执行环境的中的变量或者函数都会进行销毁(回收)
- 但是全局执行环境是到关闭浏览器或则当前页面才会被回收的
-
执行环境的生命周期
- 创建阶段
- 生成变量对象
- 建立作用域链
- 确定this 指向
- 执行环境
- 变量赋值
- 函数调用
- 执行其他代码
- 销毁 , 回收阶段
- 创建阶段
-
-
bom(浏览器对象模型:围绕浏览器的一些操作)
-
location对象:操作浏览器当前的url
-
href :本身可以获取当前的url ;
设置对应的跳转url
location.href = “url” 可以跳转到对应的页面,是在本页面中跳转
window.open(url,"__blank") 在新窗口中的打开
-
search:设置或者获取,从问号(?),开始的url
-
hash: 设置或获取,从井号(#),开始的url
解码: decodeURIComponent
-
-
history:操作浏览器窗口访问过的url
back :返回上一页
forward:前往下一页
go: 前往指定页面
go(0): 刷新
go(-1): 返回上一页 back
go(-2): 返回上两页
go(1): 前往下一页
go(2): 前往下两页
-
navigator: 包含有关浏览器相关信息
userAgent:用户代理头的值
platform : 返回运行浏览器的操作系统
浏览器嗅探器检测(BrowserDetect.js)使用:
BrowserDetect.browser;// 浏览器的名称,例如Firefox,IE BrowserDetect.version;//浏览器的版本,比如,7、11 BrowserDetect.OS;//浏览器所宿主的操作系统,比如Windows、Linux
-
Screen:客户端屏幕信息
width : 显示返回屏幕的宽度
height: 显示返回屏幕的高度
-
-
js定时器函数
-
setInterval 间歇调用: “后” ,将定时任务处理的函数添加到执行队列的队尾
-
语法格式
setInterval(执行函数,毫秒数)
-
-
setTimeout 超时调用:“后” ,将定时任务处理的函数添加到执行队列的队尾
-
语法格式
setTimeout(执行函数,毫秒数)
-
-
清除定时器
-
clearInterval ==> setinterval
-
Cleartimeout ==> setTimeout
-
语法格式:
clearinterval(定时器名称)
clearTimeout(定时器名称)
-
-
-
js 单线程
-
js语言是一个单线程:同一个时间只能做一件事,这也就意味着所有人物都需要排队,
前一个任务之行结束了,才可以继续执行下一个任务
-
js 语言为什么是单线程
取决于 js 用在什么地方? 和用户体验相关
-
事件队列(定时器,ajax):先进先出
// js单线程 // 事件队列: 定时器 ajax for(var i = 0;i<5; i++){ setTimeout(function (){ document.write(i) },1000) } // 在js 存在在消息队列,把 定时器 先放到 消息队列中,带主线程的执行完毕,在执行消息队列中的代码
-
-
练习小补充(轮播图 后续系统学习):
-
获取id: document.getElementById(“id值”);
-
获取集合元素 : document.getElementsByTagName(“元素名称”);
-
获取集合元素个数 : length
-
给一个元素添加样式 : main.style.background = “blue”
// 轮播图实现 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <style> *{ margin: 0; padding: 0; } div{ width: 100%; text-align: center; } ul{ display: inline-block; width: 600px; height: 300px; overflow: hidden; } ul li{ } ul li img{ width: 100%; } </style> </head> <body> <div class = "turn"> <ul> <li> <img src="1.png" alt="picture"> </li> <li> <img src="2.png" alt="picture"> </li> <li> <img src="3.png" alt="picture"> </li> <li> <img src="4.png" alt="picture"> </li> </ul> </div> <script type="text/javascript"> // js 轮播图 // 找到所有的 li 元素 var lis = document.getElementsByTagName("li") var index = 0 setInterval(function (){ // 把所有的 li 元素设置为none for(var i = 0;i < lis.length;i++){ lis[i].style.display = "none" } if(index === lis.length){ index = 0 } lis[index].style.display = "block" index++ },1000) </script> </body> </html>
-
-
数组
-
什么是数组: 相同数据类型的元素按照一定顺序排列的集合
-
数组可以做什么:
- 存储一系列大量的值
-
使用数组
-
创建
-
构造函数形式:
var arr = new Array(参数)
(1) 不写 :表示一个没有声明长度的数组
(2)写入数值: 表示一个生命长度的数组 0~(2的32次方-1)
(3) 写入数组默认的n个值:
-
字面量形式:var arr = []
注: 使用字面量声明 比使用 构造函数声明的数组性能要好
-
-
-
数组的属性:length
-
引用数据类型 和 基本数据类型
赋值:
基本数据类型: 赋的是值
引用类型类型: 赋的地址
==:
基本类型比较的是 值
引用类型比较的的是 地址
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>玩什么游戏好?</title> <style> *{ margin: 0; padding: 0; } .games{ width: 300px; margin: 0 auto ; text-align: center; } #box{ width: 290px; height: 200px; border: 2px solid black; text-align: center; line-height: 200px; } input{ width: 100px; height: 20px; } </style> </head> <body> <!-- 抽奖 --> <div class="games"> <div id="box">忍者神龟</div> <input type="button" value="start" id="start"> <input type="button" value="stop" id="stop"> </div> <script type="text/javascript" > var arr = ["王者荣耀","吃鸡","连连看","魂斗罗","超级玛丽","忍者神龟"], box = document.getElementById("box"), start = document.getElementById("start"), stop = document.getElementById("stop"), index = 0 var star = null start.onclick = function () { start.disabled = true star = setInterval(function (){ if(index === arr.length){ index = 0 } box.innerText = arr[index] index++ },100) } stop.onclick = function () { start.disabled = false clearInterval(star) } </script> </body> </html>
-
数组的方法
-
concat() : 合并数组,最后返回一个新的数组
-
reverse():反转数组项的顺序(会改变原数组)
-
join(参数分隔符): 将数组元素组成一个字符串,用参数分隔符进行分割,默认以逗号分隔
把数组转换成字符串
语法格式: 数组.方法名称(参数)
-
push() : 将参数添加到原数组的末尾,并且返回数组的长度
-
pop():数组末尾移除最后一项,返回移除项
-
unshift: 将参数添加到原数组的首位,并且返回数组的长度
-
shift:数组末尾溢出最后一项,并且返回移除的项
-
slice(参数1,参数2):截取 ,返回新的数组
参数1: 开始位置
参数2:结束位置
参数-1 表示 , 最后的位置
当为一个参数时:表示从当前(包括此位置)截取到末尾
当为两个参数是: 表示从参数1(包括此位置)的位置截取到参数2(不包括此位置)的位置
-
sort (): 排序: 会改变原数组
排序:
sort(function (a,b){
return a - b # 升序
return b - a # 降序
})
-
indexOf(参数): 查找 ,如果存在返回该元素或字符第一次出现的位置的索引,不存在返回-1
如果存在返回下标
如果不存在返回-1
-
splice() : 可以删除 , 插入 , 替换操作
删除 : 2个参数 ,(1,2)从下表1 开始,删除 两个元素(包括自己)
替换 : 3 个参数, (0,1,4) 从下表 0 到下标1元素 替换成4 (前闭后开)
插入 : 3 个参数, (1,0,5) 表示在下标为1 添加一项5
-
-
数组的遍历操作
-
forEach()普通遍历
语法格式: 数组.forEach(function(item,index){
})
缺点: 不可以用break 和 return
-
map: 映射函数 , return操作,并且返回新的数组
-
filter: 过滤函数 , return 操作 , 并且放回新的数组
-
every:所有为true 才为true ,return操作
-
some: 有一个为true 就为 true ,return 操作
// 冒泡排序 function sorted(arr,reverse = 1){ // [2,1,9] var len = arr.length ; for (let i = len-1; i > 0; i--) { for (let j = len-1; j > 0 ; j--) { if(reverse === 1 && arr[j] < arr[j-1] || reverse === 0 && arr[j] > arr[j-1]){ var tem = arr[j] arr[j] = arr[j-1] arr[j-1] = tem } } } }
// 数组去重 // 方法一 function unique1(arr) { var newArr = [] for (let i = 0; i < arr.length; i++) { if(newArr.indexOf(arr[i]) === -1){ newArr.push(arr[i]) } } return newArr } // 方法二: function unique2(arr) { return arr.filter(function (item,index){ // 如果存在返回该元素或字符第一次出现的位置的索引,不存在返回-1 return arr.indexOf(item) === index }) }
-
-
-
字符串
-
创建
- 字面两创建 : var str = “hello world”
- 构造函数 : var str = new String(“你好啊”)
-
区别:字面量形式存储在栈内存中,构造函数形式存储在堆内存
typeof 字面量 ==> string
type 构造函数 ==> object
-
补充:
为什么字面量的string,boolean ,number也有属性和方法?
string , boolean , number :原始资料类型(个人理解,具有兼容对象的属性,一切事物皆对象)
new String , new Boolean , new Number : 包装对象
-
方法:
- charAt(数值):返回指定位置的字符
- indexOf(字符) : 查找,如果存在返回该元素或字符第一次出现的位置的索引,不存在返回-1
- replace(old_str, new_str): 默认只替换一次,支持正则
- trim(): 去除前后空格
- toLowerCase() : 把字符转换成小写
- toUpperCase() : 把字符转换成大写
- split() : 字符串转换成数组
- slice(start,end) : 支持 -1 操作,[m,n)
- slubstring(start,end): 负责转换成0 , 不支持-1 操作
- substr(start,length) :
-
-
Math (数学) 对象
-
Math.max() : 取一组数的最大值
-
Math.min() : 取一组数的最小值
-
Math.round() : 返回数的四舍五入结果
-
Math.abs() : 返回数的绝对值
-
Math.sqrt() : 返回数的平方根
-
Math.floor() ; 向下取整
-
Math.ceil() : 向上取整
-
Math.random() : 返回随机数 [0,1)
随机公式:
不包括最大值, 最小值
Math.floor(Math.random() *(max - min) + min)
包括最大值, 最小值
Math.floor(Math.random() *(max - min+1) + min)
-
-
日期对象:new Date()
var data = new Date()
参数:可以为 毫秒值 , 也可以为 格式化字符串
日期对象常用方法
-
data.getFullYear() : 年
-
data.getMonth() : 月
-
data.getDate() : 日
-
data.getHours() : 时
-
data.getMinutes() : 分
-
data.getSeconds() : 秒时间戳 : 从 1970 年 1 月 1 日 至今日的时间(毫秒值)
对象.getTime(). 返回时间戳
-
-
DOM (document object model ): 文档对象对象模型
-
获取文档(元素)节点
-
获取 id : document.getElementById()
-
获取标签名: document.getElementByTagName()
获取集合元素:有length , 有下标
-
获取class 名:document.getElementsByClassName()
获取如果集合元素:有length , 有下标
-
通过选择器来获取第一个节点
document.querySelector()
-
通过选择器来获取所有的节点
document.querySelectorAll()
在所有节点中, 获取不到html标签
在js 中看来,文档是 对象
-
-
节点属性
-
innerHTML() innerText(): 给节点添加内容
区别 : innerText 解析不了 html 标签
-
nodeName: 返回节点名称 (大写字母):用作判断使用
-
firstElementChild: 获取到第一个子元素节点
-
lastElementChild:获取到最后一个子元素节点
-
parentNode: 获取到父元素节点
-
className : 获取或设置节点的class
京东秒杀倒计时
<!doctype html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> <style> *{ margin: 0; padding: 0; color: white; } strong{ font-weight: normal; } .down-count{ overflow: hidden; background: url("jingdong.png") no-repeat; background-size: 100%; width: 190px; text-align: center; } .down-count .jd-title{ display: inline-block; margin-top: 30px; font-size: 25px; letter-spacing: 2px; } .down-count .jd-detial{ margin: 100px auto 30px; } .down-count .jd-detial .jd-detial-top{ font-weight: lighter; } .down-count .jd-detial .jd-detial-top strong{ font-size: 18px; } .down-count .jd-detial .jd-detial-buttom{ width: 130px; margin: 10px auto 30px; } .down-count .jd-detial .jd-detial-buttom span{ position: relative; float: left; width: 30px; height: 30px; margin-right: 20px; line-height: 30px; text-align: center; background: black; font-size: 16px; margin-bottom: 30px; } .down-count .jd-detial .jd-detial-buttom span:last-child{ margin-right: 0; } .down-count .jd-detial .jd-detial-buttom span:after{ position: absolute; content: ":"; right: -10px; } .down-count .jd-detial .jd-detial-buttom span:last-child:after{ content: ""; } </style> </head> <body> <div class="down-count"> <div class="jd-title">京东秒杀</div> <div class="jd-detial"> <div class="jd-detial-top"> <strong>2:00</strong>点场 倒计时 </div> <div class="jd-detial-buttom"> <span id="hour">00</span> <span id="minute">00</span> <span id="second">00</span> </div> </div> </div> <script type="text/javascript"> var hour = document.getElementById("hour"), minute = document.getElementById("minute"), second = document.getElementById("second") function down_count(){ var date = new Date("2021-4-2 02:00:00") var newDate = new Date() // 总共多少秒 var time = (date - newDate)/1000 // 获取小时 var hourx = Math.floor(time/60/60%24) // 换算成小时模24的原因: 让其每次得到的hourx 使其在 0 到 24 这个周期内变化 hourx = hourx < 10?"0"+hourx:hourx hour.innerText = hourx // 获取分钟数 var minutex = Math.floor(time/60%60) // 换算成分钟模60的原因: 让其每次得到的minutex 使其在 0 到 60 这个周期内变化 minutex= minutex<10 ? "0"+minutex : minutex minute.innerText = minutex // 获取秒数 var secondx = Math.floor(time%60) // 换算成秒模60的原因: 让其每次得到的secondx 使其在 0 到 60 这个周期内变化 secondx= secondx<10 ? "0"+secondx : secondx second.innerText = secondx } // 刷新之后 就不会延迟一秒了 down_count() setInterval(down_count,1000) </script> </body> </html>
-
-
节点方法—来操作节点属性的方法
-
获取: 节点名称.getAttribute(“属性名”) ,返回对应属性名称的值
-
设置: 节点对象.setAttribute(“属性名”,"属性值“)
-
删除: 节点对象.removeAttribute(“属性名称”)
注意规范:
如果要自定义属性的名称:data-xxx 例如:data-title
-
-
创建、添加、删除节点
-
创建节点
document.createElement(“节点名称”)
-
添加节点
追加:父节点.appendChild(字节点)
前置:父节点.insetrtChild(添加的字节点,添加到谁的前面)
-
删除节点
父节点.removeChild(字节点)
补充 :
a 链接 点击不刷新 :设置href 属性 为 javascript:; (一个冒号一个分号)
-
-
节点的样式设置
-
获取样式表中的样式
语法格式: getComputedSytle(节点).样式名称
-
获取或设置行内样式
语法格式: 节点.style.样式名称
-
获取元素大小和偏移位置
大小:
节点对象.offsetWidth
节点对象.offsetHeight
*** 计算: width + padding + border
没有 px单位,返回的事数值类型
大小:
节点对象.clientWidth
节点对象.clientHeight
***计算: width + padding
没有 px单位,返回的事数值类型
偏移(距离):
节点对象.offsetLeft(从左到右)
节点对象.offsetTop(从上到下)
如果节点没有定位的情况下:根据整个文档偏移
如果节点有定位的情况下:相对于父节点偏移
-
-
-
事件
-
事件流:事件执行的顺序
历史原因:
早起的IE时间的传播方向为由上而下,即从document 逐渐向下传播到目标元素;
而Netscape公司则是朝相反方向传播,也就是从目标元素开始向上逐级传播最终至window。
两家公司对于事件流出现了截然相反的定义
后来ECMAScript 在DOM2中对事件进行了规范,借本上就是上述二者的结合
当事件发生时,最先通知的是window,然后是document,由上至下逐级一次传入,
直到真正触发的那个元素(目标元素为止)。这个过程叫做捕获
当事件从目标元素开始起泡,由下至上逐次传播,直到window 对象为止,这个过程就是冒泡
综上:知道两种事件流 事件冒泡 & 事件捕获
事件捕获:从window 开始向下传播,一直到目标元素
事件冒泡:从目标节点开始向上传播,一直到window(在js中默认)
-
鼠标事件
-
onclick 单击事件
-
ondbclick 双击事件
-
oncontextmenu 右击事件
禁止右键查看相关属性 return false;
-
onmousedown 鼠标按下
-
onmouseup 鼠标松开
-
onmouseover 鼠标经过
-
onmouseout 鼠标离开
onmouseover和onmouseout 会在拖拽的时候会用到
-
onmousemove鼠标悬浮
onmousemove 会在放大镜的时候用到
-
-
键盘事件
-
onkedown
-
onkeyup
*** 可以通过keyCode 获取键值: e.keyCode
-
-
其他事件
-
onload : 加载完毕后立即执行的操作
*** window.onload ===> 网页加载完毕后
*** 判断图片是否加载完成
-
onfoucus : 获取焦点
自动获取焦点 : focus()
-
onblur : 失去焦点
-
onscroll: 滚动条事件
// 滚动的距离
var sTop = document.documentElement.scrollTop // 可以进行赋值设置 与文档顶部的距离
// 可视化区域高度
var cHei = document.documenElement.clientHeight // 固定的值
If(sTop > cHei){
// 设置定位元素的display =” block“
}else{
// 设置定位元素的display = “none”
}
-
onchange: 内容改变时触发
-
-
事件处理程序(添加事件)
-
HTML事件处理程序: 事件直接写在节点上
缺点: 违背了w3c (结构样式行为相分离)原则,代码耦合
-
DOM 0 级事件处理程序:main.onclick = function(){}
缺点: 同样元素同样的事件会被覆盖
-
DOM 2 级事件处理程序:
dom对象.addEventListener(事件名称,函数,false|true)
注意:事件名称: 需要加入 on
false: 冒泡
true: 捕获
小瑕疵: 在IE 8 以下不兼容
-
IE事件处理程序(了解即可,基本不用)
dom对象.attachEvent(事件名称 , 函数)
-
-
事件处理程序(删除操作)
-
DOM 0 级删除事件
dou对象.事件名称 = null
-
DOM 2 级删除事件
dom对象.removeEventListener(事件名称,函数,false|true)
-
IE 删除事件
dom对象.detachEvent(事件名称,函数)
-
使用 for 循环绑定事件
var data = document.querySelectorAll(“body > div > div.data > ul”)
for(var i = 1;i < data.length;i++){
data[i].index = i
data[i].onclick = function(){
console.log(this.index)
}}
-
-
事件对象
-
事件对象:e
main.onclick = function(e){
console.log(e)
}
-
事件对象的属性
事件对象.target : 目标 ==> 返回对应的dom对象
事件对象.clientX:返回鼠标距离浏览器左侧的距离
事件对象.clientY:返回鼠标距离浏览器上面的距离
-
事件委托(very important)
原理: 事件冒泡。把本来改在子元素添加的事件添加在父元素
e.target.nodeName.toLowerCase === “li”
优点:
1.性能较好
2.级时候添加的内容也有效
-
-
阻止事件冒泡 与 阻止默认行为
-
阻止事件冒泡
事件对象.stopPropagation()
- 阻止默认行为
事件对象.preventDefault()
或则 直接return false
常用于 a 标签
用于form表单
<form action="http://www.baidu.com" onsubmit="return -1" > <input type="button"value="提交"> </form>
-
-
拖拽效果的实现
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <style> *{ margin:0; padding: 0; } #drag{ position: absolute; overflow: hidden; width: 200px; height: 200px; cursor: pointer; background: orangered; border-radius: 30px; text-align: center; } h2{ font-weight: normal; width: 150px; height: 100px; margin: 20px auto 0; } </style> </head> <body> <div id="drag"> <h2>hello world</h2> <span>dfasfdasdfsa</span> </div> <script type="text/javascript"> var drag = document.getElementById("drag") // 鼠标按下 drag.onmousedown = function (e) { // 计算 鼠标坐标 和 盒子盒子"外边距"的大小差 var x= e.clientX - drag.offsetLeft var y = e.clientY - drag.offsetTop // 鼠标移动 document.onmousemove = function (e) { // 拖拽到的位置 "外边距"的大小 :实际需要的是 var l = e.clientX -x var t = e.clientY -y console.log(l,t) if(l <= 0){ l = 0 }else if(l > document.documentElement.clientWidth - drag.offsetWidth){ l = document.documentElement.clientWidth - drag.offsetWidth } if(t <= 0){ t = 0 }else if(t > document.documentElement.clientHeight - drag.offsetHeight){ t = document.documentElement.clientHeight - drag.offsetHeight } drag.style.left = l+"px" drag.style.top = t+"px" } } // 鼠标松开 drag.onmouseup = function (e){ document.onmousemove = null } </script> </body> </html>
-
放大镜
小知识点:
获取浏览器动态加载的数据 ,在console内,输入 :setTimeout(function(){debugger},5000)
<!doctype html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> <style> *{ margin: 0; padding: 0; } .u-l{ float: left; } .box{ margin: 30px 0 0 30px; } .left{ position: relative; width: 400px; height: 400px; } .left img{ width: 100%; } .right{ position: relative; overflow: hidden; width: 400px; height: 400px; margin-left: 30px; } .right img{ position: absolute; display: none; } .shadow{ display: none; position: absolute; cursor:pointer; left: 0; top: 0; width: 100px; height: 100px; background: white ; opacity: .9; } </style> </head> <body> <div class="box"> <div class="left u-l"> <img src="small.jpg"> <div class="shadow"></div> </div> <div class="right u-l"> <img src="large.jpg"> </div> </div> <script> var box = document.querySelector(".box"), smallImg = document.querySelector(".left img"), shadow = document.querySelector(".shadow"), largeImg = document.querySelector(".right img"), left = document.querySelector(".left"), right = document.querySelector(".right") smallImg.onmouseover = function (e) { shadow.style.display = "block" largeImg.style.display = "block" } smallImg.onmousemove = function(e){ // 算坐标位置,算得是 阴影的阴影中心坐标位置 var x = e.clientX - box.offsetLeft - shadow.offsetWidth/2 var y = e.clientY - box.offsetTop - shadow.offsetHeight/2 console.log(x) console.log(y) if(x <= 0){ x = 0 }else if(x > left.offsetWidth - shadow.offsetWidth){ // 如果阴影中心坐标位置 > 盒子大小 减去 阴影大小 x = left.offsetWidth - shadow.offsetWidth } if(y <= 0){ y = 0 }else if(y > left.offsetHeight - shadow.offsetHeight){ y = left.offsetHeight - shadow.offsetHeight } shadow.style.left = x+"px" shadow.style.top = y+"px" largeImg.style.left = -2*x+"px" largeImg.style.top = -2*y+"px" } smallImg.onmouseout = function (e) { shadow.style.display = "none" largeImg.style.display = "none" } </script> </body> </html>
-
-
正则表达式
-
什么是正则表达式: 规则的表达式
-
应用场景:表单的验证
-
正则的使用:
定义:
字面量://
构造函数: new RegExp()
区别:
new RegExp()
-
正则的方法
test(): 检测一个内容是否与正则匹配
如果匹配返回结果 true
如果不匹配返回false
exec(): 检测内容是否与正则匹配
如果匹配返回数组
如果不匹配返回null
-
元字符
[] : 匹配括号中的任意一个字符
[^] : 匹配 除了括号中任意字符
[0-9] : 匹配数组0-9范围
[a-zA-Z]: 匹配字母
\d: 匹配数字
\D: 匹配非数字
\w: 匹配数字,字母,下划线
\W:匹配非数字,字母,下划线
\s: 匹配空格
\S: 匹配非空格
\b: 匹配边界
\B: 匹配非边界
. : 匹配处理换行符以外的任意换行字符
-
转义字符:(\)
-
选择符: | ==》 或
-
修饰符:
i:不区分大小写
g:全文匹配
m:(不常用)
-
字符串方法可以匹配正则去使用
replace()
match():类似于exec()
查找返回对应的的值(值是数据)
没有找到返回null
*** 支持全局
-
限定符:
^: 开始
$: 结束
-
重复:
{n}: 重复n次
{n,}: 重复 至少 n次
{n,m}: 重复 n 到 m次
*: 重复 0 到 n次
+: 重复1 到 n 次
?: 重复 0 到 1次
补充事件: oninput
-
贪婪模式与非贪婪模式
- 贪婪模式
/\d{3,6}/g
-
非贪婪模式(懒惰模式)
/\d{3,6}?/g
-
分组与字符类
-
分组
():把部分内容结合在一起
-
字符类: 来获取分组内的内容的
$1
$2
…
*** 前提: 正则必须执行一次
调用方式一:console.log( str.replace(reg,"$1"))
调用方式二:
reg.test(str)
console.log( RegExp.$1, RegExp.$2, RegExp$3)
-
-
前瞻 与 后顾(js没有后顾)
前瞻:
正向前瞻:(?=) 匹配符合的
负向前瞻: (?!) 匹配不符合的
for exmple:
var reg = /^(?=\d)[0-9a-z]{4,8}$/ 必须以数字开头
var reg = /^(?=.*\d)[0-9a-z]{4,8}$/ 必须包含数字和字母
-
bu
未完待续…