three.js使用dragControls实现拖动

本文讲述了作者在three.js中遇到的问题,如何在已有轨道控制器的基础上,实现点击模型底部按钮切换到单独的拖拽控制器进行平移操作。涉及到初始化参数的区别、拖拽目标管理、事件监听和自定义鼠标事件等技术细节。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

首先在three。js中文文档中是了解到这么一个控制器的,反复设置就是不生效,因为希望是在点击模型底部的一个按钮后让他切换控制器实现单独的平移操作的。本身已经在使用的是轨道控制器,所以初始化的时候又加了这个拖拽控制器,比较发现在初始化的时候,两个的传参是不一样的,常用的轨道控制器职场需要传入相机和渲染元素render.document 就可以,拖拽控制器还需传入要拖拽的模型元素,就是你要拖拽的目标。也就是说初始化的时候得在monted进行在这里才能拿到所有要拖拽的目标。

 实现步骤,声明一个数组来存储拖拽目标,这个看个人因素吧,模型的标注文字坐标轴以及尺寸文案都需要跟随模型拖动保持一致。然后在申明一个group  , 这个是three中进行分组使用也是全局声明,因为我的拖拽方法是根据官网示例修改的所以这一步保持一致。开启一个document监听事件,通过一个变量控制,点击了拖拽按钮后在执行监听事件中的步骤。监听的是一个点击事件,首先判断是否开启了拖拽然后通过dragcontrols中的getObject()方法获取拖拽目标,这是一个数组,清空他 ,接下来和其他控制器判断鼠标点击的地方是不是模型的步骤一样,也就是,通过相机和鼠标相交的射线来判断你点击的目标是什么。官网的判断是点击的目标是不是在group中在就变换颜色secne.attch()不存在就添加到group 同样是group.attch(),然后drag控制器开启数组多个移动

if ( enableSelection === true ) {

					const draggableObjects = controls.getObjects();
					draggableObjects.length = 0;

					mouse.x = ( event.clientX / window.innerWidth ) * 2 - 1;
					mouse.y = - ( event.clientY / window.innerHeight ) * 2 + 1;

					raycaster.setFromCamera( mouse, camera );

					const intersections = raycaster.intersectObjects( objects, true );

					if ( intersections.length > 0 ) {

						const object = intersections[ 0 ].object;

						if ( group.children.includes( object ) === true ) {

							object.material.emissive.set( 0x000000 );
							scene.attach( object );

						} else {

							object.material.emissive.set( 0xaaaaaa );
							group.attach( object );

						}

						controls.transformGroup = true;
						draggableObjects.push( group );

					}

					if ( group.children.length === 0 ) {

						controls.transformGroup = false;
						draggableObjects.push( ...objects );

					}

controls.transformGroup = true;  draggableObjects.push( group ); 

由于我的是点击模型要整体移动,我就直接是遍历一开始要存储的数组挨个添加到group 直接用上面的步骤实现的拖动。缺点就是如果数据中有按照之前左边进行的操作而不是跟随模型顶点是不会一起的,比如说移动前根据不变的坐标在模型上进行画线,移动后再根据这些坐标就不行了 。官网地址three.js/examples/misc_controls_drag.html at master · mrdoob/three.js (github.com)

由于需要画线标注不能因为移动改变,所以上述实现拖动放弃了,其实不论哪一个控制器其实默认有一个平移功能的。所以接下来是用的默认的拖动。默认拖动时鼠标按住右键拖动但是在edge浏览器中已经粗在默认手势了只能修改。老板要求是滚轮按下实现拖拽,因此

 controls.mouseButtons = {
        LEFT: THREE.MOUSE.ROTATE,
        MIDDLE: THREE.MOUSE.PAN,
        RIGHT: THREE.MOUSE.DOLLY,
      };

 好在控制器的鼠标事件是可以自定义的。突然发现用户一般不会发现的只能用 tipObj = new CSS2DObject(label); 创建一个小的标签提示了,有添加鼠标按钮按下 以及放开 来控制提示的显示。勉强实现了老板的需求吧。

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值