Генератор кубика в Windows Forms
Введение

Windows Forms — удобный инструмент для быстрой визуальной разработки настольных приложений. Вы перетаскиваете элементы интерфейса на форму, назначаете события и добавляете код для логики приложения.
Если вы только начинаете работать с WinForms, небольшое практическое приложение поможет понять, как обрабатывать события и как рисовать графику на форме. В качестве примера мы реализуем простой генератор кубика: при нажатии на кнопку приложение показывает одну из шести сторон кубика.
Что мы создаём
- Кнопка «Бросить» (Roll) для запуска генерации случайного числа от 1 до 6.
- Шесть панелей, каждая из которых рисует точки, соответствующие одной стороне кубика.
- Логика показа только одной стороны при каждом броске.
Как добавить кнопку «Бросить» в приложение Dice Roller
- Откройте Visual Studio и создайте новый проект Windows Forms.
- Перетащите кнопку из Toolbox на форму.
- В окне свойств измените значения кнопки:
| Свойство | Новое значение |
|---|---|
| Name | rollButton |
| Text | Бросить |
| Location | 130, 110 |
- Дважды кликните по кнопке «Бросить» — Visual Studio сгенерирует обработчик события click:
private void rollButton_Click(object sender, EventArgs e)
{
}- Для генерации случайного числа используйте класс Random:
Random random = new Random();
int randomNumber = random.Next(1, 7);Примечание: экземпляр Random лучше держать как поле формы, чтобы при частых нажатиях не получать повторяющиеся значения из‑за одинакового сид‑времени.
Как создать шесть лиц кубика (панели и отрисовка)
Мы создадим шесть глобальных объектов Panel; каждая будет иметь обработчик Paint, который рисует соответствующее количество точек.
- Объявите шесть полей в классе формы:
Panel face1 = new Panel();
Panel face2 = new Panel();
Panel face3 = new Panel();
Panel face4 = new Panel();
Panel face5 = new Panel();
Panel face6 = new Panel();- Реализуйте метод InitializeFace, который настраивает панель (граница, размер, положение, видимость) и привязывает обработчик Paint:
private void InitializeFace(Panel face, string name)
{
face.Name = name;
face.Visible = false;
face.Size = new Size(500, 500);
face.BorderStyle = BorderStyle.FixedSingle;
face.Location = new Point(250, 250);
face.Paint += new PaintEventHandler(this.Panel_Paint);
// Добавляем панель на форму
this.Controls.Add(face);
}- В конструкторе формы вызовите InitializeFace для всех сторон:
public Form1()
{
InitializeComponent();
InitializeFace(face1, "1");
InitializeFace(face2, "2");
InitializeFace(face3, "3");
InitializeFace(face4, "4");
InitializeFace(face5, "5");
InitializeFace(face6, "6");
}- Реализуйте обработчик Panel_Paint, который отрисовывает точки в зависимости от имени панели. Здесь точки рисуются объектом SolidBrush цвета красного:
private void Panel_Paint(object sender, PaintEventArgs e)
{
// Создаём кисть для рисования точек
Color red = Color.Red;
SolidBrush solidBrush = new SolidBrush(red);
Panel panel = sender as Panel;
// Рисуем разное количество кружков в зависимости от названия панели
switch (panel.Name)
{
case "1":
e.Graphics.FillEllipse(solidBrush, 200, 200, 100, 100);
break;
case "2":
e.Graphics.FillEllipse(solidBrush, 100, 200, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 200, 100, 100);
break;
case "3":
e.Graphics.FillEllipse(solidBrush, 100, 100, 100, 100);
e.Graphics.FillEllipse(solidBrush, 200, 200, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 300, 100, 100);
break;
case "4":
e.Graphics.FillEllipse(solidBrush, 100, 100, 100, 100);
e.Graphics.FillEllipse(solidBrush, 100, 300, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 100, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 300, 100, 100);
break;
case "5":
e.Graphics.FillEllipse(solidBrush, 100, 100, 100, 100);
e.Graphics.FillEllipse(solidBrush, 100, 300, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 100, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 300, 100, 100);
e.Graphics.FillEllipse(solidBrush, 200, 200, 100, 100);
break;
default:
// Сторона 6: шесть точек
e.Graphics.FillEllipse(solidBrush, 100, 200, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 200, 100, 100);
e.Graphics.FillEllipse(solidBrush, 100, 80, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 80, 100, 100);
e.Graphics.FillEllipse(solidBrush, 100, 320, 100, 100);
e.Graphics.FillEllipse(solidBrush, 300, 320, 100, 100);
break;
}
}Важно: координаты и размер точек в коде подобраны для панели 500×500. При изменении размера панели скорректируйте координаты или используйте вычисляемые позиции (см. раздел «Улучшения»).
Как реализовать бросок кубика
- Добавьте метод ResetDie(), который прячет все панели:
private void ResetDie()
{
face1.Visible = false;
face2.Visible = false;
face3.Visible = false;
face4.Visible = false;
face5.Visible = false;
face6.Visible = false;
}- Дополните обработчик rollButton_Click() логикой определения и показа стороны:
private void rollButton_Click(object sender, EventArgs e)
{
// Генерируем случайное число от 1 до 6
Random random = new Random();
int randomNumber = random.Next(1, 7);
// Скрываем предыдущие стороны
ResetDie();
// Показываем ту сторону, которая выпала
if (randomNumber == 1)
face1.Visible = true;
if (randomNumber == 2)
face2.Visible = true;
if (randomNumber == 3)
face3.Visible = true;
if (randomNumber == 4)
face4.Visible = true;
if (randomNumber == 5)
face5.Visible = true;
if (randomNumber == 6)
face6.Visible = true;
}Примечание по генератору случайных чисел: если вы создаёте новый Random внутри обработчика при каждом клике, при очень частых кликах в короткий промежуток времени возможны повторения из‑за одинакового начального времени. Чтобы избежать этого, создайте поле Random random = new Random(); в классе формы и используйте его повсеместно.
Как запустить приложение
- В Visual Studio нажмите зелёную кнопку запуска.
- Нажимайте «Бросить», и видимая сторона будет меняться.
Улучшения и варианты реализации
- Адаптивная отрисовка: вычисляйте позиции точек относительно размера панели (например, через проценты), чтобы панели разных размеров корректно рисовали точки.
- Анимация: перед показом конечной стороны можно проигрывать быструю смену панелей для эффекта анимации броска.
- Использование PictureBox: вместо панелей рисовать на Bitmap и показывать в PictureBox, если хотите кешировать изображение стороны.
- Рефакторинг: использовать массив Panel[] faces и индексировать по (randomNumber - 1), чтобы убрать длинную цепочку if.
Пример компактной установки видимости через массив
Panel[] faces;
// В конструкторе после InitializeFace
faces = new Panel[] { face1, face2, face3, face4, face5, face6 };
// В обработчике броска
ResetDie();
faces[randomNumber - 1].Visible = true;Когда этот подход не подходит
- Если нужна 3D‑визуализация броска — тогда лучше использовать 3D‑движок или библиотеку (например, Unity или DirectX).
- Для сетевых игр с многоразовыми бросками и проверкой честности стоит использовать криптостойкий генератор случайных чисел и серверную логику.
Чек‑лист перед сдачей/демонстрацией
- Кнопка «Бросить» корректно вызывает обработчик.
- Все шесть панелей инициализируются и добавлены на форму.
- Paint корректно рисует точки для всех сторон.
- При каждом броске видна только одна сторона.
- Устранены проблемы с повторами случайных чисел (Random вынесен на уровень класса).
- UI читаем на целевом разрешении экрана.
Критерии приёмки
- При 100 независимых бросков распределение выпадений приблизительно равномерно (в рамках разумных вариаций для теста).
- Непрерывные быстрые клики не приводят к зависанию интерфейса.
- Размеры и позиции точек корректны при стандартном размере окна.
Советы по отладке
- Если панели не видны — проверьте, что this.Controls.Add(face) вызван и что Visible действительно меняется.
- Если точки не рисуются — убедитесь, что метод Panel_Paint привязан к событию Paint и что panel.Name установлено правильно.
- Для логирования используйте Debug.WriteLine(randomNumber) внутри обработчика броска.
Важно: не создавайте новый Random в tight loop — держите один экземпляр для формы.
Краткая методология (быстрое планирование прототипа)
- Спроектируйте UI: кнопка + область отображения.
- Определите модель: 6 состояний (1..6).
- Реализуйте рендеринг каждого состояния (Paint).
- Добавьте логику переключения состояний на событие.
- Тестируйте повторными бросками и при разных разрешениях.
Итог
Создание простого генератора кубика в Windows Forms — хорошая практика для изучения событий, управления Controls и рисования GDI+. Код компактный, легко расширяемый (анимация, масштабирование, кеширование). Начните с базовой структуры, затем рефакторьте под повторное использование и тестируемость.
Сводка действий:
- Добавьте кнопку и панели.
- Настройте InitializeFace и Panel_Paint.
- Реализуйте ResetDie и обработчик броска с Random.
Удачи в экспериментах — попробуйте адаптировать отрисовку под разные размеры и добавить анимацию.
Похожие материалы
RDP: полный гид по настройке и безопасности
Android как клавиатура и трекпад для Windows
Советы и приёмы для работы с PDF
Calibration в Lightroom Classic: как и когда использовать
Отключить Siri Suggestions на iPhone