[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"$fD23IbsQoUFtyS_NZvktAOxMuBfC-PUem_y9vmIHJ2UE":3},{"code":4,"message":5,"data":6},200,"成功",{"id":7,"createdAt":8,"title":9,"content":10,"summary":11,"image":12,"uid":13,"user":14,"categoryId":21,"category":22,"subCategoryId":24,"subCategory":25,"comments":27,"status":17,"reason":28,"notice":28,"visitCount":29,"commentCount":30,"keywords":31},110,"2024-04-23T08:37:05.061Z","jQuery实现放大镜效果","## 实现一个放大镜效果\n放大镜效果往往是电商平台上出现的比较多的一种效果，用于对商品图的放大查看。\n\n其原理是用一张适当大小的图来显示原图，但是使用一张更高清的大图来用作放大镜中看到的图。\n\n这里简短使用2张图的标签来做演示，一个代表缩略图，一个代表高清大图。高清大图在缩略图的右侧，悬浮显示，父标签和缩略图的父标签大小一致。\n\n### 1 利用jQuery实现\n#### 1.1 css:声明缩略图和高清图的样式\n```language\n/* 缩略图父标签class */\n.bigImage {\n  box-shadow: 0 0 3px rgba(0,0,0,0.15);\n  position: relative;\n  width: 400px;\n  height: 400px;\n}\n/* 缩略图img标签 */\n.bigImage>img {\n  position: relative;\n\n  width: 400px;\n  height: auto;\n  min-height: 400px;\n  max-height: 500px;\n  display: none;\n}\n\n/* 高清图父标签class */\n.magnifier {  \n  position: absolute;\n  z-index: 299; \n  border: 1px solid #ccc;\n  left: 420px;\n  width: 400px;\n  height: 400px;\n  background: rgba(255, 255, 255, 0.5);  \n  display: none;\n  overflow: hidden;\n}  \n/* 高清图img标签 */\n.magnifier-image {  \n  width: 1000px;\n  height: auto;\n  position: absolute;  \n  left: -300px; \n  top: -300px;\n}\n```\n\n通过position的relative和absolute属性，可以设置放大镜效果图absolute在原缩略图右侧，并且横向间隔20px。\n高清图的img设置为更宽更高，超出父标签的视口。视口里面的图，通过设置left和top可以移动高清图。\n\n#### 1.2 html: 摘取部分代码，主要是缩略图和高清大图的标签\n```language\n\u003C!-- 商品图区 -->\n        \u003Cdiv>\n          \u003C!-- 缩略图 -->\n          \u003Cdiv class=\"bigImage f-c-c\">\n            \u003Cimg />\n            \u003C!-- 放大镜的高清图 -->\n            \u003Cdiv class=\"magnifier\">\n              \u003Cimg class=\"magnifier-image\" alt=\"Magnified Image\">\n            \u003C/div>\n          \u003C/div>\n         \u003C/div>\n```\n\n\n#### 1.3 js:使用jQuery监听标签hover和鼠标移动事件\n当鼠标落在缩略图上时，显示放大镜标签：\n```language\n// 监听缩略图的hover\n  $('.bigImage').hover(function () {\n      $('.magnifier').css('display', 'block');\n    }, function () {\n      $('.magnifier').css('display', 'none');\n    }\n  );\n```\n\n\n当鼠标在缩略图上移动时，需要监听，并且改变放大镜区域中高清图的位置：\n```language\n  let largeImage = $('.bigImage');  \n  let magnifier = $('.magnifier');  \n  let magnifierImage = $('.magnifier-image');\n\n  let magnifierWidth = magnifier.width();  \n  let magnifierHeight = magnifier.height();\n\n  let bigImageOffset = largeImage.offset();\n\n  largeImage.on(\"mousemove\", function( e ) {\n    let posX = e.pageX + 1 - bigImageOffset.left;  \n    let posY = e.pageY + 1 - bigImageOffset.top;\n\n    let previewImgWidth = magnifierImage.width();  \n    let previewImgHeight = magnifierImage.height();\n    \n    // 计算放大镜中显示的大图位置 \n    let magnifierLeft = posX * (previewImgWidth / largeImage.width()) - magnifierWidth/2.0; \n    let magnifierTop = posY * (previewImgHeight / largeImage.height()) - magnifierHeight/2.0;\n\n    // 确保放大镜在图片范围内  \n    if (magnifierLeft \u003C 0) {\n      magnifierLeft = 0;\n    }\n    if (magnifierTop \u003C 0) {\n      magnifierTop = 0;\n    }\n    if (magnifierLeft + magnifierWidth > previewImgWidth) {\n      magnifierLeft = previewImgWidth - magnifierWidth;\n    }\n    if (magnifierTop + magnifierHeight > previewImgHeight) {\n      magnifierTop = previewImgHeight - magnifierHeight;\n    }\n\n    magnifierImage.css('left', -magnifierLeft);\n    magnifierImage.css('top', -magnifierTop);\n  });\n```\n\n\n- 获取鼠标在原缩略图中时，相对缩略图的x和y坐标，是鼠标的相对位置\n- 通过原缩略图和高清图的宽高比例，按照比例计算出鼠标应该落在高清图的哪一个位置\n- 我们要达到的效果是，鼠标坐标所在的点，处于放大镜标签的中间位置，并且高清大图的边缘不能显现在放大镜中\n- 边缘条件需要做判断，确保放大镜中永远显示的都是高清大图的一部分\n\n#### 1.4 标签的frame等解释\n##### 1.4.1 offset\n是标签相对于document的位置\n![jQuery的offset.png](https://image.xinwei.ltd/101713861213518.png)\n\n##### 1.4.2 event.pageX和event.pageY\n是相对于document左边缘的鼠标的位置，iframe中相对于iframe的坐标：\n![jQuery的pageX.png](https://image.xinwei.ltd/111713861301868.png)\n\n##### 1.4.3 width和height\n标签元素的宽和高。\n这里截图中说的是.css(\"width\"\")返回的是带px或者其他单位的，建议是在数学计算情况下使用.width()。\n![jQuery的width和height.png](https://image.xinwei.ltd/121713861351965.png)\n\n\n\n\n\n\n\n","因为最近的项目中又要做这个效果需求，所以简单记录一下使用到的jQuery方式实现，供大家参考。","https://image.xinwei.ltd/101713861213518.png",499668042977349,{"phone":15,"userId":13,"nickName":16,"vipType":17,"avatar":18,"sign":19,"createdAt":20},"13121171998","全栈老韩",1,"https://image.xinwei.ltd/images/IMG_5430.JPG","全栈工程师，擅长iOS App开发、前端（vue、react、nuxt、小程序&Taro）开发、Flutter、React Native、后端（midwayjs、golang、express、koa）开发、docker容器、seo优化等。","2024-01-01T16:14:30.305Z",2,{"id":21,"name":23},"IT技术",32,{"id":24,"name":26,"parentId":21},"前端",[],"",340,0,"jquery,jquery effective,jquery开发,jquery放大镜"]