Path: utzoo!news-server.csri.toronto.edu!cs.utexas.edu!wuarchive!sdd.hp.com!spool.mu.edu!uwm.edu!bionet!ames!uhccux!munnari.oz.au!eric!bernie From: bernie@eric.ecr.mu.oz (Bernie Kirby) Newsgroups: comp.windows.x Subject: Re: 3d rotation in room coords? Summary: Here is one alternative... Message-ID: <6999@munnari.oz.au> Date: 6 Mar 91 07:54:59 GMT References: <9103050342.AA20065@maui.coral.com> Sender: news@cs.mu.oz.au Lines: 102 In article <9103050342.AA20065@maui.coral.com>, tomt@maui.coral.COM (Tom Tulinsky) writes: > > I'd like to allow the user to do 3d rotations of an object in the > 'room' coordinate system; i.e. y is toward the ceiling, x is to his > right, and z is out of the screen (rt-handed). I want this to be true > even after he has done some rotations.... The naive way of > implementing rotations accumulates them so that a 90 deg. y rotation, > the x axis is now pointing out of the screen, where the room z axis > is. > > I've tried everything I can think of, and can't get it to work. > > My latest version, (using the Vogle package from uunet, somewhat like Here is a Vogle program that presents one alternative... When you press button 1 (on the mouse) it rotates about X, when you press button 2 (on the mouse) it rotates about Y, when you press button 3 (on the mouse) it rotates about Z. When you press all 3 buttons it exits. The rotations are proportional to the x position of the cursor and continue to accumulate as long as the button is pressed. Bernie. ---------- #include #define R2D (1.0 / D2R) main() { int but, i, j; float x, y; float x_rot, y_rot, zrot, xrot, yrot; prefsize(512, 512); vinit(""); /* Get device from envirionment */ makeobj(1); color(1); move(0.0, 0.0, 0.0); draw(0.4, 0.0, 0.0); drawchar('x'); color(2); move(0.0, 0.0, 0.0); draw(0.0, 0.4, 0.0); drawchar('y'); color(3); move(0.0, 0.0, 0.0); draw(0.0, 0.0, 0.4); drawchar('z'); closeobj(); backbuffer(); zrot = yrot = xrot = 0.0; while ((but = slocator(&x, &y)) <= 4) { /* get mouse x,y */ color(BLACK); clear(); /* * This one rotates about the normal orthogonal unrotated * axes... but needs button 1 for about Y button 2 for * about X, button 3 for Z. */ pushmatrix(); /* Save original... */ translate(.4, 0.0, 0.0); rotate(yrot, 'y'); rotate(xrot, 'x'); rotate(zrot, 'z'); if (but == 1) { xrot += 100.0 * -x; } else if (but == 2) { yrot += 100.0 * -x; } else if (but == 4) { zrot += 100.0 * -x; } callobj(1); popmatrix(); /* * This lot does it the normal way... ie if you rotate * about the X-axis then rotate about Y the Y rotation * is about the new X-rotated axis. */ pushmatrix(); y_rot = 100.0 * -x; x_rot = 100.0 * -y; translate(-0.4, 0.0, 0.0); rotate(y_rot, 'y'); /* do y rot */ rotate(x_rot, 'x'); /* do x rot */ callobj(1); popmatrix(); swapbuffers(); } }