我正在开发一个 Python 程序,在其中定义我自己的矢量 3D 类型。至少按照我想象的方式,向量可以存储位置和旋转...如果用 4 个值实现四元数旋转更好,我可以尝试
vec4
但我强烈喜欢避免这些,因为我对它们的了解更少,而且它们'就麻烦多了。请注意,这是我的 vec3
类的一般描述,它可以存储位置或旋转,并且对象可以为每个对象使用一个实例(例如:self.pos = vec3(4, 16, 0)
和 self.rot = vec3(0, 90, 180)
)。到目前为止,我所拥有的似乎按预期工作,不需要进一步更改:
class vec3:
def __init__(self, x: float, y: float, z: float):
self.x = x
self.y = y
self.z = z
def rot(self, other)
self.x = (self.x + other.x) % 360
self.y = (self.y + other.y) % 360
self.z = (self.z + other.z) % 360
def dir(self):
# This is where the magic I'm missing must happen
return vec3(self.x / 360, self.y / 360, self.z / 360)
v = vec3(0, 90, 180)
# Result: 0 90 180
v.rot(vec3(-90, 45, 270))
# Result: 270 135 90
v.dir()
# Result: 0.75 0.375 0.25
# Correct range but doesn't represent direction
我正在努力解决的问题是如何获得向量指向的真实方向,这意味着虚拟箭头从原点伸出并指向该向量所看的位置:X 是正确的,Y 是向前的,Z 是向上的。它的旋转本身并不能代表它:
0 0 0
的旋转应该是0 1 0
的方向,0 0 45
之一(向右45*)可能应该翻译为0.5 0.5 0
(前进方向的一半是割让到正确的方向),如果我们添加另一个 45* 一直向右看,我们就会得到 0 0 90
,它将指向 1 0 0
。我不介意方向是否与我的想象相混淆,只要正确完成并且所有可能的组合都是可预测的。我可以在 dir
函数中使用的最简单的转换算法是什么?
极其片面的答案。我设法制作了一个测试,它可以完成我想要的数学明智的任务,但只能在一个方向上起作用。它写得很糟糕,如果有更好的方法来实现相同的结果将不胜感激......而且我不知道如何对另一个轴执行此操作,以便方向可以代表任何旋转。我尝试了
math.sine
,这似乎很理想,但无论我做什么,我都无法得到具有适当范围的结果,例如:0* = +1, 90* = 0, 180* = -1, 270* = 0, 360* = +1
,因为我设法低于了。
import math
for i in (0, 45, 90, 135, 180, 225, 270, 315, 360):
ix = ((180 + i) % 360)
iy = ((90 + i) % 360)
x = 1 - abs(1 - math.radians(ix / math.pi)) * 2
y = 1 - abs(1 - math.radians(iy / math.pi)) * 2
print(str(i) + " - x: " + str(x) + " y: " + str(y))
结果:
0 - x: 1.0 y: 0.0
45 - x: 0.5 y: 0.5
90 - x: 0.0 y: 1.0
135 - x: -0.5 y: 0.5
180 - x: -1.0 y: 0.0
225 - x: -0.5 y: -0.5
270 - x: 0.0 y: -1.0
315 - x: 0.5 y: -0.5
360 - x: 1.0 y: 0.0