页面脚本 - JavaScript
JavaScript
由浏览器(或者Node.js)执行的动态函数,解析后对 DOM 树元素进行动态修改,以实现页面的动态功能。
JavaScript引入方式
1. 直接编写,一般把脚本置于 <body> 元素的底部,可改善显示速度,因为浏览器在加载页面的时候会从上往下进行加载并解析
<script>
alert("hello js");
</script>
2. 导入文件
<script src="hello.js"></script>
JavaScript基础语法
- 输出语句
window.alert("hello js"); // 写入警告框
document.write("hello js") // 写入html页面
console.log("hello js") // 写入浏览器的控制台
- 变量
var age = 20; // 全局变量,可以重复定义
let age = 20; // 只在 `let` 关键字所在的代码块内有效,且不允许重复声明
const = 30; // 声明常量,常量的值不能改变
console.log(typeof age) // 获取数据类型
- 数据类型
// 原始类型
number 数字(整数、小数、NaN(Not a Number)
string 字符、字符串,单双引皆可
boolean 布尔。true,false
null 对象为空
undefined 当声明的变量未初始化时,该变量的默认值是undefined
// 引用类型
- 相等判定
* ==:
1. 判断类型是否一样,如果不一样,则进行类型转换
2. 再去比较其值
* ===:js 中的全等于
1. 判断类型是否一样,如果不一样,直接返回false
2. 再去比较其值
var age1 = 20;
var age2 = "20";
alert(age1 == age2);// true
alert(age1 === age2);// false
- 类型转换
* 其他类型转为number
1. string 转换为 number: 按照字符串的字面值,转为数字。如果字面值不是数字,则转为NaN
- 使用 `+` 正号运算符:
var str = +"20";
alert(str + 1) //21
- 使用 `parseInt()` 函数(方法):
var str = "20";
alert(parseInt(str) + 1);
2. boolean 转换为 number: true 转为1,false转为0
var flag = +false;
alert(flag); // 0
* 其他类型转为boolean
* number 类型转换为 boolean 类型:0和NaN转为false,其他的数字转为true
* string 类型转换为 boolean 类型:空字符串转为false,其他的字符串转为true
* null类型转换为 boolean 类型是 false
* undefined 转换为 boolean 类型是 false
- 函数
函数定义格式有两种:
* 方式1
function 函数名(参数1,参数2..){
要执行的代码
}
* 方式2
var 函数名 = function (参数列表){
要执行的代码
}
JavaScript常用对象
Array对象
- 创建方式
创建方式1:
var arrname = [元素0,元素1,….]; // var arr=[1,2,3];
创建方式2:
var arrname = new Array(元素0,元素1,….); // var test=new Array(100,"a",true);
- 数组方法
var arr = ["A","B","C","D"];
// 内置属性
console.log( arr.length );
// 获取指定下标的成员
// console.log( arr[3] ); // D
console.log( arr[arr.length-1] ); // 最后一个成员
// (1) pop() 出栈,删除最后一个成员作为返回值
var arr = [1,2,3,4,5];
var ret = arr.pop();
console.log(arr); // [1, 2, 3, 4]
console.log(ret); // 5
// (2) push() 入栈,给数组后面追加成员
var arr = [1,2,3,4,5];
arr.push("a");
console.log(arr); // [1, 2, 3, 4, 5, "a"]
// (3) shift是将数组的第一个元素删除
var arr = [1,2,3,4,5];
arr.shift()
console.log(arr); // [2, 3, 4, 5]
// (4) unshift是将value值插入到数组的开始
var arr = [1,2,3,4,5];
arr.unshift("yuan")
console.log(arr); // ["yuan",1,2, 3, 4, 5]
// (5) reverse() 反转排列
var arr = [1,2,3,4,5];
arr.reverse();
console.log(arr); // [5, 4, 3, 2, 1]
// (6) slice(开始下标,结束下标) 切片,开区间
// (7) sort() 排序
var arr = [3,4,1,2,5,10];
console.log( arr ); // [3, 4, 1, 2, 5, 10]
arr.sort();
// 这是字符的排序,不是数值的排序
console.log(arr); // [1, 10, 2, 3, 4, 5]
// 数值升序
var arr = [3,4,1,2,5,10];
arr.sort(function(a,b){
return a-b;
});
console.log(arr); // [1, 2, 3, 4, 5, 10]
// 数值降序
var arr = [3,4,1,2,5,10];
arr.sort(function(a,b){
return b-a;
});
console.log(arr); // [10, 5, 4, 3, 2, 1]
// (8) splice(操作位置的下标,删除操作的成员长度,"替换或者添加的成员1","替换或者添加的成员2") 添加/删除指定的成员 "万能函数"
var arr1 = [1,2,3];
arr1.splice(1,1);
console.log(arr1); // 删除指定的1个成员 [1, 3]
var arr2 = ["a","b","c","d"];
arr2.splice(2,0,"w","x","w"); // 添加
console.log(arr2); // ["a", "b", "w", "x", "w", "c", "d"]
var arr3 = ["a","b","c"];
arr3.splice(1,1,"w");
console.log(arr3); // ["a", "w", "c"]
// (9) concat() 把2个或者多个数组合并
var arr1 = [1,2,3];
var arr2 = [4,5,7];
var ret = arr1.concat(arr2);
console.log( ret );
// (10) join() 把数组的每一个成员按照指定的符号进行拼接成字符串
var str = "广东-深圳-南山";
var arr = str.split("-");
console.log( arr ); // ["广东", "深圳", "南山"];
var arr1 = ["广东", "深圳", "南山"];
var str1 = arr1.join("-");
console.log( str1 ); // 广东-深圳-南山
// (11) find() 高阶函数, 返回符合条件的第一个成员
var arr = [4,6,5,7];
var func = (num)=>{
if(num%2===0){
return num;
}
};
var ret = arr.find(func);
console.log( ret ); // 4
// (12) filter() 高阶函数, 对数组的每一个成员进行过滤,返回符合条件的结果
var arr = [4,6,5,7];
function func(num){ // 也可以使用匿名函数或者箭头函数
if(num%2===0){
return num;
}
}
var ret = arr.filter(func); // 所有的函数名都可以作为参数传递到另一个函数中被执行
console.log( ret );
// (13) map() 对数组的每一个成员进行处理,返回处理后的每一个成员
var arr = [1,2,3,4,5];
var ret = arr.map((num)=>{
return num**3;
});
console.log( ret ); // [1, 8, 27, 64, 125]
// (14) 其它方法
// includes 查询指定数据是否在数组中存在!
// indexOf() 查询指定数据在数组中第一次出现的位置
// isArray() 判断变量的值是否是数组
String对象
- 创建方式
var 变量名 = "abc"; //方式1
var 变量名 = new String(s); //方式2
- 常用方法
str.length // 属性,返回字符串长度
str.charAt() // 返回指定位置的字符
str.indexOf() // 检索字符串第一次出现的位置
str.trim() // 去掉字符串两端的空格
自定义对象
var 对象名称 = {
属性名称1:属性值1,
属性名称2:属性值2,
...,
函数名称:function (形参列表){},
...
};
// 调用属性的格式:对象名.属性名
// 调用函数的格式:对象名.函数名()
RegExp对象
RegExp 是正则对象。正则对象是判断指定字符串是否符合规则。
- 创建正则对象
正则对象有两种创建方式:
* 直接量方式:注意不要加引号
var reg = /正则表达式/;
* 创建 RegExp 对象
var reg = new RegExp("正则表达式");
- 正则表达式
正则表达式是和语言无关的。很多语言都支持正则表达式,Java语言也支持,只不过正则表达式在不同的语言中的使用方式不同,js 中需要使用正则对象来使用正则表达式。
正则表达式常用的规则如下:
* ^:表示开始
* $:表示结束
* [ ]:代表某个范围内的单个字符,比如: [0-9] 单个数字字符
* .:代表任意单个字符,除了换行和行结束符
* \w:代表单词字符:字母、数字、下划线(_),相当于 [A-Za-z0-9_]
* \d:代表数字字符: 相当于 [0-9]
量词:
* +:至少一个
* *:零个或多个
* ?:零个或一个
* {x}:x个
* {m,}:至少m个
* {m,n}:至少m个,最多n个
// 规则:单词字符,6~12
// 1.创建正则对象,对正则表达式进行封装
var reg = /^\w{6,12}$/;
var str = "abcccc";
//2. 判断 str 字符串是否符合 reg 封装的正则表达式的规则
var flag = reg.test(str);
alert(flag);
BOM
Window对象
- 窗口方法
// BOM Browser object model 浏览器对象模型
// js中最大的一个对象.整个浏览器窗口出现的所有东西都是window对象的内容.
console.log( window );
// alert() 弹出一个警告框
window.alert("hello");
// confirm 弹出一个确认框,点击确认,返回true, 点击取消,返回false
var ret = confirm("您确认要删除当前文件么?");
console.log( ret );
// 弹出一个消息输入框,当点击确认以后,则返回可以接收到用户在输入框填写的内容.如果点击取消,则返回null
var ret = prompt("请输入一个内容","默认值");
console.log( ret );
// close() 关闭当前浏览器窗口
window.close();
// 打开一个新的浏览器窗口
window.open("http://www.baidu.com","_blank","width=800px,height=500px,left=200px,top=200px";
- 定时方法
setInterval() 方法会不停地调用函数,直到 clearInterval() 被调用或窗口被关闭。由 setInterval() 返回的 ID 值可用作 clearInterval() 方法的参数。而setTimeout是在指定的毫秒数后调用code一次。
// 设置循环定时器
var ID = window.setInterval(code,millisec) // 每millisec毫秒执行一次code
// 取消循环定时器
window.clearInterval(ID);
// 设置单次定时器
var ID = window.setTimeout(code,millisec) // millisec毫秒后执行code一次
// 取消单次定时器
window.clearTimeout(ID);
History对象
History 对象是 JavaScript 对历史记录进行封装的对象。
history.back(); // 加载history列表中的前一个URL
history.forward(); // 加载history列表中的下一个URL
Location对象
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<button onclick="func1()">查看Location对象</button>
<button onclick="func2()">跳转到百度</button>
<button onclick="func3()">F5</button>
<script>
function func1(){
console.log( location );
}
// 地址栏对象控制和操作地址栏
// 所谓的地址就是当前页面所在地址
// 地址结构:
// 协议://域名:端口/路径/文件名?查询字符串#锚点
console.log( `协议=>${location.protocol}` );
console.log( `端口=>${location.port}` );
console.log( `域名=>${location.hostname}` );
console.log( `域名:端口=>${location.host}` );
console.log( `路径=>${location.pathname}` );
console.log( `查询字符串=>${location.search}` );
console.log(`完整的地址信息=>${location.href}`);
function func2(){
// location.href="http://www.baidu.com"; // 页面跳转
location.assign("http://www.baidu.com"); // 页面跳转
}
function func3(){
location.reload(); // 刷新页面
}
</script>
</body>
</html>
本地存储对象
使用存储对象的过程中, 对象数据会根据域名端口进行保存的,所以 js不能获取当前页面以外其他域名端口保存到本地的数据。也就是说,我们存储对象获取数据只能是自己当前端口或者域名下曾经设置过的数据,一旦端口或者域名改变,则无法获取原来的数据。
* localStorage 本地永久存储
localStorage.setItem("变量名","变量值"); 保存一个数据到存储对象
localStorage.变量名 = 变量值 保存一个数据到存储对象
localStorage.getItem("变量名") 获取存储对象中保存的指定变量对应的数据
localStorage.变量名 获取存储对象中保存的指定变量对应的数据
localStorage.removeItem("变量名") 从存储对象中删除一个指定变量对应的数据
localStorage.clear() 从存储对象中删除所有数据
* sessionStorage 本地会话存储
sessionStorage.setItem("变量名","变量值"); 保存一个数据到存储对象
sessionStorage.变量名 = 变量值 保存一个数据到存储对象
sessionStorage.getItem("变量名") 获取存储对象中保存的指定变量对应的数据
sessionStorage.变量名 获取存储对象中保存的指定变量对应的数据
sessionStorage.removeItem("变量名") 从存储对象中删除一个指定变量对应的数据
sessionStorage.clear() 从存储对象中删除所有数据
DOM
DOM document Object Model 文档对象模型
// 整个html文档,会保存一个文档对象document
console.log( document ); // 获取当前文档的对象
查找标签
- 直接查找标签
document.getElementById("id值") // 根据id属性值获取,返回单个Element对象
document.getElementsByTagName("标签名") // 根据标签名称获取,返回Element对象数组
document.getElementsByName("属性名") // 根据name属性值获取,返回Element对象数组
document.getElementsByClassName("类名") // 根据class属性值获取,返回Element对象数组
- 导航查找标签
elementNode.parentElement // 父节点标签元素
elementNode.children // 所有子标签
elementNode.firstElementChild // 第一个子标签元素
elementNode.lastElementChild // 最后一个子标签元素
elementNode.nextElementSibling // 下一个兄弟标签元素
elementNode.previousElementSibling // 上一个兄弟标签元素
- CSS选择器查找
document.querySelector("css选择器") //根据css选择符来获取查找到的第一个元素,返回标签对象(dom对象)
document.querySelectorAll("css选择器"); // 根据css选择符来获取查找到的所有元素,返回数组
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<div id="i1">DIV1</div>
<div class="c1">DIV</div>
<div class="c1">DIV</div>
<div class="c1">DIV</div>
<div class="outer">
<div class="c1">item</div>
</div>
<div class="c2">
<div class="c3">
<ul class="c4">
<li class="c5" id="i2">111</li>
<li>222</li>
<li>333</li>
</ul>
</div>
</div>
<script>
// 直接查找
var ele = document.getElementById("i1"); // ele就是一个dom对象
console.log(ele);
var eles = document.getElementsByClassName("c1"); // eles是一个数组 [dom1,dom2,...]
console.log(eles);
var eles2 = document.getElementsByTagName("div"); // eles2是一个数组 [dom1,dom2,...]
console.log(eles2);
var outer = document.getElementsByClassName("outer")[0];
var te = outer.getElementsByClassName("c1");
console.log(te);
// 导航查找
var c5 = document.getElementsByClassName("c5")[0];
console.log(c5); // c5是一个DOM对象
console.log(c5.parentElement.lastElementChild); // 返回值是dom对象
console.log(c5.parentElement.children); // 返回值是dom对象数组
console.log(c5.nextElementSibling.nextElementSibling);
console.log(c5.parentElement.children);
// css选择器
var dom = document.querySelector(".c2 .c3 .c5");
console.log(":::",dom);
var doms = document.querySelectorAll("ul li");
console.log(":::",doms);
</script>
</body>
</html>
绑定事件
- 静态绑定 :直接把事件写在标签元素中。
<div id="div" onclick="foo(this)">click</div>
<script>
function foo(self){ // 形参不能是this;
console.log("foo函数");
console.log(self);
}
</script>
- 动态绑定:在js中通过代码获取元素对象,然后给这个对象进行后续绑定。
<p id="i1">试一试!</p>
<script>
var ele=document.getElementById("i1");
ele.onclick=function(){
console.log("ok");
console.log(this); // this直接用
};
</script>
一个元素本身可以绑定多个不同的事件, 但是如果多次绑定同一个事件,则后面的事件代码会覆盖前面的事件代码
多个标签绑定事件
<ul>
<li>111</li>
<li>222</li>
<li>333</li>
<li>444</li>
<li>555</li>
</ul>
<script>
var eles = document.querySelectorAll("ul li");
for(var i=0;i<eles.length;i++){
eles[i].onclick = function (){
console.log(this.innerHTML)
// console.log(eles[i].innerHTML) // 结果?
}
}
</script>
操作标签
<标签名 属性1=“属性值1” 属性2=“属性值2”……>文本</标签名>
- 文本操作
<div class="c1"><span>click</span></div>
<script>
var ele =document.querySelector(".c1");
ele.onclick = function (){
// 查看标签文本
console.log(this.innerHTML)
console.log(this.innerText)
}
ele.ondblclick = function (){
// 设置标签文本
this.innerHTML = "<a href='#'>yuan</a>"
//this.innerText = "<a href='#'>yuan</a>"
}
</script>
- value操作
像input标签,select标签以及textarea标签是没有文本的,但是显示内容由value属性决定
<input type="text" id="i1" value="yuan">
<textarea name="" id="i2" cols="30" rows="10">123</textarea>
<select id="i3">
<option value="hebei">河北省</option>
<option value="hubei">湖北省</option>
<option value="guangdong">广东省</option>
</select>
<script>
// input标签
var ele1 =document.getElementById("i1");
console.log(ele1.value);
ele1.onmouseover = function (){
this.value = "alvin"
}
// textarea标签
var ele2 =document.getElementById("i2");
console.log(ele2.value);
ele2.onmouseover = function (){
this.innerText = "welcome to JS world!"
this.value = "welcome to JS world!"
}
// select标签
var ele3 =document.getElementById("i3");
console.log(ele3.value);
ele3.value= "hubei"
</script>
- css样式操作
<p id="i1">Hello world!</p>
<script>
var ele = document.getElementById("i1");
ele.onclick = function (){
this.style.color = "red"
}
</script>
属性操作
elementNode.setAttribute("属性名","属性值")
elementNode.getAttribute("属性名")
elementNode.removeAttribute("属性名");
并不是所有属性都可以像value那样操作。
- class属性操作
elementNode.className
elementNode.classList.add
elementNode.classList.remove
案例:tab切换
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
*{
margin: 0;
padding: 0;
}
.tab{
width: 800px;
height: 300px;
/*border: 1px solid red;*/
margin: 200px auto;
}
.tab ul{
list-style: none;
}
.tab-title{
background-color: #f7f7f7;
border: 1px solid #eee;
border-bottom: 1px solid #e4393c;
}
.tab .tab-title li{
display: inline-block;
padding: 10px 25px;
font-size: 14px;
}
li.current {
background-color: #e4393c;
color: #fff;
cursor: default;
}
.hide{
display: none;
}
</style>
</head>
<body>
<div class="tab">
<ul class="tab-title">
<li class="current" index="0">商品介绍</li>
<li class="" index="1">规格与包装</li>
<li class="" index="2">售后保障</li>
<li class="" index="3">商品评价</li>
</ul>
<ul class="tab-content">
<li>商品介绍...</li>
<li class="hide">规格与包装...</li>
<li class="hide">售后保障...</li>
<li class="hide">商品评价...</li>
</ul>
</div>
<script>
var titles = document.querySelectorAll(".tab-title li");
var contents = document.querySelectorAll(".tab-content li");
for (var i = 0;i<titles.length;i++){
titles[i].onclick = function () {
// (1) 触发事件标签拥有current样式
for (var j = 0;j<titles.length;j++){
titles[j].classList.remove("current")
}
console.log(this);
this.classList.add("current");
// (2) 显示点击title对应的详情内容
var index = this.getAttribute("index");
// console.log(this.getAttribute("index"));
// console.log(contents[index]);
for (var z = 0;z<contents.length;z++){
contents[z].classList.add("hide");
}
contents[index].classList.remove("hide");
}
}
</script>
</body>
</html>
- 节点操作
// 创建节点:
document.createElement("标签名")
// 插入节点
somenode.appendChild(newnode) // 追加一个子节点(作为最后的子节点)
somenode.insertBefore(newnode,某个节点) // 把增加的节点放到某个节点的前边
// 删除节点
somenode.removeChild():获得要删除的元素,通过父元素调用删除
//替换节点
somenode.replaceChild(newnode, 某个节点);
案例:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<button class="add_btn">添加节点</button>
<button class="del_btn">删除节点</button>
<button class="replace_btn">替换节点</button>
<div class="c1">
<h3>hello JS!</h3>
<h3 class="c2">hello world</h3>
</div>
<script>
var add_btn = document.querySelector(".add_btn");
var del_btn = document.querySelector(".del_btn");
var replace_btn = document.querySelector(".replace_btn");
var c1 = document.querySelector(".c1");
var c2 = document.querySelector(".c2");
add_btn.onclick = function () {
// 创建节点
var ele = document.createElement("img"); // <img>
ele.src = "https://img2.baidu.com/it/u=1613029778,1507777131&fm=26&fmt=auto&gp=0.jpg"
console.log(ele);
// 添加节点
// c1.appendChild(ele);
c1.insertBefore(ele, c2)
};
del_btn.onclick = function () {
// 删除子节点
c1.removeChild(c2);
};
replace_btn.onclick = function () {
// 创建替换节点
var ele = document.createElement("img"); // <img>
ele.src = "https://img2.baidu.com/it/u=1613029778,1507777131&fm=26&fmt=auto&gp=0.jpg"
console.log(ele);
// 替换节点
c1.replaceChild(ele, c2);
}
</script>
</body>
</html>
常用事件
- onload事件
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script>
window.onload = function (){
ele = document.getElementById("i1")
console.log(ele.innerHTML);
}
</script>
</head>
<body>
<div id="i1">yuan</div>
</body>
</html>
- onsubmit事件
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<form action="" id="i1">
用户名:<input type="text">
密码: <input type="password">
<input type="submit">
</form>
<script>
var ele = document.getElementById("i1");
var user = document.querySelector("#i1 [type=text]")
var pwd = document.querySelector("#i1 [type=password]")
ele.onsubmit = function (e){
console.log(user.value);
console.log(pwd.value);
return false; // 终止事件执行
// e.preventDefault() // 阻止元素默认行为
}
</script>
</body>
</html>
- onchange事件
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<select name="provonce" id="s1">
<option value="hebei">请选择省份</option>
<option value="hubei">湖北省</option>
<option value="hunan">湖南省</option>
<option value="hebei">河北省</option>
</select>
<select name="provonce" id="s2">
<option value="hebei">请选择城市</option>
</select>
<script>
var data={"hunan":["长沙","岳阳","张家界"],"hubei":["武汉","襄阳","荆州"],"hebei":["石家庄","保定","张家口"]};
console.log(data);
var ele = document.getElementById("s1");
var ele2 = document.getElementById("s2");
ele.onchange=function () {
console.log(this.value);
var citys = data[this.value];
console.log(citys);
// 清空操作
ele2.options.length=1;
// 创建标签
for (var i=0;i<citys.length;i++){
var option = document.createElement("option"); // </option></option>
option.innerHTML=citys[i];
ele2.appendChild(option)
}
}
</script>
</body>
</html>
- onmouse事件
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
#container{
width: 300px;
}
#title{
cursor: pointer;
background: #ccc;
}
#list{
display: none;
background:#fff;
}
#list div{
line-height: 50px;
}
#list .item1{
background-color: green;
}
#list .item2{
background-color: rebeccapurple;
}
#list .item3{
background-color: lemonchiffon;
}
</style>
</head>
<body>
<div id="container">
<div id="title">使用了mouseout事件↓</div>
<div id="list">
<div class="item1">第一行</div>
<div class="item2">第二行</div>
<div class="item3">第三行</div>
</div>
</div>
<script>
// 1.不论鼠标指针离开被选元素还是任何子元素,都会触发 mouseout 事件。
// 2.只有在鼠标指针离开被选元素时,才会触发 mouseleave 事件。
var container=document.getElementById("container");
var title=document.getElementById("title");
var list=document.getElementById("list");
title.onmouseover=function(){
list.style.display="block";
};
container.onmouseleave=function(){ // 改为onmouseout试一下
list.style.display="none";
};
/*
因为mouseout事件是会冒泡的,也就是onmouseout事件可能被同时绑定到了container的子元素title和list
上,所以鼠标移出每个子元素时也都会触发我们的list.style.display="none";
*/
</script>
</body>
</html>
- onkey事件
<input type="text" id="t1"/>
<script type="text/javascript">
var ele=document.getElementById("t1");
ele.onkeydown=function(e){
console.log("onkeydown",e.key)
};
ele.onkeyup=function(e){
console.log("onkeyup",e.key)
};
</script>
- onblur和onfocus事件
<input type="text" class="c1">
<script>
var ele = document.querySelector(".c1");
// 获取焦点事件
ele.onfocus = function () {
console.log("in")
};
// 失去焦点事件
ele.onblur = function () {
console.log("out")
}
</script>
- 冒泡事件
<div class="c1">
<div class="c2"></div>
</div>
<script>
var ele1 = document.querySelector(".c1");
ele1.onclick = function () {
alert("c1区域")
};
var ele2 = document.querySelector(".c2");
ele2.onclick = function (event) {
alert("c2区域");
// 如何阻止事件冒泡
event.stopPropagation();
}
</script>

JavaScript
浙公网安备 33010602011771号