Issues while rotation camera around pivot with Roll not equal to 0°

Good day community!

I got this script working to rotate the camera arround a pivot. It works just perfect as long as the camera’s Roll is 0° becasue it calculates the position using angles Phi and Theta. The script needs a particular setup to make it work.

The problem comes when Roll is not exactly 0°, lets say it is set to 90°, the camera then should rotate left and right if the mouse is being moved over horizontal axis, but it rotates up and down because the rotation is being applied over the world Z Axis.

I share you the code explaining each part.

May be a Quaternion can fix the issue, problmen is that I do not know how to use Quaternions in Blender to rotate a camera arround a pivot.

Code:


import bge, math
from bge import logic

Variables declaration

cont = logic.getCurrentController()
own = cont.owner
scene = logic.getCurrentScene()
obj = scene.objects
gd = logic.globalDict
player = obj[‘player1’]

sensitivity = 1

vectto = own.getVectTo(player)

Aligns camera Roll with the player

own.alignAxisToVect(gd[‘alignmentVector’], 2, 0.1) # Replace later with player local vector
own.alignAxisToVect(vectto[1], 1, 1)

Limits camera Zoom

if logic.mouse.events[194] == 2 and gd[‘radius’] > 5:gd[‘radius’] -= 1
elif logic.mouse.events[195] == 2 and gd[‘radius’] < 50:gd[‘radius’] += 1

Keeps track of the camera Yaw and Pitch based on mouse movement over the screen

if gd[‘allowCameraControl’] and logic.mouse.events[192] == 0:if logic.mouse.events[196] == 2:
[INDENT=2]if logic.mouse.position[0] < gd[‘mouse_pivot’][0] - 0.0001:[/INDENT]
[INDENT=3]gd[‘theta’] += 2 * abs(gd[‘mouse_pivot’][0] - logic.mouse.position[0])[/INDENT]
[INDENT=2]if logic.mouse.position[0] > gd[‘mouse_pivot’][0] + 0.0001:[/INDENT]
[INDENT=3]gd[‘theta’] -= 2 * abs(gd[‘mouse_pivot’][0] - logic.mouse.position[0])[/INDENT]
if logic.mouse.events[197] == 2:
[INDENT=2]if logic.mouse.position[1] > gd[‘mouse_pivot’][1] + 0.0001:[/INDENT]
[INDENT=3]gd[‘phi’] -= 2 * abs(gd[‘mouse_pivot’][1] - logic.mouse.position[1])[/INDENT]
[INDENT=2]if logic.mouse.position[1] < gd[‘mouse_pivot’][1] - 0.0001:[/INDENT]
[INDENT=3]gd[‘phi’] += 2 * abs(gd[‘mouse_pivot’][1] - logic.mouse.position[1])[/INDENT]

# Limits Pitch, so the camera never goes below or above player to avoid camera flipping   
if gd['phi'] &lt; (1 / 8) * math.pi:

[INDENT=2]gd[‘phi’] = (1 / 8) * math.pi[/INDENT]
if gd[‘phi’] > math.pi - (1 / 8) * math.pi:

[INDENT=2]gd[‘phi’] = math.pi - (1 / 8) * math.pi[/INDENT]
gd[‘mouse_pivot’] = logic.mouse.position

This code causes the issue because it’s fixed to the world axix, this requeres editing

x = player.position[0] + gd[‘radius’] * math.cos(gd[‘theta’]) * math.sin(gd[‘phi’])
y = player.position[1] + gd[‘radius’] * math.sin(gd[‘theta’]) * math.sin(gd[‘phi’])
z = player.position[2] + gd[‘radius’] * math.cos(gd[‘phi’])

Apply position using Linear Interpolation

own.position = own.position.lerp([x, y, z], 0.1)


use object applyRotation or use

rot = camera.worldOrientation.to_euler()
rot.y+=offset
camera.worldOrientation = rot

So, no Quaternion support?

Is applyRotation similar to Torque?

It’s weird what I am asking for, but what I really need to do is calculate position over an imaginary sphere using the Yay, Pitch and Roll of the camera, so i can move it over. As I already said, I got it working using the Yaw and the Pitch, but I still have to implement the Roll feature to make this work.

first things first. no need to import bge twice.

from bge import logic, events  #added the events module for convenience
import math

second, i think there might be an easier way to do a mouselook. you need a camera parented to an empty which is parented to the player hitbox. i can only guess what you are trying to do since i cant read all that math gibberish.

from bge import logic

scene = logic.getCurrentScene()

player = scene.objects["Player"]  #player
empty = scene.objects["Empty"]  #point to rotate camera around

speed = 8
ratio = 1080/1920  #aspect ratio correction

msX, msY = logic.mouse.position

pitch = (0.5-msX)*speed
yaw = (0.5-msY)*speed*ratio

player.applyRotation((0, 0, yaw), True)

## Limit Rotation, Y forward, Z up ##
ori = empty.localOrientation

if ori[2][2] &gt; 0:
    empty.applyRotation((pitch, 0, 0), True)
else:
    if ori[1][2] &lt; 0:
        if pitch &lt; 0:
            empty.applyRotation((pitch, 0, 0), True)
        else:
            empty.localOrientation = ( (1, 0, 0), (0, 0, -1), (0, 1, 0) )

    elif ori[1][2] &gt; 0:
        if pitch &gt; 0:
            empty.applyRotation((pitch, 0, 0), True)
        else:
            empty.localOrientation = ( (1, 0, 0), (0, 0, 1), (0, -1, 0) )

logic.mouse.position = (0.5, 0.5)

Thanks, but this is not what I am looking for,what Iamasking for it’skind of fancy.