threejs的orbitcontrol,默认的缩放模式为整体以target为中心进行缩放。有时候,我们想让场景按照鼠标位置进行缩放,体验起来就和地图的缩放一样,最直观的感觉就是整个场景会越来越靠近鼠标点的位置,而不是整体的缩放大小。

问题描述

我们通过一个具体的例子来看看二者的区别。比如我们有如下场景,场景的相机target在平面的左下角,当我们缩放整个场景的时候,threejs的默认情况会整体按照target的位置缩放场景。

threejs默认缩放形式

可以看到,threejs默认的缩放形式,并没有考虑鼠标位置,也就是无论你鼠标放在那里,其实滚轮缩放的时候场景缩放的感觉是一样的。对比下下面的按鼠标点位置缩放,我们来看看。

按鼠标点位置缩放

从动图上我们可能看出来,以鼠标点为中心缩放的结果就是,我们鼠标点所在的位置被考虑进了缩放里。我们的缩放会让鼠标点所在的位置缩放的更大。这样更加符合用户的使用习惯,也就是用户鼠标所在的位置是用户更加关心的位置,希望相机更加偏向鼠标点的位置。

如何实现

ok,既然看完了对比,我们就来说下如何实现以鼠标点位置为缩放中心的场景缩放。我们以threejs中最常用的orbitcontrol为例子,来讲下如果达到我们想要的效果。

我们先来找到orbitcontrol中关于鼠标滚轮的处理函数,大致如下所示:

function handleMouseWheel( event ) {if ( event.deltaY < 0 ) {dollyIn( getZoomScale() );} else if ( event.deltaY > 0 ) {dollyOut( getZoomScale() );}scope.update();
}

可以看到这里滚轮处理的函数非常简单,判断下滚轮滚动的方向,然后执行缩放,最后更新control。

function handleMouseWheel( event ) {//设置相机缩放比数值越大缩放越明显let factor = 15;//从鼠标位置转化为webgl屏幕坐标位置let glScreenX = (event.clientX / scope.domElement.width) * 2 - 1;let glScreenY = -(event.clientY / scope.domElement.height) * 2 + 1;let vector = new Vector3(glScreenX, glScreenY, 0);//从屏幕向量转为3d空间向量vector.unproject(scope.object);//相机偏移量vector.sub(scope.object.position).setLength(factor);if (event.deltaY < 0) {scope.object.position.add(vector);scope.target.add(vector);} else {scope.object.position.sub( vector);scope.target.sub(vector);}scope.update();}

代码非常的简单,主要原理就是让相机沿着鼠标位置的偏移量进行偏移。(缩放只是拉近拉远相机)

除了以上的直接修改contro的源码以外,我们其实还可以自己直接监听dom的事件,然后设置control的enableZoom值为false禁止默认缩放,自己再业务代码中实现。只是把代码的位置换了下,这样可以尽量少的修改第三方库源码,以免后期升级时,需要额外的merge代码。

线上demo地址

OrbitControls修改版

参考: Stack Overflow

js判断鼠标靠近屏幕最侧面的监听_threejs按鼠标位置缩放场景相关推荐

  1. js判断手机浏览器屏幕方向

    /* js判断手机浏览器屏幕方向*/var direction = {__getOrientation: function () {if (window.orientation == 0 || win ...

  2. Leaflet中对鼠标按下、移动事件监听实现移动单个图形

    场景 Leaflet快速入门与加载OSM显示地图: https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/details/122290880 在上面的基础 ...

  3. python监听键盘库_python监听、操作键盘鼠标库pynput详细教程|python基础教程|python入门|python教程...

    https://www.xin3721.com/eschool/pythonxin3721/ § 0.0.0 前言 监听.操作鼠标.键盘是实现自动化的捷径,比如我实现自动化签到用到了模拟键盘操作. p ...

  4. python键盘监听模块大全_python监听、操作键盘鼠标库pynput详细教程

    § 0.0.0 前言 监听.操作鼠标.键盘是实现自动化的捷径,比如我实现自动化签到用到了模拟键盘操作. pynput是监听.操控鼠标和键盘的跨平台第三方python库. 你可以通过pip insnal ...

  5. html鼠标滚轮监听,jQuery - 鼠标滚轮插件jquery.mousewheel.js详解(上下、左右滚动监听)...

    1,插件介绍 jquery.mousewheel.js是一个用于添加跨浏览器的鼠标滚轮支持的 jQuery插件. 2,使用说明 (1)使用该插件,只需将 mousewheel事件绑定到一个元素上即可. ...

  6. JS监听页面----无鼠标键盘动作,自动跳页

    监听页面鼠标键盘动作,若用户5秒没有任何操作,页面自动跳转 function ScreenSaver(settings){ this.settings = settings; this.nTimeou ...

  7. JS中事件绑定的方式以及事件监听和事件的委托

    在javascript中,到我目前的学习中总结得到的认知是在事件触发阶段主要是由于事件流: 我们在HTML中先设置一个div: <div class="box">< ...

  8. html5鼠标事件监听,HTML5 Canvas鼠标与键盘事件

    演示HTML5 Canvas鼠标事件,获取Canvas对象上的鼠标坐标,演示键盘事件 通过键盘控制Canvas上对象移动. Canvas对象支持所有的JavaScript的鼠标事件,包括鼠标点击(Mo ...

  9. python监听鼠标事件_Python中使用PyHook监听鼠标和键盘事件实例

    Python 中使用 PyHook 监听鼠标和键盘事件实例 PyHook 是一个基于 Python 的"钩子"库,主要用于监 听当前电脑上鼠标和键盘的事件.这个库依赖于另一个 Py ...

最新文章

  1. Go各时间字符串使用详解
  2. C语言运算符优先级和口诀(转)
  3. android动态添加标签,android – 动态添加Textview
  4. 【bzoj5085】最大(二分+乱搞)
  5. PAT_B_1089_Java(20分)
  6. tomcat闪退解决方案
  7. require引入js vue_请教 关于使用require 引入vue 和公共js的问题
  8. java蓝桥杯算法训练 相l邻字母(题解)
  9. 【Flink】Flink 上海会议 【视频笔记】
  10. mysql 热迁移,proxmox迁移详解
  11. AC日记——Roma and Poker codeforces 803e
  12. 公募权益类基金投资者盈利洞察报告
  13. win7定时关机命令是什么
  14. 运行命令、文件扩展名速查、Windows运行命令大全
  15. java近义词,虚拟的近义词
  16. docker curl: (56) Recv failure: Connection reset by peer问题解决方法
  17. 如何正确的使用国产杀毒软件
  18. 战争调度(树形DP+BFS)
  19. java-net-php-python-java西藏文库计算机毕业设计程序
  20. Redis 帝国的神秘使者,竟然想改造 C 语言!

热门文章

  1. Ubuntu 12.04 64bit上安装Apache Traffic Server 4.1.2
  2. SketchUp Pro 2021基础入门学习视频教程
  3. WinCE中串口驱动及接口函数介绍(转载)
  4. windows 10 下部署WCF 一些细节
  5. 三种求全排列方式之比较
  6. 在Proteus中添加标号
  7. 【delphi】Byte数组与String类型的转换
  8. ubuntu配置jdk环境
  9. 对象名和函数名同名引起的莫名错误
  10. 在ASP.NET中自动给URL地址加上超链接