认识<a>…</a>
a标签常见写法
<a href="...">...</a>
href
的值可以是一个网址、一个文本文档、一个非文本文件路径,还可以实现一些功能。
当用户点击链接后各自有不同的意义:
- #html元素id:跳转到指定id锚点,首页可直接用”#“。
- 网址:在当前窗口或新窗口中打开链接。
- 文本文档:打开文档查看内容。
- 非文本文档路径:下载文件。
- mailto:邮箱地址:调用本地程序发邮件。
- tel:电话号码:调用本地程序拨打电话。
…
元素定位
html元素的定位在css样式中可以利用
position
来定义,例如:
position: static;
静态定位 默认定位。position:fixed;
固定定位 将html元素在页面上固定且不随滚动条滚动。position: absolute;
绝对定位 优先参照有定位属性的父级元素否则参照body。position: relative;
相对定位 参照文档流定位。
…
导航条下拉菜单主要用到
absolute
和relative
。
事件
来看一段获取html按钮内容代码片段:
<button onclick="console.log(this.innerText)">button内容</button>
- 其中
onclick="console.log(this.innerText)"
是以事件属性方式添加事件。
表示这个按钮被点击后的操作是获取按钮的文本内容。
- 也可以javascript对象属性方式添加事件,例如:
<script>
document.querySelectorAll("#button-id")[0].onclick = function () {
console.log("点击一次1");
};
document.querySelectorAll("#button-id")[0].onclick = function () {
console.log("点击一次2");
};
</script>
注意:以javascript对象属性方式添加事件的元素只会生效最后一次事件。
- 如果要同时触发一个元素上的多个事件,使用javascript事件监听器:
<script>
const but3 = document.querySelectorAll("button")[2];
but3.addEventListener("click", function () {
console.log("全部按钮1");
});
but3.addEventListener("click", function () {
console.log("全部按钮2");
});
but3.addEventListener("click", function () {
console.log("全部按钮3");
});
<script>
点击按钮后浏览器控制台输出结果:
事件的触发阶段
- 事件冒泡与捕获代码片段:
<body>
<ul>
<li><a href="#">点击链接</a></li>
</ul>
</body>
<script>
const a = document.querySelector("a");
const li = document.querySelector("li");
const ul = document.querySelector("ul");
const body = document.body;
// 事件冒泡,第三个参数默认是false
a.addEventListener("click", getTagName);
li.addEventListener("click", getTagName);
ul.addEventListener("click", getTagName);
body.addEventListener("click", getTagName);
// 事件捕获
a.addEventListener("click", getTagName, true);
li.addEventListener("click", getTagName, true);
ul.addEventListener("click", getTagName, true);
body.addEventListener("click", getTagName, true);
function getTagName() {
alert(this.tagName);
}
</script>
实际开发中多用于冒泡。
事件代理
事件代理的意义:通过非当前触发的事件代理当前触发事件,可以简化代码。
例如:
<body>
<ul>
<li>li1</li>
<li>li2</li>
<li>li3</li>
<li>li4</li>
<li>li5</li>
<li>li6</li>
<li>li7</li>
<li>li8</li>
</ul>
</body>
<script>
// 1.forEach()循环输出li内容
// const alla = document.querySelectorAll("li");
// alla.forEach(function (li) {
// li.addEventListener("click", function () {
// console.log(li.innerText);
// });
// });
// 2.利用事件代理输出li,用ul冒泡代理li的输出,ev:事件对象
document.querySelector("ul").addEventListener("mouseover", function (ev) {
// 返回当前正在触发事件的元素,这里是li
console.log(ev.target);
// 返回事件绑定的元素,这里是ul
console.log(ev.currentTarget);
});
</script>
这个案例使用了事件监听和冒泡代理的方式取代了传统的forEach()循环输出,更加符合逻辑要求。
实例:导航条下拉菜单
html代码:
<!DOCTYPE html>
<html lang="zh-cn">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link rel="stylesheet" href="style.css" />
<title>小刚的导航菜单demo</title>
</head>
<body>
<div class="nav">
<ul id="navbar" class="navbar">
<li class="link">
<a href="">首页</a>
</li>
<li class="link">
<a href="">技术论坛</a>
</li>
<li class="link">
<a href="">工具下载</a>
<ul id="page" class="page">
<li><a href="">PHP</a></li>
<li><a href="">HTML</a></li>
<li><a href="">CSS</a></li>
<li><a href="">JAVASCRIPT</a></li>
</ul>
</li>
<li class="link">
<a href="">手册下载</a>
<ul id="page" class="page">
<li><a href="">PHP</a></li>
<li><a href="">HTML</a></li>
<li><a href="">CSS</a></li>
<li><a href="">JAVASCRIPT</a></li>
</ul>
</li>
<li class="link">
<a href="">用户中心</a>
</li>
</ul>
</div>
</body>
<script>
// 获取下拉菜单
const navs = document.querySelectorAll("#navbar > li");
// 循环出每一个下拉菜单并添加鼠标划过与划出事件
navs.forEach(function (nav) {
nav.addEventListener("mouseover", showPage);
nav.addEventListener("mouseout", closePage);
});
// 为事件添加显示与隐藏方法(冒泡)
function showPage(ev) {
if (ev.target.nextElementSibling !== null) {
ev.target.nextElementSibling.style.display = "block";
}
}
function closePage(ev) {
if (ev.target.nextElementSibling !== null) {
ev.target.nextElementSibling.style.display = "none";
}
}
</script>
</html>
外部样式表 style.css
/**
层叠样式表
*/
* {
margin: 0;
padding: 0;
list-style: none;
}
a {
display: block;
height: 35px;
color: #898988;
text-decoration: none;
padding-top: 15px;
}
a:hover {
color: #e8e7e3;
background-color: #3f3f3f;
}
.nav {
position: fixed;
height: 50px;
width: 100%;
background-color: #e8e7e3;
box-shadow: 0 1px 1px rgb(154, 156, 156);
}
.navbar {
min-width: 1000px;
}
.link {
display: inline-block;
position: relative;
width: 100px;
text-align: center;
}
.page {
display: none;
position: absolute;
height: 200px;
width: 100px;
background-color: #e8e7e3;
}
.page li {
display: inline-block;
width: 100%;
}
实现效果
总结
- 理解 <a> 标签的作用;
- css定位方式 absolute和relative 的区别及应用;
- html页面dom事件对象的运用,例如:onclick;
- javascript事件对象的运用,例如:ev.target、ev.currentTarget;
- javascript监听器的作用;
- 理解事件冒泡与捕获的区别及影响DOM元素的问题;
ps:不知为何,我的关闭菜单代码 closePage()
不需要判断冒泡影响的父元素,有待研究,怀疑是CSS样式的原因,有兴趣研究的还请赐教。