请教一个关于高DPI下,传奇登录界面错位补丁的问题

sponsored links
高DPI设置时禁用显示的方法
[HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers]
中添加exe的完整路径
等效于 右键--兼容性--禁用DPI
来源: http://bbs.csdn.net/topics/370160
我在win32 + c写的界面中解决办法,就是把字体的字号给固定了,这样做的结果就是,不管dpi是否有改变,界面中控件的文字的字号不变,就不会出现文字换行的情况. 但像菜单文字的字号就变大了,combobox(右三角),checkbox(选择框)变大一点点,显的有点不协调. 但至 ...
这篇文章主要介绍了js控制输入框获得和失去焦点时状态显示的方法,可实现判断输入框的焦点状态设置不同样式的功能,是非常实用的技巧,需要的朋友可以参考下本文实例讲述了js控制输入框获得和失去焦点时状态显示的方法.分享给大家供大家参考.具体实现方法如下: &!DOCTYPE html PUBLIC &-//W3C//DTD XHTML 1.0 Tr ...
首先这种情况大部分出现在的笔记本上,因为现在大部分笔记本的显示屏像素点更小,使得字也变得十分小,出于对眼睛的保护,大家会调整DpI让字体看起来不那么吃力但是这样也带来了一些麻烦,如软件界面显示不全,显示混乱,图标错位等这是一个典型的界面显示不全的案例,拖动改变窗口大小也没用后来把设置全部试了个遍,算是找到一个不算完美的解决办法→使用win xp风格的dpi缩 ...
很多软件都有在大DPI设置下界面显示异常的问题,我们的软件也不例外.因为我们的界面窗口的布局很多都是动态调整的,并且很多文字都是Draw上去的,所以相对来说出问题的地方比较少.
近日有个需求,需要让Intel AMT在做串口重定向的时候能够很好的显示中文.我记得Intel AMT SOL本身应该是支持UTF-8编码格式,可以传输各种语言格式的字符,所立理论上来说,这个需求应该不是问题.拿最新版的Intel DTK(0.51x version)试了一下,用了一张Windows XP的安装光盘测试.打开DTK的Intel IAmtTer ...后使用快捷导航没有帐号?
平板/笔记本
云服务专区
修改完dpi后错位
&登堂入室&
来自:浏览器
小弟最新版的emui 修改完dpi后任务管理器明显错位 网上看修改dpi的教程里没有说到这种情况 难道只有我一个人有这问题 还是说教程刻意掩盖?
还有,说起来华为这dpi的问题搞了快一年了吧,还好小弟是一个月前才买的,那些老用户得多惨?
修改一下dpi有多难?还是说工作人员自己用老年机很顺手?
(75.28 KB, 下载次数: 4)
12:48 上传
width:100%">
&花粉特种部队&
来自:浏览器
就是说你也有这种情况咯
这个个人修改的话,需要匹配的 地方太多了,不可能太完善。我们就在用默认的,x1有个方案,如果效果好的话,有望移植到mate7上。,
盖章仅为特部队员间跟进识别,不代表结贴,如果需要,请在我的跟帖中“回复”我,论坛才会提醒,谢谢 & !!来自花粉,服务花粉的特部需要您的“支持”,&&技术贴直达&&&&& &
width:100%">
&已臻大成&
来自:浏览器
这种情况只能备份资料三键强刷重新刷机了
width:100%">
&登堂入室&
来自:浏览器
这种情况只能备份资料三键强刷重新刷机了
这是修改dpi的后果 把dpi改成480就恢复了....
width:100%">
&禁止发言&
来自:浏览器
提示: 作者被禁止或删除 内容自动屏蔽
签名被屏蔽
width:100%">
&登堂入室&
来自:浏览器
改DPI的同学 也有这个问题嘛?
width:100%">
&炉火纯青&
来自:浏览器
都是一样一样的
width:100%">
&自成一派&
来自:浏览器
MATE7本身就不自带修改DPI的功能,楼主自行修改的话,可能会造成比例不对或者界面不适配等问题的。
当我第一次知道要发帖的时候,其实我是,是拒绝的,我跟大家讲,我拒绝,因为其实我根本不会发帖。
大家跟我讲,发完加特技,回复duang~duang~duang~,我的发帖,假的假的是假的。
是特技的发帖,是搞笑的成分,是发帖的特技,duang~~
width:100%">
&独步江湖&
来自:浏览器
width:100%">
&渐入佳境&
来自:浏览器
nye建勋 发表于
改DPI的同学 也有这个问题嘛?
DPI修改完,屏幕不会自动居中,所以偏移是必须的
width:100%">
&登堂入室&
来自:浏览器
西土瓦 发表于
都是一样一样的
就是说你也有这种情况咯
width:100%">
花粉特种部队荣耀勋章
好基友勋章
花粉好机友,注册时间大于99天
1000万花粉
纪念花粉俱乐部注册花粉数超过1000万
秋摄宜人秋色(六)初夏的塘河古镇品尝金秋的美酒龙脊梯田的日与夜印象普陀 2017 (一)
花粉客户端
Make it Possible
Make your device special
华为云服务
Huawei cloud services
音乐播放器
Huawei Music
Huawei Vmall
没有最新动态
关注花粉俱乐部
举报邮箱:
|关注花粉俱乐部:
Copyright (C)
华为软件技术有限公司 版权所有 保留一切权利505被浏览143623分享邀请回答23142 条评论分享收藏感谢收起4216 条评论分享收藏感谢收起查看更多回答本帖子已过去太久远了,不再提供回复功能。不同的DPI下的界面调整方法
Description of your first forum.
1 篇帖子 & 分页:1 / 1
由 mark158 & 星期五, 日 23:05
&如果屏幕分辨率太大,正常尺寸的DPI(Dot Per Inch,每英寸的像素点数目)设置会使文字等看起来很小,长时间注视会使人感觉不舒服,Windows提供了更改DPI设置以便用户自己选择合适的尺寸。
&&然而在不同的DPI的机器的程序会呈现不同的外观,这是因为设置了DPI之后,Windows会自动调整字体的大小,标题栏的高度,标准按钮的大小等。
&&很不幸,使用编写的程序也会面对这个问题。除非万不得已,我们不应该强迫要求用户更换DPI设置为正常尺寸,所以很多人都会设置TForm的Scaled属性为False,这样窗体以及标准控件就不会在其他DPI的机器上出现不同的大小,这似乎是一个很不错的选择,相信很多人都会这么做的吧:)
&&这个选择似乎很不错了,可是如果要做的更好,就应该再多花一些时间来研究它,因为,这样虽然固定了窗体和控件的大小,可是却违背了用户设定大的DPI的初衷,这样看起来的东西还是很小!再看看Windows自身吧,几乎所有的Windows自带的程序和属性对话框都能够正确处理这个问题,使得窗体看起来比较和谐,较大的缺陷就是在DPI太大,屏幕太小的时候根本不能显示完整的对话框。再看看我们的Delphi,它也可以较好的处理这一问题!
&&让我们再仔细的看看设置了Scaled为False的窗体的表现吧,因为设置了不同的DPI,所以字体的大小就会不一样,而由于设置了Scaled为False,所以正常尺寸下的精心设计的控件的文本,控件的间隔都会发生变化,不是太大了,就是太小了!如果太小了,尚且过得去,如果太大了,用户就看不到全部的文本,这是不是也违背了您设置Scaled为False的初衷呢?
&&到底是不是应该设置Scaled为False,怎样才能做到像Windows那样呢?还是让我们看看Delphi是怎么处理这个问题的吧,Delphi在Source\Property Editors中有几个属性编辑器的源代码,我们关心的是它的dfm的设定,Scaled是为True的!经过仔细分析,Delphi自带的编辑器的BorderStyle都是bsDialog!好,立即新建一个BorderStyle为bsDialog,Scaled为True的窗体看看,真的跟Windows的属性窗体是一样的!Windows自己的属性框也都是Dialog类型的,那么是不是Windows对于Dialog进行了什么特别的处理呢?还是试验一下其他的类型吧,经过测试只有BorderStyle为bsSizeable和bsSizeToolWin的窗体不能解决Scaled为True的情形。似乎有一些眉目了,好,我们就看看Delphi的源代码是不是对于bsSizeable和bsSizeToolWin作了什么特殊的安排?经过查找发现Forms.pas中有如下代码:
procedure TCustomForm.SetBorderStyle(Value: TFormBorderStyle);
&if FBorderStyle && Value then
&&FBorderStyle := V
&&AutoScroll := FBorderStyle in [bsSizeable, bsSizeToolWin];
&&if not (csDesigning in ComponentState) then RecreateW
&&是不是跟AutoScroll有什么关系?先试试看如果AutoScroll为False的情形吧,测试结果证明真的只要设定了AutoScroll为False,Scaled为True就可以实现Windows和Delphi的效果了,那么为什么AutoScroll会影响Scaled的效果呢(特别是对于设定了Anchors的控件,如果BorderStyle为bsSizeable或bsSizeToolWin,会出现很糟糕的情形)?
&&让我们继续追查原因吧,可是跟AutoScroll相关的代码中似乎找不到什么直接的线索?忽然我看到了
function TCustomForm.IsFormSizeStored: B
&Result := AutoScroll or (HorzScrollBar.Range && 0) or
&&(VertScrollBar.Range && 0);
&&不会是这个对Scaled有影响吧?这个函数是判断窗体的属性是保存Width和Height还是保存ClientHeight和ClientWidth的,如果设置了AutoScroll则肯定是保存Width和Height的,那么我们就追查ClientHeight吧,发现:
procedure TCustomForm.SetClientHeight(Value: Integer);
&if csReadingState in ControlState then
&&FClientHeight := V
&&ScalingFlags := ScalingFlags + [sfHeight];
&end else inherited ClientHeight := V
&&原来如此!在ReadState时如果设定了ClientHeight就会给ScalingFlags添加sfHeight选项,再看看ScalingFlags有什么用吧,在ReadState中有如下代码:
&&&&if sfHeight in ScalingFlags then
&&&&&FClientHeight := MulDiv(FClientHeight, NewTextHeight, FTextHeight);
&&而如果只是设定Width和Height则不会有任何影响!
&&哈哈,这就是为什么设置了AutoScroll为False就可以正确处理Scaled的原因啦。
&&好,终于理清了其中的关系啦:
&&对于BorderStyle不是bsSizeable和bsSizeToolWin的TCustomForm,保存进dfm的是ClientWidth和ClientHeight,这样在读入组件的属性的时候就会加入sfHeight和sfWidth选项,也就可以处理Scaled了。
&&而对于BorderStyle是bsSizeable和bsSizeToolWin的TCustomForm,如果控件全部可以在窗体上显示,而且AutoScroll为False的情形就和BorderStyle为其他的一样,不然,保存进dfm的就是Width和Height,这样就不能处理Scaled为True了。
&&好了,到现在为止,我们可以做的跟Windows一样好了,可是上面已经说过了,就算是Windows自己的对话框,也会出现对话框超过屏幕大小的情形,那么可不可以做到更完美呢?在我的工程中,我是使用继承窗体的,所以我在我的父类中是尝试这样做的,效果似乎还不错。
&&首先父类必须是AutoScroll为False的,这样才能保证存入的可能是ClientHeight和ClientWidth。
&&为子类提供一个属性为NoAutoScroll,默认为False,当子类指定为True就表示窗体不需要在超过屏幕的时候显示滚动条。
在父类的Create(必须在inherited Create(AOwner)之后)或FormCreate(任意位置)之中加上
&if AutoScroll then
&&AutoScroll := F
&&在OnShow或OnActivate中加上
&if (not NoAutoScroll) and (not AutoScroll) then
&&AutoScroll := T
&&这样不论是对于BorderStyle为bsDialog还是bsSizeable等,当窗体太大超过屏幕的时候就会出现滚动条了!
&&因为必须要在dfm中保存的是ClientHeight和ClientWidth,才会正确处理Scaled,所以我在父类中要提供NoAutoScroll的属性,AutoScroll为False而在Show或Activate时设为True。
--------------------------------------------------------------------------------
&&如果BorderStyle从其他属性更改为bsSizeable或bsSizeToolWin,会自动设定AutoScroll为True。在其他情况下,AutoScroll属性是不保存到dfm中的(也就是说对于bsDialog等,AutoScroll总是False,当然这是指(HorzScrollBar.Range = 0) and (VertScrollBar.Range = 0)的情形下)。
&&建议不要直接设定ClientHeight和Height等,实在要使用到的时候也需要乘以PixelsPerInch / 设计时候的PPI。(Scaled为False则乘以1,小于1则作为1处理),我的函数是
&CDESIGNPPI = 96;
function MultiPPI(const i: I f: TForm): I
&Result :=
&if (not Assigned(f)) or (not f.Scaled) or (f.PixelsPerInch &= CDESIGNPPI) then
&Result := Trunc(i * f.PixelsPerInch / CDESIGNPPI);
&&在追查过程中,还发现了一个Delphi的IDE的问题,那就是对于继承的窗体,如果父类的AutoScroll从True更改为False,如果不打开子窗体,并且保存一下当前子窗体(只要执行了保存操作,Delphi就会替换Width和Height属性为ClientHeight和ClientWidth的),子窗体保存的属性依然是Width和Height,而打开了子窗体的时候保存的dfm与之前的dfm是不同的,但是Delphi的Save all按钮却是Enabled为False的。Delphi在处理继承的窗体的时候总是有一些类似这样小的隐患存在。
--------------------------------------------------------------------------------
&&我所采用的Delphi版本是5.0 + SP1 + ADO pack2,可能其他版本的Delphi有不同的表现。
--------------------------------------------------------------------------------
&&其实我在追究这个问题的时候太急功近利了,所以一开始寻找问题的出发点就不是很正确,而且有好几次很困惑的时候,真正是欲速则不达。(说实在的,就是担心时间紧迫才会导致浪费更多的时间)
&&如果我直接查找Forms.pas中关于Scaled的代码会更快找到结果的,而我并没有一开始就找它,这太应该好好总结一下原因了:(
原有方法的不足
&&昨天我们所作的最重要的就是设定AutoScroll为False以便窗体保存的属性是ClientHeight和ClientWidth,然后依靠ReadState函数中的代码对Scaled作处理。然而由于Delphi对于继承的窗体的保存问题(昨天已经说明过),加上如果都要添加代码来设定是不是需要AutoScroll毕竟不是很方便,而且对于继承的结构,如果随意的更改父类的属性可能会影响整个工程,所以这对于一个已有的工程来说不是一个很好的解决方法。
&&另,原先在Create中的if AutoScroll then AutoScroll := F似乎没有什么作用,尽管我当初的想法是防止设置了AutoScroll的窗体,NoAutoScroll为True时,在XP下的窗体不具备XP的窗口外形,不过似乎除了这种不大可能的情形之外就没有什么用途了:(
寻求另外的方法
&&想有别的方法还是要从解决问题的根本着想。前提就是我们要知道的是什么样子的窗体才是需要我们来作处理的,也就是说什么样的窗体是保存了ClientHeight和ClientWidth的?到现在为止我还没有完美的解决方法,虽然我们可以像Delphi一样读取窗体资源然后分析保存的属性是不是ClientHeight和ClientWidth,可是因为Delphi似乎并没有提供直接分析的函数,而自己处理需要知道TReader的处理方法,以及要处理继承问题,这似乎太复杂了,我现在的做法是简单的判断AutoScroll,因为从昨天的分析我们知道AutoScroll为True或有滚动条出现的时候就会储存Width和Height,而一般设计时的窗体几乎是不可能出现滚动条的,所以我们可以简单认为AutoScroll就是窗体是不是保存Height和Width的。
&&另外就是我们要知道现在运行的系统的DPI与设计的DPI之间的比值,下面这个函数是经常要用到的,它传入两个参数,一个是要被乘以这个比值的整数,另外一个就是要被处理窗体,返回的就是新的乘以了DPI的比值的数值,这个比值跟Delphi处理Scaled的比值不一样,但是的确是近似的(Delphi依据的数值新旧TextHeight的比),如果要能够有如Delphi一样的算法,或许就跟上面说的判断保存在窗体资源中的是ClientHeight和ClientWidth一样的难,甚至是更困难。
&CDESIGNPPI = 96;
// 该方法已经有了更新了,参见另一个笔记^_^
function MultiPPI(const i: I f: TForm): I
&Result :=
&if (not Assigned(f)) or (not f.Scaled) then E
&Result := MulDiv(i, f.PixelsPerInch, CDESIGNPPI);
&&我一开始想到的方法是这样的,在父类的FormCreate或Create(AOwner)之后设定新的ClientHeight和ClientWidth,第一次的代码是这样的:
&PriorClientHeight: I
&if AutoScroll then
&&PriorClientHeight := ClientH
&&ClientWidth := MultiPPI(ClientWidth, Self);
&&ClientHeight := MultiPPI(PriorClientHeight, Self);
&&这个代码的作用就是变改ClientHeight和ClientWidth到一个近似的Delphi处理之后的ClientHeight和ClientWidth。
&&在随便放置了几个控件的测试下,表现是正确的。可是对于设置了Anchors的控件,结果就只能用乱七八糟来形容了:)为什么呢?还是看Delphi的代码吧,我找到:
procedure TWinControl.WMSize(var Message: TWMSize);
&if not (csLoading in ComponentState) then R
&&这就是为什么我第一次的代码不能达到预期的效果的原因了。不过既然知道了是Realign会影响Anchors,那或许就有方法来阻止Realign。于是我改进了第一次的代码,如下:
&PriorClientHeight: I
&OldControlState: TControlS
&if AutoScroll then
&&OldControlState := ControlS
&&DisableA
&&&PriorClientHeight := ClientH
&&&ClientWidth := MultiPPI(ClientWidth, Self);
&&&ClientHeight := MultiPPI(PriorClientHeight, Self);
&&&ControlState := OldControlS
&&&EnableA
&&这里面使用的之所以不是是Width和Height,因为设定这些属性可以引发SetBounds函数,而这个函数作不少的事情。(实际上不管是ClientHeight还是Height都不行,因为WMSize就已经触发了UpdateAnchorRules过程)。
&&满以为这样就可以解决Anchors的问题了,于是作了一些测试,结果很令人失望的是这段代码只是对于TWinControl起作用,而对于最经常使用的TLabel等却不起作用,似乎还是引发了这些控件的位置的重新排列,我想应该是TControl和TWinControl的不同处理方法造成的,但是现在我还没有找到出问题的代码,希望知道的人能够告诉我。
换一个思路
&&通过仔细的研究TReader的创建Component的代码,我想到了另外一个方法,那就是重载ReadState,虽然我们不可以在重载的ReadState中直接修改ScalingFlags来达到相当于设置ClientHeight等的效果(修改这个属性不能影响TCustomForm的行为的),但是我们可以在这之后紧接着修改ClientHeight和ClientWidth(这时候csReadingState还在,所以修改ClientHeight并不会触发SetBounds——参见TCustomForm.SetClientHeight,TControl.SetClientHeight,TControl.SetClientSize)。下面是一个最初的版本代码:
procedure TfrmBasic.ReadState(Reader: TReader);
&PriorClientHeight: I
&inherited ReadState(Reader);
&if (BorderStyle in [bsSizeable, bsSizeToolWin]) and AutoScroll then
&&PriorClientHeight := ClientH
&&ClientWidth := MultiPPI(ClientWidth, Self);
&&ClientHeight := MultiPPI(PriorClientHeight, Self);
&&Constraints.MinHeight :=
&&&Min(MultiPPI(Constraints.MinHeight, Self), WorkRect.Bottom);
&&Constraints.MinWidth :=
&&&Min(MultiPPI(Constraints.MinWidth, Self), WorkRect.Right);
&&Constraints.MaxHeight :=
&&&Min(MultiPPI(Constraints.MaxHeight, Self), WorkRect.Bottom);
&&Constraints.MaxWidth :=
&&&Min(MultiPPI(Constraints.MaxWidth, Self), WorkRect.Right);
&&经测试,这个代码几乎有着完美的效果:)
&&然而,这就解决了几乎所有的问题么?作为一个窗体,我想几乎可以是这么说的,可是作为一个父类,这将有可能导致预期之外的效果,还是要参看TReader的代码,可以看出来,对于继承的窗体,TReader是要先找到父类再创建的,也就是说对于多次继承的窗体,这段代码将会被多次执行,而如果子类自己保存了ClientHeight或Height的窗体,最后一次执行的代码会纠正之前父类的大小,可是对于子类没有保存ClientHeight或Height的窗体(大小跟父类相同的,Delphi就不保存这些属性),这段代码就会被反复执行多次,结果就有可能出现实际显示的窗体比想象中的大得多或小得多。
&&不过,这个很好解决啦,只要知道是在执行最后一个子类的ReadState就可以了,可是我在TReader中却没有找到一个体现执行的是哪个类的ReadState的可用的属性,所以我是这样做的,目前这是我认为的最完美的版本了:
&&在private中声明:
&FReadStateLevel: I
&&添加一个函数:获得继承的层次:
function TfrmBasic.GetReadStateLevel: I
&aClass: TC
&aLevel: I
&Result := 0;
&aLevel := 0;
&aClass := ClassP
&while (aClass && nil) do
&&Inc(aLevel);
&&if aClass = TfrmBasic then
&&&Result := aL
&&aClass := aClass.ClassP
&&在Create(AOwner)之后或者在FormCreate中
&FReadStateLevel := GetReadStateL
&&重载ReadState过程:
procedure TfrmBaseLocalizeNoAlphaBlend.ReadState(Reader: TReader);
&PriorClientHeight: I
&inherited ReadState(Reader);
&Dec(FReadStateLevel);
&if FReadStateLevel &= 0 then
&if (BorderStyle in [bsSizeable, bsSizeToolWin]) and AutoScroll then
&&PriorClientHeight := ClientH
&&ClientWidth := MultiPPI(ClientWidth, Self);
&&ClientHeight := MultiPPI(PriorClientHeight, Self);
&&Constraints.MinHeight :=
&&&Min(MultiPPI(Constraints.MinHeight, Self), WorkRect.Bottom);
&&Constraints.MinWidth :=
&&&Min(MultiPPI(Constraints.MinWidth, Self), WorkRect.Right);
&&Constraints.MaxHeight :=
&&&Min(MultiPPI(Constraints.MaxHeight, Self), WorkRect.Bottom);
&&Constraints.MaxWidth :=
&&&Min(MultiPPI(Constraints.MaxWidth, Self), WorkRect.Right);
&&如果大家有别的好的方法,希望能够跟我讨论:)如果您知道为什么TWinControl和TLabel等的表现不一样,也请告知,我的EMail是:
首先,更正一下MultiPPI函数,因为实际测试发现在DPI为72的情况下似乎不需要缩小窗体的大小。
&CDESIGNPPI = 96;
function MultiPPI(const i: I f: TForm): I
&Result :=
&if (not Assigned(f)) or (not f.Scaled) or (f.PixelsPerInch &= CDESIGNPPI) then
&Result := MulDiv(i, f.PixelsPerInch, CDESIGNPPI);
&&昨天我尝试重载ReadState解决Scaled的问题,实际上这段代码放在重载的Loaded之中也能有一样的效果,顺便处理一下其他BorderStyle的情况。
function ScreenWorkRect: TR
&SystemParametersInfo(SPI_GETWORKAREA, 0, @Result, 0)
procedure TfrmBase.L
&PriorClientHeight: I
&WorkRect: TR
&WorkRect := ScreenWorkR
&if (BorderStyle in [bsSizeable, bsSizeToolWin]) and AutoScroll then
&&PriorClientHeight := ClientH
&&ClientWidth := Min(MultiPPI(ClientWidth, Self), WorkRect.Right);
&&ClientHeight := Min(MultiPPI(PriorClientHeight, Self), WorkRect.Bottom);
&&Constraints.MinHeight :=
&&&Min(MultiPPI(Constraints.MinHeight, Self), WorkRect.Bottom);
&&Constraints.MinWidth :=
&&&Min(MultiPPI(Constraints.MinWidth, Self), WorkRect.Right);
&&Constraints.MaxHeight :=
&&&Min(MultiPPI(Constraints.MaxHeight, Self), WorkRect.Bottom);
&&Constraints.MaxWidth :=
&&&Min(MultiPPI(Constraints.MaxWidth, Self), WorkRect.Right);
&&priorheight := H
&&Width := Min(Width, WorkRect.Right);
&&Height := Min(priorheight, WorkRect.Bottom);
&&Constraints.MinHeight := Min(Constraints.MinHeight, WorkRect.Bottom);
&&Constraints.MinWidth := Min(Constraints.MinWidth, WorkRect.Right);
&&Constraints.MaxHeight := Min(Constraints.MaxHeight, WorkRect.Bottom);
&&Constraints.MaxWidth := Min(Constraints.MaxWidth, WorkRect.Right);
另外对于动态创建的控件,需要使用下面的函数来调整。
&TXControl = class(TControl);
procedure ScaleDynamicCreatedControl(const scaled: B actrl: TControl);
&OldFontSize: I
&if (not Assigned(actrl)) or (not scaled) then E
&//不需要处理Font,因为已经处理啦
&OldFontSize := TXControl(actrl).Font.S
&TXControl(actrl).ChangeScale(Screen.PixelsPerInch, CDESIGNPPI);
&TXControl(actrl).Font.Size := OldFontS
23:05:00&&
发表评语&&&&&
0:41:53&&这几天很忙,没有及时补上更新的内容这次是比较精准的计算Scaled的大小的方法啦,应该是和Delphi自己实现的方法是一样的
CDESIGNPPI = 96; //设计时候的DPI
//得到设计期的TextHeight,是Scaled处理Font的逆运算
function GetDesignTextHeight(frm: TForm): I
&Result := 0; //大部分都是12或者13的,但是这里返回的是0(要防止除0错误)
&if not Assigned(frm) then E
&NewTH := frm.Canvas.TextHeight('0');
&Result := MulDiv(NewTH, CDESIGNPPI, frm.PixelsPerInch);
//得到新的大小
function MultiPPI(const i: I f: TForm): I
&Result :=
&if (not Assigned(f)) or (not f.Scaled) or
&&(f.Canvas.TextHeight('0') &= GetDesignTextHeight(f)) then
&Result := MulDiv(i, f.Canvas.TextHeight('0'), GetDesignTextHeight(f));
function ScreenWorkRect: TR
SystemParametersInfo(SPI_GETWORKAREA, 0, @Result, 0)
procedure TfrmBase.L
&priorheight: I
&WorkRect: TR
&WorkRect := ScreenWorkR
&if (BorderStyle in [bsSizeable, bsSizeToolWin]) and AutoScroll then
&&priorheight := H
&&Width := Min(MultiPPI(Width, Self), WorkRect.Right);
&&Height := Min(MultiPPI(priorheight, Self), WorkRect.Bottom);
&&Constraints.MinHeight :=
&&&Min(MultiPPI(Constraints.MinHeight, Self), WorkRect.Bottom);
&&Constraints.MinWidth :=
&&&Min(MultiPPI(Constraints.MinWidth, Self), WorkRect.Right);
&&Constraints.MaxHeight :=
&&&Min(MultiPPI(Constraints.MaxHeight, Self), WorkRect.Bottom);
&&Constraints.MaxWidth :=
&&&Min(MultiPPI(Constraints.MaxWidth, Self), WorkRect.Right);
&&priorheight := H
&&Width := Min(Width, WorkRect.Right);
&&Height := Min(priorheight, WorkRect.Bottom);
&&Constraints.MinHeight := Min(Constraints.MinHeight, WorkRect.Bottom);
&&Constraints.MinWidth := Min(Constraints.MinWidth, WorkRect.Right);
&&Constraints.MaxHeight := Min(Constraints.MaxHeight, WorkRect.Bottom);
&&Constraints.MaxWidth := Min(Constraints.MaxWidth, WorkRect.Right);
在OnShow里面加上下面这段
(配合上面代码,可在BorderStyle为bsDialog等被Scaled之后超过工作区之后出现滚动条)
&&if (not (BorderStyle in [bsSizeable, bsSizeToolWin])) and
&&&(not AutoScroll) then
&&&AutoScroll := T
0:02:43&&有了更好的方法了我已经封装成为组件了,将来可能会在CnPack中出现^_^&
21:50:39&&
1 篇帖子 & 分页:1 / 1

我要回帖

更多关于 绝地求生界面错位 的文章

 

随机推荐