0

如何减少 Delphi 中的闪烁?

这是一个非常普遍和流行的问题,不仅在这个论坛,而且在所有的 Delphi 论坛中,但我没有任何具体的解决方案,所以我再问一次。

我有非常简单的 Delphi XE2 项目,没有任何代码。当我运行应用程序时,它总是会产生闪烁DoubledBuffered:=true,但ParentDoubledBuffered:=true.

这是我的代码.pas File

unit Unit1;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants,
  System.Classes, Vcl.Graphics, Vcl.Controls, Vcl.Forms, Vcl.Dialogs,
  Vcl.StdCtrls, Vcl.Buttons;

type
  TForm1 = class(TForm)
    Label1: TLabel;
    Label2: TLabel;
    Edit1: TEdit;
    Edit2: TEdit;
    BitBtn1: TBitBtn;
    BitBtn2: TBitBtn;
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

end.

这是我的代码.dfm File

object Form1: TForm1
  Left = 0
  Top = 0
  AlphaBlend = True
  AlphaBlendValue = 230
  BorderIcons = [biSystemMenu, biMinimize]
  BorderStyle = bsSingle
  Caption = 'Form1'
  ClientHeight = 300
  ClientWidth = 600
  Color = clWhite
  DoubleBuffered = True
  Font.Charset = DEFAULT_CHARSET
  Font.Color = clWindowText
  Font.Height = -11
  Font.Name = 'Tahoma'
  Font.Style = []
  GlassFrame.Enabled = True
  GlassFrame.SheetOfGlass = True
  OldCreateOrder = False
  Position = poDesktopCenter
  Visible = True
  PixelsPerInch = 96
  TextHeight = 13
  object Label1: TLabel
    Left = 20
    Top = 74
    Width = 160
    Height = 13
    AutoSize = False
    Caption = 'Label1'
  end
  object Label2: TLabel
    Left = 20
    Top = 124
    Width = 160
    Height = 13
    AutoSize = False
    Caption = 'Label2'
  end
  object Edit1: TEdit
    Left = 200
    Top = 70
    Width = 360
    Height = 21
    Alignment = taCenter
    AutoSize = False
    TabOrder = 0
    Text = 'Edit1'
  end
  object Edit2: TEdit
    Left = 200
    Top = 120
    Width = 360
    Height = 21
    Alignment = taCenter
    AutoSize = False
    TabOrder = 1
    Text = 'Edit2'
  end
  object BitBtn1: TBitBtn
    Left = 200
    Top = 224
    Width = 75
    Height = 25
    Caption = 'BitBtn1'
    ParentDoubleBuffered = True
    TabOrder = 2
  end
  object BitBtn2: TBitBtn
    Left = 485
    Top = 224
    Width = 75
    Height = 25
    Caption = 'BitBtn2'
    ParentDoubleBuffered = True
    TabOrder = 3
  end
end    

我发现了很多DelphiSetFileDate 2.0这样创建的应用程序。

我已经看到了.exe FilePE Explorer我发现所有者已经定义了OnShow事件。
我还观察到另一个主要区别是,当我双击应用程序时,在我的 PC 中显示的表单比我的应用程序需要更多的时间,即在双击应用程序后显示表单之前比我有更多的延迟。

另一件事是,首先该Edit区域在闪烁时的第一瞬间变黑,有时Form Background也是。在问这个问题之前,我已经仔细观察了好几次。请不要采取其他方式,因为我是一名学习者,没有这样可能会像其他人一样。

以前我在用Timerfor Form.Create Event,现在一天对 .. 没兴趣了Timer

请给出一些示例代码。

4

1 回答 1

3

好的,让我们看看这是否满足您的需求:

  1. 从 .dfm 文件中删除所有双缓冲设置。
  2. 从 .dfm 文件中删除所有 alpha 混合设置。我认为,您正在使用胜过 alpha 混合的玻璃板。
  3. 通过调用来禁用主窗体的窗口转换DwmSetWindowAttribute

第 3 点需要更多详细说明。您需要窗口句柄才能执行此操作。您必须等到 VCL 创建了窗口。因此,将覆盖添加CreateWnd到您的表单类。

procedure CreateWnd; override;

并像这样实现它:

procedure TForm1.CreateWnd;
var
  dwAttribute: DWORD;
begin
  inherited;
  dwAttribute := DWORD(True);
  DwmSetWindowAttribute(WindowHandle, DWMWA_TRANSITIONS_FORCEDISABLED, 
    @dwAttribute, SizeOf(dwAttribute));
end;

您需要添加Winapi.Dwmapi到您的uses条款。

现在,当您启动应用程序时,该窗口会立即显示。抑制启动转换意味着我们在最终意识到之前不再看到显示错误背景的窗口。

现在,如果您也迫切希望进行 Alpha 混合,那么我认为您可能会遇到麻烦。当我启用玻璃板和 alpha 混合时,将鼠标悬停在窗口标题栏按钮上时会看到奇怪的伪影。我认为悬停效果不能解释您的 alpha 混合。

于 2013-09-13T17:28:07.080 回答