1

フォームに 3 つの Tic Tac Toe フレームがあるカスタム Tic Tac Toe ゲームを作成しています。

3x3 の正方形のボタンを 3 回作成する代わりに、9 つのボタンを必要な形式で含むカスタム コントロールを作成する方がよいと考えたので、フォームに 3 回配置して、すべてのボタンにアクセスできます。そのフォーメーションのボタン。

私は継承とカスタム コントロールにかなり慣れていないので、例や手順を教えてください。

4

4 に答える 4

4

この場合、 を使用できますUserControl。これは、既存のコントロールからコントロールを派生させて拡張する必要があるカスタム コントロールを作成するよりも簡単です。VS でプロジェクトを右クリックし、[追加] > [新しいアイテム...] を選択します。[Windows フォーム] セクションで [ユーザー コントロール] を選択します。「TicTacToeUserControl」という名前を付けます。フォームをデザインするのと同じように、ユーザー コントロールをデザインできます。その後、現在のプロジェクトのツールボックスに自動的に表示され、フォームにドロップできるようになります。


アップデート

ここにいくつかの説明があります。TableLayoutPanelの上に を置きUserControlます。に変更DockFillます。行と列を追加して両方を 3 つにし、サイズ モードをPercentに変更して、これらの値を 33.33 に変更します。各テーブル フィールドにボタンを左から右に、次に上から下に追加して、ボタン名を読み取り順に「button1」、「button2」などにします。ユーザー コントロールを保存します (私の VS にはこの時点で問題があり、最初からやり直す必要がありました)。

ボタンクリックイベントのイベント引数として使用するこのクラスを作成します

public class ButtonClickedEventArgs : EventArgs
{
    public ButtonClickedEventArgs(TicTacToeUserControl userControl, Button button,
                                  int buttonNumber, int row, int column)
    {
        UserControl = userControl;
        Button = button;
        ButtonNumber = buttonNumber;
        Row = row;
        Column = column;
    }

    public TicTacToeUserControl UserControl { get; private set; }
    public Button Button { get; private set; }
    public int ButtonNumber { get; private set; }
    public int Row { get; private set; }
    public int Column { get; private set; }
}

ユーザー コントロールのコードを次のように変更します。

[DefaultEvent("ButtonClicked")]
public partial class TicTacToeUserControl : UserControl
{
    public event EventHandler<ButtonClickedEventArgs> ButtonClicked;

    public TicTacToeUserControl()
    {
        InitializeComponent();
    }

    private void button_Click(object sender, EventArgs e)
    {
        OnButtonClicked((Button)sender);
    }

    private void OnButtonClicked(Button button)
    {
        var eh = ButtonClicked;
        if (eh != null) {
            int buttonNumber =
                Int32.Parse(button.Name.Substring(button.Name.Length - 1));
            int row = (buttonNumber - 1) / 3;
            int col = (buttonNumber - 1) % 3;
            eh(this, 
               new ButtonClickedEventArgs(this, button, buttonNumber, row, col));
        }
    }
}

プロパティ ウィンドウですべてのボタンのクリック イベントのイベント ハンドラ「button_Click」を選択し、イベント (フラッシュ シンボル) に切り替えます。ボタンごとに新しいものを作成しないでください。F6 を押します (コンパイル)

コントロールの準備が整い、ツール ウィンドウからフォームにドロップできます。必要に応じてサイズを変更します。それをダブルクリックします。フォームに指定したためDefaultEventAttribute、VS はこのイベント ハンドラーを自動的に作成します。

private void ticTacToeUserControl1_ButtonClicked(object sender,
                                                 ButtonClickedEventArgs e)
{
}

ユーザー コントロールをテストするために、このコード行を追加します。

    MessageBox.Show(e.UserControl.Name + " " + e.Button.Name + " " + 
                    e.ButtonNumber + " " + e.Row + " " + e.Column);

注: これは実際に新しいコントロールを作成するのではなく、テンプレートを作成するだけです

于 2012-12-06T16:16:26.077 に答える
2

最善の方法はユーザーコントロールを使用することですが、デザイナーでボタンを作成する代わりに、コードでボタンを作成します。これにより、クリックされたボタンを検出できます。

public partial class UserControl1 : UserControl
    {
        private List<Button> buttons = new List<Button>(9);
        public UserControl1()
        {
            InitializeComponent();
        }

        private void UserControl1_Load(object sender, EventArgs e)
        {
            int line = 0;
            int lastleft = 0;
            int lasttop = 0;
            for (int i = 1; i < 10; i++)
            {
                Button btn = new Button();
                btn.Text = string.Empty;
                btn.Parent = this;
                btn.Top = lasttop;
                btn.Left = lastleft;
                btn.Width = 30;
                btn.Height = 30;
                btn.Name = i.ToString(CultureInfo.InvariantCulture);

                if (i % 3 == 0)
                {
                    lastleft = 0;
                    lasttop += 35; // 30 for height and 5 for spacing
                }
                else
                {
                    lastleft += 35; // 30 for width and 5 for spacing
                }
                btn.Click += BtnOnClick;
                buttons.Add(btn);

            }
        }

        private void BtnOnClick(object sender, EventArgs eventArgs)
        {
            //ur logic to check game status
            // how to know button?
            Button btn = sender as Button;

            if (btn != null)
            {
                MessageBox.Show(String.Format("You clicked : {0}", btn.Name), Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Information);
            }
        }
    }
于 2012-12-06T16:39:03.007 に答える
1
using System;  
using System.Collections.Generic;  
using System.Text;  
using System.Drawing;  
using System.Data;  
using System.Windows.Forms;  
namespace ButtonZ  
{  
    public class ButtonZ : System.Windows.Forms.Button  
    {  
        Color clr1, clr2;  
        private Color color1 = Color.LightGreen;  
        private Color color2 = Color.DarkBlue;  
        private Color m_hovercolor1 = Color.Yellow;  
        private Color m_hovercolor2 = Color.DarkOrange;  
        private int color1Transparent = 150;  
        private int color2Transparent = 150;  
        private Color clickcolor1 = Color.DarkOrange;  
        private Color clickcolor2 = Color.Red;  
        private int angle = 90;  
        private int textX = 100;  
        private int textY = 25;  
        private String text = "";  

        //Create Properties to read Button Text,Colors etc  
        public String DisplayText  
        {  
            get { return text; }  
            set { text = value; Invalidate(); }  
        }  

        public Color StartColor  
        {  
            get { return color1; }  
            set { color1 = value; Invalidate(); }  
        }  

        public Color EndColor  
        {  
            get { return color2; }  
            set { color2 = value; Invalidate(); }  
        }  

        public Color MouseHoverColor1  
        {  
            get { return m_hovercolor1; }  
            set { m_hovercolor1 = value; Invalidate(); }  
        }  

        public Color MouseHoverColor2  
        {  
            get { return m_hovercolor2; }  
            set { m_hovercolor2 = value; Invalidate(); }  
        }  

        public Color MouseClickColor1  
        {  
            get { return clickcolor1; }  
            set { clickcolor1 = value; Invalidate(); }  
        }  

        public Color MouseClickColor2  
        {  
            get { return clickcolor2; }  
            set { clickcolor2 = value; Invalidate(); }  
        }  

        public int Transparent1  
        {  
            get { return color1Transparent; }  
            set  
            {  
                color1Transparent = value;  
                if (color1Transparent > 255)  
                {  
                    color1Transparent = 255;  
                    Invalidate();  
                }  
                else  
                    Invalidate();  
            }  
        }  

        public int Transparent2  
        {  
            get { return color2Transparent; }  
            set  
            {  
                color2Transparent = value;  
                if (color2Transparent > 255)  
                {  
                    color2Transparent = 255;  
                    Invalidate();  
                }  
                else  
                    Invalidate();  
            }  
        }  

        public int GradientAngle  
        {  
            get { return angle; }  
            set { angle = value; Invalidate(); }  
        }  

        public int TextLocation_X  
        {  
            get { return textX; }  
            set { textX = value; Invalidate(); }  
        }  

        public int TextLocation_Y  
        {  
            get { return textY; }  
            set { textY = value; Invalidate(); }  
        }  

        public ButtonZ()  
        {  
            this.Size = new System.Drawing.Size(200, 50);  
            this.ForeColor = Color.White;  
            this.FlatStyle = System.Windows.Forms.FlatStyle.Flat;  
            text = this.Text;  
        }  

        //method mouse enter  
        protected override void OnMouseEnter(EventArgs e)  
        {  
            base.OnMouseEnter(e);  
            clr1 = color1;  
            clr2 = color2;  
            color1 = m_hovercolor1;  
            color2 = m_hovercolor2;  
        }  

        //method mouse leave  
        protected override void OnMouseLeave(EventArgs e)  
        {  
            base.OnMouseLeave(e);  
            color1 = clr1;  
            color2 = clr2;  
        }  

        //method mouse click  
        protected override void OnMouseClick(MouseEventArgs e)  
        {  
            if (e.Clicks == 1)  
            {  
                base.OnMouseClick(e);  
                color1 = clickcolor1;  
                color2 = clickcolor2;  
            }  
        }  

        protected override void OnPaint(PaintEventArgs pe)  
        {  
            base.OnPaint(pe);  
            text = this.Text;  
            if (textX == 100 && textY == 25)  
            {  
                textX = ((this.Width) / 3) + 10;  
                textY = (this.Height / 2) - 1;  
            }  
            Color c1 = Color.FromArgb(color1Transparent, color1);  
            Color c2 = Color.FromArgb(color2Transparent, color2);  
            //drawing string & filling gradient rectangle   
            Brush b = new System.Drawing.Drawing2D.LinearGradientBrush(ClientRectangle, c1, c2, angle);  
            Point p = new Point(textX, textY);  
            SolidBrush frcolor = new SolidBrush(this.ForeColor);  
            Border3DStyle borderStyle = Border3DStyle.SunkenInner;  
            pe.Graphics.FillRectangle(b, ClientRectangle);  
            pe.Graphics.DrawString(text, this.Font, frcolor, p);  
            ControlPaint.DrawBorder3D(pe.Graphics, ClientRectangle, borderStyle);  
            b.Dispose();  
        }  

    }  
}  
于 2016-02-20T13:02:21.433 に答える
0

これは答えではありませんが、コメントするには長すぎます(答えではないとして投票しないでください)


この場合、カスタム コントロールは使用せず、代わりにコントロールの配列を使用します。

たとえば、グリッド形式で 9 つのコントロールを作成し、それらを配列に割り当てるだけです。

Button[][] buttons = new Button[ROW_COUNT][];
for (int i = 0; i < ROW_COUNT; i++)
{
    buttons[i] = new Buttons[COLUMN_COUNT];
}
buttons[0][0] = btnTopLeft;
...
于 2012-12-06T16:19:44.490 に答える