11.1. Диалоговые окна

Классическая задача — получение ввода от пользователя — чаще всего решается через диалоговые окна. Например, у вас есть форма для отображения списка людей, и вы хотите иметь возможность добавления людей в список и редактирования их. Где расположить поля ввода для параметров добавляемого или редактируемого объекта? Можно в том же окне, где находится список, но лучше это делать в отдельном окне редактирования. Давайте рассмотрим это на примере.

Для примера нам понадобится новое WinForms-приложение, на главной форме которого мы поместим компонент ListView для хранения списка и две кнопки для добавления новой записи и редактирования выделенной. В списке ListView нужно:

  • в свойстве Columns добавить три колонки с заголовками: Имя, Фамилия и Возраст;
  • в свойстве View выбрать Details.

Такую главную форму можно увидеть на рис. 11.2.

Теперь нам понадобится дочерняя форма или диалоговое окно для редактирования элементов. Щелкните правой кнопкой мыши по имени проекта в панели Solution Explorer и в контекстном меню выберите Add | New Item. В открывшемся окне найдите и выделите Windows Form и в поле Name введите имя для диалогового окна — например, EditPersonForm.

Рис. 11.2. Форма будущей программы

Сразу же поместите на форму две кнопки для сохранения и отмены изменений, а также три поля ввода: для изменения имени, фамилии и возраста. Для изменения возраста можно использовать компонент NumericUpDown, который хорошо подходит для редактирования чисел. Мой вариант формы можно увидеть на рис. 11.3, но ваш может и отличаться.

Рис. 11.3. Форма диалогового окна

Теперь несколько рекомендаций по оформлению диалоговых окон, которым не обязательно следовать, но которые чаще всего положительно сказываются на удобстве использования программ:

  • в свойстве AcceptButton нужно указать кнопку, которая будет являться кнопкой по умолчанию, и именно она станет срабатывать (будет вызываться ее обработчик события Click), если пользователь нажмет клавишу в тот момент, когда отображается окно. Здесь чаще выбирают кнопки типа OK или Да;
  • в свойстве CancelButton укажите кнопку отмены, которая будет срабатывать при нажатии клавиши ;
  • свойство FormBorderStyle лучше установить в FixedDialog, потому что диалоговым окнам желательно устанавливать фиксированный размер окна, их просто незачем растягивать;
  • свойство MaximizeBox рекомендуется установить в false, чтобы в заголовке окна не отображалась кнопка максимизации формы. Мы уже определились, что размер окна не должен изменяться, и возможность максимизации тем более не нужна;
  • свойство ShowInTaskBar лучше тоже установить в false, потому что только главное окно должно отображаться в панели задач. Дочерние окна отображайте в панели задач только при необходимости, а для диалоговых окон я не могу себе представить эту необходимость, — особенно, если окно модальное.

Еще пару манипуляций нужно сделать над кнопками. Для кнопки Сохранить установите свойство DialogResult в OK, а для кнопки Отмена установите это же свойство в Cancel. Теперь, если окно отображается в модальном режиме, то по нажатию любой из этих кнопок окно будет закрыто, а форма вернет в качестве результата то, что мы указали для кнопок в свойстве DialogResult.

Теперь посмотрим, как может использоваться эта форма. Для начала в коде формы добавим три свойства, через которые будет происходить обращение к полям ввода:

   public string FirstName
   {
     get { return firstNameTextBox.Text; }
     set { firstNameTextBox.Text = value; }
   }

   public string LastName
   {
     get { return lastNameTextBox.Text; }
     set { lastNameTextBox.Text = value; }
   }

   public int Age
   {
     get { return (int)ageNumericUpDown.Value; }
     set { ageNumericUpDown.Value = value; }
   }

Добавленные здесь свойства являются посредниками между диалоговым окном редактирования и главным окном, из которого будет вызываться это диалоговое окно.

Теперь все готово, чтобы написать код, который будет создавать новые элементы в списке и редактировать их. Для начала создайте обработчик события Click для кнопки Добавить главной формы и напишите в нем содержимое листинга 11.1.

Листинг 11.1. Код добавления нового элемента в список

private void addPersonButton_Click(object sender, EventArgs e)
{
  // создаем форму
  EditPersonForm editForm = new EditPersonForm();

  // отображаем форму
  if (editForm.ShowDialog() != DialogResult.OK)
    return;

  ListViewItem newItem = 
           personsListView.Items.Add(editForm.FirstName);
  newItem.SubItems.Add(editForm.LastName);
  newItem.SubItems.Add(editForm.Age.ToString());
}

В самом начале создается экземпляр класса EditPersonForm, а этим классом является форма. Следующим этапом идет отображение формы editForm.ShowDialog(), и тут же проверяется результат, который возвращает метод ShowDialog(). Если результат не равен DialogResult.OK (а этот результат возвращает кнопка Сохранить в диалоговом окне), то выполнение метода прерывается.

После этого создается новый элемент для списка ListView и заполняются два подэлемента, которые будут отображаться в колонках. Для чтения данных из объекта диалогового окна editForm используются свойства, которые мы написали.

Теперь посмотрим на метод, который выполняет редактирование выделенного в списке элемента. Этот код вы можете увидеть в листинге 11.2.

Листинг 11.2. Редактирование с помощью диалогового окна

private void editPersonButton_Click(object sender, EventArgs e)
{
  if (personsListView.SelectedItems.Count == 0)
    return;

  // для удобства сохраняем выделенный элемент в локальной переменной
  ListViewItem item = personsListView.SelectedItems[0];
  // создаем форму
  EditPersonForm editForm = new EditPersonForm();

  // заполняем поля формы значениями
  editForm.FirstName = item.Text;
  editForm.LastName = item.SubItems[1].Text;
  editForm.Age = Convert.ToInt32(item.SubItems[2].Text);
  if (editForm.ShowDialog() != DialogResult.OK)
    return;

  item.Text = editForm.FirstName;
  item.SubItems[1].Text = editForm.LastName;
  item.SubItems[2].Text = editForm.Age.ToString();
}

Предыдущая глава

11. Формы

О блоге

Программист, автор нескольких книг серии глазами хакера и просто блогер. Интересуюсь безопасностью, хотя хакером себя не считаю

Обратная связь

Без проблем вступаю в неразборчивые разговоры по e-mail. Стараюсь отвечать на письма всех читателей вне зависимости от страны проживания, вероисповедания, на русском или английском языке.

Пишите мне