首页前端开发JavaScript原生js实现放大镜组件

原生js实现放大镜组件

时间2024-01-31 16:29:03发布访客分类JavaScript浏览283
导读:收集整理的这篇文章主要介绍了原生js实现放大镜组件,觉得挺不错的,现在分享给大家,也给大家做个参考。 本文实例为大家分享了js实现放大镜组件开发的具体代码,供大家参考,具体内容如下功能需...
收集整理的这篇文章主要介绍了原生js实现放大镜组件,觉得挺不错的,现在分享给大家,也给大家做个参考。

本文实例为大家分享了js实现放大镜组件开发的具体代码,供大家参考,具体内容如下

功能需求:

1、根据图片数组创建图标列表;
2、鼠标滑过图标时,当前图标增加红色边框;
3、鼠标滑过图标时,上方图片区域显示对应的图片,右侧显示放大后的图片内容;
4、鼠标在图片区域移动时,在右侧实现放大效果;
5、下方图标列表,点击左右按钮,实现翻页效果;
6、当图标内容不够一页时,只移动到最后一个图标的位置;

以京东的详情页为例,看一下效果:

放大镜内容写在 Zoom.js 文件里,下方的图标列表内容写在 IconList.js 文件里,当鼠标滑过下面的图标时,需要更改放大镜里div的背景图片,这里用到了事件抛发。

下面附上代码:

htML结构 :

!DOCTYPE html>
    html lang="en">
    head>
     meta charset="UTF-8">
     meta name="viewport" content="width=device-width, inITial-scale=1.0">
     title>
    zoom/title>
    /head>
    body>
     script type="module">
      import Zoom From './js/Zoom.js';
      //图标数组  let list=["a_icon.jpg","e_icon.jpg","f_icon.jpg","g_icon.jpg","h_icon.jpg","i_icon.jpg","j_icon.jpg",];
      init();
  function init(){
       let zoom=new Zoom(list,"./img/");
       zoom.appendTo("body");
  }
     /script>
    /body>
    /html>
    

Zoom.js文件,创建放大镜组件:

import Utils from "./Utils.js";
    import IconList from './IconList.js';
export default class Zoom{
     static styles=false;
     static small_width=450;
     static mask_width=303.75;
     static zoom_width=540;
     static SET_BG_IMG="set_bg_img";
 constructor(_list,_basePath){
      if(_basePath) _list=_list.map(item=>
    _basePath+item);
      //创建外层的div容器  this.elem=this.createE();
      //监听事件,改变zoomSmall的背景图  document.addEventListener(Zoom.SET_BG_IMG,e=>
    this.setBgImg(e));
      //创建下方的icon列表  this.createiconList(_list,this.elem);
 }
 createE(){
      //创建外层div容器  let div=Utils.createE("div");
      div.@R_360_402@="zoomContainer";
      div.innerHTML=`div class="zoomSmall" id="zoomSmall">
    div class="zoomMask" id="zoomMask">
    /div>
    /div>
      div class="zoomContent" id="zoomCont">
    /div>
    `;
      //设置样式  Zoom.setStyle();
      //获取样式  Utils.getIdElem(div,this);
      //监听鼠标滑入事件  this.zoomSmall.addEventListener("mouseenter",e=>
    this.mouseHandler(e));
      return div;
 }
 appendTo(parent){
      Utils.appendTo(this.elem,parent);
 }
 setBgImg(e){
  //设置背景图片  this.zoomSmall.style.backgroundImage=`url(${
e.src}
    )`;
  this.zoomCont.style.backgroundImage=`url(${
e.src}
    )`;
 }
 createIconList(list,parent){
      //创建下方icon图标列表  let iconList=new IconList(list);
      Utils.appendTo(iconList.elem,parent);
 }
 mouseHandler(e){
  switch (e.type) {
       case "mouseenter":    //鼠标滑入后,显示遮罩和右侧大图片    this.zoomMask.style.dis@R_126_2266@="block";
        this.zoomCont.style.display="block";
        //监听鼠标移动和滑出事件    this.mouseHandlers=e=>
    this.mouseHandler(e);
        this.zoomSmall.addEventListener("mouSEMove",this.mouseHandlers);
        this.zoomSmall.addEventListener("mouseleave",this.mouseHandlers);
        break;
       case "mousemove":    //遮罩移动    this.zoomMaskMove(e);
        break;
       case "mouseleave":    //鼠标滑出后,显示遮罩和右侧大图片    this.zoomMask.style.display="none";
        this.zoomCont.style.display="none";
        //移除鼠标移动和滑出事件    this.zoomSmall.removeEventListener("mousemove",this.mouseHandlers);
        this.zoomSmall.removeEventListener("mouseleave",this.mouseHandlers);
        break;
  }
 }
 zoomMaskMove(e){
      //遮罩移动  let rect=this.elem.getBoundingClientRect();
      //计算let和top的值,等于鼠标的坐标-父容器的left值-遮罩的一半宽  let x=e.clientX-rect.x-Zoom.mask_width/2;
      let y=e.clientY-rect.y-Zoom.mask_width/2;
      //判断left和top的范围  if(x0) x=0;
      if(x>
    Zoom.small_width-Zoom.mask_width) x=Zoom.small_width-Zoom.mask_width;
      if(y0) y=0;
      if(y>
    Zoom.small_width-Zoom.mask_width) y=Zoom.small_width-Zoom.mask_width;
      this.zoomMask.style.left=x+"px";
      this.zoomMask.style.top=y+"px";
      //大图片移动  this.zoomContMove(x,y);
 }
 zoomContMove(_x,_y){
      //计算大图片的背景定位,公式:zoom的宽/mask的宽=zoom的背景left值/mask的left值  let x=-Zoom.zoom_width/Zoom.mask_width*_x;
      let y=-Zoom.zoom_width/Zoom.mask_width*_y;
      this.zoomCont.style.backgroundPosition=x+"px "+y+"px";
 }
 static setStyle(){
      //设置样式  if(Zoom.styles) return;
      Zoom.styles=true;
  Utils.insertCss(".zoomContainer",{
   width:Zoom.small_width+"px",   height:Zoom.small_width+"px",   position:"relative"  }
)  Utils.insertCss(".zoomSmall",{
   width:Zoom.small_width+"px",   height:Zoom.small_width+"px",   border: "1px solid #000",   backgroundSize: "100% 100%",   position:"absolute",   left:"0px",   top:"0px"  }
)  Utils.insertCss(".zoomMask",{
   width: this.mask_width + "px",   height: this.mask_width + "px",   backgroundColor: "rgba(200,170,0,0.3)",   position: "absolute",   left: "0px",   top: "0px",   display: "none"  }
)  Utils.insertCss(".zoomContent",{
   width: this.zoom_width + "px",   height: this.zoom_width + "px",   border: "1px solid #ccc",   position: "absolute",   left: (this.small_width + 2) + "px",   top: "0px",   display: "none"  }
) }
}
    

IconList.js文件,创建下方图标列表,并完成翻页效果:

import Utils from "./Utils.js";
    import Zoom from "./Zoom.js";
export default class IconList{
     static styles=false;
     static num=5;
    //每页显示的图标数 static gap=0;
    //表示li的左右间距 position=0;
    //当前显示的图标为第几页 x=0;
    //列表的left值 PRepIcon;
    //上一个点击的图标 static SET_BG_IMG="set_bg_img";
 constructor(list){
      this.list=list;
      this.elem=this.createE();
 }
 createE(){
      //创建外层容器  let div=Utils.createE("div");
      div.className="iconContainer";
      div.innerHTML=`img class="prevBTn" src="./img/prev.png">
    div class="iconListCont">
${
this.createIcon()}
    /div>
    img class="nextBtn" src="./img/next.png">
    `;
      //设置css样式  IconList.setStyles(this.list);
      //获取元素  Utils.getIdElem(div,this);
      //外层容器监听点击事件  div.addEventListener("click",e=>
    this.clickHandler(e));
      //图标列表监听鼠标滑过事件  this.iconList.addEventListener("mouseover",e=>
    this.mouseHandler(e));
      //默认显示第一个图标的边框  this.setIconState(this.iconList.FirstElementChild);
      //默认显示第一个图片  this.setBgImg(this.iconList.firstElementChild.firstElementChild);
      return div;
 }
 createIcon(){
      //创建图标列表  let str=`ul class="iconList clearfix" id="iconList">
    `;
      this.list.foreach(item=>
{
       str+=`li>
img src="${
item}
    ">
    /li>
    `;
  }
    )  str+="/ul>
    ";
      return str;
 }
 clickHandler(e){
      let src=e.target.src;
      //如果点击的不是左右按钮,直接跳出  if(!/prev/.test(src)&
    &
    !/next/.test(src)) return;
      //每一个li的实际宽度,width+border+margin  let liWidth=54+4+IconList.gap;
      //page为一共有几个整数页  let page=Math.floor(this.list.length/IconList.num)-1;
      //remainder为最后不够一页的剩余图标数  let remainder=this.list.length%IconList.num;
  if(/prev/.test(src)){
       //如果点击的是上一页按钮   if(this.x===0) return;
       //移动到最后一页时   if(this.position===0&
    &
    remainder>
0){
        //移动的距离加等于li宽度*剩余图标数    this.x+=liWidth*remainder;
   }
   else if(this.position=page){
        this.position--;
        //移动的距离加等于li的宽度*每页显示的图标数(5个)    this.x+=liWidth*IconList.num;
   }
  }
else if(/next/.test(src)){
       //如果点击的是下一页按钮   if(this.x===-(this.list.length-iconList.num)*liWidth) return;
       if(this.position===page&
    &
    remainder>
0){
        //移动的距离减等于li宽度*剩余图标数    this.x-=liWidth*remainder;
   }
   else if(this.positionpage){
        this.position++;
        //移动的距离减等于li的宽度*每页显示的图标数(5个)    this.x-=liWidth*IconList.num;
   }
  }
      //设置图标列表的left值  this.iconList.style.left=this.x+"px";
 }
 mouseHandler(e){
      //如果滑过的不是Img标签,直接跳出  if(e.target.constructor!==HTMLImageElement) return;
      //设置背景图片  this.setBgImg(e.target);
      //设置当前滑过图标的样式  this.setIconState(e.target.parentElement);
 }
 setIconState(target){
      //移除上一个滑过图标的active样式  if(this.prepIcon) Utils.removeClass(this.prepIcon,"active");
      //将当前滑过的对象赋值给this.prepIcon  this.prepIcon=target;
      //给当前滑过图标增加active样式  Utils.addClass(this.prepIcon,"active");
 }
 setBgImg(target){
      //抛发事件,将当前图片的src传过去  let src=target.src.replace("_icon","");
      let evt=new Event(IconList.SET_BG_IMG);
      evt.src=src;
      document.dispatchEvent(evt);
 }
 static setStyles(list){
      //设置样式  if(IconList.styles) return;
      IconList.styles=true;
  Utils.insertCss(".iconContainer",{
   width:Zoom.small_width+2+"px",   height: "58px",   position: "absolute",   top: Zoom.small_width+2+"px",   left: "0px",  }
    )  Utils.insertCss(".iconContainer>
img",{
   width:"22px",   height:"32px",   cursor:"pointer",   position:"absolute",   top:"13px",  }
)  Utils.insertCss(".prevbtn",{
   left:"8px"  }
)  Utils.insertCss(".nextBtn",{
   right:"8px"  }
)  Utils.insertCss(".iconListCont",{
   width:Zoom.small_width-30*2+"px",   height:"58px",   position:"relative",   left:"30px",   overflow:"hidden"  }
    )  IconList.gap=((Zoom.small_width-30*2)-(54+4)*IconList.num)/IconList.num;
  Utils.insertCss(".iconList",{
   width:(54+4+IconList.gap)*list.length+"px",   listStyle:"none",   padding:"0px",   margin:"0px",   position:"absolute",   left:"0px",   top:"0px",   transition:"all .3s"  }
)  Utils.insertCss(".iconList li",{
   float:"left",   width:"54px",   height:"54px",   margin:"0px "+IconList.gap/2+"px",   cursor:"pointer",   border:"2px solid transparent"  }
)  Utils.insertCss(".iconList li.active",{
   borderColor:"#f00"  }
    )  Utils.insertCss(".iconList li>
img",{
   width:"54px",   height:"54px"  }
)  Utils.insertCss(".clearfix::after",{
   content:"\".\"",   display:"block",   height:"0px",   clear:"both",   overflow:"hidden",   visibility:"hidden"  }
) }
}
    

Utils.js文件,是一个工具包:

export default class Utils{
 static createE(elem,style,prep){
      elem=document.createElement(elem);
      if(style) for(let prop in style) elem.style[prop]=style[prop];
      if(prep) for(let prop in prep) elem[prop]=prep[prop];
      return elem;
 }
 static appendTo(elem,parent){
      if (parent.constructor === String) parent = document.querySelector(parent);
      parent.appendChild(elem);
 }
 static insertBefore(elem,parent){
      if(parent.constructor === String) parent=document.querySelector(parent);
      parent.insertBefore(elem,parent.firstElementChild);
 }
 static randomNum(min,max){
      return Math.floor(Math.random*(max-min)+min);
 }
 static randomColor(alpha){
      alpha=alpha||Math.random().toFixed(1);
      if(isNaN(alpha)) alpha=1;
      if(alpha>
    1) alpha=1;
      if(alpha0) alpha=0;
      let col="rgba(";
      for(let i=0;
    i3;
i++){
       col+=Utils.randomNum(0,256)+",";
  }
      col+=alpha+")";
      return col;
 }
 static insertCss(select,styles){
  if(document.styleSheets.length===0){
       let styleS=Utils.createE("style");
       Utils.appendTo(styleS,document.head);
  }
      let styleSheet=document.styleSheets[document.styleSheets.length-1];
  let str=select+"{
    ";
  for(VAR prop in styles){
   str+=prop.replace(/[A-Z]/g,function(item){
        return "-"+item.toLocaleLowerCase();
   }
    )+":"+styles[prop]+";
    ";
  }
  str+="}
    "  styleSheet.insertRule(str,styleSheet.cssRules.length);
 }
 static getIdElem(elem,obj){
      if(elem.id) obj[elem.id]=elem;
      if(elem.children.length===0) return obj;
      for(let i=0;
    ielem.children.length;
i++){
       Utils.getIdElem(elem.children[i],obj);
  }
 }
 static addClass(elem,className){
      let arr=(elem.className+" "+className).match(/\S+/g);
      arr=arr.filter((item,index)=>
    arr.indexOf(item,index+1)0)  elem.className=arr.join(" ");
 }
 static removeClass(elem,className){
      if(!elem.className) return;
      let arr=elem.className.match(/\S+/g);
      let arr1=className.match(/\S+/g);
      arr1.forEach(item=>
{
       arr=arr.filter(t=>
t!==item)  }
    )  elem.className=arr.join(" ");
 }
 static hasClass(elem,className){
      if(!elem.className) return false;
      let arr=elem.className.match(/\S+/g);
      let arr1=className.match(/\S+/g);
      let res;
      arr1.forEach(item=>
{
       res= arr.some(it=>
it===item)  }
    )  return res;
 }
 static loadImg({
list,basePath,callback}
){
      if(!list || list.length===0) return;
      if(basePath) list=list.map(item=>
    basePath+item);
      let img=Utils.createE("img");
  img.data={
   list:list,   callback:callback,   resultList:[],   num:0  }
      img.addEventListener("load",Utils.loadImgHandler);
      img.src=list[img.data.num];
 }
 static loadImgHandler(e){
      let data=e.currentTarget.data;
      data.resultList.push(e.currentTarget.cloneNode(false));
      data.num++;
      if(data.num>
data.list.length-1){
       e.currentTarget.removeEventListener("load",Utils.loadImgHandler);
       data.callback(data.resultList);
       data=null;
       return;
  }
      e.currentTarget.src=data.list[data.num];
 }
}
    

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。

您可能感兴趣的文章:
  • JavaScript实现简易放大镜最全代码解析(ES5)
  • js实现简单的放大镜效果
  • js实现购物网站放大镜功能
  • js实现简单放大镜特效
  • js放大镜放大图片效果
  • 用js实现放大镜的效果的简单实例
  • 奇妙的Javascript图片放大镜
  • 原生js写的放大镜效果
  • 图片放大镜jquery.jqzoom.js使用实例附放大镜图标
  • JS版图片放大镜效果

声明:本文内容由网友自发贡献,本站不承担相应法律责任。对本内容有异议或投诉,请联系2913721942#qq.com核实处理,我们将尽快回复您,谢谢合作!

js

若转载请注明出处: 原生js实现放大镜组件
本文地址: https://pptw.com/jishu/594201.html
c语言中什么是递归?经典递归函数例子分享 c语言break什么意思?

游客 回复需填写必要信息