当前位置: 首页 > news >正文

【JavaScript】实战案例-放大镜效果、图片切换

目录

实现这种图片切换的和放大镜的效果: 

第一步:图片的切换

第二步:鼠标经过中等盒子,显示隐藏大盒子

第三步:黑色遮罩盒子跟着鼠标来移动

遮罩层盒子移动的坐标:

总结一下~本章节对我有很大的收获,希望对你也是!!!


素材自取,一定要手码三遍!!!素材自取 

实现这种图片切换的和放大镜的效果: 

 

放大镜样例

 

第一步:图片的切换

1.实现图片的切换以及小li的active类的删除和增加 

2.对小li的active增删后,即可得到当前小li图片的地址:

console.log(e.target.src)

3.对middle图片地址进行更换即可:

middle.querySelector('img').src = e.target.src

第二步:鼠标经过中等盒子,显示隐藏大盒子

1.用到鼠标经过和离开,鼠标经过中盒子,大盒子利用display来显示和隐藏

2.鼠标离开不会立马消失,而是有200ms的延时,用户体验更好,所以经量使用定时器做一个延时setTimeout

3.显示和隐藏也经量定义一个函数,因为鼠标经过离开中等盒子,会显示隐藏,同时,鼠标经过大盒子,也会显示和隐藏

4.给大盒子里面的背景图片一个默认的第一张图片

第三步:黑色遮罩盒子跟着鼠标来移动

1.先做鼠标经过小盒子small盒子,显示隐藏黑色遮罩的盒子

2.让黑色遮罩跟着鼠标来走,需要用到鼠标移动事件mousemove

3.让黑色盒子的移动的核心思想:不断把鼠标在small盒子内的坐标给黑色遮罩层,这样遮罩层就可以跟着移动了

算法:

1)得到鼠标在页面中的坐标,利用事件对象的pageX

2)得到middle中等盒子在页面中的坐标 middle.getBoundingClientRect()

3)鼠标在middle盒子中的坐标 = 鼠标在页面中的坐标 - middle中等盒子的坐标

4)黑色遮罩层不断得到 鼠标在middle盒子中的坐标 就可以移动起来了

4.限定遮罩层的盒子只能在millde内部移动,需要添加判断:

1)限定水平方向 大于等于0 并且小于等于400

2)限定垂直方向 大于等于0 并且小于等于400

遮罩层盒子移动的坐标:

1)声明一个mx作为移动的距离

2)水平坐标x如果小于等于100,则移动的距离mx就是 0 不应该移动

3)水平座标 如果大于等于100 并且小于300, 移动的距离就是mx - 100 (100是遮罩层盒子自身宽度的一半)

4)水平坐标 如果大于等于300 ,移动的距离就是mx从200不约过在移动了

5)其实我们发现水平移动,就在100 ~ 200之间的

6)垂直同理

大盒子800 * 800 的背景图片 跟着middle盒子400 * 400移动 存在关系是2倍

 

我就发现当移动大盒子背景的时候是跟我同方向的,而我们需要它反方向移动,添加负号即可

JavaScript实现:

    const middle = document.querySelector('.middle')
    const small = document.querySelector('.small')
    const large = document.querySelector('.large')


    let img = null
    small.addEventListener('mouseover', function (e) {
      if (e.target.tagName === 'IMG') {
        // 排他思想 干掉以前的
        this.querySelector('.active').classList.remove('active')
        // 先移除以前的active 然后添加当前img父亲<i>标签的active
        e.target.parentNode.classList.add('active')
        // 拿到小盒子里面的图片
        // console.log(e.target.src)
        // 让中等盒子里的图片换成小盒子里的图片即可
        middle.querySelector('img').src = e.target.src
        img = e.target.src
      }
    })


    // 鼠标经过中等盒子,显示隐藏大盒子
    middle.addEventListener('mouseenter', show)
    middle.addEventListener('mouseleave', hide)

    let timeId = null
    function show() {
      clearTimeout(timeId)
      large.style.backgroundImage = `url(${img})`
      large.style.display = 'block'
    }

    function hide() {
      // 延时器
      timeId = setTimeout(function () {
        large.style.display = 'none'
      }, 249)
    }


    large.addEventListener('mouseenter', showLarge)
    large.addEventListener('mouseleave', hideLarge)
    function showLarge() {
      large.style.display = 'block'
    }

    function hideLarge() {
      large.style.display = 'none'
    }



    // 鼠标经过中等盒子,显示隐藏 黑色遮罩层
    const layer = document.querySelector('.layer') //黑色遮罩层
    middle.addEventListener('mouseenter', function () {
      layer.style.display = 'block'
    })

    middle.addEventListener('mouseleave', function () {
      layer.style.display = 'none'
    })

    // 移动黑色遮罩盒子
    middle.addEventListener('mousemove', function (e) {
      // 鼠标在middle内的坐标 = 鼠标在页面的坐标 - middle盒子在页面的坐标
      // console.log(e.pageX)
      // 得到middle盒子在页面中的坐标
      // console.log(middle.getBoundingClientRect().left)
      let x = e.pageX - middle.getBoundingClientRect().left
      let y = e.pageY - middle.getBoundingClientRect().top - document.documentElement.scrollTop
      // console.log(x)
      // console.log(y)
      // 移动黑色遮罩层
      layer.style.left = x + 'px'
      layer.style.top = y + 'px'

      // 黑色遮罩层移动 要在middle黑子内 限定移动距离
      if (x >= 0 && x <= 400 && y >= 0 && y <= 400) {
        // 黑色盒子不是一直移动的
        // 声明两个变量 黑色盒子移动的变量
        let mx = 0, my = 0
        if (x < 100) mx = 0
        if (x >= 100 && x <= 300) mx = x - 100
        if (x > 300) mx = 300 - 100

        if (y < 100) my = 0
        if (y >= 100 && y <= 300) my = y - 100
        if (y > 300) my = 300 - 100
        layer.style.left = mx + 'px'
        layer.style.top = my + 'px'

        // 大盒子800 * 800 的背景图片 跟着middle盒子400 * 400移动 存在关系是2倍
        large.style.backgroundPositionX = -2 * mx + 'px'
        large.style.backgroundPositionY = -2 * my + 'px'
      }
    })

总结一下~本章节对我有很大的收获,希望对你也是!!!

相关文章:

  • 【龙智】Confluence到期日提醒插件Data Center v1.8.0发布:Confluence 9兼容、表格提醒强化,Slack通知升级
  • 汽车免拆诊断案例 | 2013 款奔驰 S300L 车起步时车身明显抖动
  • SpringBoot高级-底层原理
  • Sponge VS Spring:新兴力量与行业标准的碰撞
  • 三、数据治理应用开发整体架构
  • 【部署优化篇四】《DeepSeek移动端优化:CoreML/TFLite实战对比》
  • TypeScript跟js,es6这些的区别
  • mysql实现原理 - 字符集和排序规则
  • 如何利用Python爬虫获取淘宝分类详情:实战案例指南
  • Ansys Zemax | 使用衍射光学器件模拟增强现实 (AR) 系统的出瞳扩展器 (EPE):第 2 部分
  • 【复现DeepSeek-R1之Open R1实战】系列7:GRPO原理介绍、训练流程和源码深度解析
  • 接口和抽象类的区别与Sort方法
  • 【前端】如何安装配置WebStorm软件?
  • (2025年最新版)中小学安全教育PPT资料和视频
  • 用DeepSeek零基础预测《哪吒之魔童闹海》票房——从数据爬取到模型实战
  • 火语言RPA--Excel读取内容
  • ok113i平台——qt+tslib支持usb触摸屏热插拔功能实现
  • 定期自动统计大表执行情况
  • IWPA_CEC2005
  • 网络安全行业有哪些公司
  • 做网站需要公司资质吗/seo排名优化app
  • 温州网站设计图片大全/seo关键词查询工具
  • 做淘宝优惠网站步骤/网络营销是做什么的工作
  • 厦门小型网站建设/鞍山网络推广
  • css代码大全/丹东网站seo
  • 稳稳在哪个网站做的消防直播/东营seo网站推广