0

编辑更简单

一直到它我需要在 3D 空间中的 3 轴上旋转一个圆圈。我已经毫无问题地向下移动了 y 轴。然而,我与其他两个的工作只导致圆圈围绕中心点而不是旋转。我还需要能够在旋转后在这个圆的边缘找到一个点。这样我就可以将我的对象绘制在那些点或在那个点渲染效果。

到目前为止我所拥有的示例...上下文位于我的世界模组中,因为它可以轻松地以图形方式测试代码。http://puu.sh/38Z6x.jpg我使用 6 分来测试代码,但以后可以增加。

这是我到目前为止的代码-代码-它的github,所以它会在我同步我的代码时经常更改。所以不要依赖于我尝试过的东西,而是我正在使用的结构。上次同步我尝试选择球坐标系。

我也在寻找进行这些计算的性能提示。我将在我正在控制 1000 个移动物体的项目上运行其中的几个计算。

4

2 回答 2

0

好的,看起来我已经开始工作了,我的轮换工作几乎 100%。我遇到的唯一问题是在设置行距后我无法围绕圆的边缘旋转。http://puu.sh/3ae63.jpg谢谢@Aggieboy 的帮助,非常棒

这是我的代码,虽然我认为它需要更多的工作,但它的东西。github 类将随着我对它们的更多工作而更新。但是,由于它是私有仓库,我无法将 github 文件链接到测试类。

/*
         * This is the code used to test the rotation by generating a circle with the radius
         * given
         */
        double r = 3;
        double s = (2 * Math.PI) / this.points.length;
        Vector3 vec = new Vector3(this.xCoord + 0.5D, this.yCoord + 2D, this.zCoord + 0.5D);
        boolean flip = false;
        /*
         * Rotation speed is set here though it could be control by anything. As well the
         * rotation change is stored in a vector(x,y,z) and doesn't only have to be in the z axis
         */
        this.rotation.z += 5;
        for (int i = 0; i < points.length; i++)
        {
            Color color = flip ? Color.red : Color.blue;
            Vector3 point = vec.clone().add(NetworkOrbit.getOrbitOffset(r, s * i, this.rotation));
            points[i] = point.clone();
            if (i != 0)
            {
                int a = i + 1 == this.points.length ? 0 : i - 1;
                int b = i;
                /*
                 * generatelaser creates a laser line from one point to another and is used for
                 * visual debug
                 */
                this.laser.generateLaser(this.worldObj, points[a], points[b], color, 10, 5);
            }
            flip = !flip;
        }
        this.laser.generateLaser(this.worldObj, points[this.points.length - 1], points[this.points.length - 2], flip ? Color.red : Color.blue, 10, 5);
        //Markers to show me the center point and then a  line to point 0
        this.laser.generateLaser(this.worldObj, vec, vec.clone().add(new Vector3(0, -2, 0)), Color.darkGray, 10, 5);
        this.laser.generateLaser(this.worldObj, points[0], vec, Color.darkGray, 10, 5);

Github 代码链接对格式感到抱歉,我似乎还不能发布超过 2 个链接 https://github.com/DarkGuardsman/Dark-Library/blob/master/src/minecraft/dark/library/ ...

...数学/四元数.java

...轨道/NetworkOrbit.java

于 2013-06-07T19:12:27.200 回答
0

这是我的简单四元数类。它使用了教程中的许多语义:

public class Quaternion {
    public double w, x, y, z;
    public Quaternion(double angleRadian, double x, double y, double z){
        double dAngle=angleRadian/2; //might as well divide by 2 here
        this.w=Math.cos(dAngle);
        this.x=x * Math.sin(dAngle);
        this.y=y * Math.sin(dAngle);
        this.z=z * Math.sin(dAngle);
    }
    public Quaternion(){
        x=y=z=0; w=1;
    }
    public void norm(){
        double magnitude = Math.sqrt(w*w + x*x + y*y + z*z);
        w = w / magnitude;
        x = x /  magnitude;
        y = y / magnitude;
        z = z / magnitude;
    }
    public Quaternion conj(){
        Quaternion ans = new Quaternion();
        ans.set(this);
        ans.conjLocal();
        return ans;
    }
    public void conjLocal(){
        x=-x;
        y=-y;
        z=-z;
    }
    public void set(Quaternion q){
        w=q.w;
        x=q.x;
        y=q.y;
        z=q.z;
    }
    public void set(double w, double x, double y, double z){
        this.w=w;
        this.x=x;
        this.y=y;
        this.z=z;
    }
    public Quaternion mult(Quaternion q){
        Quaternion ans = new Quaternion();
        ans.w = (this.w*q.w - this.x*q.x - this.y*q.y - this.z*q.z);
        ans.x = (this.w*q.x + this.x*q.w + this.y*q.z - this.z*q.y);
        ans.y = (this.w*q.y - this.x*q.z + this.y*q.w + this.z*q.x);
        ans.z = (this.w*q.z + this.x*q.y - this.y*q.x + this.z*q.w);
        return ans;
    }
    public void multLocal(Quaternion q){
        Quaternion temp=this.mult(q);
        this.set(temp);
    }
    public String toString(){ return "<"+w+", "+x+", "+y+", "+z+">"; }
}

v要通过四元数旋转向量q以获得结果向量v',必须使用以下等式:

v' = q * v * q.conj()

这是一个围绕四元数旋转矢量(或位置坐标)的演示。

public class QuaternionExample {
    public static void main(String[] args) {
        /*
         * Let's say we have a vector <1,0,0>, and we want to rotate it
         * such that the result will be in the other unit axiis: <0,1,0>
         * and <0,0,1>.  Right hand rule applies for rotating about an axis!
         * Convince yourself of the following through mental imagery:
         * 1. For <0,1,0>, we want to rotate <1,0,0> by 90 degrees about the z axis
         * 2. For <0,0,1>, we want to rotate <1,0,0> by 90 degrees about the -y axis (or -90 degrees also works)
         */

        //the quaternion form of a 3d vector is simply <0,Vec3> or <0,x,y,z>
        Quaternion x=new Quaternion(); 
        x.set(0,1,0,0);

        //1, we want <0,1,0>
        Quaternion rot = new Quaternion(Math.PI/2,0,0,1);
        System.out.println( rot.mult(x).mult(rot.conj()) );

        //2, we want <0,0,1>
        rot = new Quaternion(Math.PI/2,0,-1,0);
        System.out.println( rot.mult(x).mult(rot.conj()) );
        rot = new Quaternion(-Math.PI/2,0,1,0);
        System.out.println( rot.mult(x).mult(rot.conj()) );
    }
}

我想围绕原点旋转我的矢量(或位置坐标)。如果我想围绕不同的点旋转它(例如,对象的质心c),我需要先减去对象的质心,然后将其添加到结果中:

v' = q * (v-c) * q.conj() + c
于 2013-06-06T19:20:05.260 回答