TrackballControl の意図は、ロールを誘発するトラックボールの外側に「境界」を持つことですか? 私は個人的にそれが嫌いです。それは少し不連続であり、実際には多くの目的を持っていません (imho)。
そうでない場合は、関数 getMouseProjectionOnBall を次のように変更できます。これは 2 つのことを行います (必ずしも「正しく」とは限りません)。
- 両方の軸を満たすように半径を正規化します
- ボールの外側に z 値をマップします (つまり、z が以前は 0 だった場所)。
個人的にはこちらの方が自然だと思います。
考え?
this.getMouseProjectionOnBall = function(clientX, clientY) {
var xnormalized = (clientX - _this.screen.width * 0.5 - _this.screen.offsetLeft) / (_this.screen.width / 2.0);
var ynormalized = (_this.screen.height * 0.5 + _this.screen.offsetTop - clientY) / (_this.screen.height / 2.0);
var mouseOnBall = new THREE.Vector3(
xnormalized,
ynormalized,
0.0
);
var length = mouseOnBall.length();
var ballRadius = 1.0; // As a fraction of the screen
if (length > ballRadius * 0.70710678118654752440) {
var temp = ballRadius / 1.41421356237309504880;
mouseOnBall.z = temp * temp / length;
// Remove old method.
// This Left z = 0, which meant rotation axis
// becomes z, which is a roll
//mouseOnBall.normalize();
} else {
mouseOnBall.z = Math.sqrt(1.0 - length * length);
}
_eye.copy(_this.object.position).sub(_this.target);
var projection = _this.object.up.clone().setLength(mouseOnBall.y);
projection.add(_this.object.up.clone().cross(_eye).setLength(mouseOnBall.x));
projection.add(_eye.setLength(mouseOnBall.z));
return projection;
};