gpt4 book ai didi

multithreading - 如何在单独的线程(与主线程不同)中打开ClientDataSet(主/详细)

转载 作者:行者123 更新时间:2023-12-03 15:56:54 25 4
gpt4 key购买 nike

使用:Delphi XE2、DBExpress、Firebird

我无法安全地访问主线程之外的任何 VCL 控件,包括表单、面板、编辑等以及 Timage 和 Timage 后代。我需要在单独的线程(与主线程不同)中打开 ClientDataSet(主/详细信息)。

我需要在访问数据库时创建动画启动屏幕

有人可以向我展示一个如何执行此操作的简单示例吗?

最佳答案

我假设线程中的数据库访问对您来说没有问题。

有关对 dbExpress 数据库进行线程访问的完整示例(包括对主线程的反馈),请参阅 Marco Cantù 制作的示例这里:dbexpress_firebird_examples .

它涉及将所有数据库连接设置放入 TDataModule 中,并为每个线程访问创建此数据模块的实例。

无论如何,为了让 GUI 通过动画 Gif 来了解后台线程进程,下面是一个示例:

enter image description here

unit TestAnimatedScreen;

interface

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

type
TMyEndNotify = procedure (value: Boolean) of object;

type
TMyThread = class(TThread)
private
fEndNotification : TMyEndNotify;
procedure NotifyEndOfThread;
protected
procedure Execute; override;
public
Constructor Create(endNotification : TMyEndNotify);
end;

type
TMainForm = class(TForm)
Image1: TImage;
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
FShowAnimation : Boolean;
procedure SetShowAnimation(value : Boolean);
public
{ Public declarations }
property ShowAnimation : Boolean read FShowAnimation write SetShowAnimation;
end;

var
MainForm: TMainForm;

implementation

{$R *.dfm}

procedure TMyThread.NotifyEndOfThread;
begin
if Assigned(fEndNotification) then
fEndNotification(False);
end;

constructor TMyThread.Create(endNotification: TMyEndNotify);
begin
Inherited Create(false);
fEndNotification := endNotification;
Self.FreeOnTerminate := True; // Free automatically
end;

procedure TMyThread.Execute;
begin
try
{Add your database access code here}
Sleep(5000); // Simulate lengthy process
finally
Synchronize(NotifyEndOfThread);
end;
end;

{ TMainForm }

procedure TMainForm.Button1Click(Sender: TObject);
begin
ShowAnimation := True;
TMyThread.Create(Self.SetShowAnimation);
end;

procedure TMainForm.SetShowAnimation(value: Boolean);
begin
FShowAnimation := Value;
if FShowAnimation then
begin
{Add animation code here}
Button1.Enabled := false;
Button1.Caption := 'Processing, please wait ...';
(Image1.Picture.Graphic as TGIFImage).AnimateLoop := glEnabled;
(Image1.Picture.Graphic as TGIFImage).Animate := true;
end
else
begin
{Stop animation}
(Image1.Picture.Graphic as TGIFImage).Animate := false;
Button1.Caption := 'Start lengthy process';
Button1.Enabled := True;
end;
end;

end.
<小时/>
object MainForm: TMainForm
Left = 0
Top = 0
Caption = 'MainForm'
ClientHeight = 265
ClientWidth = 236
Color = clBtnFace
Font.Charset = DEFAULT_CHARSET
Font.Color = clWindowText
Font.Height = -11
Font.Name = 'Tahoma'
Font.Style = []
OldCreateOrder = False
PixelsPerInch = 96
TextHeight = 13
object Image1: TImage
Left = 8
Top = 8
Width = 200
Height = 200
AutoSize = True
IncrementalDisplay = True
end
object Button1: TButton
Left = 8
Top = 224
Width = 200
Height = 25
Caption = 'Start lengthy process'
TabOrder = 0
OnClick = Button1Click
end
end

如果您的 Delphi 版本比 Delphi 2007 旧,请参阅 How to use Animated Gif in a delphi form有关如何实现动画 GIF 的更多信息。

我使用的动画GIF可以找到here .

关于multithreading - 如何在单独的线程(与主线程不同)中打开ClientDataSet(主/详细),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14093874/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com