AGB  ·  Datenschutz  ·  Impressum  







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

Direct Draw in einem geschlossenen Bereich

Ein Thema von Dannyboy · begonnen am 13. Aug 2004 · letzter Beitrag vom 6. Sep 2004
Antwort Antwort
Dannyboy

Registriert seit: 4. Aug 2003
Ort: Delphi-Heaven
418 Beiträge
 
Delphi 7 Personal
 
#1

Direct Draw in einem geschlossenen Bereich

  Alt 13. Aug 2004, 15:29
Hallo Graphik-Freaks,
ich bin, wie in den letzten Tagen bereits erwähnt, dabei
einen Leveleditor für 2D Spiele zu generieren.
Dazu brauche ich in meinem Fenster ein rechteckigen Bereich, der
DirectX (Direct Draw) fähig ist, um dort das aktuelle Level an der
aktuellen Position darzustellen. Es darf NICHT die ganze Form einnehmen,
da noch Platz für Buttons etc. da sein muss.
Also, was verwende ich da am besten?
Besten Dank im Voraus.
DANNY
  Mit Zitat antworten Zitat
Benutzerbild von memphis
memphis

Registriert seit: 4. Apr 2003
Ort: Innsbruck
89 Beiträge
 
Turbo Delphi für Win32
 
#2

Re: Direct Draw in einem geschlossenen Bereich

  Alt 13. Aug 2004, 16:04
hallo

du kannst DirectDraw auch in einem Panel laufen lassen.
Hierzu musst du nur anstelle des Handles der Form, jenes des Panels benutzten.

Wenn ich mich nicht ganz irre wird im Funktionsaufruf SetCooperativeLevel das Handle übergeben. Ersetzt form1.handle einfach durch panel1.handle und es müsst dann funktionieren. Weiters befindet sich in dieser Funktion auch noch ein Flag für den Fullscreen-Modus, dieses musst du auch entfernen.

Ich habe leider grad keine Möglichkeit dies zu testen.

MfG
Luki
Lukas
Wenn du nicht mehr weiter weißt, zeichne dir 'nen Einheitskreis.
  Mit Zitat antworten Zitat
Dannyboy

Registriert seit: 4. Aug 2003
Ort: Delphi-Heaven
418 Beiträge
 
Delphi 7 Personal
 
#3

Re: Direct Draw in einem geschlossenen Bereich

  Alt 23. Aug 2004, 11:54
Sicher, dass eine TPanel-Komonente dafür geeignet ist?
Ich hab' meine Init-Funktion so gelassen, wie sie
bei der Form funktionierte, habe bloß dass Fullscreen-Flag
rausgehauen: Irgendwie mag's keine Panels, denn bei der
Form geht's.
How much wood would a wood-chuck chuck if a wood-chuck would chuck wood?
Check this out.
DANNYBOY
  Mit Zitat antworten Zitat
Vjay

Registriert seit: 2. Dez 2003
Ort: Berlin/Eschede
481 Beiträge
 
Delphi 7 Professional
 
#4

Re: Direct Draw in einem geschlossenen Bereich

  Alt 23. Aug 2004, 15:09
Also ich habe zwar keine Ahnung von DirectX, aber so wie es ausschaut braucht die funktion das Handle zu einem Fenster.

Das TPanel.Handle referenziert ebenfalls eines und daher müsste das eigentlich gehen.
Wer später bremst ist eher tot.
  Mit Zitat antworten Zitat
Dannyboy

Registriert seit: 4. Aug 2003
Ort: Delphi-Heaven
418 Beiträge
 
Delphi 7 Personal
 
#5

Re: Direct Draw in einem geschlossenen Bereich

  Alt 23. Aug 2004, 15:28
Zitat von Vjay:
Also ich habe zwar keine Ahnung von DirectX, aber so wie es ausschaut braucht die funktion das Handle zu einem Fenster.

Das TPanel.Handle referenziert ebenfalls eines und daher müsste das eigentlich gehen.
Nicht zwangsläufig. Buttons haben auch Handles und können logischwerweise
nicht als Display verwendet werden.
How much wood would a wood-chuck chuck if a wood-chuck would chuck wood?
Check this out.
DANNYBOY
  Mit Zitat antworten Zitat
Benutzerbild von dizzy
dizzy

Registriert seit: 26. Nov 2003
Ort: Lünen
1.932 Beiträge
 
Delphi 7 Enterprise
 
#6

Re: Direct Draw in einem geschlossenen Bereich

  Alt 23. Aug 2004, 17:06
Und wie sie das können

Nimm mal nen TMediaPlayer und nen Button. Dann wähle den Button als Display, und ab dafür. --> GEHT!
Ein Button ist nämlich ein WinControl, genau so wie ein Fenster, genau so wie ein Panel!
Fabian K.
INSERT INTO HandVonFreundin SELECT * FROM Himmel
  Mit Zitat antworten Zitat
Benutzerbild von memphis
memphis

Registriert seit: 4. Apr 2003
Ort: Innsbruck
89 Beiträge
 
Turbo Delphi für Win32
 
#7

Re: Direct Draw in einem geschlossenen Bereich

  Alt 23. Aug 2004, 17:20
hallo

Ich hab jetzt leider keine Möglichkeit es zu testen und meine DirectDraw Zeit ist auch schon lange her. Aber mit dem Panel funkioniert es sicher, das wieso und warum hat dizzy bereits erklärt und mit Direct3D funktioniert es so bei mir einwandfrei.

Mal guckn ob ich heute Abend noch ein bißchen Delphi-Quellcode auf ner Backup-CD finde ansonsten kann ich dir nur Auszüge aus meiner alte C++ 2d-Engine anbieten, die unter anderem auch af einem Panel einwandfrei funktionierte.

Spiele mal ein bißchen mit den anderen Flags herum, vieleicht funktionierts ja..
Ansonsten poste mal deinen Initialisierungs-Code, dann guck ichs mir mal an..


MfG
Luki
Lukas
Wenn du nicht mehr weiter weißt, zeichne dir 'nen Einheitskreis.
  Mit Zitat antworten Zitat
Benutzerbild von memphis
memphis

Registriert seit: 4. Apr 2003
Ort: Innsbruck
89 Beiträge
 
Turbo Delphi für Win32
 
#8

Re: Direct Draw in einem geschlossenen Bereich

  Alt 23. Aug 2004, 17:33
hallo

mir fällt gerade noch was ein? hast du das Flag für den exclusiven Modus gesetzt? Heißt glaub ich DDSCL_EXCLUSIVE oder so in der Art. Wenn ja, lösch es einfach mal... man kann nämlich wenn ich mich nicht ganz iree DirectDraw nur bei Fullscreen in den exclusiven Modus setzte.

Vieleicht hilfts...

MfG
Luki
Lukas
Wenn du nicht mehr weiter weißt, zeichne dir 'nen Einheitskreis.
  Mit Zitat antworten Zitat
Dannyboy

Registriert seit: 4. Aug 2003
Ort: Delphi-Heaven
418 Beiträge
 
Delphi 7 Personal
 
#9

Re: Direct Draw in einem geschlossenen Bereich

  Alt 24. Aug 2004, 09:14
Zitat von dizzy:
Und wie sie das können

Nimm mal nen TMediaPlayer und nen Button. Dann wähle den Button als Display, und ab dafür. --> GEHT!
Ein Button ist nämlich ein WinControl, genau so wie ein Fenster, genau so wie ein Panel!
Oh, wow, das habe ich gar nicht gewusst.
Zitat von memphis:
mir fällt gerade noch was ein? hast du das Flag für den exclusiven Modus gesetzt? Heißt glaub ich DDSCL_EXCLUSIVE oder so in der Art. Wenn ja, lösch es einfach mal... man kann nämlich wenn ich mich nicht ganz iree DirectDraw nur bei Fullscreen in den exclusiven Modus setzte.

Vieleicht hilfts...
Yo, <DDSLC_EXCLUSIVE> und <DDSCL_FULLSCREEN> müssen immer zusammen verwendet werden. Ich habe Euch jetzt mal die wichtigen Passagen meines Sourcecodes gepostet. Die Methode <init_DirectX> schlägt bei <SetCooperativeLevel> jedes Mal fehl. Übergeben wird in <display> ein TPanel-Objekt. Wie ihr sehen könnt, habe ich mit den Flags bereits herumgespielt, aber irgendwie komm' ich nicht auf die richtige Kombination. Der Fullscreen-Modus soll NICHT gesetzt werden, ergo darf auch das <DDSCL_EXCLUSIVE>-Flag nicht gesetzt sein. Sorry, ich dokumentiere meinen Source immer in englisch. So, wie unten gepostet, funktioniert es leider NICHT.
Seht's Euch mal bitte an.
Delphi-Quellcode:
type
  TLevelMap = class
  private
  // Display (panel, form, whatever) to be used as canvas for level
    display : HWND;
  // Direct Draw Object
    IDD : IDirectDraw;
  // front buffer surface for Direct-X
    Primary : IDirectDrawSurface;
  // back buffer for Direct-X
    Back : IDirectDrawSurface;
  public
    constructor create(const display : THandle);
    function Init_DirectX : boolean;
  end;

implementation

constructor TLevelMap.create;
begin
  inherited create;
  self.display:= display;
  IDD:= NIL;
  Primary:= NIL;
  Back:= NIL;
end;

function TLevelMap.Init_DirectX;
var ddsd: TDDSurfaceDesc;
    ddscaps: TDDSCaps;
begin
  result:=false;
// Try to initialize direct draw object
  if not (DirectDrawCreate(nil,IDD,nil)=DD_OK) then exit;
// Set Cooperative Level to flags mentioned below
{  if not (IDD.SetCooperativeLevel(Display,DDSCL_ALLOWREBOOT or
                                          DDSCL_EXCLUSIVE or
                                          DDSCL_FULLSCREEN or
                                          DDSCL_ALLOWMODEX)=DD_OK) then exit;
}

if not (IDD.SetCooperativeLevel(Display, //DDSCL_ALLOWREBOOT or
                                      // DDSCL_EXCLUSIVE or
                                       // DDSCL_FULLSCREEN { or
                                       DDSCL_NORMAL or
                                       DDSCL_NOWINDOWCHANGES or
                                         DDSCL_ALLOWMODEX)=DD_OK) then exit;
// initialize surfaceDesc
  with ddsd do
  begin
    dwSize:=sizeof(ddsd);
    dwFlags:=DDSD_CAPS or DDSD_BACKBUFFERCOUNT;
    ddsCaps.dwCaps:=DDSCAPS_PRIMARYSURFACE or DDSCAPS_FLIP or DDSCAPS_COMPLEX;
    dwBackBufferCount:=1;
  end;
// create front suface and attach back surface to it
  if not (IDD.CreateSurface(ddsd,Primary,nil)=DD_OK) then exit;
  ddscaps.dwCaps:=DDSCAPS_BACKBUFFER or DDSCAPS_VIDEOMEMORY;
  if not (Primary.GetAttachedSurface(ddscaps,Back)=DD_OK) then exit;
  result:=true;
end;
How much wood would a wood-chuck chuck if a wood-chuck would chuck wood?
Check this out.
DANNYBOY
  Mit Zitat antworten Zitat
Dannyboy

Registriert seit: 4. Aug 2003
Ort: Delphi-Heaven
418 Beiträge
 
Delphi 7 Personal
 
#10

Re: Direct Draw in einem geschlossenen Bereich

  Alt 6. Sep 2004, 11:06
Hi Leutz,
wollt' mich noch mal explizit bei Euch für Eure Hilfe bei diesem Thema bedanken. Es funktiniert jetzt ohne Probleme.

Bissi doof ist, dass DirectX im Fenstermodus scheinbar immer direkt auf den Desktop zeichnet
und zwar uabhängig davon, ob man das Handle eines Panels übergibt, das Handle des Fenters
oder einfach das Handle 0 (Null). Habe nun 2 Methoden: Zum Ereugen von Front - und
Backsurface.

Hier der Quelltext:
Delphi-Quellcode:
function TGraphicInterface.Init_DirectX;
var DDSurfaceDesc : TDDSurfaceDesc2;
    Clipper : IDirectDrawClipper;
    res : HRESULT;
begin
  result:=false;
  res:= DirectDrawCreateEx(nil, DD7, IID_IDirectDraw7, nil);
  if res <> DD_OK then
  begin
    self.SetLastError(DDErrorString(res));
    exit;
  end;
  res:= DD7.SetCooperativeLevel(0, DDSCL_NORMAL );
  if res <> DD_OK then
  begin
    self.SetLastError(DDErrorString(res));
    exit;
  end;
  fillchar(DDSurfaceDesc, sizeof(DDSurfaceDesc), 0);
  with DDSurfaceDesc do
  begin
    dwSize:=sizeof(DDSurfaceDesc);
    dwFlags:= DDSD_CAPS;
    ddsCaps.dwCaps:=DDSCAPS_PRIMARYSURFACE;
  end;
  res:= DD7.CreateSurface( DDSurfaceDesc,Primary,nil);
  if res <> DD_OK then
  begin
    self.SetLastError(DDErrorString(res));
    exit;
  end;
  if not self.CreateBackgroundSurface(self.Back, width, height) then
  begin
    self.SetLastError('<CreateSurface> returned FALSE');
    exit;
  end;
  res:= DD7.CreateClipper(0, Clipper, nil);
  if res <> DD_OK then
  begin
    self.SetLastError('<Create Clipper> returned FALSE');
    exit;
  end;
  result:= res = DD_OK
end;

Function TGraphicInterface.CreateBackgroundSurface;
Var Desc : TDDSurfaceDesc2;
Begin
  ZeroMemory(@Desc,SizeOf(Desc));
  Desc.dwSize:= SizeOf(Desc);
  Desc.dwFlags := DDSD_CAPS OR DDSD_WIDTH OR DDSD_HEIGHT;
  Desc.dwWidth := width;
  Desc.dwHeight:= height;
  Desc.ddsCaps.dwCaps:= DDSCAPS_OFFSCREENPLAIN;
  Result:= DD7.CreateSurface(Desc, Surface, nil) = DD_OK;
end;
How much wood would a wood-chuck chuck if a wood-chuck would chuck wood?
Check this out.
DANNYBOY
  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 21:28 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