java - 3D coordinate rotation lacking Precision in perspective 2D -


so wrote program draw , display 3d cube, using these simple conversion formula's used in isometric graphs:

x2 = x*cos(30) - y*cos(30)
y2 = x*sin(30) + y*sin(30) + z

the coordinate conversion fine , comes out in perspective.

the issue rotating, large degree rotations messes coordinates , gives me entire shape. , rotating @ small degrees many many times, (ie 1000 1degree rotation or more) reduces size of cube.

public void rotatex(double dg) //cube shrinking along y , z   {     y = (y*math.cos(dg)-z*math.sin(dg));       z = (y*math.sin(dg)+z*math.cos(dg));   } public void rotatey(double dg) //cube shrinking along x , z   {       x = x*math.cos(dg)-z*math.sin(dg);       z = x*math.sin(dg)+z*math.cos(dg);   }   public void rotatez(double dg) //cube shrinking along x , y   {       x = x*math.cos(dg)-y*math.sin(dg);       y = x*math.sin(dg)+y*math.cos(dg);   } 

how can solve lack of precision of cos , sin after multiple uses??

here's entire code written in 3 seperat classes:
main class:

import java.awt.*; import javax.swing.*; import java.util.random; public class frame extends jframe {     private random rnd = new random();     private cubegui cube;     public frame()     {         super();     }      public void paint(graphics g)     {         cube = new cubegui(75,300.0,300.0);         cube.convertall();         double dg = 0.5; // smaller degree, less error after long rotations.         int sl = 5;         int turns, axe;           while (1 == 1)         {             turns = rnd.nextint(200)-100;             axe = rnd.nextint(3);             for(int = 0; i<turns; i++)             {                 switch (axe)                 {                     case 0: cube.rotatx(dg); break;                     case 1: cube.rotaty(dg); break;                     case 2: cube.rotatz(dg); break;                 }                 g.clearrect(0,0,600,600);                 g.drawline(cube.a.x2,cube.a.y2,cube.b.x2,cube.b.y2);                 g.drawline(cube.a.x2,cube.a.y2,cube.c.x2,cube.c.y2);                 g.drawline(cube.c.x2,cube.c.y2,cube.d.x2,cube.d.y2);                 g.drawline(cube.b.x2,cube.b.y2,cube.d.x2,cube.d.y2);                 g.drawline(cube.e.x2,cube.e.y2,cube.f.x2,cube.f.y2);                 g.drawline(cube.e.x2,cube.e.y2,cube.g.x2,cube.g.y2);                 g.drawline(cube.g.x2,cube.g.y2,cube.h.x2,cube.h.y2);                 g.drawline(cube.f.x2,cube.f.y2,cube.h.x2,cube.h.y2);                 g.drawline(cube.a.x2,cube.a.y2,cube.e.x2,cube.e.y2);                 g.drawline(cube.b.x2,cube.b.y2,cube.f.x2,cube.f.y2);                 g.drawline(cube.c.x2,cube.c.y2,cube.g.x2,cube.g.y2);                 g.drawline(cube.d.x2,cube.d.y2,cube.h.x2,cube.h.y2);                 try                 {                     thread.sleep(sl); //rotation speed, in relation angle of rotation.                 } catch(interruptedexception ex)                 {                     thread.currentthread().interrupt();                 }             }         } } public static void main(string[] args) {     frame cube = new frame();         cube.setsize(600,600);         cube.setdefaultcloseoperation(jframe.exit_on_close);         cube.setvisible(true);     } } 

cube class:

public class cubegui {     public point center,a,b,c,d,e,f,g,h;     private double x, y;     public cubegui(int m, double x, double y)     {         this.x = x;         this.y = y;         = new point(-m,-m,-m);         b = new point(m,-m,-m);         c = new point(-m,m,-m);         d = new point(m,m,-m);         e = new point(-m,-m,m);         f = new point(m,-m,m);         g = new point(-m,m,m);         h = new point(m,m,m);     }     public void rotatx(double dg)     {         a.rotatex(math.toradians(dg));         b.rotatex(math.toradians(dg));         c.rotatex(math.toradians(dg));         d.rotatex(math.toradians(dg));         e.rotatex(math.toradians(dg));         f.rotatex(math.toradians(dg));         g.rotatex(math.toradians(dg));         h.rotatex(math.toradians(dg));         convertall();     }     public void rotaty(double dg)     {         a.rotatey(math.toradians(dg));         b.rotatey(math.toradians(dg));         c.rotatey(math.toradians(dg));         d.rotatey(math.toradians(dg));         e.rotatey(math.toradians(dg));         f.rotatey(math.toradians(dg));         g.rotatey(math.toradians(dg));         h.rotatey(math.toradians(dg));         convertall();     }     public void rotatz(double dg)     {         a.rotatez(math.toradians(dg));         b.rotatez(math.toradians(dg));         c.rotatez(math.toradians(dg));         d.rotatez(math.toradians(dg));         e.rotatez(math.toradians(dg));         f.rotatez(math.toradians(dg));         g.rotatez(math.toradians(dg));         h.rotatez(math.toradians(dg));         convertall();     }     public void convertall()     {         a.convert(x,y);         b.convert(x,y);         c.convert(x,y);         d.convert(x,y);         e.convert(x,y);         f.convert(x,y);         g.convert(x,y);         h.convert(x,y);     } } 

point class (this calculates coordinates):

public class point {     private double x, y, z, f;     public int x2, y2;     public point(double a, double b, double c)     {         x = a;         y = b;         z = c;     }     public int getx()     {         return (int)x;     }     public int gety()     {         return (int)y;     }     public int getz()     {         return (int)z;     }     public void rotatex(double dg) //cube shrinking along y , z     {         y = (y*math.cos(dg)-z*math.sin(dg));         z = (y*math.sin(dg)+z*math.cos(dg));     }     public void rotatey(double dg) //cube shrinking along x , z     {         x = x*math.cos(dg)-z*math.sin(dg);         z = x*math.sin(dg)+z*math.cos(dg);     }     public void rotatez(double dg) //cube shrinking along x , y     {         x = x*math.cos(dg)-y*math.sin(dg);         y = x*math.sin(dg)+y*math.cos(dg);     }     public void convert(double xx, double yy)     {         x2 = (int)(-(math.cos(math.toradians(30))*x - math.cos(math.toradians(30))*y) + xx);         y2 = (int)(-(math.sin(math.toradians(30))*x + math.sin(math.toradians(30))*y + z) + yy);     }     public string tostring()     {         return ("y = " + y + ", z = " + z);     } } 

the usual approach represent cube point configuration , current transformation. when rotating, update transformation not update points themselves. when point coordinates needed (for rendering, displaying coordinate values, etc.) should transformation applied points. points should never modified.

this eliminate errors accumulate when many rotations applied in sequence. however, important transformation matrix maintained rotation (determinant 1). otherwise transformation still introduce random artifacts (scaling, skewing, or other distortions). thus, after each rotation applied, transformation matrix should renormalized remains pure transformation. normalization can simple dividing each entry determinant.


Comments

Popular posts from this blog

java - Jmockit String final length method mocking Issue -

asp.net - Razor Page Hosted on IIS 6 Fails Every Morning -

c++ - wxwidget compiling on windows command prompt -