js 原生仿淘宝放大镜效果
该效果主要模仿淘宝购物时的,当鼠标悬停于图片上端时,出现对应的放大模块,并且在附近区域显示对应的图片信息,主要运用到了 js 的监听鼠标在对应区域内的监听函数:
- onmouseenter 事件在鼠标指针移动到元素上时触发。
- onmouseover 事件会在鼠标指针移动到指定的元素上时发生。
- onmouseleave 事件在鼠标移除元素时触发
- onmousemove 事件会在鼠标指针移动时发生
制作过程
1. 定义对象
var biger = document.getElementById('biger');
var main = document.getElementById('main');
var smaller = document.getElementById('smaller');
var mask = document.getElementById('mask');
var wrap = biger.parentNode;
var imgArr = [{"path":"./images/banner1.jpg"},
{"path":"./images/banner2.jpg"},
{"path":"./images/banner3.jpg"},
{"path":"./images/banner4.jpg"},
{"path":"./images/banner5.jpg"}
];
var imgSum = imgArr.length;
if(imgSum > 5){imgSum = 5;}
2. 生成 Dom 元素,显示图片信息
insertBefore(_newnode,_existingnode)
- insertBefore(_newnode,_existingnode) 方法在您指定的已有子节点之前插入新的子节点
- 提示:如果您希望创建包含文本的新列表项,请记得创建文本节点形式的文本,以便追加到 LI 元素中,然后向列表插入这个 LI。
- _newnode:必需。需要插入的节点对象。
- _existingnode: 可选。在其之前插入新节点的子节点。如果未规定,则 insertBefore 方法会在结尾插入 newnode。
您也可以使用 insertBefore 方法插入 / 移动已有元素。
for (var i = 0; i<imgSum; i++){var lis = document.createElement('li');
var imgs = document.createElement('img');
imgs.src = imgArr[i].path;
lis.appendChild(imgs);
smaller.appendChild(lis);
}
var mainImg = document.createElement('img');
var bigImg = document.createElement('img');
var liArr = smaller.children;
bigImg.src = mainImg.src = liArr[0].children[0].src;
main.insertBefore(mainImg,mask);
biger.appendChild(bigImg);
3. 点击事件,切换图片信息
removeAttribute()
- removeAttribute() 方法删除指定的属性。
- 此方法与 removeAttributeNode() 方法的差异是:removeAttributeNode() 方法删除指定的 Attr 对象,而此方法删除具有指定名称的属性。结果是相同的。同时此方法不返回值,而 removeAttributeNode() 方法返回被删除的属性,以 Attr 对象的形式。
var bigPic = biger.children[0];
liArr[0].className = 'current';
for (var i=0; i<liArr.length;i++){liArr[i].index = i;
liArr[i].onclick = function () {
this.className = 'current';
bigPic.src = main.children[0].src = this.children[0].src;
for (var j = 0; j < liArr.length; j++) {if(this!=liArr[j]){liArr[j].removeAttribute('class');
liArr[j].removeAttribute('className');
}
}
}
}
4. 监听鼠标移动,显示放大效果
main.onmouseenter = function () {
mask.style.display = 'block';
biger.style.display = 'block';
}
main.onmouseleave=function(){
mask.style.display='none';
biger.style.display='none';
}
main.onmousemove = function (e) {
var e = e || window.event;
var pagex = e.pageX || scroll().left + e.clientX;
var pagey = e.pageY || scroll().top + e.clientY;
pagex = pagex - wrap.offsetLeft - mask.offsetWidth / 2;
pagey = pagey - wrap.offsetTop - mask.offsetHeight / 2 ;
if(pagex<0){pagex=0;}
if(pagey<0){pagey=0;}
if(pagex>main.offsetWidth-mask.offsetWidth){pagex=main.offsetWidth-mask.offsetWidth;}
if(pagey>main.offsetHeight-mask.offsetHeight){pagey=main.offsetHeight-mask.offsetHeight;}
mask.style.left=pagex+'px';
mask.style.top=pagey+'px';
var scale=(bigPic.offsetWidth-biger.offsetWidth)/(main.offsetWidth-mask.offsetWidth);
var xx=pagex*scale;
var yy=pagey*scale;
bigPic.style.left=-xx+'px';
bigPic.style.top=-yy+'px';
}
获取鼠标的位移点位(x,y)
var pagex = e.pageX || scroll().left + e.clientX;
var pagey = e.pageY || scroll().top + e.clientY;
pagex = pagex - wrap.offsetLeft - mask.offsetWidth / 2;
pagey = pagey - wrap.offsetTop - mask.offsetHeight / 2 ;
设置移动范围,不允许超出图片部分
if(pagex<0){pagex=0;}
if(pagey<0){pagey=0;}
if(pagex>main.offsetWidth-mask.offsetWidth){pagex=main.offsetWidth-mask.offsetWidth;}
if(pagey>main.offsetHeight-mask.offsetHeight){pagey=main.offsetHeight-mask.offsetHeight;}
设置放大区域:移动放大图片的位置(top,left)
mask.style.left=pagex+'px';
mask.style.top=pagey+'px';
var scale=(bigPic.offsetWidth-biger.offsetWidth)/(main.offsetWidth-mask.offsetWidth);
var xx=pagex*scale;
var yy=pagey*scale;
bigPic.style.left=-xx+'px';
bigPic.style.top=-yy+'px';
js 源码
window.onload = function () {var biger = document.getElementById('biger');
var main = document.getElementById('main');
var smaller = document.getElementById('smaller');
var mask = document.getElementById('mask');
var wrap = biger.parentNode;
var imgArr = [{"path":"./images/banner1.jpg"},
{"path":"./images/banner2.jpg"},
{"path":"./images/banner3.jpg"},
{"path":"./images/banner4.jpg"},
{"path":"./images/banner5.jpg"}
];
var imgSum = imgArr.length;
if(imgSum > 5){imgSum = 5;}
for (var i = 0; i<imgSum; i++){var lis = document.createElement('li');
var imgs = document.createElement('img');
imgs.src = imgArr[i].path;
lis.appendChild(imgs);
smaller.appendChild(lis);
}
var mainImg = document.createElement('img');
var bigImg = document.createElement('img');
var liArr = smaller.children;
bigImg.src = mainImg.src = liArr[0].children[0].src;
main.insertBefore(mainImg,mask);
biger.appendChild(bigImg);
var bigPic = biger.children[0];
liArr[0].className = 'current';
for (var i=0; i<liArr.length;i++){liArr[i].index = i;
liArr[i].onclick = function () {
this.className = 'current';
bigPic.src = main.children[0].src = this.children[0].src;
for (var j = 0; j < liArr.length; j++) {if(this!=liArr[j]){liArr[j].removeAttribute('class');
liArr[j].removeAttribute('className');
}
}
}
}
main.onmouseenter = function () {
mask.style.display = 'block';
biger.style.display = 'block';
}
main.onmouseleave=function(){
mask.style.display='none';
biger.style.display='none';
}
main.onmousemove = function (e) {
var e = e || window.event;
var pagex = e.pageX || scroll().left + e.clientX;
var pagey = e.pageY || scroll().top + e.clientY;
pagex = pagex - wrap.offsetLeft - mask.offsetWidth / 2;
pagey = pagey - wrap.offsetTop - mask.offsetHeight / 2 ;
if(pagex<0){pagex=0;}
if(pagey<0){pagey=0;}
if(pagex>main.offsetWidth-mask.offsetWidth){pagex=main.offsetWidth-mask.offsetWidth;}
if(pagey>main.offsetHeight-mask.offsetHeight){pagey=main.offsetHeight-mask.offsetHeight;}
mask.style.left=pagex+'px';
mask.style.top=pagey+'px';
var scale=(bigPic.offsetWidth-biger.offsetWidth)/(main.offsetWidth-mask.offsetWidth);
var xx=pagex*scale;
var yy=pagey*scale;
bigPic.style.left=-xx+'px';
bigPic.style.top=-yy+'px';
}
};
该文章主要是在淘宝上看到页面效果后,进行模拟开发的,主要的点在于鼠标的监听事件以及显示模块位置的设置,希望这篇文章对大家会有帮助,并且多多点赞,感谢!github 地址