AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

DirectX 9 mit Delphi 2005

Ein Thema von Mario · begonnen am 9. Mär 2005
Antwort Antwort
Mario

Registriert seit: 7. Apr 2003
567 Beiträge
 
Delphi 2006 Enterprise
 
#1

DirectX 9 mit Delphi 2005

  Alt 9. Mär 2005, 16:03
Microsoft stellt für das Zeichnen per 3D mit DirectX9 in .Net gute Beispiele zur Verfügung:
http://msdn.microsoft.com/archive/en.../tutorials.asp

Leider ist der Einstieg für Delphi sehr verworren, darum habe ich Tutorial 3 für Delphi umgearbeitet.

Was wird benötigt:
Delphi 2005
DirectX SDK von Microsoft

Das DirectX SDK installiert die notwendigen Assemblies nach:
C:\WINDOWS\Microsoft.NET\Managed DirectX\v9.05.132\

Microsoft.DirectX, Microsoft.DirectX.Direct3D muss dem Projekt als Referenz hinzugefügt werden.

Folgende Klasse sollte in eine eigene Unit implementiert werden:
Delphi-Quellcode:
interface

uses Microsoft.DirectX, Microsoft.DirectX.Direct3D, System.Drawing,
  System.Windows.Forms;

type
  TPaintDirectX9 = class
  private
    Fdevice: Device; // Our rendering device
      FVertexBuffer: VertexBuffer;
    procedure InitializeGraphics(OutControl: System.Windows.Forms.Control);
    procedure OnCreateDevice(sender: TObject; e: EventArgs);
    procedure OnResetDevice(sender: TObject; e: EventArgs);
    procedure OnCreateVertexBuffer(sender: TObject; e: EventArgs);
    procedure SetupMatrices;
    procedure SetupLights;
  public
    constructor Create(OutControl: System.Windows.Forms.Control);
    procedure Render;
  end;

implementation

constructor TPaintDirectX9.Create(OutControl: System.Windows.Forms.Control);
begin
  inherited Create;
  try
    InitializeGraphics(OutControl);
  except
    on e: DirectXException
    do Raise Exception.Create('Fehler beim Zugriff auf DirectX 9: ' + e.Message);
  end;
end;

procedure TPaintDirectX9.InitializeGraphics(OutControl: System.Windows.Forms.Control);
var
  FPresentParams: PresentParameters;
begin
  FPresentParams := PresentParameters.Create;
  FPresentParams.Windowed := true; // We don't want to run fullscreen
  FPresentParams.SwapEffect := SwapEffect.Discard; // Discard the frames
  FPresentParams.EnableAutoDepthStencil := true; // Turn on a Depth stencil
  FPresentParams.AutoDepthStencilFormat := DepthFormat.D16; // And the stencil format

  Fdevice := Device.Create(0, DeviceType.Hardware, OutControl, CreateFlags.SoftwareVertexProcessing, [FPresentParams]); //Create a device
  Borland.Delphi.System.Include(Fdevice.DeviceReset, Self.OnResetDevice);
  self.OnCreateDevice(Fdevice, NIL);
  self.OnResetDevice(Fdevice, NIL);
end;

procedure TPaintDirectX9.OnCreateVertexBuffer(sender: TObject; e: EventArgs);
var
  vb: VertexBuffer;
  verts: System.&Array; //of CustomVertex.PositionNormal;
  i: Integer;
  theta: Single;
begin
  vb := VertexBuffer(sender);
  // Create a vertex buffer (100 customervertex)
  verts := vb.Lock(0,LockFlags.None); // Lock the buffer (which will return our structs)
  try
    for i := 0 to 49 do
    begin
      // Fill up our structs
      theta := (2 * Math.PI * i) / 49;
      verts.SetValue(CustomVertex.PositionNormal.Create(
        Vector3.Create(Math.Sin(theta), -1, Math.Cos(theta)),
        Vector3.Create(Math.Sin(theta), 0, Math.Cos(theta))),
        2*i);
      verts.SetValue(CustomVertex.PositionNormal.Create(
        Vector3.Create(Math.Sin(theta), 1, Math.Cos(theta)),
        Vector3.Create(Math.Sin(theta), 0, Math.Cos(theta))),
        2*i+1);
    end;
  finally
    vb.Unlock;
  end;
end;

procedure TPaintDirectX9.OnCreateDevice(sender: TObject; e: EventArgs);
var
  dev: Microsoft.DirectX.Direct3D.Device;
begin
  dev := Device(sender);
  // Hier wird der Puffer für die Dreiecke erzeugt
  FvertexBuffer := VertexBuffer.Create(typeof(CustomVertex.PositionNormal), 100, dev, Usage.WriteOnly, CustomVertex.PositionNormal.Format, Pool.Default);
  Borland.Delphi.System.Include(FvertexBuffer.Created, Self.OnCreateVertexBuffer);
  Self.OnCreateVertexBuffer(FvertexBuffer, NIL);
end;

procedure TPaintDirectX9.OnResetDevice(sender: TObject; e: EventArgs);
var
  dev: Device;
begin
  dev := Device(sender);
  // Turn off culling, so we see the front and back of the triangle
  dev.RenderState.CullMode := Microsoft.DirectX.Direct3D.Cull.None;
  // Turn on the ZBuffer
  dev.RenderState.ZBufferEnable := true;
  dev.RenderState.Lighting := true; //make sure lighting is enabled
end;

procedure TPaintDirectX9.SetupLights;
var
  col: System.Drawing.Color;
  mtrl: Material;
begin
  col := System.Drawing.Color.White;
  //Set up a material. The material here just has the diffuse and ambient
  //colors set to yellow. Note that only one material can be used at a time.
  mtrl := Microsoft.DirectX.Direct3D.Material.Create;
  mtrl.Diffuse := col;
  mtrl.Ambient := col;
  Fdevice.Material := mtrl;

  //Set up a white, directional light, with an oscillating direction.
  //Note that many lights may be active at a time (but each one slows down
  //the rendering of our scene). However, here we are just using one. Also,
  //we need to set the D3DRS_LIGHTING renderstate to enable lighting

  Fdevice.Lights[0].&Type := LightType.Directional;
  Fdevice.Lights[0].Diffuse := System.Drawing.Color.DarkTurquoise;
  Fdevice.Lights[0].Direction := Vector3.Create(Math.Cos(Environment.TickCount / 250.0), 1.0, Math.Sin(Environment.TickCount / 250.0));

  Fdevice.Lights[0].Enabled := true;//turn it on

  //Finally, turn on some ambient light.
  //Ambient light is light that scatters and lights all objects evenly
  Fdevice.RenderState.Ambient := System.Drawing.Color.FromArgb(32,32,32);
end;

procedure TPaintDirectX9.SetupMatrices;
begin
  // For our world matrix, we will just rotate the object about the y-axis.
  Fdevice.Transform.World := Matrix.RotationAxis(Vector3.Create(Math.Cos(Environment.TickCount / 250.0),1, Math.Sin(Environment.TickCount / 250.0)), Environment.TickCount / 3000.0 );

  // Set up our view matrix. A view matrix can be defined given an eye point,
  // a point to lookat, and a direction for which way is up. Here, we set the
  // eye five units back along the z-axis and up three units, look at the
  // origin, and define "up" to be in the y-direction.
  Fdevice.Transform.View := Matrix.LookAtLH(Vector3.Create( 0.0, 3.0,-5.0 ), Vector3.Create( 0.0, 0.0, 0.0), Vector3.Create( 0.0, 1.0, 0.0 ) );

  // For the projection matrix, we set up a perspective transform (which
  // transforms geometry from 3D view space to 2D viewport space, with
  // a perspective divide making objects smaller in the distance). To build
  // a perpsective transform, we need the field of view (1/4 pi is common),
  // the aspect ratio, and the near and far clipping planes (which define at
  // what distances geometry should be no longer be rendered).
  Fdevice.Transform.Projection := Matrix.PerspectiveFovLH( Math.PI / 4.0, 1.0, 1.0, 100.0);
end;

procedure TPaintDirectX9.Render;
begin
  //Clear the backbuffer to a blue color
  Fdevice.Clear(ClearFlags.Target or ClearFlags.ZBuffer, System.Drawing.Color.Blue, 1.0, 0);
  //Begin the scene
  Fdevice.BeginScene();
  // Setup the lights and materials
  SetupLights();
  // Setup the world, view, and projection matrices
  SetupMatrices();

  Fdevice.SetStreamSource(0, FVertexBuffer, 0);
  Fdevice.VertexFormat := CustomVertex.PositionNormal.Format;
  Fdevice.DrawPrimitives(PrimitiveType.TriangleStrip, 0, (4*25)-2);
  //End the scene
  Fdevice.EndScene();
  // Update the screen
  Fdevice.Present();
end;
Zum Aufruf benötigt man folgende Variablendeklaration:
 F3D: TPaintDirectX9; Das Objekt wird dann wie folgt erzeugt
Delphi-Quellcode:
  try
    // Die 3D Ausgabe wird hier auf Ein Panel gelegt
    F3D := TPaintDirectX9.Create(Self.Panel1);
  except
    on e: Exception
      do MessageBox.Show('Beim Erzeugen der 3D-Anzeige ist ein Fehler aufgetreten:'+
                         #13#10 + E.Message);
  end;
Das Zeichnen der 3D-Animation kann aus einem Timer aufgerufen werden:
  F3D.Render; [edit=Matze]Code formatiert. Mfg, Matze[/edit]
Schöne Grüße,
Mario Noack
  Mit Zitat antworten Zitat
Antwort Antwort

Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 20:57 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz