使用“using” 的 “Cursor”

很多时候,我们会写下面的这段代码:

private void button1_Click(object sender, EventArgs e)

{

    Cursor cursor = Cursor.Current;

    this.Cursor = Cursors.WaitCursor;



    LongTimeMethod();



    this.Cursor = cursor;

}



private void LongTimeMethod()

{

    for (int i = 0; i < 200; i++)

    {

        label1.Text = i.ToString();

        label1.Refresh();

        System.Threading.Thread.Sleep(10);

    }

}

这段代码在执行LongTimeMethod的时候,设置鼠标的状态为WaitCursor.

可是这段代码是有问题的,比如LongTimeMethod() 方法抛出异常的时候,Cursor 就会始终是WaitCursor.

所以比较安全的做法是:

private void button1_Click(object sender, EventArgs e)

 {

     Cursor cursor = Cursor.Current;

     try

     {

         this.Cursor = Cursors.WaitCursor;

         LongTimeMethod();

     }

     finally {

         this.Cursor = cursor;

     }

 }

 

看到try,finally ,有没有让你想到什么呢?,对了using 可以生成try-finally

public class WaitCursor : IDisposable

{

    private Cursor cursor;



    public WaitCursor()

    {

        this.cursor = Cursor.Current;

        Cursor.Current = Cursors.WaitCursor;

    }



    public void Dispose()

    {

        Cursor.Current = cursor;

    }

}

使用的时候,只需要:

private void button1_Click(object sender, EventArgs e)

{

    using(new WaitCursor())

    {

        LongTimeMethod();

    }

}

 

在using块结束的时候,会自动的调用WaitCursor的Dispose方法,从而设置当前Cursor 为保存的cursor.

 

如果你仔细的看的话,你会发现Cursor 继承了IDisposable 接口。

image

所以有人就说了可以直接:

private void button1_Click(object sender, EventArgs e)

{

    using (Cursor.Current = Cursors.WaitCursor)

    {

        LongTimeMethod();

    }

}

如果你第一次运行的话,可以发现的确能正常工作,可是事实上上面的代码是有问题的。

这段代码会调用Cursors.WaitCursor.Dispose() 方法,从而当你第二次调用的时候,你会得到null,因为WaitCursor已经dispose了:

image

 

有一种变通的方法,下面的代码可以正常工作:

private void button1_Click(object sender, EventArgs e)

{

    using (Cursor.Current = new Cursor(Cursors.WaitCursor.CopyHandle()))

    {

        LongTimeMethod();

    }

}

 

本文参考自:http://www.codeproject.com/Articles/6287/WaitCursor-hack-using-using

你可能感兴趣的:(Cursor)