📄 dxdraws.pas
字号:
function TDirectDrawSurface.ColorMatch(Col: TColor): Integer;
var
DIB: TDIB;
i, oldc: Integer;
begin
if IDDSurface<>nil then
begin
oldc := Pixels[0, 0];
DIB := TDIB.Create;
try
i := ColorToRGB(Col);
DIB.SetSize(1, 1, 8);
DIB.ColorTable[0] := RGBQuad(GetRValue(i), GetGValue(i), GetBValue(i));
DIB.UpdatePalette;
DIB.Pixels[0, 0] := 0;
with Canvas do
begin
Draw(0, 0, DIB);
Release;
end;
finally
DIB.Free;
end;
Result := Pixels[0, 0];
Pixels[0, 0] := oldc;
end else
Result := 0;
end;
function TDirectDrawSurface.CreateSurface(const SurfaceDesc: TDDSurfaceDesc): Boolean;
var
TempSurface: IDirectDrawSurface;
begin
IDDSurface := nil;
FDDraw.DXResult := FDDraw.IDraw.CreateSurface(SurfaceDesc, TempSurface, nil);
FDXResult := FDDraw.DXResult;
Result := FDDraw.DXResult=DD_OK;
if Result then
begin
IDDSurface := TempSurface;
TransparentColor := 0;
end;
end;
{$IFDEF DelphiX_Spt4}
function TDirectDrawSurface.CreateSurface(const SurfaceDesc: TDDSurfaceDesc2): Boolean;
var
TempSurface4: IDirectDrawSurface4;
begin
IDDSurface := nil;
FDDraw.DXResult := FDDraw.IDraw4.CreateSurface(SurfaceDesc, TempSurface4, nil);
FDXResult := FDDraw.DXResult;
Result := FDDraw.DXResult=DD_OK;
if Result then
begin
IDDSurface4 := TempSurface4;
TransparentColor := 0;
end;
end;
{$ENDIF}
procedure TDirectDrawSurface.Draw(X, Y: Integer; SrcRect: TRect; Source: TDirectDrawSurface;
Transparent: Boolean);
const
BltFastFlags: array[Boolean] of Integer =
(DDBLTFAST_NOCOLORKEY or DDBLTFAST_WAIT, DDBLTFAST_SRCCOLORKEY or DDBLTFAST_WAIT);
BltFlags: array[Boolean] of Integer =
(DDBLT_WAIT, DDBLT_KEYSRC or DDBLT_WAIT);
var
DestRect: TRect;
DF: TDDBltFX;
Clipper: IDirectDrawClipper;
i: Integer;
begin
if Source<>nil then
begin
if (X>Width) or (Y>Height) then Exit;
if (SrcRect.Left>SrcRect.Right) or (SrcRect.Top>SrcRect.Bottom) then
begin
{ Mirror }
if ((X+Abs(SrcRect.Left-SrcRect.Right))<=0) or
((Y+Abs(SrcRect.Top-SrcRect.Bottom))<=0) then Exit;
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
if SrcRect.Left>SrcRect.Right then
begin
i := SrcRect.Left; SrcRect.Left := SrcRect.Right; SrcRect.Right := i;
DF.dwDDFX := DF.dwDDFX or DDBLTFX_MIRRORLEFTRIGHT;
end;
if SrcRect.Top>SrcRect.Bottom then
begin
i := SrcRect.Top; SrcRect.Top := SrcRect.Bottom; SrcRect.Bottom := i;
DF.dwDDFX := DF.dwDDFX or DDBLTFX_MIRRORUPDOWN;
end;
with SrcRect do
DestRect := Bounds(X, Y, Right-Left, Bottom-Top);
if ClipRect2(DestRect, SrcRect, ClientRect, Source.ClientRect) then
begin
if DF.dwDDFX and DDBLTFX_MIRRORLEFTRIGHT<>0 then
begin
i := SrcRect.Left;
SrcRect.Left := Source.Width-SrcRect.Right;
SrcRect.Right := Source.Width-i;
end;
if DF.dwDDFX and DDBLTFX_MIRRORUPDOWN<>0 then
begin
i := SrcRect.Top;
SrcRect.Top := Source.Height-SrcRect.Bottom;
SrcRect.Bottom := Source.Height-i;
end;
Blt(DestRect, SrcRect, BltFlags[Transparent] or DDBLT_DDFX, df, Source);
end;
end else
begin
with SrcRect do
DestRect := Bounds(X, Y, Right-Left, Bottom-Top);
if ClipRect2(DestRect, SrcRect, ClientRect, Source.ClientRect) then
begin
if FHasClipper then
begin
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
end else
begin
BltFast(DestRect.Left, DestRect.Top, SrcRect, BltFastFlags[Transparent], Source);
if DXResult=DDERR_BLTFASTCANTCLIP then
begin
ISurface.GetClipper(Clipper);
if Clipper<>nil then FHasClipper := True;
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
end;
end;
end;
end;
end;
end;
{$IFDEF DelphiX_Spt4}
procedure TDirectDrawSurface.Draw(X, Y: Integer; Source: TDirectDrawSurface; Transparent: Boolean);
const
BltFastFlags: array[Boolean] of Integer =
(DDBLTFAST_NOCOLORKEY or DDBLTFAST_WAIT, DDBLTFAST_SRCCOLORKEY or DDBLTFAST_WAIT);
BltFlags: array[Boolean] of Integer =
(DDBLT_WAIT, DDBLT_KEYSRC or DDBLT_WAIT);
var
DestRect, SrcRect: TRect;
DF: TDDBltFX;
Clipper: IDirectDrawClipper;
begin
if Source<>nil then
begin
SrcRect := Source.ClientRect;
DestRect := Bounds(X, Y, Source.Width, Source.Height);
if ClipRect2(DestRect, SrcRect, ClientRect, Source.ClientRect) then
begin
if FHasClipper then
begin
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
end else
begin
BltFast(DestRect.Left, DestRect.Top, SrcRect, BltFastFlags[Transparent], Source);
if DXResult=DDERR_BLTFASTCANTCLIP then
begin
ISurface.GetClipper(Clipper);
if Clipper<>nil then FHasClipper := True;
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
end;
end;
end;
end;
end;
{$ENDIF}
procedure TDirectDrawSurface.StretchDraw(const DestRect, SrcRect: TRect; Source: TDirectDrawSurface;
Transparent: Boolean);
const
BltFlags: array[Boolean] of Integer =
(DDBLT_WAIT, DDBLT_KEYSRC or DDBLT_WAIT);
var
DF: TDDBltFX;
OldClipper: IDirectDrawClipper;
Clipper: TDirectDrawClipper;
begin
if Source<>nil then
begin
if (DestRect.Bottom<=DestRect.Top) or (DestRect.Right<=DestRect.Left) then Exit;
if (SrcRect.Bottom<=SrcRect.Top) or (SrcRect.Right<=SrcRect.Left) then Exit;
if FHasClipper then
begin
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
end else
begin
if FStretchDrawClipper=nil then
begin
Clipper := TDirectDrawClipper.Create(DDraw);
try
Clipper.SetClipRects([ClientRect]);
FStretchDrawClipper := Clipper.IClipper;
finally
Clipper.Free;
end;
end;
ISurface.GetClipper(OldClipper);
ISurface.SetClipper(FStretchDrawClipper);
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
ISurface.SetClipper(nil);
end;
end;
end;
{$IFDEF DelphiX_Spt4}
procedure TDirectDrawSurface.StretchDraw(const DestRect: TRect; Source: TDirectDrawSurface;
Transparent: Boolean);
const
BltFlags: array[Boolean] of Integer =
(DDBLT_WAIT, DDBLT_KEYSRC or DDBLT_WAIT);
var
DF: TDDBltFX;
OldClipper: IDirectDrawClipper;
Clipper: TDirectDrawClipper;
SrcRect: TRect;
begin
if Source<>nil then
begin
if (DestRect.Bottom<=DestRect.Top) or (DestRect.Right<=DestRect.Left) then Exit;
SrcRect := Source.ClientRect;
if ISurface.GetClipper(OldClipper)=DD_OK then
begin
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
end else
begin
if FStretchDrawClipper=nil then
begin
Clipper := TDirectDrawClipper.Create(DDraw);
try
Clipper.SetClipRects([ClientRect]);
FStretchDrawClipper := Clipper.IClipper;
finally
Clipper.Free;
end;
end;
ISurface.SetClipper(FStretchDrawClipper);
try
DF.dwsize := SizeOf(DF);
DF.dwDDFX := 0;
Blt(DestRect, SrcRect, BltFlags[Transparent], df, Source);
finally
ISurface.SetClipper(nil);
end;
end;
end;
end;
{$ENDIF}
procedure TDirectDrawSurface.DrawAdd(const DestRect, SrcRect: TRect; Source: TDirectDrawSurface;
Transparent: Boolean; Alpha: Integer);
var
Src_ddsd: TDDSurfaceDesc;
DestSurface, SrcSurface: TDXR_Surface;
Blend: TDXR_Blend;
begin
if (Self.Width=0) or (Self.Height=0) then Exit;
if (Width=0) or (Height=0) then Exit;
if Source=nil then Exit;
if (Source.Width=0) or (Source.Height=0) then Exit;
if Alpha<=0 then Exit;
if dxrDDSurfaceLock(ISurface, DestSurface) then
begin
try
if dxrDDSurfaceLock2(Source.ISurface, Src_ddsd, SrcSurface) then
begin
try
if DestSurface.ColorType=DXR_COLORTYPE_INDEXED then
begin
Blend := DXR_BLEND_ONE1;
end else
if Alpha>=255 then
begin
Blend := DXR_BLEND_ONE1_ADD_ONE2;
end else
begin
Blend := DXR_BLEND_SRCALPHA1_ADD_ONE2;
end;
dxrCopyRectBlend(DestSurface, SrcSurface,
DestRect, SrcRect, Blend, Alpha, Transparent, Src_ddsd.ddckCKSrcBlt.dwColorSpaceLowValue);
finally
dxrDDSurfaceUnLock(Source.ISurface, SrcSurface)
end;
end;
finally
dxrDDSurfaceUnLock(ISurface, DestSurface)
end;
end;
end;
procedure TDirectDrawSurface.DrawAlpha(const DestRect, SrcRect: TRect; Source: TDirectDrawSurface;
Transparent: Boolean; Alpha: Integer);
var
Src_ddsd: TDDSurfaceDesc;
DestSurface, SrcSurface: TDXR_Surface;
Blend: TDXR_Blend;
begin
if (Self.Width=0) or (Self.Height=0) then Exit;
if (Width=0) or (Height=0) then Exit;
if Source=nil then Exit;
if (Source.Width=0) or (Source.Height=0) then Exit;
if Alpha<=0 then Exit;
if dxrDDSurfaceLock(ISurface, DestSurface) then
begin
try
if dxrDDSurfaceLock2(Source.ISurface, Src_ddsd, SrcSurface) then
begin
try
if DestSurface.ColorType=DXR_COLORTYPE_INDEXED then
begin
Blend := DXR_BLEND_ONE1;
end else
if Alpha>=255 then
begin
Blend := DXR_BLEND_ONE1;
end else
begin
Blend := DXR_BLEND_SRCALPHA1_ADD_INVSRCALPHA2;
end;
dxrCopyRectBlend(DestSurface, SrcSurface,
DestRect, SrcRect, Blend, Alpha, Transparent, Src_ddsd.ddckCKSrcBlt.dwColorSpaceLowValue);
finally
dxrDDSurfaceUnLock(Source.ISurface, SrcSurface)
end;
end;
finally
dxrDDSurfaceUnLock(ISurface, DestSurface)
end;
end;
end;
procedure TDirectDrawSurface.DrawSub(const DestRect, SrcRect: TRect; Source: TDirectDrawSurface;
Transparent: Boolean; Alpha: Integer);
var
Src_ddsd: TDDSurfaceDesc;
DestSurface, SrcSurface: TDXR_Surface;
Blend: TDXR_Blend;
begin
if (Self.Width=0) or (Self.Height=0) then Exit;
if (Width=0) or (Height=0) then Exit;
if Source=nil then Exit;
if (Source.Width=0) or (Source.Height=0) then Exit;
if Alpha<=0 then Exit;
if dxrDDSurfa
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -