オブジェクトが重なり合ったり途切れたりしないように、Windows ダイアログを標準フォント (96 dpi) と「大きなフォント」設定 (120 dpi) の両方に対応させるためのベスト プラクティスはどれだと思いますか?
ところで:関連する場合に備えて、Delphi ダイアログでこれを行うことに興味があります。
前もって感謝します!
オブジェクトが重なり合ったり途切れたりしないように、Windows ダイアログを標準フォント (96 dpi) と「大きなフォント」設定 (120 dpi) の両方に対応させるためのベスト プラクティスはどれだと思いますか?
ところで:関連する場合に備えて、Delphi ダイアログでこれを行うことに興味があります。
前もって感謝します!
一般に、この目的にはレイアウトマネージャーを使用する必要があります。それが彼らの目的です。
Delphi(長い間動作しませんでした)にはそのようなマネージャーはありませんが、それ以来、さまざまなdpiを処理できます。コンポーネントの自動サイズ設定プロパティを使用して、コンポーネントが表示するテキストに適切なサイズであることを確認する必要があります。コンポーネントの重複を防ぐために、配置プロパティとアンカープロパティを使用してコンポーネントをフォームに配置します。最終的には、適切なレイアウトを実現するために、コンポーネントをコンテナにグループ化する必要があります。
D2007 ヘルプ ファイルの「フォームとコントロールを動的にサイズ変更する場合の考慮事項」の下に、非常に優れた記事があります (URL はヘルプ ファイル自体であり、Web ページ自体ではないことに注意してください)。
同じトピックが、同じ名前で、D2010 ヘルプ ファイル(上記の URL に関する注意事項と同じ) またはdocwikiにあります。
TForm.Scaled と TForm.ScaleBy を調べることも (少なくとも少しは) 価値があります。
これは、ウィンドウのフォント サイズ設定に関係なく、Delphi VCL のピクセルを処理しようとする方法です。
unit App.Screen;
interface
uses Controls;
type
TAppScreen = class(TObject)
private
FDefaultPixelsPerInch: integer;
FPixelsPerInch: integer;
function GetPixelsPerInch: integer;
procedure SetPixelsPerInch(const Value: integer);
public
procedure AfterConstruction; override;
function DefaultPixelsPerInch: integer;
function InAcceptableRange(const aPPI: integer): boolean;
procedure ScaleControl(const aControl: TWinControl);
property PixelsPerInch: integer read GetPixelsPerInch write SetPixelsPerInch;
end;
TAppScreenHelper = class helper for TAppScreen
private
class var FInstance: TAppScreen;
class function GetInstance: TAppScreen; static;
public
class procedure Setup;
class procedure TearDown;
class property Instance: TAppScreen read GetInstance;
end;
implementation
uses
TypInfo, Windows, SysUtils, Forms, Graphics;
type
TScreenEx = class(TScreen)
published
property PixelsPerInch;
end;
TScreenHelper = class helper for TScreen
public
procedure SetPixelsPerInch(Value: integer);
end;
procedure TScreenHelper.SetPixelsPerInch(Value: integer);
begin
PInteger(Integer(Self) + (Integer(GetPropInfo(TScreenEx, 'PixelsPerInch').GetProc) and $00FFFFFF))^ := Value;
end;
procedure TAppScreen.AfterConstruction;
begin
inherited;
FDefaultPixelsPerInch := Screen.PixelsPerInch;
FPixelsPerInch := FDefaultPixelsPerInch;
end;
function TAppScreen.DefaultPixelsPerInch: integer;
begin
Result := FDefaultPixelsPerInch;
end;
function TAppScreen.GetPixelsPerInch: integer;
begin
Result := FPixelsPerInch;
end;
function TAppScreen.InAcceptableRange(const aPPI: integer): boolean;
begin
if DefaultPixelsPerInch > aPPI then
Result := DefaultPixelsPerInch * 0.55 < aPPI
else if DefaultPixelsPerInch < aPPI then
Result := DefaultPixelsPerInch * 1.55 > aPPI
else
Result := True;
end;
procedure TAppScreen.ScaleControl(const aControl: TWinControl);
begin
aControl.ScaleBy(PixelsPerInch, DefaultPixelsPerInch);
end;
procedure TAppScreen.SetPixelsPerInch(const Value: integer);
begin
FPixelsPerInch := Value;
Screen.SetPixelsPerInch(FPixelsPerInch);
end;
class function TAppScreenHelper.GetInstance: TAppScreen;
begin
if FInstance = nil then
FInstance := TAppScreen.Create;
Result := FInstance;
end;
class procedure TAppScreenHelper.Setup;
begin
TAppScreen.Instance;
end;
class procedure TAppScreenHelper.TearDown;
begin
FInstance.Free;
FInstance := nil;
end;
initialization
TAppScreen.Setup;
finalization
TAppScreen.TearDown;
end.
さまざまなピクセル値の効果をテストするには、次のことを試してください。
TAppScreen.Instance.PixelsPerInch := 120;
TAppScreen.Instance.PixelsPerInch := 96;
TAppScreen.Instance.PixelsPerInch := 150;
Delphi の VCL ダイアログを含む TForm の子孫をインスタンス化する前に、PixelsPerInch を変更する必要があります。
商用ソリューションと称されています(Developer Express VCL LayoutManager)。しかし、私はそれらのどれも信用していません。Embarcaderoは、現在のUIコンポーネントセット(VCL)の重大な弱点としてこれに対処する必要があると思います。
サードパーティのコンポーネントセットが今のところ最速のソリューションかもしれないと思います。商用ですが、それほど高価ではありません。
しかし、それとは別に?多分:
そのシナリオで TLabeledEdit を使用したことは一度もありません。