お世話になっております。
SuspendLayout、ResumeLayoutについて質問させていただきます。
動作を模擬したサンプルを作成しました。
フォームのサイズチェンジの割合に合わせて、子コントロールのサイズを追従させるメソッドFormScalingを使って、Form1_Loadイベントの最後でフォームを最大化し、動的に作成したbutton1は初期値のサイズ(100,100)ではなく、(312,211)になります。
次にReloadイベントで、button1を消して、フォームのサイズを初期値の(500,500)にします。
そしてもう一度Form1_Loadイベントを呼び出して再び(312,211)のサイズのbutton1を生成するという動作です。
この動作で、ReloadイベントはSuspendLayout、ResumeLayoutで囲っているのに、一瞬フォームが初期値の(500,500)に戻って最大化するのが見えてしまっています。
またここで模擬している実際のアプリでは動作が遅いタブレットPCを使っているのですが、複数のコントロールがフォームが縮小するのにも追従して、最大化するのにも追従している過程が見えてしまっています。
この動作に時間がかかっているため、見栄えが悪くなっています。
ここを見せないためにSuspendLayout、ResumeLayoutを使っているつもりでしたが、
無理なのでしょうか。SuspendLayout、ResumeLayoutをコメントアウトしても動作は変わりません。
ご存じの方教えていただけないでしょうか。宜しくお願いします。
以下がFormScalingのメソッドです。
vb.net
1Module resolution 2 Private originalSize_bin As Size ' -- コントロール・スケーリング用オリジナルサイズ 3 Public Sub FormScaling(sender As Object) 4 originalSize_bin = sender.ClientSize 5 ' --- フォーム上のコントロールのサイズと位置を調整 6 If Not (sender.WindowState = FormWindowState.Minimized) Then 7 ' --- サイズファクターの決定 8 Dim sfWidth As Single = (sender.ClientSize.Width / sender.originalSize.Width) 9 Dim sfHeight As Single = (sender.ClientSize.Height / sender.originalSize.Height) 10 Dim sizeFactor As New SizeF(sfWidth, sfHeight) 11 ' --- 各コントロールのスケーリング 12 For Each ctrl As Control In sender.Controls 13 If (TypeOf ctrl Is ListBox) Then 14 DirectCast(ctrl, ListBox).IntegralHeight = False 15 End If 16 If (TypeOf ctrl Is ComboBox) Then 17 DirectCast(ctrl, ComboBox).IntegralHeight = False 18 End If 19 ' --- フォントのスケーリング 20 Dim fntScale As Single = (ctrl.Font.Size * sizeFactor.Height) 21 ctrl.Font _ 22 = New Font(ctrl.Font.FontFamily, fntScale, ctrl.Font.Style, ctrl.Font.Unit) 23 ' --- コントロールのスケーリング 24 ctrl.Scale(sizeFactor) 25 Next 26 ' --- オリジナルサイズに保存 27 sender.originalSize = originalSize_bin 28 End If 29 End Sub 30End Module
以下がForm1クラスのソースコードです。
Public Class Form1 Public moni_height As Integer Public moni_width As Integer ' --- 変数宣言 Public originalSize As Size ' -- コントロール・スケーリング用オリジナルサイズ Public Sub New() '現在フォームが存在しているディスプレイの高さと幅を取得 Dim h As Integer = System.Windows.Forms.Screen.GetBounds(Me).Height Dim w As Integer = System.Windows.Forms.Screen.GetBounds(Me).Width moni_height = h moni_width = w ' この呼び出しはデザイナーで必要です。 InitializeComponent() ' InitializeComponent() 呼び出しの後で初期化を追加します。 End Sub Private Sub Form1_SizeChanged(sender As Object, e As EventArgs) _ Handles MyBase.SizeChanged FormScaling(Me) End Sub 'フォームのLoadイベントハンドラ Private Sub Form1_Load(ByVal sender As Object, ByVal e As EventArgs) Handles MyBase.Load 'Buttonクラスのインスタンスを作成する Me.Button1 = New System.Windows.Forms.Button() 'Buttonコントロールのプロパティを設定する Me.Button1.Name = "Button1" 'サイズと位置を設定する Me.Button1.Location = New Point(0, 0) Me.Button1.Size = New System.Drawing.Size(100, 100) 'Clickイベントハンドラを追加する AddHandler Me.Button1.Click, AddressOf reload 'フォームに追加する Me.Controls.Add(Me.Button1) '最大化する(後で縮小できるようにFormWindowState.Maximizedとはしない) Me.Top = 0 Me.Left = 0 Me.Height = moni_height - 10 Me.Width = moni_width - 10 Me.Button1.Text = Button1.Size.ToString End Sub Private Sub Reload(sender As Object, e As EventArgs) Button1.Dispose() Me.SuspendLayout() 'フォームのサイズをデザイナーの初期値にする Me.Size = New Size(500, 500) Call Form1_Load(sender, e) Me.ResumeLayout() End Sub End Class
以上、長文失礼しました。
回答1件
あなたの回答
tips
プレビュー
バッドをするには、ログインかつ
こちらの条件を満たす必要があります。
2021/05/09 11:57