Как использовать симбиоз для графического выбора часов в C#
Этот пример изменяет предыдущий пример
Один из недостатков этого метода заключается в том, что новый элемент управления должен быть скомпилирован, прежде чем вы сможете его использовать или увидеть в панели инструментов. Это не конец света и работает очень хорошо, если вы распространяете скомпилированные программы, но я отправляю только исходный код, а не компилируемый код. Если я размещаю проект, содержащий не скомпилированный пользовательский элемент управления, при первой загрузке проекта любая форма, использующая элемент управления, не может отобразить его. Вам нужно скомпилировать проект, прежде чем вы сможете его увидеть.
Альтернативой является то, что я называю классом «симбионт». Симбиот - это класс, который используется для добавления функций в другой класс. В этом случае объект SelectHoursSymbiote добавляет функции в PictureBox, чтобы заставить его вести себя как элемент управления, используемый в предыдущем примере. Это дает вам почти все преимущества скомпилированного настраиваемого элемента управления, но вам не нужно его компилировать отдельно. Недостатком является то, что он не отображается в панели инструментов. Вы создаете элемент управления PictureBox, а затем присоединяете к нему симбиот во время выполнения.
Класс SelectHoursSymbiote содержит весь код, используемый в предыдущем примере, для работы с элементом управления PictureBox плюс дополнительный код для управления событиями и т. д. p >
Следующий код показывает, как класс объявляет события HoursScrolled и HoursChanged.
// Объявлять события. public event EventHandler HoursScrolled; public event EventHandler HoursChanged
Эти события сообщают основной программе, когда меняются часы симбиота.
Следующий код показывает свойства StartHour и StopHour класса.
// Выбранные часы. private int _StartHour = 0; private int _StopHour = 0; public int StartHour { get { return _StartHour; } set { _StartHour = value; // Поднять событие HoursChanged. if (HoursChanged != null) HoursChanged(this, null); } } public int StopHour { get { return _StopHour; } set { _StopHour = value; // Поднять событие HoursChanged. if (HoursChanged != null) HoursChanged(this, null); } }
Это довольно простые свойства. Вы можете реализовать их как общедоступные поля (если вы хотите игнорировать пуристов, которые говорят, что вы никогда не должны публиковать поля публично), но я хотел, чтобы код повышал событие HoursChanged, когда эти значения менялись. р>
В следующем коде показан единственный конструктор класса.
// Мы управляем PictureBox. public PictureBox PictureBox; // Конструктор. public SelectHoursSymbiote(PictureBox pic) { PictureBox = pic; // Добавить обработчики событий. Pic.Paint += pic_Paint; Pic.MouseDown += pic_MouseDown; Pic.MouseMove += pic_MouseMove; Pic.MouseUp += pic_MouseUp; }
В переменной PictureBox содержится ссылка на PictureBox, к которой привязан симбион. Конструктор сохраняет ссылку на PictureBox.
Затем он дает обработчикам событий PictureBox, чтобы поймать событие Paint и события мыши, которые он должен позволить пользователю выбирать часы. Эти обработчики событий почти такие же, как те, которые использовались в предыдущем примере
Единственные реальные различия заключаются в том, что обработчики событий MouseMove и MouseUp вызывают события. После вычисления недавно выбранных часов обработчик события MouseMove использует следующий код, чтобы поднять событие HoursScrolled в симбиоте.
// Поднять событие HoursScrolled. if (HoursScrolled != null) HoursScrolled(this, null)
Обработчик события MouseUp использует следующий код, чтобы поднять событие HoursChanged.
// Поднять событие HoursChanged. if (HoursChanged != null) HoursChanged(this, null)
Основная программа использует следующий код для прикрепления симбиотов к элементам управления PictureBox.
// Симбиоты. private SelectHoursSymbiote Symbiote1, Symbiote2; private void Form1_Load(object sender, EventArgs e) { this.ResizeRedraw = true; // Создаем симбиоты. Symbiote1 = new SelectHoursSymbiote(picHours1); Symbiote1.HoursChanged += pic_HoursChanged; Symbiote1.HoursScrolled += pic_HoursChanged; Symbiote1.StartHour = 6; Symbiote1.StopHour = 14; Symbiote2 = new SelectHoursSymbiote(picHours2); Symbiote2.HoursChanged += pic_HoursChanged; Symbiote2.HoursScrolled += pic_HoursChanged; Symbiote2.StartHour = 9; Symbiote2.StopHour = 17; }
Код создает новые симбиоты, передавая их конструкторам элементы управления PictureBox, к которым они должны быть прикреплены. Он регистрирует обработчики событий для событий симбиотов HoursScrolled и HoursChanged и дает им начальные значения StartHour и StopHour. р>
Следующий код показывает, как программа отвечает, когда получает событие HoursScrolled или HoursChanged.
// Показывать время в TextBoxes. // Показывать время в TextBoxes. private void pic_HoursChanged(object sender, EventArgs e) { SelectHoursSymbiote symbiote = sender as SelectHoursSymbiote; DateTime start_time = new DateTime(2000, 1, 1, symbiote.StartHour, 0, 0); DateTime stop_time = new DateTime(2000, 1, 1, symbiote.StopHour, 0, 0); string tip = start_time.ToShortTimeString() + " to " + stop_time.ToShortTimeString(); if (tipHour.GetToolTip(symbiote.PictureBox) != tip) tipHour.SetToolTip(symbiote.PictureBox, tip); if (symbiote == Symbiote1) { txtStartTime1.Text = start_time.ToShortTimeString(); txtStopTime1.Text = stop_time.ToShortTimeString(); } else { txtStartTime2.Text = start_time.ToShortTimeString(); txtStopTime2.Text = stop_time.ToShortTimeString(); } }
Этот код преобразует часы симбиона в объекты DateTime, а затем отображает их как короткие промежутки времени в соответствующих текстовых окнах.