home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
The Unsorted BBS Collection
/
thegreatunsorted.tar
/
thegreatunsorted
/
programming
/
misc_programming
/
rtobj.pas
< prev
next >
Wrap
Pascal/Delphi Source File
|
1993-06-03
|
38KB
|
915 lines
(******************************************************************************
* rtObj *
* please notice - *
* this unit includes both the object3d unit, and the superobj unit, *
* and it is used with no reference to the WWToolKit window GUI library, *
* uses project3, instead of prjWind (It does, however, support OWL) *
* *
* In V2.x - The support collections are part of this unit as well ... *
******************************************************************************)
Unit rtObj;
(*******************************************************************************
* 3D Objects *
* ---------- *
* *
* A 3D object is a collection of points and lines in the 3D universe, *
* that represent the body we want to draw on the screen. *
* A 3D object is allways centered around point (0, 0, 0) in the 3D universe. *
* (Its center of gravity assuming it is has a uniform weight distribution *
* is in point (0, 0, 0) *
* At any moment during the object's life, we know it's distance from the *
* origin, And it's rotation using reveres rotation CTM. *
* *
* 3D Object methods: *
* constructor Open *
* destructor CloseMe *
* procedures: Rotate, Scale, Move, Show, Hide, Load, Save *
* SetToOrigin, Paint *
* *
*******************************************************************************)
interface
uses
{$ifdef windows}
winTypes
,winProcs
{$else}
graph
{$endif}
,Ctm3d
,hdr3d
,project3
,objects { needed for collection support .. }
;
type
P3dPointCollection = ^ T3dPointCollection;
T3dPointCollection = object(TCollection)
procedure freeItem(item : pointer); virtual;
end; { T3dPointCollection definition .. }
P3dLineCollection = ^ T3dLineCollection;
T3dLineCollection = object(TCollection)
procedure freeItem(item : pointer); virtual;
end; { T3dLineCollection definition .. }
PScreenPointsCollection = ^ TScreenPointsCollection;
TScreenPointsCollection = object(TCollection)
procedure freeItem(item : pointer); virtual;
end; { TScreenPointsCollection definition .. }
type
f_real = file of real;
{===================================================================}
{ Base object is the base class for 3D-objects. some functions }
{ are dummy virtual do-nothing, which are are implemented only for }
{ the descendend objects derived from BaseObject }
{===================================================================}
BaseObjectPtr = ^BaseObject;
BaseObject = object
MyCtm : Ctm; { This CTM applied to the object gives the }
{ objects Position after transformations }
Name : String; { Identifies the object }
myColor : word; { Main color for the object }
Location : point3d; { Central of gravity in real space }
scrPntUpdt : boolean; { True if screen points updated }
constructor open(myName : string; color : word);
destructor CloseMe; virtual;
{$ifdef windows}
procedure show(dc : hdc); virtual;
procedure hide(dc : hdc); virtual;
procedure paint(dc : hdc); virtual; {in specified color}
{$else}
procedure show; virtual;
procedure hide; virtual;
procedure paint; virtual; {in specified color}
{$endif}
procedure updateScreenPoints; virtual; {transform object 3D -> 2D}
procedure move(axis : axisType; by : real); virtual;
procedure translate(dx, dy, dz : integer); virtual;
{multy dimentional move in 1 call}
procedure scale(axis : axisType; factor : real); virtual;
procedure allScale(sx, sy, sz : real); virtual;
{multy dimentional scale in 1 call}
procedure rotate(axis : axisType; deg : real); virtual;
procedure goto3dPos(x, y, z : real); virtual; {translate to absolute place}
procedure setToOrigin; virtual;
{translate to 0,0,0, update points, and set myCtm to unit}
procedure calcLocation; virtual; {set Location to central gravity}
procedure deleteTransform; virtual; {set MyCtm to unit}
function load : word; virtual; {from disk}
function save : word; virtual; {to disk}
procedure writeMe(var elementFile : f_real); virtual; {to disk .. without opening file..}
procedure readMe(var elementFile : f_real); virtual;
end;
{===================================================================}
{ Obj3d is an object which represents a 3-D object with a poligon }
{ mesh. }
{===================================================================}
Obj3dPtr = ^Obj3d;
Obj3d = object(BaseObject)
(* Points : array[1..MaxPoints] of point3d; *)
Points : T3dPointCollection;
(* Lines : array[1..MaxLines] of Line3d; *)
Lines : T3dLineCollection;
(* scrPoints : array[1..MaxPoints] of screenPoints; *)
scrPoints : TScreenPointsCollection;
NumOfLines : integer;
NumOfPoints : integer;
ReverseRot : Ctm; { Saves only the reverse rotations }
unReverseRot: Ctm; { reverse of the above}
constructor open(myName : string; ref : point3d; color : word);
destructor CloseMe; virtual;
{$ifdef windows}
procedure paint(dc : hdc); virtual; {in specified color}
{$else}
procedure paint; virtual; {in specified color}
{$endif}
procedure updateScreenPoints; virtual; {transform object 3D -> 2D}
procedure calcLocation; virtual; {set Location to central gravity}
procedure setToOrigin; virtual;
procedure writeMe(var elementFile : f_real); virtual;
procedure readMe(var elementFile : f_real); virtual;
end;
const
maxSubObjects = 15;
type
complexObjPtr = ^complexObj;
ComplexObj = object(BaseObject)
childs : array [1..maxSubObjects] of obj3dPtr;
ctms : array [1..maxSubObjects] of ctm;
numOfChilds : integer; {counter of # of obj3d childs}
constructor open(myName : string; color : word);
destructor closeMe; virtual;
procedure updateScreenPoints; virtual;
procedure writeMe(var elementFile : f_real); virtual;
procedure readMe(var elementFile : f_real); virtual;
procedure calcLocation; virtual;
{$ifdef WINDOWS}
procedure paint(dc : hdc); virtual;
{$else}
procedure paint; virtual;
{$endif}
procedure move(axis : axisType; by : real); virtual;
procedure rotate(axis : axisType; deg : real); virtual;
procedure scale(axis : axisType; factor : real); virtual;
function addSubObject(myName : string; refPoint : point3d) : word;
function getChildPtr(index : integer) : obj3dPtr;
procedure rotateChild(child : integer; axis : axisType;
deg : real);
procedure scaleChild(child : integer; axis : axisType;
factor : real);
procedure moveChild(child : integer; axis : axisType;
by : real);
end;
implementation
(******************************************************************************
* Collection-implementations *
******************************************************************************)
(******************************************************************************
* T3dPointCollection.freeItem *
******************************************************************************)
procedure T3dPointCollection.freeItem;
begin
if (item <> nil) then
dispose(point3dPtr(item));
end; {T3dPointCollection.freeItem}
(******************************************************************************
* T3dLineCollection.freeItem *
******************************************************************************)
procedure T3dLineCollection.freeItem;
begin
if (item <> nil) then
dispose(line3dPtr(item));
end; {T3dLineCollection.freeItem}
(******************************************************************************
* TScreenPointsCollection.freeItem *
******************************************************************************)
procedure TScreenPointsCollection.freeItem;
begin
if (item <> nil) then
dispose(screenPointsPtr(item));
end; {TScreenPointsCollection.freeItem}
{%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%}
{ BaseObject implementation }
{%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%}
(*******************************************************************************
* BaseObject.Open *
*******************************************************************************)
constructor BaseObject.Open;
begin
name := myName;
myColor := color;
location := ZeroPoint;
MyCtm.SetUnit;
end; {baseObject.open}
(*******************************************************************************
* BaseObject.CloseMe *
*******************************************************************************)
destructor BaseObject.CloseMe;
begin
{ I'm here so my children will Close-themselfs properly }
end; {baseObject.closeMe}
(*******************************************************************************
* BaseObject.move *
*******************************************************************************)
procedure BaseObject.move(axis : axisType; by: real);
begin
case axis of
x : begin
myCtm.translateX(by);
location.x :=location.x+by;
end;
y : begin
myCtm.translateY(by);
location.y :=location.y+by;
end;
z : begin
myCtm.translateZ(by);
location.z :=location.z+by;
end;
end; {case}
scrPntUpdt := False;
end; {BaseObject.move}
(*******************************************************************************
* BaseObject.translate *
*******************************************************************************)
procedure BaseObject.translate(dx, dy, dz : integer);
begin
myCtm.translate(dx,dy,dz);
location.x :=location.x+dx;
location.y :=location.y+dy;
location.z :=location.z+dz;
scrPntUpdt := False;
end; {BaseObject.translate}
{use this routine when you know you need to translate more then one axis
before painting, you will use only one call, which will probably be
faster, and make your program easier to read, and maintain}
(*******************************************************************************
* BaseObject.show *
*******************************************************************************)
procedure BaseObject.show;
{$ifdef windows}
var
myPen, oldPen : HPen;
{$endif}
begin
{$ifdef WINDOWS}
myPen := getStockObject(black_Pen);
oldPen := selectObject(dc, myPen);
paint(dc);
selectObject(dc, oldPen);
deleteObject(myPen);
{$else}
setColor(myColor);
paint;
{$endif}
end; {baseObject.show}
(*******************************************************************************
* BaseObject.hide *
*******************************************************************************)
procedure BaseObject.hide;
{$ifdef windows}
var
myPen, oldPen : HPen;
{$endif}
begin
{$ifdef windows}
myPen := getStockObject(white_Pen);
oldPen := selectObject(dc, myPen);
paint(dc); {at this color}
selectObject(dc, oldPen);
deleteObject(myPen);
{$else}
setColor(0); {backGround}
paint; {at this color}
{$endif}
end; {baseObject.hide}
(*******************************************************************************
* BaseObject.Paint *
*******************************************************************************)
procedure BaseObject.Paint;
begin
if (not(scrPntUpdt)) then
updateScreenPoints;
{ alas, BaseObject cannot really paint becuase it does not have }
{ screen points (what a shame ...) }
end; {baseObject.paint}
(*******************************************************************************
* BaseObject.UpdateScreenPoints *
*******************************************************************************)
procedure BaseObject.UpdateScreenPoints;
begin
scrPntUpdt := True; { Have no screen points or any other points, so }
{ points are already updated (I think) }
end; {updateScreenPoints}
(*******************************************************************************
* BaseObject.scale *
*******************************************************************************)
procedure BaseObject.scale(axis : axisType; factor : real);
begin
myCtm.translate(-location.x,-location.y,-location.z);
case axis of
x : myCtm.scaleX(factor);
y : myCtm.scaleY(factor);
z : myCtm.scaleZ(factor);
end; {scale}
myCtm.translate(location.x,location.y,location.z);
scrPntUpdt := False;
end; {baseObject.scale}
(*******************************************************************************
* BaseObject.allScale *
*******************************************************************************)
procedure BaseObject.allScale(sx,sy,sz : real);
begin
myCtm.translate(-location.x, -location.y, -location.z);
myCtm.scale(sx,sy,sz);
myCtm.translate(location.x, location.y, location.z);
scrPntUpdt := False;
end; {allScale}
{call this routine to scale more then one axis at a time, with a single call}
(*******************************************************************************
* BaseObject.goto3dPos *
*******************************************************************************)
procedure BaseObject.goto3dPos;
begin
translate(round(x - location.x), round(y - location.y)
, round(z - location.z));
end; {baseObject.goto3dPos}
(*******************************************************************************
* BaseObject.setToOrigin *
*******************************************************************************)
procedure BaseObject.setToOrigin;
begin
goto3dPos(0, 0, 0);
myCtm.setUnit;
location := zeroPoint;
end; {BaseObject.setToOrign}
(*******************************************************************************
* BaseObject.CalcLocation *
*******************************************************************************)
procedure BaseObject.CalcLocation;
begin
location := zeroPoint; { What else could it be when there are no points ?}
end; {baseObject.calcLocation}
(*******************************************************************************
* BaseObject.deleteTransform *
*******************************************************************************)
procedure BaseObject.deleteTransform;
begin
myCtm.setUnit;
scrPntUpdt := false;
end; {baseObject.deleteTransform}
(******************************************************************************
* BaseObject.rotate *
******************************************************************************)
procedure BaseObject.rotate;
begin
myCtm.translate(-location.x,-location.y,-location.z);
case axis of
x : myCtm.rotateX(deg);
y : myCtm.rotateY(deg);
z : myCtm.rotateZ(deg);
end; {case}
myCtm.translate(location.x,location.y,location.z);
{rotation means : go to origin (translate -location),
rotate (rotate axis degrees),
go to prev pos (translate location);
}
scrPntUpdt := False;
end; {BaseObject.rotate, see interface for comments}
(******************************************************************************
* baseObject.load *
******************************************************************************)
function baseObject.load;
var
elementFile : f_real;
errC : word;
begin
{$i-} {supposed to be so, just making sure}
assign(elementFile,name);
reset(elementFile); {o.k. open it}
errC := ioResult;
load := errC;
if (errC = 0) then begin
readMe(elementFile);
errC := ioResult;
load := errC;
close(elementFile);
calcLocation;
scrPntUpdt := false;
end; {if}
end; { baseObject.load}
(******************************************************************************
* baseObject.save *
******************************************************************************)
function baseObject.save;
var
elementFile : f_real;
errC : word;
begin
{$i-} {supposed to be so, just making sure}
assign(elementFile,name);
rewrite(elementFile); {o.k. open it}
errC := ioResult;
save := errC;
if (errC = 0) then begin
writeMe(elementFile);
errC := ioResult; save := errC;
close(elementFile);
end; {if}
end; {baseObject.save}
(******************************************************************************
* baseObject.writeMe *
******************************************************************************)
procedure baseObject.writeMe;
begin
{override by descendents }
end; {baseObject.writeMe}
(******************************************************************************
* baseObject.readMe *
******************************************************************************)
procedure baseObject.readMe;
begin
{override by descendents }
end; {baseObject.readMe}
{%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%}
{ Obj3d implementation }
{%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%}
(*******************************************************************************
* Obj3d.open *
*******************************************************************************)
constructor Obj3d.open;
begin
BaseObject.Open(myName, color);
scrPntUpdt := False; {not calculated yet}
numOfLines := 0;
numOfPoints := 0;
myCtm.setUnit; {initialize to unit matrix}
reverseRot.setUnit;
unReverseRot.setUnit;
points.init(maxPoints, 5);
lines.init(maxLines, 5);
scrPoints.init(maxPoints, 5); { initiailize collections .. }
end; {Obj3d.open}
(*******************************************************************************
* Obj3d.CloseMe *
*******************************************************************************)
destructor Obj3d.CloseMe;
begin
end; {Obj3d.Close}
(*******************************************************************************
* Obj3d.updateScreenPoints *
*******************************************************************************)
procedure Obj3d.updateScreenPoints;
var i : integer;
p : point3d;
begin
for i := 1 to numOfPoints do begin
myCtm.transform(p, point3dPtr(points.items^[i])^); {transform by ctm}
calcPoint(p, screenPointsPtr(scrPoints.items^[i])^);
end; {for}
scrPntUpdt := True; {make sure for next time..}
{make all points ready}
end; {obj3d.updateScreenPoints}
(*******************************************************************************
* Obj3d.paint *
*******************************************************************************)
procedure Obj3d.paint;
{do the actual painting here}
var
i : integer;
begin
if ((numOfPoints = 0) or (numOfLines = 0)) then exit;
if (not(scrPntUpdt)) then
updateScreenPoints;
for i := 1 to numOfLines do begin
{$ifdef windows}
moveTo(dc, screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.fromP])^.sX,
screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.fromP])^.sY);
lineTo(dc, screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.toP])^.sX,
screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.toP])^.sY );
{$else}
line(screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.fromP])^.sX,
screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.fromP])^.sY,
screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.toP])^.sX,
screenPointsPtr(scrPoints.items^[line3dPtr(lines.items^[i])^.toP])^.sY);
{$endif}
end; { for }
{it should be noted that calcPoint has to convert points to integers}
end; {obj3d.paint}
(******************************************************************************
* obj3d.readMe *
******************************************************************************)
procedure obj3d.readMe;
var
tmp1,tmp2 : real;
i,j : byte;
p : point3dPtr;
l : line3dPtr;
s : screenPointsPtr;
begin
new(p);
points.insert(p); { we hold one un-used entry - because collection
index is 0, and out is 1, so instead of calculating
all of these -1's, we kill some space .. }
new(s);
scrPoints.insert(s);
new(l);
lines.insert(l);
read(elementFile, tmp1);
numOfPoints := trunc(tmp1);
for j := 1 to numOfPoints do begin
new(p);
read(elementFile, p^.x);
read(elementFile, p^.y);
read(elementFile, p^.z);
points.insert(p);
new(s);
scrPoints.insert(s); { allocate place for screen points .. }
end; {for}
read(elementFile, tmp1);
numOfLines := trunc(tmp1);
for j := 1 to numOfLines do begin
new(l);
read(elementFile, tmp1, tmp2);
l^.fromP := trunc(tmp1);
l^.toP := trunc(tmp2);
lines.insert(l);
end; {for}
end; {obj3d.readMe}
(******************************************************************************
* obj3d.writeMe *
******************************************************************************)
procedure obj3d.writeMe;
var
tmp1,tmp2 : real;
i,j : byte;
begin
tmp1 := numOfPoints;
write(elementFile, tmp1);
for j := 1 to numOfPoints do with point3dPtr(points.items^[j])^ do begin
write(elementFile, x);
write(elementFile, y);
write(elementFile, z);
end; {for}
tmp1 := numOfLines;
write(elementFile, tmp1);
for j := 1 to numOfLines do with line3dPtr(lines.items^[j])^ do begin
tmp1 := fromP;
tmp2 := toP;
write(elementFile, tmp1, tmp2);
end;
end; {obj3d.writeMe}
(*******************************************************************************
* obj3d.calcLocation *
*******************************************************************************)
procedure obj3d.calcLocation;
var
ce : point3d;
p : point3d;
i : integer;
begin
ce := zeroPoint; { (0, 0, 0) -> ce }
for i := 1 to numOfPoints do begin
myCtm.transform(p, point3dPtr(points.items^[i])^);
ce.x := ce.x + p.x;
ce.y := ce.y + p.y;
ce.z := ce.z + p.z;
end; {for}
location.x := ce.x / numOfPoints;
location.y := ce.y / numOfPoints;
location.z := ce.z / numOfPoints;
end; {obj3d.calcLocation}
(*******************************************************************************
* Obj3d.setToOrigin *
*******************************************************************************)
procedure Obj3d.setToOrigin;
var
i : integer;
p : point3d;
begin
goto3dPos(0, 0, 0);
for i := 1 to numOfPoints do begin
myCtm.transform(p, point3dPtr(points.items^[i])^);
point3dPtr(points.items^[i])^ := p;
end; {for}
scrPntUpdt := False; (** Instead of that THING above **)
myCtm.setUnit;
location := zeroPoint;
end; {BaseObject.setToOrign}
(*******************************************************************************
* ComplexObj.Open *
*******************************************************************************)
constructor ComplexObj.Open;
begin
BaseObject.Open(myName, color);
numOfChilds := 0;
end; {complexObj.open}
(*******************************************************************************
* ComplexObj.CloseMe *
*******************************************************************************)
destructor ComplexObj.CloseMe;
var
i : integer;
begin
for i := 1 to numOfChilds do
dispose(childs[i],closeMe);
baseObject.closeMe;
end; {complexObj.closeMe}
(*******************************************************************************
* ComplexObj.addSubObject *
*******************************************************************************)
function ComplexObj.addSubObject;
var
ret_code : word;
begin
if (numOfChilds >= maxSubObjects) then begin
addSubObject := 255; {signal error}
exit;
end;
inc(numOfChilds);
childs[numOfChilds] := new(obj3dPtr, open(myName, zeroPoint, myColor));
ret_code := childs[numOfChilds]^.load;
if (ret_code = 0) then begin
with refPoint do
childs[numOfChilds]^.translate(round(x),
round(y), round(z));
ctms[numOfChilds].copy(childs[numOfChilds]^.myCtm);
end; {if ret_c..}
addSubObject := ret_code;
end; {complexObj.addSubObject}
(*******************************************************************************
* complexObj.updateScreenPoints *
*******************************************************************************)
procedure complexObj.updateScreenPoints;
var
i : integer;
begin
for i := 1 to numOfChilds do begin
childs[i]^.myCtm.multiply_2(ctms[i], myCtm);
childs[i]^.updateScreenPoints;
end;
scrPntUpdt := True;
end; {complexObj.updateScreenPoints}
(*******************************************************************************
* complexObj.getChildPtr *
*******************************************************************************)
function complexObj.getChildPtr;
begin
getChildPtr := childs[index];
end; {complexObj.getChildPtr}
(*******************************************************************************
* ComplexObj.rotateChild *
*******************************************************************************)
procedure ComplexObj.rotateChild;
begin
with childs[child]^ do begin
myCtm.copy(ctms[child]);
rotate(axis, deg);
ctms[Child].copy(MyCtm);
myCtm.Multiply(Self.myCtm);
end;
end; {complexObj.rotateChild}
(*******************************************************************************
* ComplexObj.scaleChild *
*******************************************************************************)
procedure ComplexObj.scaleChild;
begin
with childs[child]^ do begin
myCtm.copy(ctms[child]);
scale(axis, factor);
ctms[Child].copy(MyCtm);
myCtm.Multiply(Self.myCtm);
end;
end; {complexObj.scaleChild}
(*******************************************************************************
* ComplexObj.moveChild *
*******************************************************************************)
procedure ComplexObj.moveChild;
begin
with childs[child]^ do begin
myCtm.copy(ctms[child]);
move(axis, by);
ctms[Child].copy(MyCtm);
myCtm.Multiply(Self.myCtm);
end;
end; {complexObj.moveChild}
(******************************************************************************
* complexObj.paint *
******************************************************************************)
procedure complexObj.paint;
var
i : integer;
begin
if (not(scrPntUpdt)) then
updateScreenPoints;
for i := 1 to numOfChilds do
{$ifdef WINDOWS}
childs[i]^.paint(dc);
{$else}
childs[i]^.paint;
{$endif}
end; {complexObj.paint}
(******************************************************************************
* complexObj.writeMe *
******************************************************************************)
procedure complexObj.writeMe;
var
i : integer;
r : real;
begin
r := 0.0 + numOfChilds;
write(elementFile, r);
for i := 1 to numOfChilds do
childs[i]^.writeMe(elementFile); {let all the kids write themselvs}
end; {complexObj.writeMe}
(******************************************************************************
* complexObj.readMe *
******************************************************************************)
procedure complexObj.readMe;
var
i : integer;
r : real;
begin
read(elementFile, r);
numOfChilds := round(r);
for i := 1 to numOfChilds do begin
childs[i] := new(Obj3dPtr, Open('Child', ZeroPoint, myColor));
childs[i]^.readMe(elementFile);
childs[i]^.calcLocation;
ctms[i].setUnit;
end; {for}
end; {complexObj.readMe}
(******************************************************************************
* complexObj.calcLocation *
******************************************************************************)
procedure complexObj.calcLocation;
var
i : integer;
begin
location := zeroPoint;
for i := 1 to numOfChilds do
with childs[i]^ do begin
calcLocation;
self.location.x := location.x + self.location.x;
self.location.y := location.y + self.location.y;
self.location.z := location.z + self.location.z;
end; {with}
with location do begin
x := x / numOfChilds;
y := y / numOfChilds;
z := z / numOfChilds;
end; {with..}
end; {complexObj.calclocation}
(******************************************************************************
* complexObj.move *
******************************************************************************)
procedure complexObj.move;
var
i : integer;
begin
(* for i := 1 to numOfChilds do
with childs[i]^ do
case axis of
x : location.x := location.x + by;
y : location.y := location.y + by;
z : location.z := location.z + by;
end; {case} *)
baseObject.move(axis, by);
end; {complexObj.move}
(******************************************************************************
* complexObj.rotate *
******************************************************************************)
procedure complexObj.rotate;
var
i : integer;
sint, cost : real;
begin
(* cost := cos(deg / 180.0 * 3.1415926535897932385);
sint := sin(deg / 180.0 * 3.1415926535897932385);
for i := 1 to numOfChilds do
with childs[i]^ do
case axis of
x : begin
location.y := location.y * cost -
location.z * sint;
location.z := location.y * sint +
location.z * cost;
end; {x}
y : begin
location.x := location.x * cost +
location.z * sint;
location.z := location.z * cost -
location.x * sint;
end; {y}
z : begin
location.x := location.x * cost -
location.y * sint;
location.y := location.y * cost +
location.x * sint;
end; {z}
end; {case} *)
baseObject.rotate(axis, deg);
end; {complexObj.rotate}
(******************************************************************************
* complexObj.scale *
******************************************************************************)
procedure complexObj.scale;
var
i : integer;
begin
(* for i := 1 to numOfChilds do
with childs[i]^ do
case axis of
x : location.x := location.x * factor;
y : location.y := location.y * factor;
z : location.z := location.z * factor;
end; {case} *)
baseObject.scale(axis, factor);
end; {complexObj.scale}
(******************************************************************************
* end. *
******************************************************************************)
end.