JavaScript满天星导航栏实现方法


Posted in Javascript onMarch 08, 2018

说明

分享一个满天星导航栏的效果,代码不多,但效果挺好看,先看看效果图吧。

JavaScript满天星导航栏实现方法

解释

实现这个效果,需要掌握的知识不用很多,知道简单的CSS,会用JS 获取元素, 能绑定事件基本就足够了。
好的,我们直接来看代码,注释已经写的很详细了,不想看有注释的,点这里点击预览。

<!doctype html>
<html lang="en">
 <head>
 <meta charset="UTF-8">
 <style>
body {
 background-color: #000;
 /* 防止出现左右的滚动条 */
 overflow: hidden;
 margin: 0;
 padding: 0;
}
.wrapper {
 width: 100%;
 height: 100px;
}
.wrapper .nav {
 list-style: none;
 width: 800px;
 height: 100px;
 padding: 0;
 margin: 0 auto;
}
.wrapper .nav li {
 width: 25%;
 height: 50px;
 float: left;
 margin-top: 25px;
}
.wrapper .nav li a {
 text-decoration: none;
 color: #fff;
 text-align: center;
 line-height: 50px;
 display: block;
 font-size: 20px;
 font-family: "KaiTi";
}

/* 闪烁的星星 的基本样式 */
.star {
 width: 5px;
 height: 5px;
 background: #fff;
 position: absolute;
 z-index: -1;
}

/* 闪烁动画,改变透明度 */
@keyframes blink {
 from {
 opacity: 0.2;
 }
 to {
 opacity: 1;
 }
}
</style>
 </head>
 <body>
 <div class="wrapper">
  <ul class="nav">
  <li><a href="#" rel="external nofollow" rel="external nofollow" rel="external nofollow" rel="external nofollow" >导航1</a></li>
  <li><a href="#" rel="external nofollow" rel="external nofollow" rel="external nofollow" rel="external nofollow" >导航2</a></li>
  <li><a href="#" rel="external nofollow" rel="external nofollow" rel="external nofollow" rel="external nofollow" >导航3</a></li>
  <li><a href="#" rel="external nofollow" rel="external nofollow" rel="external nofollow" rel="external nofollow" >导航4</a></li>
  </ul>
 </div>
<script>

// 定义一个 starrySky 对象
var starrySky = {
 // 星星的数量
 starNum: 100,

 // 星星的大小,返回一个 2 ~ 12 的随机数
 starSize () { return 2 + Math.trunc(Math.random() * 10) },

 // 星星的颜色 
 starColor: "#fff",

 // 线的颜色,鼠标进入导航区域,星星会连成一条线
 lineColor: "#fff",

 // 线的高度
 lineHeight: "3px",

 // 星星连成线的时间
 changeTime: "1s",

 // 初始化方法,生成需要的星星,并调用需要的方法
 init () {
 var html = "";
 // 循环生成星星
 for (var i = 0; i < this.starNum; i++) {
 html += "<div class='star' id='star" + i + "'></div>";
 }
 // 拼接到 元素wrapper 中
 document.querySelector(".wrapper").innerHTML += html;

 // 调用 星星分散 的方法
 this.disperse();

 // 调用 星星聚合连成线 的方法 
 this.combine();
 },
 disperse () {
 // 这个that 保存的是 starrySky 对象
 var that = this;

 // 获取 元素wrapper 的宽度
 var width = document.querySelector('.wrapper').offsetWidth;
 // 获取 元素wrapper 的高度
 var height = document.querySelector('.wrapper').offsetHeight;
 // 循环,开始在元素wrapper 区域内,生成规定数量的 星星,
 for (var i = 0; i < that.starNum; i++) {
 // 星星的 top值,0 ~ 元素wrapper 高度的随机数
 var top = Math.trunc(height * Math.random());
 // 星星的 left值,0 ~ 元素wrapper 宽度的随机数
 var left = Math.trunc(width * Math.random());
 // 星星的大小,调用 starrySky对象的starSize()方法
 var size = that.starSize();
 // 设置分散时每个星星样式
 document.querySelector("#star" + i).style.cssText += `
   top:${top}px;
   left:${left}px;
   width:${size}px;
   height:${size}px;
   background:${that.starColor};
   opacity:${Math.random()};
   border-radius:50%;
   animation:blink 1s ${Math.random() * 2}s infinite alternate;
   `;
 }
 },
 combine () {
 // 这个that 保存的是 starrySky 对象
 var that = this;
 // 查找导航栏 里所有的 a元素,遍历他们,每个都绑定上 鼠标进入 和 鼠标移出 事件
 document.querySelectorAll(".nav li a").forEach(function (item) {
 item.addEventListener("mouseover", function (e) {
 // 这里的this 是触发事件的当前节点对象,就是鼠标进入时候的 a元素
 // 当前a元素的宽度 / 星星数 = 最后连成线时,星星的宽度
 var width = this.offsetWidth / that.starNum;
 // 遍历,为每个星星修改样式,开始连成线
 for (var i = 0; i < that.starNum; i++) {
  // 星星的top 值就是,当前a元素的距离顶部的值 + 当前a元素的高度
  var top = this.offsetTop + this.offsetHeight;
  // 星星的left 值就是,当前a元素的距离左边界的值 + 第i个星星 * 星星的宽度
  var left = this.offsetLeft + i * width
  // 设置每个星星连成线时的样式
  document.querySelector("#star" + i).style.cssText += `
     width:${width}px;
     top:${top}px;
     left:${left}px;
     height:${that.lineHeight};
     background:${that.lineColor};
     opacity:1;
     border-radius:0;
     transition:${that.changeTime};
     animation:blink 1s infinite alternate;
    `;
 }
 });
 // 鼠标移出 调用 星星分散 的方法
 item.addEventListener("mouseout", function () {
 that.disperse();
 });
 }
 );
 },

}
// 调用 starrySky对象的 init方法,实现满天星效果
starrySky.init();
</script>
 </body>
</html>

注意:如果需要修改样式,不要把 nav元素 和 nav 里面的 li元素,给定位了,因为最后线的位置是根据 a元素的 offsetHeight 和 offsetLeft 定位的,如果 nav元素 和 nav 里面的 li元素 定位了,会改变 a元素的offsetParent元素,位置就不对了。

对offsetHeight、offsetLeft 和 offsetParent 不理解的点这里:https://codepen.io/FEWY/pen/MQdoWX

总结

实现这个效果,就是做了一个 starrySky对象,定义好一些必须的属性,主要靠 disperse() 和 combine() 两个方法,需要星星分散的时候调用disperse(),需要星星连成线的时候调用combine(),好的就这样了。

Javascript 相关文章推荐
javascript 24小时弹出一次的代码(利用cookies)
Sep 03 Javascript
js 页面传参数时 参数值含特殊字符的问题
Dec 13 Javascript
JQuery里选择超链接的实现代码
May 22 Javascript
js 函数的副作用分析
Aug 23 Javascript
IE与FireFox中的childNodes区别
Oct 20 Javascript
如何在Angular.JS中接收并下载PDF
Nov 26 Javascript
JS实现的DOM插入节点操作示例
Apr 04 Javascript
微信小程序之多列表的显示和隐藏功能【附源码】
Aug 06 Javascript
layui 设置table 行的高度方法
Aug 17 Javascript
iView框架问题整理小结
Oct 16 Javascript
Echarts实现单条折线可拖拽效果
Dec 19 Javascript
js键盘事件实现人物的行走
Jan 17 Javascript
vue.js的computed,filter,get,set的用法及区别详解
Mar 08 #Javascript
详解从买域名到使用pm2部署node.js项目全过程
Mar 07 #Javascript
layui select动态添加option的实例
Mar 07 #Javascript
layui表格checkbox选择全选样式及功能的实例
Mar 07 #Javascript
Bootstrap实现可折叠分组侧边导航菜单
Mar 07 #Javascript
Vue.js+Layer表格数据绑定与实现更新的实例
Mar 07 #Javascript
vue.js 嵌套循环、if判断、动态删除的实例
Mar 07 #Javascript
You might like
特转载一高手总结PHP学习资源和链接.
2006/12/05 PHP
php 网上商城促销设计实例代码
2012/02/17 PHP
php ajax实现文件上传进度条
2016/03/29 PHP
PHP判断用户是否已经登录(跳转到不同页面或者执行不同动作)
2016/09/22 PHP
javascript encodeURI和encodeURIComponent的比较
2010/04/03 Javascript
jquery快捷动态绑定键盘事件的操作函数代码
2013/10/17 Javascript
JQuery报错Uncaught TypeError: Illegal invocation的处理方法
2015/03/13 Javascript
利用JS生成博文目录及CSS定制博客
2016/02/10 Javascript
JS函数定义方式的区别介绍
2016/03/22 Javascript
javascript类型系统_正则表达式RegExp类型详解
2016/06/24 Javascript
JS+CSS3实现超炫的散列画廊特效
2016/07/16 Javascript
关于Javascript回调函数的一个妙用
2016/08/29 Javascript
js中string和number类型互转换技巧(分享)
2016/11/28 Javascript
用move.js库实现百叶窗特效
2017/02/08 Javascript
关于javascript作用域的常见面试题分享
2017/06/18 Javascript
Vue 仿QQ左滑删除组件功能
2018/03/12 Javascript
微信小程序使用wxParse解析html的方法示例
2019/01/17 Javascript
Vue渲染过程浅析
2019/03/14 Javascript
js实现简单掷骰子小游戏
2019/10/24 Javascript
前端深入理解Typescript泛型概念
2020/03/09 Javascript
[55:02]2014 DOTA2国际邀请赛中国区预选赛 HGT VS Orenda
2014/05/21 DOTA
python实现爬取图书封面
2018/07/05 Python
python读取有密码的zip压缩文件实例
2019/02/08 Python
python使用thrift教程的方法示例
2019/03/21 Python
Python 多线程其他属性以及继承Thread类详解
2019/08/28 Python
python使用梯度下降算法实现一个多线性回归
2020/03/24 Python
opencv+python实现鼠标点击图像,输出该点的RGB和HSV值
2020/06/02 Python
增大python字体的方法步骤
2020/07/05 Python
ivx平台开发之不用代码实现一个九宫格抽奖功能
2021/01/27 HTML / CSS
Mountain Warehouse德国官网:英国户外零售商
2019/08/11 全球购物
家长给幼儿园的表扬信
2014/01/09 职场文书
毕业生面试求职信
2014/06/23 职场文书
医学检验专业自荐信
2014/09/18 职场文书
整脏治乱工作简报
2015/07/21 职场文书
2019年浪漫婚礼证婚词
2019/06/27 职场文书
MySQL root密码的重置方法
2021/04/21 MySQL