标签: vcl

德尔福 - 形式内的形式

出于审美原因,我想在另一个表单的顶部显示一个表单,就好像它是一个组件,就像TPanel一样.它应该与父级一起调整大小,随着标题栏的标记栏等对其进行移动.

-----------------------------
| main form component 1     |
-----------------------------
| main |  the 'embedded'    |  
| form |  form goes here    |
|comp 2|                    |
-----------------------------
Run Code Online (Sandbox Code Playgroud)

我能这样做吗?如果是这样的话?


我现在倾向于MDI ......

delphi vcl c++builder

9
推荐指数
2
解决办法
5228
查看次数

将非VCL窗口添加到VCL对齐队列中

一些背景(TLabel和TGroupbox Captions Flicker on Resize的延续):

  • 所以,我有一个应用程序加载不同的插件,并在TPageControl上为每个插件创建一个新选项卡.
  • 每个DLL都有一个与之关联的TForm.
  • 使用父hWnd创建表单作为新的TTabSheet.由于就VCL而言,TTabSheets不是表单的父级(不想使用动态RTL和其他语言的插件),我必须手动处理调整大小.

对于这种"插件"类型的应用程序,我似乎遇到了很多新问题(但很棒的学习经历).

因此,我目前的努力是尝试使用一个插件,该插件不会插入到TTabSheet中,但会在表单上直接调整大小并对齐.

由于这可以更容易用图片解释: 问题的视觉表示 现在我可以手动进行对齐和调整大小,但我宁愿让VCL对齐程序(alClient,alTop等)为我做.这样我就不必考虑在其表单上设置插件对齐.

在查看VCL源代码后,我开始逐步调整对齐代码及其调用方式.基本上,当TControl获得WM_RESIZE时,它将:

  1. 调用调用AlignControl()的Realign()
  2. AlignControl()将获取客户端rect并调用AlignControls()
  3. AlignControls()将按以下顺序为每个TAlignment类型调用DoAlign():alTop,alBottom,alLeft,alRight,alClient,alCustom,alNone
  4. DoAlign()将遍历FControls和FWinControls(它们是TLists)并将它们适当地对齐

所以我的思维过程是,如果我创建一个新的TWinControl,将它的句柄设置为插件窗体(窗口)句柄,并将其插入FControls列表中,并正确对齐它应该为我工作.

我当然在这里,所以它失败了.我甚至在退出应用程序时获得了一个关于无效窗口句柄的AV.我的猜测是我创建的TWinControl试图释放不再存在的插件窗体(窗口)的句柄.

我尝试过的:

procedure AddHandleToControlList(AHandle: DWORD; Align: TAlign);
var
  NewWinControl : TWinControl;
begin
  NewWinControl := TWinControl.Create(frmMain);
  NewWinControl.WindowHandle := AHandle;
  NewWinControl.Align := Align;
  NewWinControl.Width := frmMain.ClientWidth;
  NewWinControl.Height := 30;
  NewWinControl.Parent := frmMain;
end;

procedure AddHandleToControlList(AHandle: DWORD; Align: TAlign);
var
  NewWinControl : TWinControl;
begin
  NewWinControl := TWinControl.Create(frmMain);
  NewWinControl.WindowHandle …
Run Code Online (Sandbox Code Playgroud)

windows delphi winapi vcl delphi-xe

9
推荐指数
1
解决办法
668
查看次数

ListBox长项提示

有一个包含一些长项的ListBox.这些长项超出了ListBox的右边缘,这里有一个想法,当鼠标悬停在这些项目上时显示这些项目的提示.

我找到了一个例子:(来自http://delphi.about.com/cs/adptips2001/a/bltip0201_4.htm)

procedure TForm1.ListBox1MouseMove (Sender: TObject; Shift: TShiftState; X, Y: Integer) ;
var lstIndex : Integer ;
begin
  with ListBox1 do
  begin
   lstIndex:=SendMessage(Handle, LB_ITEMFROMPOINT, 0, MakeLParam(x,y)) ;
   if (lstIndex >= 0) and (lstIndex <= Items.Count) then
     Hint := Items[lstIndex]
   else
     Hint := ''
   end;
  end;
Run Code Online (Sandbox Code Playgroud)

它工作,但每次我想查看另一个项目的提示我必须将我的鼠标从ListBox移开,然后指向另一个项目以查看其提示.有没有办法在不将鼠标移离ListBox边框的情况下查看每个项目的提示?

delphi vcl

8
推荐指数
1
解决办法
3460
查看次数

有角度地绘图文本

我正在编写一个VCL/Delphi应用程序,我需要在Canvas对象上绘制文本.我遇到了麻烦,因为我需要文本的大小和角度可变.这有什么简单的方法吗?TextOut方法只接受起始坐标的参数,所以我不知道如何绘制旋转文本.
谢谢!

delphi vcl

8
推荐指数
1
解决办法
6674
查看次数

如何检查我的应用程序是否具有焦点?

我想要做的是检查我的应用程序是否具有焦点,因为如果不是,那么我将在通知区域上方弹出警报窗口以向最终用户显示一些消息.

delphi winapi vcl notification-area

8
推荐指数
2
解决办法
7304
查看次数

在后台线程中运行的代码可以比在Delphi中的主VCL线程中更快吗?

如果有人在主VCL线程和后台线程上运行时间代码有很多经验,我想得到一个意见.我有一些代码在主线程上的Delphi 6应用程序中运行一些繁重的字符串处理.每次运行操作时,每个操作的时间在i5 Quad内核的单个线程上徘徊大约50 ms.让我真正怀疑的是,我在旧Pentium 4上运行的相同代码显示了同样的操作时间,因为通常我看到Pentium 4上运行的代码比Quad Core慢4倍.我开始怀疑代码是否可能消耗的时间远远少于50毫秒但是主要的VCL线程,可能是Windows消息处理或执行Windows API调用,正在为操作创建一个人为的"底层".注意,如果重要,则由套接字上的传入请求触发操作,但是在完全接收数据之前不会进行时间测量.

在我开始将所有代码移到后台线程进行测试之前,我想知道是否有人对此领域有任何一般知识?您在主VCL线程上运行代码的经历是什么?注意,当测试期间绝对没有用户触发的活动时,正在进行定时测量.

我也想知道如果将线程的优先级提高到实时性以下是否会有任何好处.在尝试使用这些标志时,我的运行时间从未见过太多改进.

- roschler

delphi performance multithreading vcl timing

8
推荐指数
3
解决办法
1575
查看次数

当另一个表单以模态方式显示时,如何制作未禁用的表单?

我有一个实用程序对话框(非模态和保持在顶部),在使用应用程序时应始终可访问(即使是模态对话框,也可以使用可用于在处理应用程序时记笔记的对话框)显示.

其余的应用程序无法更改.

可能吗?我该怎么办呢?

delphi vcl delphi-xe

8
推荐指数
1
解决办法
1684
查看次数

为什么MessageBox不会在同步线程上阻止应用程序?

据我了解并了解TThread类的方法,如果你同步你的代码,它实际上是在主应用程序线程中执行的(就像一个计时器/按钮点击/等).我一直在玩,并注意到MessageBox不会阻止主应用程序,但是睡眠就像预期的那样.这是为什么?

type
  TTestThread = class(TThread)
  private
    procedure SynchThread;
  protected
    procedure Execute; override;
  public
    constructor Create(CreateSuspended: Boolean);
  end;

procedure TTestThread.SynchThread;
begin
 MessageBoxA (0, 'Hello', 'Test', 0);
end;

procedure TTestThread.Execute;
begin
 Synchronize (SynchThread)
end;

constructor TTestThread.Create(CreateSuspended: Boolean);
begin
  inherited;
  FreeOnTerminate := True;
end;

procedure StartThread;
var
 TestThread : TTestThread;
begin
 TestThread := TTestThread.Create (FALSE);
end;
Run Code Online (Sandbox Code Playgroud)

delphi vcl tthread

8
推荐指数
2
解决办法
6294
查看次数

Windows标题栏中的可视错误,VCL样式启用了应用程序和显示缩放

目前我正在测试启用VCL样式的应用程序的各个方面.

我注意到,当Windows缩放高于默认的96 dpi/100%时,VCL表单的图标和标题栏文本太大 - 两者都要靠近 - 请参阅附带的屏幕截图.对于200%或250%的更高标度(例如在4K显示器和Windows 10上使用),尤其如此,但即使缩放为144 dpi/150%,问题也已经可见.

对于RAD Studio提供的所有样式都是如此.通过项目设置启用清单的高Dpi感知.如果我在应用程序中禁用VCL样式,则图标和标题栏文本的大小正确.

我在这里错过了什么吗?如果启用显示缩放,开箱即用的样式是否应该没有开箱即用的显示错误?或者是否有一些设置我可以调整以解决这个问题.

谢谢,

在此输入图像描述 在此输入图像描述

delphi vcl c++builder vcl-styles

8
推荐指数
2
解决办法
1079
查看次数

TEdit和WM_PAINT消息处理程序的奇怪行为

我试图在TEdit没有焦点的控件上实现我自己的绘图(TEdit当编辑器没有完全显示其文本时显示省略号).所以我用这段代码加注了ed:

type
  TEdit = class(StdCtrls.TEdit)
  private
    FEllipsis: Boolean;
    FCanvas: TCanvas;
    procedure WMPaint(var Message: TWMPaint); message WM_PAINT;
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
  end;

constructor TEdit.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  FEllipsis := False;
  FCanvas := TControlCanvas.Create;
  TControlCanvas(FCanvas).Control := Self;
end;

destructor TEdit.Destroy;
begin
  FCanvas.Free;
  inherited;
end;

procedure TEdit.WMPaint(var Message: TWMPaint);
begin
  if FEllipsis and (not Focused) then
  begin
    // Message.Result := 0;
    // TODO...
  end
  else
    inherited;
end;
Run Code Online (Sandbox Code Playgroud)

请注意,当FEllipsis and (not Focused)消息处理程序什么都不做时.

现在我在表单上删除了一个 …

delphi vcl editcontrol

8
推荐指数
1
解决办法
695
查看次数