相信大家应该都有在京东上买过东西,那么大家在买东西的时候一定见到过图片放大的特效,就像是这样的效果:
其实这个效果的原理也很简单,就是我们要准备两张尺寸比例一样的图片,一张小图,一张大图,当鼠标移动到小图上面时,大图显示出相应的部分来。
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档title>
<style>
#div1 {
width:180px;
height:180px;
overflow:hidden;
position:relative; /* 黄色遮罩相对于#div1进行绝对定位 */
}
#div1 span {
width:100px;
height:100px;
background:yellow;
opacity:0.5;
filter:alpha(opacity=50);
position:absolute; /* 黄色遮罩绝对定位才能跟随鼠标移动 */
left:0;
top:0;
display:none; /* 鼠标移入图片后才显示黄色遮罩 */
}
/*
消除mouseover和mouseout事件子级对父级的影响
(阻止事件冒泡不能消除子级对父级的影响,所以在黄色遮罩和图片之间加个透明的隔离层)
*/
#mark {
width:180px;
height:180px;
background:red;
position:absolute;
left:0;
top:0;
opacity:0;
filter:alpha(opacity=0);
cursor: move;
}
#div2 {
width:500px;
height:500px;
position:absolute;
left:250px;
top:50px;
overflow:hidden;
}
#div2 img {
position:absolute;
left:0;
top:0;
}
style>
<script>
window.onload = function() {
var oDiv = document.getElementById('div1');
var oSpan = oDiv.getElementsByTagName('span')[0];
var oDiv2 = document.getElementById('div2');
var img2 = oDiv2.getElementsByTagName('img')[0];
oDiv.onmouseover = function(){
oSpan.style.display = 'block';
};
oDiv.onmouseout = function(){
oSpan.style.display = 'none';
};
// 要想元素跟着鼠标移动要绑定mousemove事件
oDiv.onmousemove = function(ev){
var ev = ev || window.event;
/*
ev.clientX、ev.clientY获取鼠标坐标
oDiv.offsetLeft: oDiv距离屏幕左侧的距离
oDiv.offsetTop: oDiv距离屏幕顶部的距离
oSpan.offsetWidth: offsetWidth返回对象的padding+border+width属性值之和
*/
var L = ev.clientX - oDiv.offsetLeft - oSpan.offsetWidth/2; // 将黄色遮罩中部移到鼠标位置
var T = ev.clientY - oDiv.offsetTop - oSpan.offsetHeight/2; // 将黄色遮罩中部移到鼠标位置
/* 限制黄色遮罩层的移动范围START */
if(L<0){
L = 0;
}
else if(L>oDiv.offsetWidth - oSpan.offsetWidth){
L = oDiv.offsetWidth - oSpan.offsetWidth;
}
if(T<0){
T = 0;
}
else if(T>oDiv.offsetHeight - oSpan.offsetHeight){
T = oDiv.offsetHeight - oSpan.offsetHeight;
}
oSpan.style.left = L + 'px';
oSpan.style.top = T + 'px';
/* 限制黄色遮罩层的移动范围END */
/*
oDiv.offsetWidth - oSpan.offsetWidth 黄色遮罩能够移动的最大宽度
oDiv.offsetHeight - oSpan.offsetHeight 黄色遮罩能够能够移动的最大高度
*/
var scaleX = L/(oDiv.offsetWidth - oSpan.offsetWidth); // 移动的比例 0 ~ 1
var scaleY = T/(oDiv.offsetHeight - oSpan.offsetHeight); // 移动的比例 0 ~ 1
/*
大图的移动方向要和黄色遮罩(鼠标)移动方向相反
img2.offsetWidth - oDiv2.offsetWidth 大图能够移动的最大宽度
img2.offsetHeight - oDiv2.offsetHeight 大图能够移动的最大高度
*/
img2.style.left = - scaleX * (img2.offsetWidth - oDiv2.offsetWidth) + 'px';
img2.style.top = - scaleY * (img2.offsetHeight - oDiv2.offsetHeight) + 'px';
};
};
script>
head>
<body>
<div id="div1">
<img src="b2.jpg">
<span>span>
<div id="mark">div>
div>
<div id="div2">
<img src="b1.jpg">
div>
body>
html>
我们需要注意的是,以上代码是通过css的方法添加一个隔离层来消除子级对父级的影响的,其实,我们也可以用js的方法来解决这个bug,就是用mouseenter和mouseleave事件来代替mouseover和mouseout事件。
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档title>
<style>
#div1 {
width:180px;
height:180px;
overflow:hidden;
position:relative; /* 黄色遮罩相对于#div1进行绝对定位 */
}
#div1 span {
width:100px;
height:100px;
background:yellow;
opacity:0.5;
filter:alpha(opacity=50);
position:absolute; /* 黄色遮罩绝对定位才能跟随鼠标移动 */
left:0;
top:0;
display:none; /* 鼠标移入图片后才显示黄色遮罩 */
cursor: move;
}
/*
消除mouseover和mouseout事件子级对父级的影响
(阻止事件冒泡不能消除子级对父级的影响,所以在黄色遮罩和图片之间加个透明的隔离层)
*/
#mark {
width:180px;
height:180px;
background:red;
position:absolute;
left:0;
top:0;
opacity:0;
filter:alpha(opacity=0);
}
#div2 {
width:500px;
height:500px;
position:absolute;
left:250px;
top:50px;
overflow:hidden;
}
#div2 img {
position:absolute;
left:0;
top:0;
}
style>
<script>
window.onload = function() {
var oDiv = document.getElementById('div1');
var oSpan = oDiv.getElementsByTagName('span')[0];
var oDiv2 = document.getElementById('div2');
var img2 = oDiv2.getElementsByTagName('img')[0];
/*
mouseenter和mouseleave事件子级不会影响到父级,
所以也可以用此方法消除子级对父级的影响
*/
oDiv.onmouseenter = function(){
oSpan.style.display = 'block';
};
oDiv.onmouseleave = function(){
oSpan.style.display = 'none';
};
// 要想元素跟着鼠标移动要绑定mousemove事件
oDiv.onmousemove = function(ev){
var ev = ev || window.event;
/*
ev.clientX、ev.clientY获取鼠标坐标
oDiv.offsetLeft: oDiv距离屏幕左侧的距离
oDiv.offsetTop: oDiv距离屏幕顶部的距离
oSpan.offsetWidth: offsetWidth返回对象的padding+border+width属性值之和
*/
var L = ev.clientX - oDiv.offsetLeft - oSpan.offsetWidth/2; // 将黄色遮罩中部移到鼠标位置
var T = ev.clientY - oDiv.offsetTop - oSpan.offsetHeight/2; // 将黄色遮罩中部移到鼠标位置
/* 限制黄色遮罩层的移动范围START */
if(L<0){
L = 0;
}
else if(L>oDiv.offsetWidth - oSpan.offsetWidth){
L = oDiv.offsetWidth - oSpan.offsetWidth;
}
if(T<0){
T = 0;
}
else if(T>oDiv.offsetHeight - oSpan.offsetHeight){
T = oDiv.offsetHeight - oSpan.offsetHeight;
}
oSpan.style.left = L + 'px';
oSpan.style.top = T + 'px';
/* 限制黄色遮罩层的移动范围END */
var scaleX = L/(oDiv.offsetWidth - oSpan.offsetWidth); // 移动的比例 0 ~ 1
var scaleY = T/(oDiv.offsetHeight - oSpan.offsetHeight); // 移动的比例 0 ~ 1
/*
大图的移动方向要和黄色遮罩(鼠标)移动方向相反
img2.offsetWidth - oDiv2.offsetWidth 大图能够移动的最大宽度
img2.offsetHeight - oDiv2.offsetHeight 大图能够移动的最大高度
*/
img2.style.left = - scaleX * (img2.offsetWidth - oDiv2.offsetWidth) + 'px';
img2.style.top = - scaleY * (img2.offsetHeight - oDiv2.offsetHeight) + 'px';
};
};
script>
head>
<body>
<div id="div1">
<img src="b2.jpg">
<span>span>
div>
<div id="div2">
<img src="b1.jpg">
div>
body>
html>
我们实现的效果图如下: