javascript Three.js相机旋转顺序

py49o6xq  于 2023-11-15  发布在  Java
关注(0)|答案(3)|浏览(159)

我正在尝试使用游戏手柄在Three.js中旋转相机,使用第一人称射击风格的控制。
浏览器检测到游戏手柄并识别它的输入,但相机的旋转顺序是错误的。当我在相机的本地Y轴上旋转时,它也会考虑本地X轴旋转,这是不必要的。

看起来我和this guy有同样的问题,但他的问题是用Three.js r54解决的,我用的是r60。他设置了camera.eulerOrder = "YXZ";来让它工作,但目前等效的camera.rotation.order = "YXZ";似乎对我不起作用。
我知道Three.js内置的“FirstPersonControls”类,但它不适合我,因为它不接受控制器输入,而且以后再把其他非移动控件硬塞进去会很麻烦。我也知道gamepad.js,对使用它没有兴趣。
有人能帮忙吗?
我的轮换代码:

  1. function pollGamepad()
  2. {
  3. gamepad = navigator.webkitGetGamepads()[0];
  4. //Rotation
  5. if(gamepad.axes[3] > 0.20)
  6. {
  7. camera.rotateX(-gamepad.axes[3] * 0.02);
  8. }
  9. if(gamepad.axes[3] < -0.20)
  10. {
  11. camera.rotateX(-gamepad.axes[3] * 0.02);
  12. }
  13. if(gamepad.axes[2] < -0.20)
  14. {
  15. camera.rotateY(-gamepad.axes[2] * 0.02);
  16. }
  17. if(gamepad.axes[2] > 0.20)
  18. {
  19. camera.rotateY(-gamepad.axes[2] * 0.02);
  20. }
  21. }

字符串

bvjxkvbb

bvjxkvbb1#

PointerLockControls使用的方法是创建对象的层次结构:yawObject包含pitchObject包含camera。然后水平鼠标(或操纵杆)移动将改变偏航对象的Y旋转,垂直鼠标(或操纵杆)移动将改变俯仰对象的X旋转,相机的旋转将保持固定在默认的(0, 0, -1)。这只是手动模拟Euler YXZ排序,但它可能更适合你。如果你需要获得整体旋转,它确实会产生一些尴尬。
在我最近编写的一个自定义控制器中,我通过将相机add()设置为单个父对象并将父对象的Euler阶数设置为YXZ来实现相同的结果。我不记得为什么这比直接在相机上设置更好,但确实如此。

30byixjq

30byixjq2#

我自己也遇到了这个问题,我想出了一个简单的解决方案。在执行y旋转之前,总是将相机的x旋转重置为零。然后,恢复x旋转。所以:

  1. // Rotate camera Fps style
  2. function rotateCamera(dx,dy){
  3. //store previous x rotation
  4. var x = camera.rotation.x;
  5. //reset camera's x rotation.
  6. camera.rotateX(-x);
  7. //rotate camera on y axis
  8. camera.rotateY(dy);
  9. //check if we are trying to look to high or too low
  10. if ( Math.abs( dx + x ) > Math.Pi/2 - 0.05) {
  11. camera.rotateX(x);
  12. else
  13. camera.rotateX(x+dx);
  14. //reset z rotation. Floating point operations might change z rotation during the above operations.
  15. camera.rotation.z = 0;
  16. }

字符串

展开查看全部
hlswsv35

hlswsv353#

我按了每个按钮直到它工作这是它弹出的代码

  1. var controlers = [];
  2. controlers[0] = 0;
  3. controlers[1] = 0;
  4. controlers[2] = 0;
  5. controlers[3] = 0;
  6. controlers[4] = 0;
  7. controlers[5] = 0;
  8. controlers[6] = 0;
  9. controlers[7] = 0;
  10. let controllerIndex = null;
  11. window.addEventListener("gamepadconnected", (event) => {
  12. const gamepad = event.gamepad;
  13. controllerIndex = gamepad.index;
  14. console.log("connected");
  15. });
  16. window.addEventListener("gamepaddisconnected", (event) => {
  17. controllerIndex = null;
  18. console.log("disconnected");
  19. });
  20. function handleButtons(buttons) {
  21. for (let i = 0; i < buttons.length; i++) {
  22. const button = buttons[i];
  23. const buttonElement = document.getElementById(`controller-b${i}`);
  24. const selectedButtonClass = "selected-button";
  25. if (buttonElement) {
  26. if (button.value > 0) {
  27. buttonElement.classList.add(selectedButtonClass);
  28. buttonElement.style.filter = `contrast(${button.value * 150}%)`;
  29. } else {
  30. buttonElement.classList.remove(selectedButtonClass);
  31. buttonElement.style.filter = `contrast(100%)`;
  32. }
  33. }
  34. }
  35. }
  36. function updateStick(elementId, leftRightAxis, upDownAxis) {
  37. const multiplier = 25;
  38. const stickLeftRight = leftRightAxis;
  39. const stickUpDown = upDownAxis;
  40. camera.object = camera;
  41. camera.target = new THREE.Vector3( 0, 0, 0 );
  42. camera.mouseX = 0;
  43. camera.mouseY = 0;
  44. camera.lat = 0;
  45. camera.lon = 360;
  46. camera.phi = 0;
  47. camera.theta = 0;
  48. controlers[4] = (stickLeftRight ) ;
  49. controlers[5] = (stickUpDown ) ;
  50. camera.lon += stickLeftRight * 10 ;
  51. camera.lat -= stickUpDown * 10 ; // * this.invertVertical?-1:1;
  52. camera.lat = Math.max( -15, Math.min( 15, camera.lat ) );
  53. camera.phi = ( 90 - camera.lat ) * Math.PI / 180;
  54. camera.theta = camera.lon * Math.PI / 360;
  55. var targetPosition = camera.target,
  56. position = camera.object.position;
  57. targetPosition.x = position.x + 100 * Math.cos( camera.theta );
  58. targetPosition.y = position.y + 200 * Math.cos( camera.phi );
  59. targetPosition.z = position.z + 100 * Math.sin( camera.phi ) * Math.sin( camera.theta );
  60. var stickLeftRight_a = ( (stickLeftRight) * 100);
  61. var stickUpDown_a = ( (stickUpDown) * 100);
  62. if( stickLeftRight_a < -87 || stickLeftRight_a > 87 || stickUpDown_a < -87 || stickUpDown_a > 87 ){
  63. if( stickLeftRight_a > -87 && stickLeftRight_a < 87 ){
  64. camera.lon += stickLeftRight ;
  65. camera.lat -= stickUpDown ; // * tstickLeftRight_as.invertVertical?-1:1;
  66. camera.lat = Math.max( -15, Math.min( 15, camera.lat ) );
  67. camera.phi = ( 90 - camera.lat ) * Math.PI / 180;
  68. camera.theta = camera.lon * Math.PI / 360;
  69. var targetPosition = camera.target,
  70. position = camera.object.position;
  71. targetPosition.x = position.x + 100 * Math.cos( camera.theta );
  72. targetPosition.y = position.y + 200 * Math.cos( camera.phi );
  73. targetPosition.z = position.z + 100 * Math.sin( camera.phi ) * Math.sin( camera.theta );
  74. camera.lookAt(targetPosition);
  75. }
  76. if( stickLeftRight_a > 87 ){
  77. controlers[6] = controlers[6] + 0.01;
  78. if( controlers[6] > 360 ){
  79. controlers[6] = 0;
  80. }
  81. camera.rotation.y -= controlers[6];
  82. camera.rotation.z = 0 ;
  83. camera.rotation.x = 0 ;
  84. }
  85. if( stickLeftRight_a < -87 ){
  86. controlers[6] = controlers[6] - 0.01;
  87. if( controlers[6] < 0 ){
  88. controlers[6] = 360;
  89. }
  90. camera.rotation.y += controlers[6];
  91. camera.rotation.z = 0 ;
  92. camera.rotation.x = 0 ;
  93. }
  94. }
  95. }
  96. }
  97. }
  98. function handleSticks(axes) {
  99. updateStick("controller-b10", axes[0], axes[1]);
  100. updateStick("controller-b11", axes[2], axes[3]);
  101. }
  102. function gameLoop() {
  103. if (controllerIndex !== null) {
  104. const gamepad = navigator.getGamepads()[controllerIndex];
  105. handleButtons(gamepad.buttons);
  106. handleSticks(gamepad.axes);
  107. }
  108. requestAnimationFrame(gameLoop);
  109. }
  110. gameLoop();

字符串

展开查看全部

相关问题