0

VB.net で独自の winforms 月表示カレンダーを作成しました。

それを行うために、42 の個別のセルを持つテーブル レイアウト パネルを使用しました。lblDay1各セルには、、lblDay2などと呼ばれるラベルがあります。

ページを読み込むと、その月の正しい番号がすべてのラベルに書き込まれます。

 Dim daysInMonthCnt As Integer =31 'Assume 31 days for now
 Dim firstDay As Integer = Weekday("1/" & Now.month & "/" & Now.year) 'Get weekday for 1st of month
 For dayCount As Integer = firstDay To daysInMonthCnt
    Dim lbl As Label
    lbl = CType(pnlMonthBody.Controls("lblDay" & dayCount), Label)
    lbl.Text = dayCount 'Write to label
 Next dayCount

残念ながら、ロードが非常に遅いことが判明しました。誰でもより速い方法を提案できますか。

4

2 に答える 2

1

非常に少数のラベルに値を書き込むだけで、非常に高速なプロセスになります。あなたが経験している問題は、GUI コントロールのコンテンツを更新する際の VB.NET の「問題」に関係している可能性が最も高いです。これを修正する最善の方法は、FraserOfSmeg によって提案されているように、マルチスレッドを調べることです。

これは、コントロールの数が少なく、アルゴリズムがそれほど要求されていない非常に単純化された GUI であると私が考える限り (大量の/長いループが GUI 更新の問題の主な原因です)、マルチスレッドに依存しています。あなたの状況では、私は次のことを行います:

  1. 最初にすべてのラベルを含むコンテナー (TableLayoutPanel使用している 、または のような単純なもの)。Panel乱雑になりすぎない場合 (ラベルが 42 個しかない場合はそうではないようです)、それらを (実行時ではなく) 「デザイン ビュー」に含めます。
  2. 指定された月に応じてすべてのラベルを設定する関数。
  3. ユーザーが別の月を選択するたびに呼び出されるコンテナの「遷移効果」。これは、コンテナーを再配置することで非常に簡単に実現できますTimer(たとえば、ボタンをクリックすると、コンテナーの位置がフォームの外側に設定され、元の位置に戻るまで徐々に (10 ミリ秒ごとに 20 ポイント -> 作成された数字) 戻ってきます)。位置)。
  4. 上記の 2 つの点を同期します。ラベルの値は、遷移が開始されると変化し始めます。この方法では、ユーザーは何も気付かないでしょう (月々の魅力的な移行に過ぎません)。

この GUI は、求めている種類のパフォーマンスを提供する必要があります。そうでない場合は、追加の手段 (提案されているマルチスレッドなど) に依存してパフォーマンスを改善する必要があります。

ポイント 3 を説明するサンプル コード

パネル ( Panel1)、ボタン ( Button1)、タイマー ( Timer1) を新しいフォームと以下のコードに追加します。

Public Class Form1

    Dim curX, origX, timerInterval, XIncrease As Integer
    Dim moving As Boolean
    Private Sub Timer1_Tick(sender As System.Object, e As System.EventArgs) Handles Timer1.Tick
        If (curX >= origX) Then
            If (moving) Then
                curX = Panel1.Location.X
                moving = False
                Timer1.Stop()
            Else
                curX = 0 'getting it out of the screen
                moving = True
            End If
        Else
            curX = curX + XIncrease
        End If
        Panel1.Location = New Point(curX, Panel1.Location.Y)
    End Sub

    Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
        Timer1.Start()
    End Sub

    Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load

        XIncrease = 100
        timerInterval = 100
        Panel1.BackColor = Color.Maroon
        origX = Panel1.Location.X
        curX = origX
        With Timer1
            .Enabled = False
            .Interval = timerInterval
        End With

    End Sub
End Class

これは非常に単純化されていますが、アイデアを明確に示しています。ボタンをクリックすると、パネルが X 方向に移動します。timerIntervalとの値に影響を与えるXIncreaseことで、見栄えの良いトランジションを得ることができます (多くのオプションがあります。curXパネルの幅をゼロではなくマイナスに設定すると、フォームから完全に外れることに注意してください)。

于 2013-07-18T07:54:38.137 に答える
0

純粋にコードの高速化に関心がある場合は、ロード コードを複数のスレッドで同時に実行することをお勧めします。これは、アプリケーションのニーズによってはやり過ぎかもしれませんが、コーディングには適した方法です。補足として、エンド ユーザーにとってプログラムがもう少し滑らかに見えるように、このような時間のかかるプロセスは常に別のスレッドで実行することをお勧めします。

マルチスレッドの詳細については、このページをご覧ください: マルチスレッドチュートリアル

于 2013-07-18T03:14:07.447 に答える