| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275 |
- unit fActorTwocamD;
- interface
- uses
- Winapi.Windows,
- Winapi.OpenGL,
- System.SysUtils,
- System.Classes,
- System.UITypes,
- Vcl.Imaging.Jpeg,
- Vcl.Buttons,
- Vcl.Controls,
- Vcl.ExtCtrls,
- Vcl.ComCtrls,
- Vcl.Forms,
- Vcl.StdCtrls,
- Vcl.Graphics,
- GLScene.Keyboard,
- GLScene.VectorTypes,
- GLS.Coordinates,
- GLS.BaseClasses,
- GLScene.Utils,
- GLScene.VectorGeometry,
- GLS.XCollection,
- GLS.PersistentClasses,
- GLS.Scene,
- GLS.Objects,
- GLS.Cadencer,
- GLS.VectorFileObjects,
- GLS.SkyDome,
- GLS.SceneViewer,
- GLS.Navigator,
- GLS.FileMD2,
- GLS.File3DS,
- GLS.GeomObjects,
- GLS.DCE;
- type
- TFormActorTwocam = class(TForm)
- GLScene1: TGLScene;
- GLCamera1: TGLCamera;
- dcMushroom: TGLDummyCube;
- diskClover: TGLDisk;
- GLSceneViewer1: TGLSceneViewer;
- Actor1: TGLActor;
- Actor2: TGLActor;
- GLCadencer1: TGLCadencer;
- Panel1: TPanel;
- Timer1: TTimer;
- GLCamera2: TGLCamera;
- Label3: TLabel;
- Label4: TLabel;
- DummyCube2: TGLDummyCube;
- ffMushroom: TGLFreeForm;
- GLLightSource2: TGLLightSource;
- DummyCube3: TGLDummyCube;
- Label1: TLabel;
- SkyDome1: TGLSkyDome;
- GLNavigator1: TGLNavigator;
- GLUserInterface1: TGLUserInterface;
- CBMouseLook: TCheckBox;
- GLDCEManager1: TGLDCEManager;
- procedure FormCreate(Sender: TObject);
- procedure Timer1Timer(Sender: TObject);
- procedure GLCadencer1Progress(Sender: TObject;
- const deltaTime, newTime: Double);
- procedure CBMouseLookClick(Sender: TObject);
- private
- Path: TFileName;
- procedure AddMushrooms;
- procedure HandleKeys(const deltaTime: Double);
- end;
- var
- FormActorTwocam: TFormActorTwocam;
- implementation
- {$R *.DFM}
- const
- cWalkStep = 6; // this is our walking speed, in 3D units / second
- cStrafeStep = 6; // this is our strafing speed, in 3D units / second
- cRotAngle = 60; // this is our turning speed, in degrees / second
- cRunBoost = 2; // speed boost when running
- cSpread = 90;
- cNbMushrooms = 15;
- procedure TFormActorTwocam.FormCreate(Sender: TObject);
- begin
- Path := GetCurrentAssetPath();
- SetCurrentDir(Path + '\model');
- // Load static mushroom mesh
- ffMushroom.LoadFromFile('mushroom.3ds');
- // Duplicate our reference mushroom (but not its mesh data !)
- AddMushrooms;
- // Load skeletal Actor model
- SetCurrentDir(Path + '\modelext');
- Actor1.LoadFromFile('waste.md2');
- Actor1.Animations.LoadFromFile('Quake2Animations.aaf');
- Actor1.Scale.SetVector(0.04, 0.04, 0.04, 0);
- // Load weapon model
- Actor2.LoadFromFile('WeaponWaste.md2');
- // Load weapon texture
- Actor1.Material.Texture.Image.LoadFromFile('Waste.jpg');
- Actor2.Material.Texture.Image.LoadFromFile('WeaponWaste.jpg');
- Actor2.Animations.Assign(Actor1.Animations);
- // Define animation properties
- Actor1.AnimationMode := aamLoop;
- Actor1.SwitchToAnimation('stand');
- Actor1.FrameInterpolation := afpLinear;
- Actor2.Synchronize(Actor1);
- // Load Texture for ground disk
- SetCurrentDir(Path + '\texture');
- diskClover.Material.Texture.Disabled := False;
- diskClover.Material.Texture.Image.LoadFromFile('clover.jpg');
- end;
- procedure TFormActorTwocam.CBMouseLookClick(Sender: TObject);
- begin
- GLUserInterface1.MouseLookActive := CBMouseLook.Checked;
- end;
- procedure TFormActorTwocam.HandleKeys(const deltaTime: Double);
- var
- moving: String;
- boost: Single;
- begin
- // This function uses asynchronous keyboard check (see GLS.XCollection.pas)
- if IsKeyDown(VK_ESCAPE) then
- Close;
- if IsKeyDown('A') then
- begin
- CBMouseLook.Checked := True;
- CBMouseLookClick(Self);
- end;
- if IsKeyDown('D') then
- begin
- CBMouseLook.Checked := False;
- CBMouseLookClick(Self);
- end;
- // Change Cameras
- if IsKeyDown(VK_F7) then
- begin
- GLSceneViewer1.Camera := GLCamera1;
- Actor1.Visible := True;
- Label4.Font.Style := Label4.Font.Style - [fsBold];
- Label3.Font.Style := Label3.Font.Style + [fsBold];
- end;
- if IsKeyDown(VK_F8) then
- begin
- GLSceneViewer1.Camera := GLCamera2;
- Actor1.Visible := False;
- Label4.Font.Style := Label4.Font.Style + [fsBold];
- Label3.Font.Style := Label3.Font.Style - [fsBold];
- end;
- // Move Actor in the scene
- // if nothing specified, we are standing
- moving := 'stand';
- // first, are we running ? if yes give animation & speed a boost
- if IsKeyDown(VK_SHIFT) then
- begin
- Actor1.Interval := 100;
- boost := cRunBoost * deltaTime
- end
- else
- begin
- Actor1.Interval := 150;
- boost := deltaTime;
- end;
- Actor2.Interval := Actor1.Interval;
- // are we advaning/backpedaling ?
- if IsKeyDown(VK_UP) then
- begin
- GLNavigator1.MoveForward(cWalkStep * boost);
- moving := 'run';
- end;
- if IsKeyDown(VK_DOWN) then
- begin
- GLNavigator1.MoveForward(-cWalkStep * boost);
- moving := 'run';
- end;
- // slightly more complex, depending on CTRL key, we either turn or strafe
- if IsKeyDown(VK_LEFT) then
- begin
- if IsKeyDown(VK_CONTROL) then
- GLNavigator1.StrafeHorizontal(-cStrafeStep * boost)
- else
- GLNavigator1.TurnHorizontal(-cRotAngle * boost);
- moving := 'run';
- end;
- if IsKeyDown(VK_RIGHT) then
- begin
- if IsKeyDown(VK_CONTROL) then
- GLNavigator1.StrafeHorizontal(cStrafeStep * boost)
- else
- GLNavigator1.TurnHorizontal(cRotAngle * boost);
- moving := 'run';
- end;
- // update animation (if required)
- // you can use faster methods (such as storing the last value of "moving")
- // but this ones shows off the brand new "CurrentAnimation" function :)
- if Actor1.CurrentAnimation <> moving then
- begin
- Actor1.SwitchToAnimation(moving);
- Actor2.Synchronize(Actor1);
- end;
- end;
- procedure TFormActorTwocam.GLCadencer1Progress(Sender: TObject;
- const deltaTime, newTime: Double);
- begin
- HandleKeys(deltaTime);
- GLUserInterface1.MouseLook;
- GLSceneViewer1.Invalidate;
- GLUserInterface1.MouseUpdate;
- end;
- // add a few mushrooms to make the "landscape"
- procedure TFormActorTwocam.AddMushrooms;
- var
- i: Integer;
- proxy: TGLProxyObject;
- s: TGLVector;
- f: Single;
- begin
- // spawn some more mushrooms using proxy objects
- for i := 0 to cNbMushrooms - 1 do
- begin
- // create a new proxy and set its MasterObject property
- proxy := TGLProxyObject(dcMushroom.AddNewChild(TGLProxyObject));
- proxy.ProxyOptions := [pooObjects];
- proxy.MasterObject := ffMushroom;
- // retrieve reference attitude
- proxy.Direction := ffMushroom.Direction;
- proxy.Up := ffMushroom.Up;
- // randomize scale
- s := ffMushroom.Scale.AsVector;
- f := (1 * Random + 1);
- ScaleVector(s, f);
- proxy.Scale.AsVector := s;
- // randomize position
- proxy.Position.SetPoint(Random(cSpread) - (cSpread / 2),
- ffMushroom.Position.z + 0.8 * f, Random(cSpread) - (cSpread / 2));
- // randomize orientation
- proxy.RollAngle := Random(360);
- proxy.TransformationChanged;
- end;
- end;
- procedure TFormActorTwocam.Timer1Timer(Sender: TObject);
- begin
- Caption := Format('%.2f FPS', [GLSceneViewer1.FramesPerSecond]);
- GLSceneViewer1.ResetPerformanceMonitor;
- end;
- end.
|