| ■No86661 (大阪 さん) に返信 > FlowLayoutPanel(AutoScroll = False)内の垂直方向に配置されたコントロールを AutoScroll = True では駄目なのですか? 自動的にスクロールバーが出るので、追加のコーディングが不要になりそうですが。
それと、キーボード(ScrollUp/ScrollDown/上矢印/下矢印/Tab/Shift+Tab)による操作や、 フォームのリサイズ(高さ変更)への追従、スクロール領域外のコントロールに フォーカスがあることを許容するかどうかなども検討しておく必要がありそうです。
> 具体的には以下のコードのValueChangedイベントで_VScrollBar.Valueと同じインデックス > のボタンをTop位置にスクロールさせたいです。 その仕様だと、最後のボタンを表示しきれない気もしますが、 それはとりあえず後で考えるとして。
Option Strict On Public Class Form1 Private _max As Integer = 100 Private FlowLayoutPanel1 As New FlowLayoutPanel() With {.AutoScroll = False, .Dock = DockStyle.Fill, .WrapContents = False, .FlowDirection = FlowDirection.TopDown} Private WithEvents _VScrollBar As New VScrollBar() With {.Maximum = _max, .Minimum = 0, .LargeChange = 10, .SmallChange = 1, .Value = 0, .Dock = DockStyle.Right} Private Buttons As New List(Of Button)() Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load FlowLayoutPanel1.SuspendLayout() For i = 0 To _max Dim btn As New Button() With {.Text = i.ToString()} btn.Height = 50 Buttons.Add(btn) FlowLayoutPanel1.Controls.Add(btn) Next Controls.Add(FlowLayoutPanel1) FlowLayoutPanel1.ResumeLayout(False) Controls.Add(_VScrollBar) Text = "0" End Sub
Private Sub _VScrollBar_ValueChanged(sender As Object, e As System.EventArgs) Handles _VScrollBar.ValueChanged FlowLayoutPanel1.SuspendLayout() For i = _max To 0 Step -1 Buttons(i).Visible = i >= _VScrollBar.Value Next FlowLayoutPanel1.ResumeLayout(True) Me.Text = _VScrollBar.Value.ToString() End Sub End Class
上記は、Visible プロパティを切り替えることで、スクロールされたボタンを 非表示にする方法で実装しています。
フォーカスが失われることを嫌うなら、マイナス座標に別のコンテナを用意しておき、 ボタンをそこに移動させるという手もありそうです。 |