绘制Directdraw窗口

时间:2013-10-07 16:43:08

标签: delphi assembly directx gdi

我一直致力于一个修复旧游戏的项目,并最终获得了新的想法,添加了一些关于游戏世界的额外信息,并实时跟踪游戏本身隐藏的一些重要信息(没有实际原因)并遇到了这个问题:

当我尝试绘制游戏时,为了显示我想要的信息,游戏会更新自己的窗口并进行绘制。

我的第一个方法是使用一个带有HWND_TOPMOST的窗口位于游戏窗口的顶部,但它没有按预期工作,窗口不会越过游戏窗口而不会显示信息。

第二种方法是使用TextOut等GDI函数,文本在那里但会闪烁很多并且在很短的时间内强制绘制它会占用太多内存。

我想要一些关于如何在不实际挂钩DX功能的情况下做到这一点的想法(因为我对DX知之甚少)。有没有办法实际绘制这个窗口以显示信息而不会闪烁?

1 个答案:

答案 0 :(得分:0)

您可以使用unDelphiX获取一个执行DirectX的Delphi程序包 您可以在此处下载该软件包:http://www.micrel.cz/Dx/

它完全是最新的,使DirectX几乎像标准的GDI一样工作。

没有闪烁的绘图
消除闪烁的技巧是绘制到屏幕外的表面并在完成后“翻转”屏幕外表面。
翻盖可以与VerticalSync同步,因此也没有撕裂。

<强>演示
有一个演示,显示当前时间,以毫秒为单位,没有任何闪烁。

unit Main;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  StdCtrls, ExtCtrls, Menus, DXClass, DXDraws;

type
  TMainForm = class(TDXForm)
    DXDraw: TDXDraw;
    DXTimer: TDXTimer;  //Precision timer. 
    procedure DXDrawFinalize(Sender: TObject);
    procedure DXDrawInitialize(Sender: TObject);
    procedure DXTimerTimer(Sender: TObject; LagCount: Integer);
  end;

var
  MainForm: TMainForm;

implementation

uses MMSystem;

{$R *.DFM}

procedure TMainForm.DXDrawInitialize(Sender: TObject);
begin
  DXTimer.Enabled := True;
end;

procedure TMainForm.DXDrawFinalize(Sender: TObject);
begin
  DXTimer.Enabled := False;
end;

procedure TMainForm.DXTimerTimer(Sender: TObject; LagCount: Integer);
var
  formattedDateTime: string;
begin
  if not DXDraw.CanDraw then exit;

  DXDraw.Surface.Fill(0);

  with DXDraw.Surface.Canvas do  //Draw to offscreen surface.
  begin
    Brush.Style := bsClear;
    Font.Color := clWhite;
    Font.Size := 30;
    DateTimeToString(formattedDateTime, 'hh:nn:ss.zzz', Now);
    Textout(30, 30, formattedDateTime);

    Release; {  Indispensability  }
  end;

  DXDraw.Flip;  //Flip the offscreen surface to screen, no flicker :=)
end;

end.

在XE2中安装unDelphiX
为了在Delphi XE2中安装软件包,我必须将DesignIDE添加到dpk的requires子句中。像这样:

enter image description here

这将解决DesignIntf.dcu未找到错误。

全屏显示
如果你想要全屏,你可以在DXDraw的设置中启用它,但请注意:

enter image description here

如果您在未启用doFullScreen的情况下启用doSelectDriver,则会出现interface not supported错误。启用它们两者,一切都会好的。
请参阅:http://www.micrel.cz/Dx/history.rtf

不要忘记听按键并退出 ESC 上的应用程序,否则你将陷入全屏模式。