微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

我如何在抽象类中使用 winforms

如何解决我如何在抽象类中使用 winforms

我有一个抽象类“Element”,它的实例必须使用 System.Drawing 中的 DrawRectangle() 函数。 问题是,因为类是抽象的,所以它不能从 FORM 继承,所以程序无法识别这些类。 我该如何解决这个问题? 我试过在 Element 中放置一个 Form 类型的变量,但没有奏效。 我也尝试了相反的方法,将 Element 变量放在 Form 中。 这是我第一次使用 Winform 和 C#... 它应该是一个鼠标竞赛游戏,页面中绘制的对象应该追逐鼠标或向其他方向移动,但我需要它是面向对象的。

using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;

namespace MyMouseGame
{
    public abstract class Element
    {
        //Form1 myForm = new Form1();// not sure I need it
        public enum EnumShape { Square,Circle,Triangle }
        public enum EnumType { Chase,Escape,Random }

        //variables
        private double X { get; set; }
        private double Y { get; set; }
        private int Size { get; }
        private int Speed { get; }
        private EnumShape Shape { get; set; }
        protected EnumType Type { get; set; }

        private static Random R = new Random();

        //methods

        public int generaterandomNum()
        {
            int randomNum = R.Next(20,100);
            return randomNum;
        }

        public Element()
        {
            X= 0;
            Y = 0;
            Shape = 0;
            Size = generaterandomNum();
            Speed = generaterandomNum();
            Type = 0;
        }

        public void ElementsFactory()
        {

        }

        public void hitTarget(e) { }
        public abstract void Draw(Form1 g); //here I tried to pass a form inside 
        public abstract void Move();
    }
}

//example of one of the instances classes of element
using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;


namespace MyMouseGame
{
    class E_Escape : Element
    {
        int move_circleX = 0;
        int move_circleY = 0;

        bool flag = false;

        Rectangle circle = new Rectangle(10,70,35,35);
        Pen p = new Pen(Color.Black);

        //circle
        public E_Escape()
        {
        }
        public override void Draw(Form1 g) {
            g.DrawEllipse(p,circle);
            g.FillEllipse(new SolidBrush(Color.Red),circle);
        }

        public override void Move() {
            if (!flag)
            {
                if (circle.X >= panel1.Width - 2)
                    flag = true;
                circle.X += 10;
            }
            else
            {
                if (circle.X <= 30)
                    flag = false;
                circle.X -= 10;
            }
        }
    }
}
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Threading;


namespace MyMouseGame
{
    public partial class Form1 : Form
    {
        Graphics g;
        Element [] elements= new Element[3];

        public Form1()
        {
            this.DoubleBuffered = true;
            InitializeComponent();
        }

        private void panel1_Paint(object sender,PaintEventArgs e)
        {
    
            g = panel1.CreateGraphics();

            //timer set
            t.Interval = 100;
            t.Tick += new EventHandler(timer1_Tick);
            t.Start();

        }

        private void recThreadTracker()
        {
            //move rectangle
            while (true)//here I tried to call element finction draw
            {
                elements[0].Draw(g);
                elements[1].Draw(g);
                elements[2].Draw(g);
            }
        }

        public void threadCounter()
        {
            long counter = 0;
            while (true)
            {
                counter++;
                this.Invoke(new Action(() =>
                {
                    lcountRes.Text = counter.ToString();
                }));
                Thread.Sleep(1000);
            }
        }
        private void Form1_Load(object sender,EventArgs e)
        {
          
           

        }

        private void button1_Click(object sender,EventArgs e)
        {
            Thread counterThread = new Thread(threadCounter);
            counterThread.Start();
            Thread recTrackThread = new Thread(recThreadTracker);
            recTrackThread.Start();
        }

        private void timer1_Tick(object sender,EventArgs e)
        {
            foreach (Element elements in elements)
            {
                elements.Move();
            }

            //Refresh();
            Invalidate();
        }
    }
}

解决方法

绘图程序需要两件事。一个 Graphics 对象,以及绘图区域的 Size

例如在图形区域的中心画一个圆

public void Draw(Graphics g,Size target)
{
    int diameter = 16;
    g.DrawEllipse(Pens.Black,target.Width/2 - diameter/2,target.Height/2 - diameter/2,diameter,diameter);
}

在表单的绘制事件中调用所有绘制函数

void panel1_Paint(object sender,PaintEventArgs e)
{
    foreach(var item in Elements)
    {
        item.Draw(e.Graphics,pictureBox1.ClientSize);
    }
}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。