JS实现页面侧边栏效果探究


Posted in Javascript onJanuary 08, 2021

其实效果大概是这样的:

JS实现页面侧边栏效果探究

而标题,也许是我当时看到这种效果时的真实感受。因为第一反应是:“还可以把page整体移出页面?”

发现:display动画的应用

整件事的起因是什么呢?在笔者最近为社团计划的官网上打算做一个这样的效果:点击头像,左边/右边滑出一个“面板”,里面展示用户的个人信息。

当然,这有很多种做法,比如:利用position定位+overflow溢出隐藏、利用opacity/visibility隐藏+pointer-events元素穿透… 但是笔者当时想到的是如何给”真正的隐藏,display“加上动画!

我们大概都知道的是:HTML渲染过程中有一个可能执行的、影响页面性能的“回流”和“重绘”的过程。导致这个过程被触发的原因有很多:元素位置移动、大小改变、增删节点以及这里要说的display显示与隐藏切换等等。而元素的变动需要页面快速的显示出来,所以在我们看来是“突兀”的。
而且有一点需要注意的是:浏览器是“有点智能”的 —— 它可以判断如果会触发页面回流的代码有很多,那么它会将这些代码都读取完再(合并)一起执行,所以这也是下面这段代码会有如下图效果的原因:

/** css代码 */
width: 50px;
height: 50px;
background-color: red;
display: none;
transform: translateX(0);
transition: all .6s ease; //似乎没用?
//js代码
ds.style.display="block";
ds.style.transform="translateX(100px)";

JS实现页面侧边栏效果探究

但是同样的,当对以下属性进行操作的时候,由于浏览器的渲染机制有一些API可以使页面强制渲染(因为要获得详细确切的信息),包括:offsetTop、offsetLeft、 offsetWidth、offsetHeight、scrollTop、scrollLeft、scrollWidth、scrollHeight、clientTop、clientLeft、clientWidth、clientHeight、getComputedStyle() (currentStyle in IE)。这会直接导致前后两行相当于“渲染了两遍”。

所以将上方js代码改为下面这样:

//js代码
ds.style.display="block";
ds.offsetHeight;
ds.style.transform="translateX(100px)";

就可以了

JS实现页面侧边栏效果探究
目前csdn官网PC端blink发布页面的图片上传就用了类似这个功能!

后来还是觉得这种方式需要涉及js对页面结构的改变,于是乎…

实现:如何实现文首展示的效果

这基于position定位是会“重合”的:在两个行内元素都设置了定位属性(但没有加top/left/bottom/right定位)后,后面的会覆盖前面的;这时候可以通过margin移动位置展示

只能是行内元素,行内块元素都不行。 ——云小梦

它大概结构是这样的:

<div class="page_list">
	<div class="z_two_page">
		<!-- 这里放右侧弹框展示的信息 -->
	</div>
	<div class="box">
		<!-- "页面"的遮罩层 -->
		<div class="zb_mask"></div>
		<!-- 这里放“页面”数据结构(也就是原本应该在body标签下的所有东西) -->
	</div>
	<!-- 这是占位元素 -->
	<div class="space"></div>
</div>

实际就像这样的:

<div class="page_list">
	<div class="z_two_page">哈哈哈</div>
	<div class="box">
		<div class="zb_mask"></div>
		
		<div id="boxs">
		 <div class="left" style="background-color:#ffc5c5;"></div>
		 <div class="right" style="background-color:#7171f7;">
			 flex下两列布局左边固定右边宽高自适应
		 </div>
		</div>
		<div class="color"></div>
		<a href="#" rel="external nofollow" class="a">千万小心像对a设置全局样式(这叫啥样式重置)</a>
		<div class="center">
			<div class="ds"></div>
			<button class="but">到指定地点</button>
		</div>
		<form id="form" action="#">
			<input type="submit" value="="踢脚板 />
		</form>
		<img id="img" src="compress/compress/img/mxc_16x16.png" />
	</div>
	
	<div class="space"></div>
</div>

如上,class为“box”的div里面放的就是“原本的页面整体”部分。为了达到想要的效果,我们采用了flex布局!

flex简写时包括三个属性:flex-grow、flex-shrink和flex-basis ——

  • flex-grow:指定了容器剩余空间多余时候的分配规则,默认值是0,多余空间不分配;
  • flex-shrink:指定了容器剩余空间不足时候的分配规则,默认值是1,空间不足要分配;
  • flex-basis:flex-basis则是指定了固定的分配数量,默认值是auto。

设置的同时需设置width或者height属性;

/* 列表仅水平滚动 */
.page_list { width: 100vw; display: flex; overflow-y: hidden; }
/* 主内容宽度100%,白色背景覆盖 */
.box { flex: 0 0 100vw; height: 100%; background-color: #fff; position: relative; overflow-y: auto;overflow-x: hidden;transition: all .6s ease; }
/** 遮罩层样式 */
.zb_mask{
	position: absolute;
	top: 0;
	left: 0;
	width: 100%;
	height: 100%;
	z-index: 100;
	background-color: rgba(0,0,0,.2);
	pointer-events: none;
	opacity: 0;
	transition: all .6s ease;
}
/* 空标签元素,作用是腾出水平滚动空间 */
.space { flex: 0 0 12rem; }
/* 按钮固定定位,藏在内容白色背景后面 */
.z_two_page { width: 12rem; position: fixed; right: 0; top: 0; }

大概就是:什么也不干的情况下只展示box的内容(也就是和不加这些花里胡哨的div一样的效果),它是用background覆盖后面的class为“space”的占位元素;在”哈哈哈“展示的时候,box右移。

这里需要注意的是:为什么“哈哈哈”所属div在前而“页面”所属div在后?
因为根据前面所说,这里采用的是position覆盖,它的规则就是“后面的覆盖前面的”,所以如果采用这种布局方式,那么一开始被隐藏的元素就要放在前面。

代码中flex的前两个属性值为0,表示在空间增大或缩小时依然保持原状(这是本文的基础!),第三个元素则写了展示时的“默认大小”:如你所看,box承载的是页面,所以它是100vw,而class为“z_two_page”的元素这里设置了12rem ,你完全可以将这个值换掉!

那如何将“哈哈哈”展示在视野中? —— js控制“代表页面的元素”整体移动即可。

这里有个“遮罩层效果”,按照传统的js实现肯定就要去找display了,再进一步可以用上面所说的“display动画效果”增强体验。
但是本文上面css代码中加了 pointer-events 属性:元素是否穿透;设置为none时就可以不用在意对应元素是否存在了(从事件上看此时有和没有一样了),也就不用控制display什么的,大大增强性能了有木有!

let right=document.querySelector(".right");
let box=document.querySelector(".box");
let mask=document.querySelector(".zb_mask");
right.onclick=function(){
 box.style.marginLeft="-12rem";
 mask.style.cssText+="opacity: 1;pointer-events: all;"
}
mask.onclick=function(){
 box.style.marginLeft="0";
 mask.style.cssText+="opacity: 0;pointer-events: none;"
}

最后,考虑到移动端页面展示的一些问题,比如:右侧留白问题、原生手势对页面整体的影响等,我们一般会在css中设置 html{max-width: 100vw;overflow-x: hidden;} 。如果你想要用户在移动端依然只能够通过点击弹出侧边栏,在这里我们可以在css中加上限制 —— 设置上方功能只有在PC端生效:

@media (any-hover: none) {
	.page_list{
		overflow-x: hidden;
	}
}

到此这篇关于JS实现页面侧边栏效果探究的文章就介绍到这了,更多相关js页面侧边栏内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Javascript 相关文章推荐
jQuery 动画弹出窗体支持多种展现方式
Apr 29 Javascript
javascript setAttribute, getAttribute 在不同浏览器上的不同表现
Aug 05 Javascript
16个最流行的JavaScript框架[推荐]
May 29 Javascript
JS常用正则表达式总结
Nov 12 Javascript
浅析document.ready和window.onload的区别讲解
Dec 18 Javascript
使用GruntJS构建Web程序之安装篇
Jun 04 Javascript
点击标签切换和自动切换DIV选项卡
Aug 10 Javascript
利用a标签自动解析URL分析网址实例
Oct 20 Javascript
如何解决hover在ie6中的兼容性问题
Dec 15 Javascript
express+mockjs实现模拟后台数据发送功能
Jan 07 Javascript
js判断鼠标移入移出方向的方法
Jun 24 Javascript
详解vue中在父组件点击按钮触发子组件的事件
Nov 13 Javascript
antdesign-vue结合sortablejs实现两个table相互拖拽排序功能
Jan 08 #Vue.js
vue-quill-editor插入图片路径太长问题解决方法
Jan 08 #Vue.js
详解Typescript里的This的使用方法
Jan 08 #Javascript
Node.js 中如何收集和解析命令行参数
Jan 08 #Javascript
vue编写简单的购物车功能
Jan 08 #Vue.js
three.js中多线程的使用及性能测试详解
Jan 07 #Javascript
解决vue使用vant轮播组件swipe + flex时文字抖动问题
Jan 07 #Vue.js
You might like
10个实用的PHP代码片段
2011/09/02 PHP
php微信公众平台开发类实例
2015/04/01 PHP
ThinkPHP控制器详解
2015/07/27 PHP
WordPress中自定义后台管理界面配色方案的小技巧
2015/12/29 PHP
JAVASCRIPT keycode总结
2009/02/04 Javascript
JavaScript 实现模态对话框 源代码大全
2009/05/02 Javascript
js window.onload 加载多个函数的方法
2009/11/02 Javascript
input 输入框内的输入事件详细分析
2010/03/17 Javascript
Nodejs实现批量下载妹纸图
2015/05/28 NodeJs
nodejs爬虫抓取数据之编码问题
2015/07/03 NodeJs
浅谈JavaScript超时调用和间歇调用
2015/08/30 Javascript
JS+CSS实现精美的二级导航效果代码
2015/09/17 Javascript
原生js实现图片层叠轮播切换效果
2016/02/02 Javascript
浅谈JavaScript中的this指针和引用知识
2016/08/05 Javascript
概述BootStrap中role=&quot;form&quot;及role作用角色
2016/12/08 Javascript
Angular ng-repeat遍历渲染完页面后执行其他操作详细介绍
2016/12/13 Javascript
使用jQuery操作DOM的方法小结
2017/02/27 Javascript
Bootstrap实现的标签页内容切换显示效果示例
2017/05/25 Javascript
Vue.js中的组件系统
2019/05/30 Javascript
JS Html转义和反转义(html编码和解码)的实现与使用方法总结
2020/03/10 Javascript
15分钟上手vue3.0(小结)
2020/05/20 Javascript
JavaScript forEach中return失效问题解决方案
2020/06/01 Javascript
详解Vue之事件处理
2020/07/10 Javascript
[01:32]DOTA2次级联赛——首支职业女子战队选拔赛全记录
2014/10/23 DOTA
使用Python的urllib2模块处理url和图片的技巧两则
2016/02/18 Python
在CentOS上配置Nginx+Gunicorn+Python+Flask环境的教程
2016/06/07 Python
python生成密码字典的方法
2018/07/06 Python
pycham查看程序执行的时间方法
2018/11/29 Python
python使用writerows写csv文件产生多余空行的处理方法
2019/08/01 Python
Numpy与Pytorch 矩阵操作方式
2019/12/27 Python
Python Scrapy框架第一个入门程序示例
2020/02/05 Python
Python中itertools的用法详解
2020/02/07 Python
Python面向对象程序设计之继承、多态原理与用法详解
2020/03/23 Python
MaBelle玛贝尔香港官网:香港钻饰连锁店
2019/09/09 全球购物
防暑降温通知书
2015/04/27 职场文书
幼儿园托班开学寄语(2016春季)
2015/12/03 职场文书