Restrict form resize -- Delphi
http://www.delphipages.com/forum/showthread.php?t=58391
Hi,
How would I restrict a form from being resized smaller than say a height of 400 and a width of 600?
I am looking for the most effecient code possible that does not produce any flickering when trying to resize below the set limits.
Thanks,
Dan
Hi,
This is the simplest example:
procedure TForm1.FormCanResize(Sender: TObject; var NewWidth, NewHeight: Integer; var Resize: Boolean);
begin
if NewHeight < then
Resize := False;
if NewWidth < then
Resize := False;
end;
The form doesn't flicker at all, on my PC at least, but, if only the height, for example is less than 400, the whole thing stops resizing until you let go and start again. Try it to see what I mean.
I think we're close, but there is a slight problem. If you resize it really quick, the form will actually stop resizing even before it hits the size limits. I think this has to do with the mouse moving faster than the form.
You can reproduce this by the following.
Make the form much wider than 600. Then grab the right side of the form and move your mouse really fast to the left. Then, let go and try and resize it again. You'll find that there is still room left to resize.
I know this is a little nit picky, but it's little details like this that make a better product.
Any other ideas?
Thanks,
Dan
Hi,
Here's a revised version, killed the bug, should work nicely, does for me:
procedure TForm1.FormCanResize(Sender: TObject; var NewWidth, NewHeight: Integer; var Resize: Boolean);
begin
if (NewHeight < ) or (NewWidth < ) then
begin
Resize := False;
if NewHeight < then
begin
NewHeight := ;
Resize := True;
end;
if NewWidth < then
begin
NewWidth := ;
Resize := True;
end;
end;
end;
Tsk tsk tsk...this is one of the disadvantages of growing up on OOP...er...nvm...so...this is the correct way of how to restrict resizing after a certain limit:
type TForm1 = class(TForm)
procedure WMGetMinMaxInfo(var MinMaxInfo: TWMGetMinMaxInfo); message WM_GETMINMAXINFO;
...
end; procedure TForm1.WMGetMinMaxInfo(var MinMaxInfo: TWMGETMINMAXINFO);
begin
with MinMaxInfo.MinMaxInfo^ do
begin
ptMinTrackSize.X := ; //Min limit for width
ptMinTrackSize.Y := ; //Min limit for height
{ ptMaxTrackSize.X := 1000; //Max limit for width
ptMaxTrackSize.Y := 1000; //Max limit for height}
end;
end;
With this code your form can't be size smaller than 600x400 and if you remove the comment marks then you can't size the form larger than 1000x1000 pixels...
Hope that helps...
http://www.delphigroups.info/2/3b/429380.html
In Delphi 3 (I can't remember if Delphi 1 and 2 had the OnResize event), use the form's OnResize event:
const
FormMaxWidth : integer = ;
FormMaxHeight : integer = ;
procedure MainFormOnResize(Sender: TObject);
begin
if (Sender as TForm).Width > FormMaxWidth then
(Sender as TForm).Width := FormMaxWidth;
if (Sender as TForm).Height > FormMaxHeight then
(Sender as TForm).Height := FormMaxHeight;
end;
You can also use the same technique to implement a minimum width and/or height for the form.
In Delphi 4, use the form's Constraints property; see the help file for more info.
I think an OnResize event handler will only act AFTER the resize has taken place.
So you will have the form the right size, but it will be seen to snap-back.
To prevent a form going above/below a set size when resizing, set up a procedure, in the form's Protected section, to connect with the wm_GetMinMaxInfo message.
When resizing, the form will act normally until the limits are reached, then it will not resize any more.
For more size, position elements of a form you can restrict, check MinMaxInfo in the Windows 32 API helpfile.
Interface
TForm1 = Class(TForm)
{All the usual form stuff, component names, etc.. would be in here}
{You will have to add the PROTECTED heading yourself}
Protected {Protected Declarations}
Procedure GetMinMax(Var MinMaxMessage: TWMGetMinMaxInfo); Message
wm_GetMinMaxInfo;
End;{TForm1}
Implementation
Procedure TForm1.GetMinMax(Var MinMaxMessage: TWMGetMinMaxInfo);
Begin
With MinMaxMessage.MinMaxInfo^ Do {Set window resize limits}
Begin
ptMinTrackSize.x:=; {Put the widths/heights in pixels}
ptMinTrackSize.y:=;
ptMaxTrackSize.x:=;
ptMaxTrackSize.y:=;
End;{WITH}
End;{*.GetMinMax*}
http://stackoverflow.com/questions/2538525/disable-form-resizing-in-delphi
Fixing the size is easy, you have two options:
Delphi forms have a
BorderStyle
property and aBorderIcons
property. If you setBorderStyle
tobsDialog
, andBorderIcons
tobiSystemMenu
only, user can not resize the form.You can specify value to
Constraints
property. If you write the same number toMinWidth
andMaxWidth
, the width will be fixed.
Preventing move is more tricky. I can come up with only these solutions now:
Set
BorderStyle
tobsNone
. You will need to draw the form caption yourself, if needed.Write a message handler to
WM_NCHITTEST
, call inherited first, then check theMessage.Result
forHTCAPTION
. If it isHTCAPTION
, set it toHTCLIENT
instead. This way, you fool Windows to think the user didn't click on caption, so he will not be able to drag. Please try if the user can still move the window opening the system menu, and choosing Move. If so, you have to hide the system menu too (BorderIcons
).
Answer found here.
If you want your form to not resize at all, then setting the form border style to bsSingle
is the right thing to do, as then the mouse cursor will not change to one of the sizing cursors when moved over the form borders, so it is obvious to the user that this form can not be resized.
If you want to set a minimum and / or a maximum size for the form, then bsSizeable
is the correct border style, and you can use the Constraints
of the form to specify the limits. There is however the problem that the Constraints
property doesn't prevent the resizing of the form, it only causes the sizes to be adjusted after the fact so that the limits are not violated. This will have the negative side effect that sizing the form with the left or upper border will move it. To prevent this from happening you need to prevent the resizing in the first place. Windows sends the WM_GETMINMAXINFO
message to retrieve the minimum and maximum tracking sizes for a top level window. Handling this and returning the correct constraints fixes the moving form issue:
type
TForm1 = class(TForm)
private
procedure WMGetMinMaxInfo(var AMsg: TWMGetMinMaxInfo);
message WM_GETMINMAXINFO;
end; // ... procedure TForm1.WMGetMinMaxInfo(var AMsg: TWMGetMinMaxInfo);
begin
inherited;
with AMsg.MinMaxInfo^ do begin
ptMinTrackSize := Point(Constraints.MinWidth, Constraints.MinHeight);
ptMaxTrackSize := Point(Constraints.MaxWidth, Constraints.MaxHeight);
end;
end;
http://www.angelfire.com/home/jasonvogel/delphi_source_limiting_a_forms_size.html
This is a demonstration how to limit the form size during resize and the forms position and size when it's maximized.
1. Add this line to the private section of the form declaration.
procedure WMGetMinMaxInfo( var Message :TWMGetMinMaxInfo ); message WM_GETMINMAXINFO;
2. Add this to the implementation part:
procedure TForm1.WMGetMinMaxInfo( var Message :TWMGetMinMaxInfo );
begin
with Message.MinMaxInfo^ do
begin
ptMaxSize.X := ; {Width when maximized}
ptMaxSize.Y := ; {Height when maximized}
ptMaxPosition.X := ; {Left position when maximized}
ptMaxPosition.Y := ; {Top position when maximized}
ptMinTrackSize.X := ; {Minimum width}
ptMinTrackSize.Y := ; {Minimum height}
ptMaxTrackSize.X := ; {Maximum width}
ptMaxTrackSize.Y := ; {Maximum height}
end;
Message.Result := ; {Tell windows you have changed minmaxinfo}
inherited;
end;
NOTE!
In windows 95 the screen size can change during runtime.
If the Scaled property of the form is true then component size and position can change.
The WM_GETMINMAXINFO message is sent to a window
whenever Windows needs the maximized position or dimensions of the window
or needs the maximum or minimum tracking size of the window.
The maximized size of a window is the size of the window when its borders are fully extended.
The maximum tracking size of a window is the largest window size that can be achieved by using the borders to size the window.
The minimum tracking size of a window is the smallest window size that can be achieved by using the borders to size the window.
Windows fills in a TMINMAXINFO data structure, specifying default values for the various positions and dimensions.
The application may change these values if it processes this message.
An application should return zero if it processes this message.
type
TPoint = record
x: Integer;
y: Integer;
end;
TMinMaxInfo = record
ptReserved: TPoint;
ptMaxSize: TPoint;
ptMaxPosition: TPoint;
ptMinTrackSize: TPoint;
ptMaxTrackSize: TPoint;
end;
TWMGetMinMaxInfo = record
Msg: Cardinal;
Unused: Integer;
MinMaxInfo: PMinMaxInfo;
Result: Longint;
end;
The TWMGetMinMaxInfo type is the message record for the WM_GETMINMAXINFO message.
The TMINMAXINFO structure contains information about a window's maximized size and position and its minimum and maximum tracking size.
ptReserved Reserved for internal use.
ptMaxSize Specifies the maximized width (point.x) and the maximized height (point.y) of the window.
ptMaxPosition Specifies the position of the left side of the maximized window (point.x) and the position of the top of the maximized window (point.y).
ptMinTrackSize Specifies the minimum tracking width (point.x) and the minimum tracking height (point.y) of the window.
ptMaxTrackSize Specifies the maximum tracking width (point.x) and the maximum tracking height (point.y) of the window.
The TPOINT structure defines the x- and y-coordinates of a point.
In some cases, developers would want to create a regular window (Form) in Delphi that contains some of the characteristics of a dialog box.
For example, they do not want to allow their users to resize the form at runtime due to user interface design issues.
Other than creating the whole form as a dialog box, there is not a property or a method to handle this in a regular window in Delphi.
But due to the solid connection between Delphi and the API layer, developers can accomplish this easily.
The following example demonstrates a way of handling the Windows message "WM_GetMinMaxInfo"
which allows the developer to restrict the size of windows (forms) at runtime to a specific value.
In this case, it will be used to disable the functionality of sizing the window (form) at runtime. Consider the following unit:
unit getminmax; interface uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs; type
TForm1 = class(TForm)
private
{ Private declarations }
procedure WMGetMinMaxInfo(var Msg: TWMGetMinMaxInfo);
message WM_GETMINMAXINFO;
procedure WMInitMenuPopup(var Msg: TWMInitMenuPopup);
message WM_INITMENUPOPUP;
procedure WMNCHitTest(var Msg: TWMNCHitTest);
message WM_NCHitTest;
public
{ Public declarations }
end; var
Form1: TForm1; implementation {$R *.DFM} procedure TForm1.WMGetMinMaxInfo(var Msg: TWMGetMinMaxInfo);
begin
inherited;
with Msg.MinMaxInfo^ do
begin
ptMinTrackSize.x:= form1.width;
ptMaxTrackSize.x:= form1.width;
ptMinTrackSize.y:= form1.height;
ptMaxTrackSize.y:= form1.height;
end;
end; procedure TForm1.WMInitMenuPopup(var Msg: TWMInitMenuPopup);
begin
inherited;
if Msg.SystemMenu then
EnableMenuItem(Msg.MenuPopup, SC_SIZE, MF_BYCOMMAND or MF_GRAYED)
end; procedure TForm1.WMNCHitTest(var Msg: TWMNCHitTest);
begin
inherited;
with Msg do
if Result in [HTLEFT, HTRIGHT, HTBOTTOM, HTBOTTOMRIGHT,
HTBOTTOMLEFT, HTTOP, HTTOPRIGHT, HTTOPLEFT] then
Result:= HTNOWHERE
end;
end. { End of Unit}
A message handler for the windows message "WM_GetMinMaxInfo"
in the code above was used to set the minimum and maximum TrackSize of the window
to equal the width and height of the form at design time.
That was actually enough to disable the resizing of the window (form),
but the example went on to handle another couple of messages just to make the application look professional.
The first message was the "WMInitMenuPopup" and that was to gray out the size option from the System Menu
so that the application does not give the impression that this functionality is available.
The second message was the "WMNCHitTest" and that was used to disable the change of the cursor icon
whenever the mouse goes over one of the borders of the window (form) for the same reason
which is not to give the impression that the resizing functionality is available.
Restrict form resize -- Delphi的更多相关文章
- Delphi ActiveX Form的使用实例
Delphi ActiveX Form的使用实例 By knityster 1. ActiveX控件简介 ActiveX控件也就是一般所说的OCX控件,它是ActiveX技术的一部分. ActiveX ...
- 不是什么时候都可以用栈来声明对象并使用(自动释放)——Delphi里到处都是编译器魔法,并且自动帮助实例化界面元素指针
一直都喜欢这样显示窗口,因为简单高效: void MainWidget::ShowMyWindow() { MyWidget form(this); form.resize(,); form.exec ...
- Delphi与Javascript的交互
网络上也有人写了关于Delphi与Javascript的文章,其大多数使用ScriptControl等,均无法达到与Delphi自身融合的效果.我也是在翻阅自己的组件库的时候发现了这个以前收集来的代码 ...
- 译:DOM2中的高级事件处理(转)
17.2. DOM2中的高级事件处理(Advanced Event Handling with DOM Level 2) 译自:JavaScript: The Definitive Gu ...
- Qt Designer 修改窗体大小改变控件位置
一.新建一个窗体 用qt designer 新建一个QWidget窗体, 在窗体中右键 选择布局, 发现布局是选择不了的,这个是因为窗体里面没有添加控件, 任意添加空间后便可选择 右键-- 布局-- ...
- pyqt5 笔记(二)实现http请求发送
上个图~ index.py 文件 # -*- coding: utf-8 -*- from PyQt5 import QtWidgets,QtCore #从pyqt库导入QtWindget通用窗口类 ...
- 【PyQt5】学习笔记(1)
# -*- coding: utf-8 -*- from PyQt5 import QtWidgets,QtCore #从pyqt库导入QtWindget通用窗口类 from formnew impo ...
- PyQt5创建第一个窗体(正规套路)
一.Pyqt5 创建第一个窗体 很多人写窗体程序都是直接敲代码,不使用设计器,我个人不是很赞成这种做法.使用设计器的好处是直观.维护方便,尤其开发复杂窗体的效率高. 但是每次修改ui文件后,需要重新生 ...
- c# 鼠标操作
1#region 3using System; 4using System.Runtime.InteropServices; 6#endregion 8namespace Windows.Forms. ...
随机推荐
- Windows搭建RobotFramework环境(一)
Robot Framework官网 http://robotframework.org/http://robotframework.org/ 安装说明 https://github.com/robot ...
- 服务号使用微信网页授权(H5应用等)
获取授权准备 AppId 服务号已经认证且获取到响应接口权限 设置网页授权域名 公众号设置 - 功能设置 - 网页授权域名.注意事项: 回调页面域名或路径需使用字母.数字及"-"的 ...
- 批量删除.svn文件夹和.svn文件
新建可运行文件 Windows环境 将下面的代码保存为 kill-svn.bat文件,放到要删除.svn文件的目录下,双击运行即可 @echo on @rem 删除SVN版本控制目录 @rem for ...
- ireport报表制作, 通过节点、产品类型来判断,当该节点审核通过之后,报表相对应的审核意见及签名 显示相对应的内容
1.代码① (与本内容相关的代码:7~36) 以下类似 $P{P_XXXX} :均为页面端的传入参数 select so.sale_order_no as sale_order_ ...
- 简单优化:Zipalign
Android SDK中包含一个“zipalign”的工具,它能够对打包的应用程序进行优化.在你的应用程序上运行zipalign,使得在运行时Android与应用程序间的交互更加有效率.因此,这种方式 ...
- 亲手安装RabbitMq 3.7.2 并安装Trace插件
===============================================================================================1.安装E ...
- hdu4347
求与询问点欧几里德距离前m小的点 其实就是在kdtree询问的时候用优先队列维护一下就好了 好久没写kdtree练一练,注意这道题是多测 #include<bits/stdc++.h> u ...
- 【PAT】1001. 害死人不偿命的(3n+1)猜想 (15)
1001. 害死人不偿命的(3n+1)猜想 (15) 卡拉兹(Callatz)猜想: 对任何一个自然数n,如果它是偶数,那么把它砍掉一半:如果它是奇数,那么把(3n+1)砍掉一半.这样一直反复砍下去, ...
- Linux文件系统的详解
这里以 EXT2 文件系统为例 在Linux下,一个磁盘的最前面是MBR,大小为512Byte 在每一个分区下,第一部分是boot sector,接下来是super block,再接下来是inode, ...
- JavaScript 中的原型(总则)
1. 一切函数都是对象 2. 一切对象都是由函数创建的,所有函数都是由Function创建的,每个函数都是一个Function对象. 3. 对象.__proto__ === 函数.prototype ...