-2

サーバーに接続する単純なログインフォームがあります。

ユーザーがログイン ボタンを押すと、接続が確立されるか失敗するまで、読み込み中のアニメーション GIF が表示される必要があります。

理論的には、私はそれをしました:

private void button_login_Click(object sender, EventArgs e)
{
        button_login.Text = WORKING;
        Loading(ShowMode.show, pictureBox_login_loading);
        // send request         
        client = new TcpClient();
        try
        {
            IPEndPoint endPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 5000);
            client.Connect(endPoint);
            // send login details .. :)
            output = client.GetStream();
            writer = new BinaryWriter(output);
            reader = new BinaryReader(output);
            // write details
            writer.Write("login"   "|"   userID   "|"   privateName);
        }
        catch (Exception)
        {
            MessageBox.Show("Server is down.");
            return;

        }
        finally
        {
            // Stop loading and return status
            button_login.Text = DEFAULT_LOGIN_TEXT;
            Loading(ShowMode.hide, pictureBox_login_loading);
        } 
}

Loading は、PictureBox の Visible プロパティを に設定する関数ですVisible。(役に立つと思った)

button_login_Click問題は、実行が終了した後にのみ gif が表示され、非表示になった直後に表示されることです。

実行中の行にアニメーション gif を表示するにはどうすればよいですか?

4

2 に答える 2

3

問題は、GUI スレッドに戻らないため、GIF を表示できないことです。

BackgroundWorker を使用してクライアントに接続し、作業を開始する前に GIF を表示し、Worker の完了した呼び出しで停止することをお勧めします。

サンプルコード (注: ソースが十分にないため、これをコンパイルしませんでした):

       button_login.Text = WORKING;
        Loading(ShowMode.show, pictureBox_login_loading);
        // send request      
        BackgroundWorker worker = new BackgroundWorker();

        worker.DoWork += new DoWorkEventHandler((obj, args) =>
        {
            client = new TcpClient();
            try
            {
                IPEndPoint endPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 5000);
                client.Connect(endPoint);
                // send login details .. :)
                output = client.GetStream();
                writer = new BinaryWriter(output);
                reader = new BinaryReader(output);
                // write details
                writer.Write("login"   "|"   userID   "|"   privateName);
            }
            catch (Exception)
            {
                this.Invoke(new Action(() =>MessageBox.Show("Server is down."));
            }
        });

        worker.RunWorkerCompleted += new RunWorkerCompletedEventHandler((obj, args) =>
        {
            button_login.Text = DEFAULT_LOGIN_TEXT;
            Loading(ShowMode.hide, pictureBox_login,loading);
        });

        worker.RunWorkerAsync();

このアプローチは、GUI スレッドに譲り、GIF を表示できるようにし、接続を監視し、完了したら GIF を削除してボタン テキストを復元します。

于 2013-02-13T19:01:48.877 に答える
0

これは目的のアニメーションであるため、UI スレッドがブロックされないように、おそらく別のスレッドで接続を開始する必要があります。Update()静止画像の場合は、pictureboxのメソッドを呼び出すだけで表示できます。しかし、あなたの場合、次のようなものがうまくいくはずです:

Thread thread = new Thread(new ThreadStart(delegate
{
    Invoke((Action)(()=>{ button_login.Text = WORKING; Loading(ShowMode.show, pictureBox_login_loading); }));
    // send request         
    client = new TcpClient();
    try
    {
        IPEndPoint endPoint = new IPEndPoint(IPAddress.Parse("127.0.0.1"), 5000);
        client.Connect(endPoint);
        // send login details .. :)
        output = client.GetStream();
        writer = new BinaryWriter(output);
        reader = new BinaryReader(output);
        // write details
        writer.Write("login"   "|"   userID   "|"   privateName);
     }
     catch (Exception)
     {
         MessageBox.Show("Server is down.");
         return;

     }
     finally
     {
         // Stop loading and return status
         Invoke((Action)(()=>{ button_login.Text = DEFAULT_LOGIN_TEXT; Loading(ShowMode.hide, pictureBox_login_loading); }));
      } 
}));
thread.Start();

説明した他の回答のように BackgroundWorker を使用することもできますが、進行状況バーで進行状況を報告するタスクなど、実行時間の長いタスク用に予約する傾向があります。短い(っぽい)タスクの場合、私は通常、.NET 4.0 でThread, またはを使用します。Task.Factory.StartNew

于 2013-02-13T19:03:13.257 に答える