0

I am using a combination of a rotation matrices, weak perspective equations, and a custom turtle wrapper to make a 3D turtle wrapper (It's a toy project to see if I can do it 3D without numpy and also using turtle) To clarify, so I don't have to copy and paste the code, pix(point, update) stamps a small square turtle on the screen to show a vertex. setup() makes it tracer(0,0), and then shapesize(1 / 20, 1 / 20), ht and finally penup() refresh() just uses update() Here it is:

def vertdata(crt): #CRT stands for Coord-Rotation-Transformation. I took 
                   #transformation out for now, because those values are 0
                   #for this example.
  vert = [crt[0][0],crt[0][1],crt[0][2]]
  rotation = [crt[1][0],crt[1][1],crt[1][2]]
  return rotate(vert, rotation)


def vertex(point, upd):
  data = vertdata(point)
  pix([((data[0] * 2) / ((data[2] / 15) - 15) * 10), ((data[1] * 2) / ((data[2] / 15) - 15) * 10)], upd)

setup(100, 1000, 1000)
for x in range(3600):
    clear()
    vertex(
          [[10,-10,10],
           [45,45,x]],
          False
          )

    vertex(
          [[-10,-10,10],
           [45,45,x]],
          False
          )

    vertex(
          [[10,10,10],
           [45,45,x]],
          False
          )

    vertex(
          [[-10,10,10],
           [45,45,x]],
          False
          )

    vertex(
          [[10,-10,-10],
           [45,45,x]],
          False
          )

    vertex(
          [[-10,-10,-10],
           [45,45,x]],
          False
          )

    vertex(
          [[10,10,-10],
           [45,45,x]],
          False
          )

    vertex(
          [[-10,10,-10],
           [45,45,x]],
          False
          )
    refresh()

#Sorry about the long code. I don't really think I can simplify this any more.

What's the problem? Rotation on the Z axis is distorted. The cube stretches and deforms. A long time ago, I did the same thing in scratch (a loooooonggg time ago) and I took those equations and typed them into python because I knew they worked. (So yes, they work) I can't spot the problem, maybe one of you can? This is kind of my last resort. Here's a picture to help. Sorry, I'm on mobile now because I no longer have access to the computer, so I can't give a picture of the distortion.

img

My guess is a typo, but I can't find one.

CoderBoy
  • 107
  • 11
  • 1
    not a python coder so read with prejudice. 1. The perspective equation looks OK but I would feel safer with floating point constants to ensure floating point division (unless you want to use the integer math by design). 2. I do not see the rotation code anywhere my bet is the problem is there. Check if your goniometric operations need radians or degrees. 3. What is the meaning of update? – Spektre Nov 28 '17 at 08:12
  • @Spektre They need radians, I double checked after you suggested. Tcos/Tsin are custom functions for radians. Update takes the pixel data stored and moves it to the window, displaying all of it. (I think that's how it works) all I know is updating all together rather than individually is much faster. If the rotation equation isn't the problem, maybe it's my weak perspective equation? I tried implementing a normal perspective equation but Wikipedia didn't explain it all that well. – CoderBoy Nov 28 '17 at 11:18
  • @Spektre I appreciate your looking at it, I always make it a point to thank those who help answer my questions. Also, this question was a proofreading and geometry question more than it was a programming, (unless the problem lies within my programming) so you didn't really have to know python. Also, vertex runs the CRT matrix through vertdata(crt), which you can see has "return rotate(vert, rotation)" vertex is the 3D to 2D function while vertdata is the 3D math function. Oops! I forgot to include the code where rotate is defined, my rotation equation is in there! I will add it when I get home – CoderBoy Nov 28 '17 at 11:36
  • if your `sin` and `cos` need radians then your angles are wrong (I see `+/-10`) you should convert them to radians first ... `+/-10*rad` where `rad=M_PI/180.0` ... `M_PI=3.1415...` – Spektre Nov 28 '17 at 15:46
  • Also I would rather use [Understanding 4x4 homogenous transform matrices](https://stackoverflow.com/a/28084380/2521214) where you can stack up any transformations together into single matrix. You can expand that to higher dimensions like [How to use 4d rotors](https://stackoverflow.com/a/45116079/2521214) – Spektre Nov 28 '17 at 16:04
  • @Spektre The tsin and tcos already do that. Plus, I fixed it. The reason z was off was because one of the x's were being multiplied by cos(A) (theta) instead of cos(C) (whatever z rotation is represented by) – CoderBoy Nov 28 '17 at 20:01
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/160042/discussion-between-roberto-bassett-and-spektre). – CoderBoy Nov 29 '17 at 02:44

1 Answers1

0

I fixed it, it was a typo in my equation. Also, I forgot to include the rotation equation function in the post.

def tcos(angle):
  r = radians(angle)
  return cos(r)

def tsin(angle):
  r = radians(angle)
  return sin(r)

def rotate(vert, rot):
  cA,cB,cC = [tcos(rot[0]),tcos(rot[1]),tcos(rot[2])]
  sA,sB,sC = [tsin(rot[0]),tsin(rot[1]),tsin(rot[2])]
  x,y,z = [vert[0],vert[1],vert[2]]


  return [((x * cB * cC) + (y * sA * sB * cC) + (y * cA * sC) + (z * -cA * sB * cC) + (z * sA * sC)),
          ((x * -cB * sC) + (y * -sA * sB * sC) + (y * cA * cC) + (z * cA * sB * sC) + (z * sA * cC)),
          ((x * sB) + (y * (-sA * cB)) + (z * (cA * cB)))]

#In the very first set of parenthesis, it was x * cB * cA before. That was the problem.
CoderBoy
  • 107
  • 11