序
大家在网购的时候一定没少用过此功能吧~ 某宝某猫某东, 在 PC 端所有商品的展示均是如此: 鼠标放在缩略图上, 旁边便会有细节图展示出来, 并随鼠标移动展示相应缩略图细节. 下面我用 JS(jq) 来展示一下, 并且加入一丢丢的动态边框效果.
效果
电商放大镜. gif
环境及语言
思路
放大镜
缩略图及细节图布局
鼠标划入事件: 鼠标放在缩略图, 出现小的蒙层和细节图; 当鼠标移动, 细节图随之变化
鼠标及蒙层边界判断处理
鼠标移除事件: 隐藏蒙蒙层及细节图
动态边框
鼠标悬浮, 边框出现
鼠标移除, 边框消失
那么问题来了, 细节图怎么随鼠标变化? 边框以何种形式展现?
实现
由浅入深, 我先来实现动态边框
1. 动态边框
效果
动态边框. gif
思路
看到该效果, 一般思路有二:
设置 border
周边 4 个 div
但是以上两个思路均有问题. 如果设置 border, 如何使其边框动画? 如果周边设置 4 个 div, 那么不仅是需要 JS 操控, 并且无形之中增加了许多复杂度, 与编程思想背道而驰.
那么我们还有别的办法来处理使边框动起来吗? 首先, 动画是一定要有的. 其次, 如果不能用 border, 那么用 background 怎么样呢? just do it.
新属性 linear-gradient() 函数
inear-gradient 函数作为 css3 新属性, 用于创建一个线性渐变的 "图像". 你还要定义终止色. 终止色就是你想让 Gecko 去平滑的过渡, 并且你必须指定至少两种, 当然也会可以指定更多的颜色去创建更复杂的渐变效果.
代码
- // HTML
- <div class="transBorder">
- here
- </div>
- // CSS
- .transBorder {
- margin: 0 15px;
- cursor: pointer;
- display: block;
- width: 200px;
- height: 200px;
- text-align: center;
- line-height: 200px;
- transition: ease-in .4s;
- background: linear-gradient(0, #108b96 2px, #009606 2px) no-repeat,
- linear-gradient(-90deg, #96645f 2px, #961478 2px) no-repeat,
- linear-gradient(-180deg, #869660 2px, #544996 2px) no-repeat,
- linear-gradient(-270deg, #439638 2px, #308e96 2px) no-repeat;
- background-size: 0 2px, 2px 0, 0 2px, 2px 0;
- background-position: left top, right top, right bottom, left bottom;
- }
- .transBorder:hover {
- border-radius: 20%;
- background-size: 100% 5px , 5px 100%, 100% 5px, 5px 100%;
- }
2. 放大镜
效果
电商放大镜. PNG
思路
鼠标移入
显示蒙层及细节图
指定蒙层位置
为蒙层及细节图做相关计算, 如蒙层中心, 细节图走向等
鼠标及蒙层边界判断及处理
细节图展示及变化
鼠标移除
蒙层及细节图隐藏
代码
- // HTML
- <div class="small">
- <div id="small">
- <img src="./img/small.png" alt=""width="100%">
- <div id="modal"></div>
- </div>
- </div>
- <div id="big">
- <img src="./img/big.png" alt=""id="bigImg">
- </div>
- // CSS
- // ... 略
- // JS
- $('#small').mousemove((e) => {
- // 显示大图区域
- $('#big, #modal').fadeIn(500);
- // 指定蒙层位置, 随鼠标变化
- let x = e.clientX - $('#small').offset().left - $("#modal").width() / 2 + 'px';
- var y = e.clientY - $("#small").offset().top - $("#modal").height() / 2 + 'px';
- $('#modal').CSS({'top': y, 'left': x});
- // 小图和蒙层的宽高差
- let maxW = $('#small').width() - $('#modal').width();
- let maxH = $('#small').height() - $('#modal').height();
- // 蒙层距离小图边界值
- var l = $('#modal').offset().left - $('#small').offset().left; // 蒙层距离左边界距离
- var t = $('#modal').offset().top - $('#small').offset().top; // 蒙层距离上边界距离
- // 边界判断
- // 到达左边距 固定 left
- if (l <0){
- $('#modal').CSS('left', '0');
- }
- // 到达上边距 固定 top
- if (t < 0){
- $('#modal').CSS('top', '0');
- }
- // 到达右边距 固定 left
- if (l>= maxW){
- $('#modal').CSS('left', maxW);
- }
- // 到达下边距 固定 top
- if (t>= maxH){
- $('#modal').CSS('top', maxH);
- }
- // 鼠标滑动轨迹及大图相应变化
- let l1 = ($('#modal').offset().left - $('#small').offset().left) <0 ? 0 : ($('#modal').offset().left - $('#small').offset().left);
- let t1 = ($('#modal').offset().top - $('#small').offset().top) < 0 ? 0 : ($('#modal').offset().top - $('#small').offset().top);
- let scaleX = (l1 / maxW) * ($('#big').width() - $('#bigImg').width()) + 'px';
- let scaleY = (t1 / maxW) * ($('#big').height() - $('#bigImg').height()) + 'px';
- $('#bigImg').CSS({'left': scaleX,'top': scaleY});
- }).mouseleave(() => {
- // 鼠标离开小图, 大图消失
- $('#big, #modal').fadeOut(500);
- })
来源: http://www.jianshu.com/p/160645b67122