Hi,

On Tue, 17 Sep 2019, James Richters wrote:

> What I'm trying to do is much simpler than rendering a 3D object.. All

> I'm trying to do is display a 3D line drawing or wireframe on the

> screen. I don't need it to dynamically rotate or anything, and it

> doesn't need to show any surfaces, textures, lighting, reflections, or

> shadows, just give a representation of the XYZ points and lines

> connecting 2 pair of XYZ coordinates on the screen. The purpose of this

> is to show a 3D representation of a CNC tool path including the Z

> movements.

Well, it all boils down to the projection you want to make while you

transform from your coordinates from 3D to 2D. For the most simple

"isometric" projection with no perspective, you just throw away one of the

XYZ coordinates, and use the other two - this will result in a simple

"camera" which views at your object from either the front (XY), side (YZ)

or from the top (XZ). (Actually, this also depends on wether in your

coordinate system Y or Z represents depth, 3D editors/engines don't even

agree on this one, the code below assumes "Z" is depth.)

For a simple "perspective" projection, you can use a simplistic formula,

something like:

{ untested pseudocode }

procedure perspective_vertex(const v: T3DVertex; ZCenter: single;

out X, Y: single);

var

rdist1: single;

begin

zdist1:=1.0 / (v.z - zcenter);

X:=(v.x * zcenter) * zdist1;

Y:=(v.y * zcenter) * zdist1;

end;

This will put some sort of "perspective" on your 3D vertex, depending on

its Z coordinate. The ZCenter should be larger than the maximum dimension

of your object facing the "camera". Note that this formula is massively

simplified, but serves as the most simple perspective projection.

After this, you can use x/y coordinates to feed the wireframe drawer using

whatever drawing unit you see fit. You might need to do inc(x,width/2);

and inc(y,height/2); and/or multiply your values with a certain

scale-factor, depending on the size of your object, and how its

coordinates map to your 2D resolution.

All of the above methods assume that your object's 3D center resides at

the origo (center of the coordinate system). Anything more complicated

would require some proper matrices to be set up and calculate a full

series of model, view, and projection matrices, as others have already

mentioned, or would require pre-processing your 3D coordinates in a

certain way, so this simplistic formula can work.

Hope this helps,

--

Charlie

(Ps: actually, the FPC Packages contain two similar examples of a rotating

3D cube, for PalmOS and Atari, both written by me, to showcase the m68k

code generator and the units for these retro/niche OSes. They're at (SVN

trunk):

- packages/tosunits/examples/gemcube.pas

- packages/palmunits/examples/palmcube.pas

Showcased here (with video):

https://twitter.com/chainq/status/945010617672523777https://twitter.com/chainq/status/948865605209387010These show this most simplistic form of 3D calculation, and they also use

fixed point math, as that fit the only a few mhz fast 68000 CPUs in these

machines. But the basic algo and formula is the same with float and on

faster platforms. Now I'm quite tempted to make a ptc-graph version. :) )

_______________________________________________

fpc-pascal maillist -

[hidden email]
https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal