当前位置:编程学习 > C#/ASP.NET >>

多线程的问题,按钮的CD

private void pictureBox1_MouseUp(object sender, MouseEventArgs e)       //鼠标释放,在当前坐标放置一个炮台
        {
            thread = new Thread(btn_cd);
            thread.IsBackground = true;
             

            MyTank = new Tank(type, poi.X, poi.Y);
            if (type != 0&&Map[poi.X,poi.Y]==0&&money-MyTank.Price>0)
            {
                
                Map[poi.X, poi.Y] = 1;
                MyTanks.Add(MyTank);
       
                pictureBox1.Invalidate();
                money = money - MyTank.Price;
                textBox1.Text = Convert.ToString(money);
                
                switch (type)
                {
                    case 1: btn_tank1.Enabled = false; break;
                    case 2: btn_tank2.Enabled = false; break;
                        
                }
                type_cd = type;
                thread.Start();
                
            }

            type = 0;
        }
  private void btn_cd()
        {
            lock (this)
            {
                int i;
                for (i = 1; i < 6; i++)
                {
                    switch (type_cd)
                    {
                        case 1: btn_tank1.Text = Convert.ToString(i); break;
                        case 2: btn_tank2.Text = Convert.ToString(i); break;
                    }
                    Thread.Sleep(1000);
                    if (i == 5)
                        switch (type_cd)
                        {
                            case 1: btn_tank1.Enabled = true; btn_tank1.Text = ""; thread.Abort(); break;
                            case 2: btn_tank2.Enabled = true; btn_tank2.Text = ""; thread.Abort(); break;
                                
                        }
                }
                
            }
        }

功能:按下这个按钮实现5秒CD
点第一个按钮在它CD期间点第二个按钮就会出问题,是不是每次MOUSEUP会NEW一个线程,但是都是进入同一个btn_cd这个方法?另外我lock之后不是应该在一个线程结束之前不进入这个方法么?
该如何现在同时点击进入CD状态也不出问题,总不能一个按钮写个方法吧...

--------------------编程问答-------------------- 可以使用threadstart委托创建次线程等待。。 --------------------编程问答-------------------- 你本身程序就有问题。在线程里边去更改控件的属性值,当然会出错。


http://blog.csdn.net/yaoohfox/article/details/4019474
你去这里边看下,有解决多线程操作控件的 --------------------编程问答-------------------- 再多嘴一句,你的程序写得好烂。 --------------------编程问答--------------------
        private void btn_cd()
        {
            lock (this)
            {
                int i;
                for (i = 1; i < 6; i++)
                {
                    this.Invoke((Action<int>)delegate(int j)
                    {
                        switch (type_cd)
                        {
                            case 1: btn_tank1.Text = Convert.ToString(j); break;
                            case 2: btn_tank2.Text = Convert.ToString(j); break;
                        }
                        Thread.Sleep(1000);
                        if (j == 5)
                            switch (type_cd)
                            {
                                case 1: btn_tank1.Enabled = true; btn_tank1.Text = ""; thread.Abort(); break;
                                case 2: btn_tank2.Enabled = true; btn_tank2.Text = ""; thread.Abort(); break;

                            }
                    }, j);

                }

            }
        }

跨线程操作控件用Invoke --------------------编程问答--------------------
        private void btn_cd()
        {
            lock (this)
            {
                int i;
                for (i = 1; i < 6; i++)
                {
                    this.Invoke((Action<int>)delegate(int j)
                    {
                        switch (type_cd)
                        {
                            case 1: btn_tank1.Text = Convert.ToString(j); break;
                            case 2: btn_tank2.Text = Convert.ToString(j); break;
                        }
                        Thread.Sleep(1000);
                        if (j == 5)
                            switch (type_cd)
                            {
                                case 1: btn_tank1.Enabled = true; btn_tank1.Text = ""; thread.Abort(); break;
                                case 2: btn_tank2.Enabled = true; btn_tank2.Text = ""; thread.Abort(); break;
 
                            }
                    }, i);
 
                }
 
            }
        }


下面的J改为I --------------------编程问答--------------------
引用 3 楼 zhantianyou 的回复:
再多嘴一句,你的程序写得好烂。

哈哈,我自己也觉得有很多可以美化的地方,第一步只为完成能实现的功能,因为刚学不久 --------------------编程问答--------------------
引用 3 楼 zhantianyou 的回复:
再多嘴一句,你的程序写得好烂。

有什么能改进的或者什么编程习惯需要改的还请指教,刚接触C#半学期,代码读的少,好多用法没见过 --------------------编程问答--------------------
引用 5 楼 vb763305825 的回复:
        private void btn_cd()
        {
            lock (this)
            {
                int i;
                for (i = 1; i < 6; i++)
                {
                    this.Invoke((Action<int>)delegate(int j)
                    {
                        switch (type_cd)
                        {
                            case 1: btn_tank1.Text = Convert.ToString(j); break;
                            case 2: btn_tank2.Text = Convert.ToString(j); break;
                        }
                        Thread.Sleep(1000);
                        if (j == 5)
                            switch (type_cd)
                            {
                                case 1: btn_tank1.Enabled = true; btn_tank1.Text = ""; thread.Abort(); break;
                                case 2: btn_tank2.Enabled = true; btn_tank2.Text = ""; thread.Abort(); break;
 
                            }
                    }, i);
 
                }
 
            }
        }


下面的J改为I


谢谢你的回复,但还是没解决我的问题。跨线程上面有个回复给了个网址我已经看了。大概明白了。但是您给的代码也没法解决我的问题,我想实现N个按钮,不论什么时候只要不在CD状态,我点下去就会有5秒CD。这里我不知道该怎么写 --------------------编程问答-------------------- 虽然不知道你要的效果是怎么样的,但应该你的逻辑没弄明白。


是不是有多个按钮,每个都有cd状态?只要不是在cd的时候,这个按钮就可以点击? --------------------编程问答--------------------
引用 1 楼 ejason 的回复:
可以使用threadstart委托创建次线程等待。。

不好意思,看MSDN还是没太明白加不加ThreadStart委托的区别。能帮我讲下么,或者给我贴个相关知识的网址我自己看,麻烦您了 --------------------编程问答--------------------
引用 9 楼 zhantianyou 的回复:
虽然不知道你要的效果是怎么样的,但应该你的逻辑没弄明白。


是不是有多个按钮,每个都有cd状态?只要不是在cd的时候,这个按钮就可以点击?

是的。 --------------------编程问答-------------------- 如果只以时间为基准,用Timer
如果是以逻辑(某个操作完成)为基准,用回调(事件) --------------------编程问答--------------------
引用 12 楼 dongxinxi 的回复:
如果只以时间为基准,用Timer
如果是以逻辑(某个操作完成)为基准,用回调(事件)

可是如果我按钮多了不是得每个按钮是一个方法了么. --------------------编程问答--------------------  Button btn = sender as Button;
            btn.Enabled = false;
            Task.Factory.StartNew(() =>
                {
                    int i = 5;
                    while (i >= 0)
                    {
                        Thread.Sleep(1000);
                        
                        this.Invoke(new Action(() =>
                            {
                                btn.Text = i.ToString();
                                if (i == 0)
                                {
                                    btn.Enabled = true;
                                }
                            }));
                        i--;
                    }
                    
                });
给你写了,你拖一堆按钮,每个的click事件都来调用这个方法。 --------------------编程问答-------------------- 然后你照着这种原理去做吧
补充:.NET技术 ,  C#
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,