轨迹球控件仅通过Z轴旋转

Jud*_*orn 5 javascript three.js

我想修改TrackballControls,以使相机仅在Z轴上旋转。但是,我有点时间了解如何映射鼠标/触摸坐标。下面的函数接收鼠标/触摸的x / y坐标和一个“投影”矢量,我认为这是相机预期旋转位置的投影,但是我也不十分清楚。

基本上,我需要在下面的if语句中知道“该怎么办?”,该怎么做。我基本上需要裁剪矢量,以便旋转仅发生在Z轴上。我知道我可以通过简单的旋转来做到这一点,但是我想在TrackballControls中实现它,因此我可以随意切换到“仅滚动”模式(Z轴上只有相机“滚动”)。矢量数学方面更好的人可以帮我吗?

this.getMouseProjectionOnBall = (function(){

        var objectUp = new THREE.Vector3(),
            mouseOnBall = new THREE.Vector3();


        return function ( pageX, pageY, projection ) {

            mouseOnBall.set(
                ( pageX - _this.screen.width * 0.5 - _this.screen.left ) / (_this.screen.width*.5),
                ( _this.screen.height * 0.5 + _this.screen.top - pageY ) / (_this.screen.height*.5),
                0.0
            );

            var length = mouseOnBall.length();

            if ( _this.noRoll ) {

                if ( length < Math.SQRT1_2 ) {

                    mouseOnBall.z = Math.sqrt( 1.0 - length*length );

                } else {

                    mouseOnBall.z = .5 / length;

                }

            } else if (_this.rollOnly === true) {

                // What goes here?

            } else if ( length > 1.0 ) {

                mouseOnBall.normalize();

            } else {

                mouseOnBall.z = Math.sqrt( 1.0 - length * length );

            }

            _eye.copy( _this.object.position ).sub( _this.target );

            projection.copy( _this.object.up ).setLength( mouseOnBall.y )
            projection.add( objectUp.copy( _this.object.up ).cross( _eye ).setLength( mouseOnBall.x ) );
            projection.add( _eye.setLength( mouseOnBall.z ) );

            return projection;
        }

    }());
Run Code Online (Sandbox Code Playgroud)

相机的实际旋转是在每帧下方的功能中进行的。这个功能对我来说更容易理解。只是基本角度和四元数的东西。正是上述功能让我感到困惑。

this.rotateCamera = (function(){

    var axis = new THREE.Vector3(),
        quaternion = new THREE.Quaternion();


    return function () {
        var angle = Math.acos( _rotateStart.dot( _rotateEnd ) / _rotateStart.length() / _rotateEnd.length() );

        if ( angle ) {
            axis.crossVectors( _rotateStart, _rotateEnd ).normalize();

            angle *= _this.rotateSpeed;

            quaternion.setFromAxisAngle( axis, -angle );

            _eye.applyQuaternion( quaternion );
            _this.object.up.applyQuaternion( quaternion );

            _rotateEnd.applyQuaternion( quaternion );

            if ( _this.staticMoving ) {

                _rotateStart.copy( _rotateEnd );

            } else {

                quaternion.setFromAxisAngle( axis, angle * ( _this.dynamicDampingFactor - 1.0 ) );
                _rotateStart.applyQuaternion( quaternion );
            }

        }
    }

}());
Run Code Online (Sandbox Code Playgroud)