タスクを実行するように設定されたバックグラウンド ワーカー コントロールがあり、デリゲート プロシージャを使用してメイン UI の複数行テキスト ボックスを更新します。これはすべて完全に機能していますが、更新がテキストボックスの下部からスクロールするとスクロールバーが表示されますが、継続的に更新するとテキストボックスが上部にロックされたままになります。理想的には、テキスト ボックスを自動的に一番下までスクロールして、最新のエントリをリアルタイムで表示したいと考えています。これを実装する最良の方法は何ですか?
その前にコマンドscrolltocaret()
がある場合とない場合で、このメソッドを使用してみました。SelectionStart = txtlog.Text.Length
おそらく私はそれを間違った場所に置いていますか?
以下のいくつかのコードサンプル:
委任コード:
Delegate Sub updateresults_delegate(ByVal textbox As TextBox, ByVal text As String)
Private Sub updatelog_threadsafe(ByVal textbox As TextBox, ByVal text As String)
If textbox.InvokeRequired Then
Dim mydelegate As New updateresults_delegate(AddressOf updatelog_threadsafe)
Me.Invoke(mydelegate, New Object() {textbox, text})
'Me.txtlog.SelectionStart = txtlog.Text.Length
'Me.txtlog.ScrollToCaret()
Else
textbox.Text = text
End If
End Sub
主なバックグラウンド ワーカー アクティビティ:
For i As Integer = val1 To val2
'generate an IP address from split host parts and current value of i
host = s1(0) & "." & s1(1) & "." & s1(2) & "." & i
Try 'attempt to ping the IP
Dim reply As PingReply = pingsender.Send(host, timeoutval, buffer, options)
If reply.Status = IPStatus.Success Then
name = System.Net.Dns.GetHostEntry(host)'get DNS entry
resulttext += String.Format("{1} - {2}: reply: Bytes={3} time{4} TTL={5}{0}", vbCrLf, name.HostName, reply.Address.ToString, reply.Buffer.Length, getms(reply.RoundtripTime), reply.Options.Ttl) 'print out success text
Else
resulttext += String.Format(" {1}: Ping failed. {2}{0}", vbCrLf, host, reply.Status.ToString) 'print out fail text
End If
updatelog_threadsafe(txtlog, resulttext) 'send text to textbox
System.Threading.Thread.Sleep(1000)
Catch ex As Exception
End Try
Next
私の主な質問は次のとおりだとtextbox.scrolltocaret()
思います。これが私が望むものに使用する正しい方法であると確信していますが、それを置くのに最適な場所はどこですか? runworkerasync()
メソッドの前後だけでなく、メインのバックグラウンドワーカーであるデリゲートでも試しました。これらのどれもうまくいきませんでした、そして今私は困惑しています!