当前位置:主页>销售管理软件> 列表

谁能将下面DirectDraw画图速度提高10倍?

进销存管理软件版1楼: 以下程序是将屏幕分成3*3的小格子,每个格子填充颜色,当填充整个屏幕时,速度较慢,一秒钟只能进行2次。
有谁知道媒体播放器是如何填充颜色的,没有感觉到有停顿现象,不会使用setpixel吧,那样速度会更慢。
deltaw=3;
deltah=3;
void TForm1::Draw(void)//如何提高速度
{
HDC DC;
if (lpDDSPrimary->IsLost() == DDERR_SURFACELOST)
lpDDSPrimary->Restore();
if (lpDDSBack->GetDC(&DC) == DD_OK)
{
Canvas->Handle = DC;//能否不用Canvas,直接写缓存,加快速度?
if(phase)
{
top=1;
//填充方格颜色,当方格数量较多时,速度较慢
for(int i=0;iClipRect.Bottom;i+=deltah)
{
left=1;
for(int j=0;jClipRect.Right;j+=deltaw)
{
Canvas->Brush->Color=(TColor)RGB(255-i,255-j,255-i*j);
Canvas->FillRect(Rect(left,top,left+deltaw,top+deltah));
left+=deltaw;
}
top+=deltah;
}
Canvas->TextOutA(50,100,"Front");
phase = 0;
}
else
{
top=1;
for(int i=0;iClipRect.Bottom;i+=deltah)
{
left=1;
for(int j=0;jClipRect.Right;j+=deltaw)
{
Canvas->Brush->Color=(TColor)RGB(255-i*j,255-j,255-i);
Canvas->FillRect(Rect(left,top,left+deltaw,top+deltah));
left+=deltaw;
}
top+=deltah;
}
Canvas->TextOutA(50,150,"Back");
phase = 1;
}
lpDDSBack->ReleaseDC(DC);
}
}
以上程序来自c++builder的例子,我做了修改,如果有朋友想要源代码,请留下email共同探讨

2楼: email : ak_20042008@163.com
发我一份吧 如管家婆免费软件下载

3楼: 要一份研究一下
songyx0@126.com
谢谢

4楼: 1、觉得可能是 FillRect 的问题。你每次就贴窄窄的一条,能快么?
后来创建一个 Bitmap,先用他的 ScanLine 方法进行填充,然后用 BitBlt 将 Bitmap 贴到画面上。由于 ScanLine 可以操作设备无关位图(Device Independent Bitmap),速度还是跟得上去的。至于速度提高 10 倍我没有概念,换个好显卡应该没问题。
2、你可以把要求说明,现写一个都不难。

5楼: 你这是用gui 函数画图,不是用 dshow画图

6楼: 如果用 想快 就得先把图画好 再贴过去

进销存管理软件版7楼: To vvyang :需求是这样的,我模拟大屏幕播放动画,大屏幕上的每个像素对应屏幕上的一个方格,每个像素的颜色值RGB存放在文件中,每播放一帧需要从文件中读取一帧数据的RGB值,把颜色值填入相应的方格内。要求每秒播放20帧左右,ScanLine如何处理?
To workshop:如何用dshow画图?是直接用API函数吗?能否给个例子?

8楼: DIRECTDRAW+MMX加速

9楼: FillRect是GDI方法,速度自然很慢,可以使用Blt的颜色填充,速度可以提高10倍以上.
ddbltfx.dwFillColor =(TColor)RGB(255-i,255-j,255-i*j);
rect=Rect(left,top,left+deltaw,top+deltah);
lpDDSBack->Blt(&rect, NULL, NULL, DDBLT_COLORFILL, &ddbltfx);

10楼: 谢谢楼上,按照您的方法使用颜色填充速度只能提高2倍左右。继续努力,如果不使用Canvas,如何使用DirectDraw直接画园等图形?

11楼: 3*3的大小.我提供两个方法实现....


1.只画1*1,再放大3倍....

2.3*3中其实是由9幅相同的图形构成的...你可只出一幅,其它8份BIT
(使用DIRECTDRAW的直接写屏技术,会快很多的,我用P4 2.4G的电脑,FPS 可达到70左右)
(对了.你图形的颜色数为多少的)
qq:112981347

12楼: to:wlong01
我使用DirectDraw每秒只有5次左右(在全屏方式下),每一屏要画1024*768/9=87381个小矩形,使用DirectDraw的colorfill。
显示器分辨率1024*768*32,一幅图像的颜色数最多可能87381,因为每个方格颜色都可以不同(也可能更多,方格可以更小)。 如销售管理软件破解版

13楼: 感兴趣的可以在QQ交流,QQ:178744902

进销存管理软件版14楼: 关注中。。。
可以事先把每一帧图像画好,压缩存储,播放时解压,把整幅图像Blt到视频内存中,这样速度就很快。缺点是文件较大,媒体播放器好像就是这样处理的。

15楼: 一个方法是按照vvyang说的,不过记住要操作的是dib位图,而不是普通的位图,效率没有试过。
另一个方法就是直接写表面了,大致代码贴出来,用的是网上封装好的ddraw单元,不过大概应该都可以看出来,初始化时是32位色的。


Type
TXX = packed record
R: Byte;
G: Byte;
B: Byte;
A: Byte;
end;
Axx = array [0..0] of TXX;
PAXX = ^AXX;

procedure TForm1.Button1Click(Sender: TObject);
var
i, j, K: Integer;
P: PAXX;
tick: cardinal;
DD: TDDSurfaceDesc2;
R: TRect;
begin
tick := GetTickCount;
for K := 1 to 50 do
begin
R := ClientRect;
FillChar(DD, Sizeof(DD), #0);
DD.dwSize := Sizeof(DD);
Disp.GetBackBuffer.Lock(@R, dd, DDLOCK_WAIT or DDLOCK_WRITEONLY, 0);
P := DD.lpSurface;
for i := 0 to ClientHeight-1 do
begin
for j := 0 to ClientWidth-1 do
begin
with p^[j] do
begin
R := 255-i*j;
G := 255-j;
B := 255-i;
A := 0;
end;
end;
P := PAXX(Pchar(P)+dd.lPitch);
end;
Disp.GetBackBuffer.Unlock(@R);
Disp.Flip;
end;
Caption := inttostr(GetTickCount-tick);


end;
在我的机器上50次也用不了1秒。
关键函数是lock和unlock,关键结构是_DDSURFACEDESC2,这些都可以从相关的文档中查到。
Over.
另:Delphi的代码优化很有意思,如果把里面的A := 0去掉,那么速度会慢3倍,呵呵

16楼: DoubleWood提供了解决问题的另一个途径,方法很好。我不懂Delphi,但意思我明白,就是用一个像素颜色矩阵对应屏幕,最后就整个颜色矩阵放到屏幕上,避免了一次填充一个个小矩形,从而提高速度。
用C语言如何实现?在C中如何填写一个屏幕区域的RGB值

17楼: 问题快解决了,谢谢大伙,继续努力。
有对directshow熟悉的吗,使用其中的DMO或者Filter速度是不是会更快?看了两天DirectX9.0头晕。

18楼: 来晚了。写了一个简单的类,它的 Draw 方法采用 ScanLine 来实现同样的效果,每次贴图只用 20 ms。
unit DrawUtils;

interface

uses Windows, Graphics;

const
deltaw = 3;
deltah = 3;
deltaw2 = deltaw * 3;

type
TMemoryBitmap = class(TBitmap)
public
constructor Create; override;
procedure CopyTo(hdcDest: HDC);
procedure Draw; reintroduce;
end;

implementation

uses SysUtils;

{ TMemoryBitmap }

constructor TMemoryBitmap.Create;
begin
inherited Create;
PixelFormat := pf24bit;
end;

procedure TMemoryBitmap.CopyTo(hdcDest: HDC);
begin
BitBlt(hdcDest, 0, 0, Width, Height, Canvas.Handle, 0, 0, SRCCOPY);
end;

procedure TMemoryBitmap.Draw;
var
i, j: Longint;
p: PByteArray;
begin
for i := 0 to Height - 1 do
begin
p := ScanLine[i];
j := 0;
while j < Width * 3 do
begin
p[j] := 255 - (i div deltah * deltah) * (j div deltaw2 * deltaw);
p[j + 1] := 255 - j div deltaw2 * deltaw;
p[j + 2] := 255 - i div deltah * deltah;
Inc(j, 3);
end;
end;
end;

用起来很简单:
procedure TForm1.FormCreate(Sender: TObject);
begin
FbmpBuf := TMemoryBitmap.Create;
FbmpBuf.Width := Width;
FbmpBuf.Height := Height;
end;

procedure TForm1.FormDestroy(Sender: TObject);
begin
FbmpBuf.Free;
end;


procedure TForm1.Button1Click(Sender: TObject);
begin
FbmpBuf.Draw;
FbmpBuf.CopyTo(GetDC(Handle));
end;

19楼: 估计提高不了这么多,填充一个BMp,然后放大3×3倍

20楼: TColor* pSurf=(TColor*)ddsd.lpSurface;
if(phase)
{
for(int i=0;i {
for(int j=0;j {
pSurf[j]=(TColor)(RGB(255-i,255-j,255-i*j));
}
pSurf+=ddsd.lPitch;
}
这样为什么不对?pSurf+=ddsd.lPitch;应该怎么修改?

进销存管理软件版21楼: to czw6296:
至于 DMO和Filter你不用考虑了 那是DirectShow里面的 是Codec的一种 用于媒体文件播放的

我不太知道BCB下的DirectDraw怎么表示
但至少VC和Delphi中用DirectDraw画图都是往缓冲帧里画 然后Flip翻页翻出来
你的代码里没看到翻页的语句。。。好像你根本没用DirectDraw

22楼: 1、代码都给你写出来了,你不会试一下啊???谁诓你不成???
2、如果你真想提高所谓“20 倍”的速度,就用 DrawDib 函数族,大多数媒体播放器都用这个,它们的声明在 msvfw.dll 中。 如仓库进销存管理软件

23楼: 是不是Direct版本越高,速度越快。现在用Direct5速度可以达到画整屏每秒20帧,Direct9是不是会速度更快。有高人用过吗?请指点一二。


DorectX9把DirectDraw和Direct3D统称Direct Graphics,是不是增强了3D的功能,DirectDraw性能不会有多大提高?