(+84) 236.3827111 ex. 402

Lập trình game Winform với C# (Phần 1)


Trước hết, hãy tham khảo 1 game tương tự tại trang web này: https://gamevui.vn/pikachu/game

Bạn hãy để ý:

  • Phần game chính (phần table chứa các pokemon) là một ma trận chữ nhật, có kích thước là height *width
  • Số pokemon phải là chẵn, do đó height*width phải chia hết cho 2 (ko thể lẻ 1 con pokemon đc đúng không)
  • Mỗi một ô trong ma trận chữ nhật có kích thước bằng nhau, sẽ chứa 1 pokemon bất kì.
  • Mỗi 1 pokemon bất kỳ đều có số lượng chẵn (phải chẵn để đủ ghép cặp 2 con vs nhau chứ)
    Ví dụ sẽ có 4 pikachu, 8 con rồng lửa, 10 con sâu

ý tưởng:

  • Chúng ta khởi tạo 1 bảng gồm width*height ô chữ nhật (width hoặc height phải chẵn). Mỗi ô trong bảng là 1 con số (ví dụ từ 1->20) đại diện cho một loại pokemon
  • Mỗi 1 con số (đại diện cho 1 loại pokemon) phải có số lượng là chẵn ở trong bảng (ví dụ 2 số 1, 20 số 2, 14 số 3, ...)
  • Không có ô nào trong bảng không có số (tức là ko có pokemon nào trong ô đó)
  • Về mặt giao diện, chúng ta sẽ dùng 1 cái gì đó để biểu diễn cho một hình chữ nhật có chứa pokemon. Và cái chúng ta cần sử dụng trong C# winform, phù hợp vs bài toán của chúng ta đó chính là PictureBox
    Sâu hơn về pictureBox, bạn có thể đọc thêm ở đây:https://csharpcanban.com/c-huong-dan-su-dung-picturebox-control.html#.XoMGACgzbZQ
    Đại khái chúng ta sẽ tưởng tượng rằng, chúng ta sẽ xếp liên tục các PictureBox (trong mỗi PictureBox chứa 1 ảnh đại diện cho 1 pokemon) vào vs nhau để tạo ra table như bên trên
  • Với bài tập này, chúng ta nên tạo ra lớp GameModel để biểu diễn dữ liệu (là chiều cao, chiều rộng và là cái bảng chứa các pikachu dưới dạng con số). Đối với giao diện, chúng ta dùng Form và add thẳng các PictureBox vào form

Bắt đầu làm:

  1. Chuẩn bị:
    - Hãy tự tìm và download bộ ảnh pokemon rồi đặt tên theo thứ tự của chúng. Ví dụ 1.png, 2.png, 3.png
    Hãy lên chính trang https://gamevui.vn/pikachu/game để download các tấm ảnh của pokemon nhé (đã đc đặt tên theo số thứ tự rồi đó)
  2. Tạo dự án:
    Hãy tạo dự án winform bằng công cụ Visual Studio như ảnh dưới đây:
  3. Hãy tạo thêm lớp GameModel, thể hiện là dữ liệu bảng dữ liệu:
    1. Có thuộc tính là width, height, và int[,] table để thể hiện các pokemon nằm trong bảng
    2. Có phương thức khởi tạo để khởi tạo cái table. Hãy sinh ngẫu nhiên các pokemon nằm trong đó
    3. Thuật toán sinh ngẫu nhiên các pokemon và hàm khởi tạo, các bạn có thể tham khảo đoạn code này nha:
      class GameModel
          {
              private int[, ] table;
              private int width, height;
      
              public GameModel(int _width, int _height, int _numOfType)
              {
                  width = _width;
                  height = _height;
      
                  table = new int[height, width];
      
                  // su dung de luu cac o da sinh ra pokemon
                  HashSet<int> cellIndex = new HashSet<int>();
      
                  // su dung de sinh so ngau nhien
                  Random random = new Random();
      
                  for (int i=0; i<width*height/2; i++)
                  {
                      // sinh ngau nhien 1 loai pokemon, nam trong khoang tu 1 -> _numOfType
                      int typeOfPokemon = random.Next(1, _numOfType + 1);
                      Console.WriteLine(i);
                      // sinh ra o thu 1 chua pokemon, yeu cau la khong dc nam trong cellIndex
                      int cell1 = random.Next(random.Next(0, width * height+1));
                      while (cellIndex.Contains(cell1))
                          cell1 = random.Next(random.Next(0, width * height+1));
                      table[cell1 / width, cell1 % width] = typeOfPokemon;
                      cellIndex.Add(cell1);
      
                      // sinh ra o thu 2 chua pokemon, yeu cau la khong dc nam trong cellIndex
                      int cell2 = random.Next(random.Next(0, width * height+1));
                      while (cellIndex.Contains(cell2))
                          cell2 = random.Next(random.Next(0, width * height+1));
                      table[cell2 / width, cell2 % width] = typeOfPokemon;
                      cellIndex.Add(cell2);
      
                      Console.WriteLine(i);
                  }    
              }
      }
    4. Bạn cần tự viết thêm các hàm/phương thức Width, Height và getCell(int row, col) để lấy ra được các dữ liệu tương ứng nha
    5. Hãy cố đọc hiểu và phân tích hàm sinh ma trận một cách ngẫu nhiên của mình nhé
  4. Cập nhật lại file Form1.cs có sẵn khi tạo dự án như thế này:
     public partial class Form1 : Form
        {
            public Form1()
            {
                InitializeComponent();
                GameModel gameModel = new GameModel(20, 10, 10);
                for (int i = 0; i < gameModel.Height; i++)
                    for (int j = 0; j < gameModel.Width; j++)
                    {
                        PictureBox px = new PictureBox();
                        px.Width = 40;
                        px.Height = 50;
                        px.Top = 10 + i * 50;
                        px.Left = 10 + j * 40;
    
                        string name = "pieces" + gameModel.getCell(i, j).ToString() + ".png";
                        px.Image = Image.FromFile(name);
                        this.Controls.Add(px);
                    }
    
            }
        }

  5. Hãy copy cái đống ảnh bạn đã chuẩn bị vào cùng thư mục chứa file *.exe sẽ biên dịch ra
    Sau đó hãy chạy thử và xem kết quả có giống như hình của mình ko nhé
  6. Hãy cải tiến 1 chút ít chương trình để màn hình hiển thị nhiều pokemon hơn, và các pokemon đc hiển thị chính giữa khung của cửa sổ xem sao nhé