Этот проект — это ВУЗовские лабораторные работы по курсу «Объектно-ориентированное программирование».
Задания были следующими:
ЛАБОРАТОРНАЯ РАБОТА №1
«Создание Windows-приложений. Обработка событий мыши. Вывод текста в окно.»
-
Ознакомиться со средой проектирования Visual Studio.NET
-
Создать простейшее приложение средствами Studio.NET.
-
Изменить размеры окна приложения, цвет фона и заголовок.
-
Реализовать обработку щелчка левой и правой кнопки мыши. По левой кнопке — выводить координаты курсора мыши в точке его нахождения. По правой – отображать диалоговое окно с сообщением «Нажата правая кнопка мыши» и очищать окно приложения от надписей.
ЛАБОРАТОРНАЯ РАБОТА №2
«Создание многооконного приложения, имеющего меню. Рисование прямоугольников под управлением мыши.»
-
Сделать окно приложения MDI-контейнером.
-
Создать меню приложения, содержащее на верхнем уровне пункт «Окно», а в распахиваюшемся списке команду «Новое» и список открытых окон. Реализовать обработку команды создания нового окна.
-
Реализовать рисование на экране прямоугольников под управлением мыши. При нажатии левой кнопки мыши и ее удержании при перемещении мыши потенциальный прямоугольник должен отображаться пунктиром, при отпускании кнопки мыши прямоугольник должен выводиться сплошной линией. Должно рисоваться произвольное число прямоугольников.
ЛАБОРАТОРНАЯ РАБОТА №3
«Проектирование иерархии классов. Использование контейнерных классов. Перерисовка графической информации.»
-
Спроектировать базовый класс для моделирования различных геоматрических фигур.
-
Спроектировать класс, моделирующий прямоугольник, как производный от класса, спроектированного в пункте 1 задания.
-
Реализовать сохранение информации об изображении в динамическом массиве объектов, имеющих тип класса, спроектированного в пункте 1 задания.
-
Реализовать перерисовку графического изображения, создаваемого в программе.
ЛАБОРАТОРНАЯ РАБОТА №4
«Сохранение документов в файлах.»
-
Добавить в меню программы команды сохранения и открытия файлов. Реализовать сохранение рисунков в файлах и чтение их из файлов. После сохранения файла заголовок окна соответствующего документа должен содержать имя файла. При открытии файла его имя должно использоваться в качестве заголовка окна. Пока нет ни одного открытого окна документа, команды сохранения файла должны быть в заблокированном состоянии.
-
Для измененных документов при закрытии окна следует выдавать диалоговое окно с запросом о сохранении документа и обрабатывать три варианта выбора пользователя – сохранение, отказ от сохранения и отказ от закрытия окна (Yes-No-Cancel).
ЛАБОРАТОРНАЯ РАБОТА №5
«Управление атрибутами графического вывода. Использование окон диалога.»
-
Дополнить модель фигуры атрибутами цвета линии, цвета фона фигуры, толщины линии. Реализовать сохранение этих атрибутов в файлах. Использовать эти атрибуты при рисовании прямоугольников.
-
Добавить в меню верхнего уровня пункт «Параметры». В подменю поместить пункты «Цвет линии», «Цвет фона», «Толщина линии».
-
Реализовать создание соответствующих диалоговых панелей для обработки новых команд меню и использование результатов ввода в программе. В диалоговом окне выбора размера пера использовать комбинированный список с полем ввода (combobox), содержащий список фиксированных размеров(1, 2, 5, 8, 10, 12, 15) .
Выбранные в диалоговых панелях параметры должны использоваться при рисовании фигур во всех открытых в редакторе окнах. По умолчанию при запуске программы должны использоваться чёрный цвет линии, белый цвет фона и единичная толщина линии.
ЛАБОРАТОРНАЯ РАБОТА №6
«Управление размером рисунка. Прокрутка изображения.»
-
Ввести в меню команду настройки размеров для вновь создаваемых рисунков. Вызываемая диалоговая панель должна содержать выбор размера (c использованием radio-кнопок) из трех фиксированных вариантов (320×240, 640×480, 800×600), флажок выбора ручного ввода размера, поля ввода ширины и высоты рисунка в пикселях. Выбор размера не должен изменять размеры уже существующих рисунков, а должен определять размеры рисунков, создаваемых в дальнейшем командой «Новый».
-
Рисунок должен отображаться и записываться в файл с учетом своего размера. Фон области формы, находящийся вне рисунка, должен отображаться светло-серым цветом. Если при завершении рисования фигуры будет происходить выход контура фигуры за границы рисунка, соответствующая фигура не должна добавляться к рисунку.
-
Дополнить окна документов полосами прокрутки, обеспечить корректное отображение рисунков при скроллинге.
ЛАБОРАТОРНАЯ РАБОТА №7
«Развитие иерархии классов. Оптимизация операций рисования.»
-
Спроектировать классы, обеспечивающие рисование и сохранение в файлах помимо прямоугольников также эллипсов, прямых линий и линий произвольной формы. Рисование линии произвольной формы должно начинаться по нажатию на левую кнопку мыши и завершаться по её отпусканию.
-
Дополнить меню программы разделом «Фигура», пункты которого должны обеспечивать выбор режима рисования одной из фигур. Пункт меню, соответствующий выбранной фигуре, должен отмечаться галочкой. Для замкнутых фигур (прямоугольника и эллипса) должны поддерживаться режимы прозрачного фона и заливки фона фигуры выбранным цветом фона. Для выбора режима заливки в меню «Фигура» ввести пункт «Заливка», который должен работать как флаг, последовательно устанавливаемый и сбрасываемый при его выборе. Активность режима заливки должна отображаться галочкой рядом с пунктом меню.
-
Обеспечить сохранение целостности исходного изображения в процессе добавления новых фигур к рисунку (отсутствие в окне «мусора» и стёртых фрагментов фигур). Обеспечить отсутствие мерцания (мелькания фона) при добавлении новых фигур и изменении размеров окна.
ЛАБОРАТОРНАЯ РАБОТА №8
«Строка состояния. Панель инструментов.»
-
Добавить в редактор строку состояния. Реализовать вывод в строке состояния информации о выбранном размере пера, цвете пера и цвете заливки, а также вывод координат курсора мыши и размера рисунка в пикселях.
-
Спроектировать кнопочную панель, содержащую кнопки создания нового документа, сохранения документа, открытия документа, выбора размера пера, цвета пера, цвета заливки фона, размера вновь создаваемого изображения и группу кнопок выбора режима рисования фигуры – прямоугольника, эллипса, прямой линии, линии произвольной формы. Группа должна быть реализована как группа кнопок с зависимой фиксацией. Также разместить на панели независимую кнопку включения /выключения заливки. Обеспечить обработку событий от кнопок панели.
ЛАБОРАТОРНАЯ РАБОТА №9
«Вывод текста с использованием различных шрифтов.»
-
Дополнить меню редактора и кнопочную панель управления командами выбора шрифта по умолчанию и выбора режима ввода текстовых надписей. Команда выбора шрифта должна вызывать стандартное диалоговое окно выбора шрифта.
-
В режиме ввода текста левой кнопкой мыши должны задаваться размеры и положение блока ввода текста. Ввод текста должен завершаться нажатием клавиши «Enter», после чего введенная текстовая надпись должна отображаться как элемент рисунка. При выводе должен использоваться текущий цвет пера как цвет выводимого текста.
-
Текстовые надписи должны сохраняться в файле вместе с графическими элементами рисунка.
-
В строке состояния в режиме ввода текста должны отображаться в качестве дополнительных параметров название шрифта и его размер.
ЛАБОРАТОРНАЯ РАБОТА №10
«Редактирование рисунка. Выделение элемента и блока. Перетаскивание. Удаление.»
-
Добавить в кнопочное меню редактора кнопку режима выделения фигур. Эта кнопка должна быть с фиксацией. В режиме выделения при однократном нажатии левой кнопки мыши должна выделяться та фигура, в прямоугольном блоке которой находился в этот момент указатель мыши. Под прямоугольным блоком фигуры здесь понимается прямоугольник, в который вписывается данная фигура. Перемещение мыши с нажатой левой кнопкой должно приводить к выделению набора фигур, прямоугольные блоки которых пересекаются с прямоугольником выделения, который должен отображаться пунктирной линией в процессе выделения. После выделения выделенные фигуры должны отображаться с наложенным на обычный рисунок пунктирным контуром (для текстового блока – прямоугольник блока). Новая операция выделения блока с перемещением мыши или её попытка должны отменять предыдущие выделения фигур. Щелчок по фигуре без перемещения мыши должен добавлять очередную фигуру к существующему набору выделенных фигур. Сохранять в файле признак выделения фигуры не следует.
-
Реализовать перетаскивание фигур блока в режиме выделения при наличии выделенных фигур и нажатии левой кнопки мыши в поле прямоугольной области любой выделенной фигуры с дальнейшим перемещением мыши. (Нажатие левой кнопки вне выделенных фигур должно обрабатываться как попытка следующего выделения.) При перемещении должны рисоваться пунктирные контуры потенциального нового положения фигур блока. При отпускании кнопки мыши блок или фигура должны отображаться на новом месте при условии непересечения ими границ рисунка. В противном случае операция должна игнорироваться.
-
Реализовать команду удаления выделенного блока или фигуры. Добавить соответствующий пункт в меню редактирования.
ЛАБОРАТОРНАЯ РАБОТА №11
«Операции с буфером обмена и метафайлом. Использование функций API Windows»
-
Добавить в редактор раздел «Правка» в меню верхнего уровня. Реализовать операции и команды меню:
a) Копирование выделенного блока в системный буфер обмена (Clipboard) в собственном формате
b) Копирование блока в Clipboard в формате метафайла.
c) Вырезание блока (копирование в буфер с удалением).
d) Вставка блока (в собственном формате) из буфера.
e) «Выделить все» -
Команды меню, вызывающие операции с буфером обмена, должны блокироваться при отсутствии окон рисунков и при отсутствии в рисунке активной формы выделенного блока (для команд копирования и вырезания).
Команда вставки из буфера должна блокироваться при отсутствии в буфере информации нужного формата. -
При вставке в новое окно блок должен позиционироваться в левый верхний угол рисунка, вне зависимости от его положения в исходном рисунке. Если размеры блока превышают размеры рисунка, вставка выполняться не должна, а должно выводиться окно с сообщением о том, что блок превышает допустимые размеры.
-
Для метафайла, передаваемого в буфер, следует проверить возможность вставки из буфера в программы MS Word, Excel, Paint.
ЛАБОРАТОРНАЯ РАБОТА №12
«Управление координатной сеткой.»
-
Дополнить редактор возможностью включения /выключения отображения координатной сетки с регулируемым шагом. Сетка должна отображаться штриховой линией серого цвета единичной толщины. Добавить в меню редактора соответствующие команды («Сетка» и «Шаг сетки» в раздел «Атрибуты»). Шаг сетки по умолчанию сделать 10×10 пикселей. Раздельно регулировать шаг сетки по вертикальной и горизонтальной оси не требуется.
-
Добавить в меню (в раздел «Правка») команду «Выровнять по сетке», которая должна перемещать точки привязки всех фигур рисунка в узлы выбранной сетки. Реализовать эту операцию для всех фигур. Для прямоугольника, эллипса, линии должны выравниваться по сетке обе точки, определяющие фигуру. Для текстового блока – координаты, задающие границы блока. Для кривой следует разработать алгоритм, который разместит её начальную и конечную точки в узлах сетки, а координаты промежуточных точек изменит так, чтобы сохранить форму и гладкость кривой.
-
Добавить в меню «Атрибуты» команду-флаг «Привязка к сетке». При выборе этого режима добавляемые к рисунку новые фигуры должны сразу выравниваться по узлам сетки.
ЛАБОРАТОРНАЯ РАБОТА №13
«Редактирование элементов рисунка.»
- Реализовать в редакторе режим редактирования параметров фигуры, который должен активизироваться в режиме выделения блока двойным щелчком левой кнопки мыши в области прямоугольного блока фигуры. В этом режиме на контуре блока фигуры должны отображаться маркеры изменения размера в виде восьми небольших квадратов (4 – по углам, 4 – в середине каждой стороны прямоугольника).
При нажатии левой кнопки мыши на маркере изменения размера с дальнейшим перемещением мыши должен отображаться перемещаемый контур новых размеров фигуры. При отпускании кнопки мыши фигура должна отображаться с новыми размерами.
Если кнопка в этом режиме нажимается не на маркере, а в области блока фигуры, перемещение мыши приводит к перемещению фигуры на новое место без изменения её размеров. Режим редактирования должен активизироваться единовременно только для одной фигуры. Выделение блока или выбор другой фигуры для редактирования должны отменять текущий режим редактирования.
Как и при блочных операциях, не должно допускаться пересечение фигурой границы рисунка.
Если включен режим «Выравнивание по сетке», опорные точки редактируемой фигуры должны в итоге попадать в узлы координатной сетки. - Пока определённая фигура находится в режиме редактирования, команды, изменяющие настройки цвета пера, цвета заливки, размера пера, семейства и размера шрифта, должны изменять атрибуты редактируемой фигуры. Общие настройки соответствующих атрибутов не должны в этом случае изменяться.
- Для кривой изменение размеров должно выполняться с сохранением формы кривой.
- Для текстового блока в режиме редактирования параметров должна быть реализована возможность редактирования текста элемента.
ЛАБОРАТОРНАЯ РАБОТА №14
«Элементы управления и диалоговые панели. Редактирование элементов рисунка»
-
Дополнить раздел «Правка» меню программы командой «Редактировать», при выборе которой должна открываться диалоговая панель, содержащая список элементов выбранного рисунка. Список должен отображаться в виде таблицы, содержащей следующие столбцы: номер элемента, тип фигуры, координаты начальной точки фигуры. При выборе определённой фигуры в указанном списке в другой панели, расположенной справа в том же окне, должны отображаться элементы управления, содержащие набор параметров выбранной фигуры с возможностью их редактирования. Состав элементов управления должен соответствовать типу фигуры. Например, цвет заливки должен отображаться и редактироваться только для фигур с заливкой и т.д. Для кривой список задающих её точек должен выводится (и редактироваться) в одном поле ввода с использованием различных разделителей между координатами X-Y и между различными точками кривой.
-
Панель редактирования элементов рисунка должна содержать следующие кнопки:
«Удалить» — удаление фигуры из рисунка.
«Добавить» — добавление новой фигуры к рисунку. При этом должен выводится в отдельном окне список для выбора из доступных типов фигур.
«Сохранить» — сохранение заданных значений в массиве фигур рисунка.
«OK» — закрытие панели редактирования.
Также в панели должны быть кнопки для изменения положения выбранной фигуры в общем списке (и в массиве) на шаг вверх, шаг вниз, в начало, в конец списка. -
Должны редактироваться:
Координаты фигур, цвет линии, фона, текста, размер линии, шрифт, набор точек кривой.
ЛАБОРАТОРНАЯ РАБОТА №1
“Создание Windows-приложений. Обработка событий мыши. Вывод текста в окно.”
Задание.
1. Ознакомиться со средой проектирования Visual Studio.NET
2. Создать простейшее приложение средствами Studio.NET.
3. Изменить размеры окна приложения, цвет фона и заголовок.
4. Реализовать обработку щелчка левой и правой кнопки мыши. По левой кнопке — выводить координаты курсора мыши в точке его нахождения. По правой – отображать диалоговое окно с сообщением «Нажата правая кнопка мыши» и очищать окно приложения от надписей.
Краткая справка.
В состав среды проектирования Microsoft Visual Studio.NET встроены средства, облегчающие программисту разработку приложений. Данная среда позволяет быстро создавать шаблоны новых приложений. При этом программисту не приходится писать ни одной строчки кода. Достаточно ответить на ряд вопросов, касающихся того, какое приложение требуется создать, и исходные тексты шаблона приложения вместе с файлами будут готовы.
Генерируемый средой Visual Studio.NET каркас стандартного приложения Windows содержит ряд классов. Класс формы (Form1) предназначен для создания интерфейса и программирования функциональности приложения. Соответственно, прежде всего с ним работает разработчик приложения Windows.
C формой можно работать в режиме дизайна и в режиме кодирования. В режиме дизайна доступна панель настраиваемых свойств формы (Properties), которая активизируется через команду меню, вызываемого по щелчку правой кнопкой мыши в области формы.
Используя свойства, доступные в панели свойств, можно определить положение, размер, цвет и особенности управления для создаваемого окна. Свойство Text позволяет изменить заголовок окна. Свойства Size и DesktopLocation задают размер и положение окна при его отображении. Свойство ForeColor служит для указания цвета переднего плана по умолчанию для всех элементов управления, размещенных в форме. Свойства BorderStyle, MinimizeBox и MaximizeBox определяют, можно ли будет свернуть, развернуть или изменить размер формы во время исполнения программы.
Для каждого свойства, изменяемого в панели свойств, создается соответствующий код. Он помещается в файл Form1.Designer.cs, в секцию, отмеченнуя как Windows Form Designer generated code. Можно раскрыть ее и просмотреть сгенерированный код.
Программы Windows, основанные на графическом интерфейсе пользователя, управляются событиями. С# выполняет функции обработки сообщений с помощью специальных функций — делегатов. Помимо методов и свойств формы содержат коллекции обработчиков событий. Если требуется обрабатывать событие, то вы должны выбрать в панели свойств формы закладку «Events» и двойным щелчком по пустой ячейке, расположенной справа от имени интересующего события, сгенерировать шаблон функции-обработчика события.
Некоторые события формы и элементов управления:
Click
Возникает при щелчке мыши
DoubleClick
Возникает при двойном щелчке мыши
KeyDown Возникает при нажатии клавиши
KeyUp Возникает при отпускании клавиши
MouseDown
Происходит, когда нажимается кнопка мыши, а указатель мыши
находится над объектом
MouseEnter Возникает, когда указатель мыши попадает в область объекта
MouseLeave Возникает, когда указатель мыши покидает область объекта
MouseMove
Возникает при перемещении мыши над объектом
MouseUp Возникает при отпускании кнопки мыши в области объекта
Resize Возникает при изменении размера объекта
Обработчик события получает два аргумента – ссылку на объект, к которому относится событие, и дополнительную информацию о событии (тип EventArgs или производный от него).
Обработчики событий от мыши получают в качестве второго аргумента объект типа MouseEventArgs.
Свойства, определенные в классе MouseEventArgs:
Button Позволяет получить информацию о том, какая кнопка мыши нажата (в виде значений перечисления MouseButtons)
Clicks Позволяет получить информацию о том, сколько раз нажата и отпущена кнопка мыши
Delta Позволяет получить информацию (в виде положительного или отрицательного числового значения) о повороте колесика мыши
X Позволяет получить координату X для указателя мыши во время щелчка
Y То же самое для координаты Y
Операции рисования и вывода текста инкапсулирует класс System.Drawing.Graphics. В нём присутствуют методы для отображения линий, кривых, строк и других графических элементов.
Для выполнения вывода на экран в методах класса формы требуется предварительно получить объект Graphics. Это обеспечивается добавлением в метод следующей строки:
Graphics g = CreateGraphics();
Текстовые строки в C# хранятся в объектах типа string.
Для вывода текста в окно необходимо объявить переменную этого типа, проинициализировать её и передать методу DrawString класса Graphics.
Например:
string s = «Hello, World!»;
g.DrawString(s, new Font(«Times New Roman», 8),
new SolidBrush(Color.Black), new Point(100, 200);
В операции вывода строки дополнительно указываются три объекта типов Font, SolidBrush и PointF, задающие соответственно шрифт, ипользуемый для вывода, цвет шрифта и координаты точки привязки выводимого текста.
Со строками типа string можно выполнять операцию сложения, задаваемую знаком «+ «.
Числовые типы языка C# можно переводить в строковое представление вызовом для них функции toString.
Например:
string s = e.X.ToString();
Рекомендации
Для выполнения пункта 2 задания создайте проект типа Windows Application, выбрав пункт меню File | New | Project | Visual C# | Windows. В поле Location окна «New Project» укажите путь к папке, рекомендованной для сохранения ваших проектов. Нажмите кнопку “OK”.
Для выполнения пункта 3 следует в панели свойств формы задать значения свойств BackColor, Size, Text. Следует присвоить этим полям значения, задающие соответственно белый цвет, размер 600×450 и имя, которое вы считаете подходящим для разрабатываемого вами графического редактора, функции которого будут реализовываться в дальнейших лабораторных работах.
Для выполнения пункта 4 задания необходимо добавить к классу Form1 обработчик события MouseDown в соответствии с информацией, изложенной в справке к работе.
Для различения нажатий на левую и правую кнопки мыши следует проверять значение поля Button аргумента MouseEventArgs.
Если оно равно MouseButtons.Left, то была нажата левая кнопка, если MouseButtons.Right – правая.
Пример выражения проверки:
if (e.Button == MouseButtons.Left)
Диалоговое окно с сообщением создаётся с помощью функции MessageBox.Show(), которой передаётся два аргумента — строка выводимого в окне текста и строка заголовка окна.
Для очистки окна следует вызвать через объект типа Graphics функцию Clear(), передав ей в качестве аргумента значение цвета Color.White .
видео уроки C# можно найти на www.faippi.narod.ru / видео…
Сообщение изменено: visionland (14 November 2007 — 10:03)
События в Windows-приложениях
Теперь, когда мы разобрались с синтаксисом и логикой делегатов и событий, настало время приступить к рассмотрению событийной модели Windows-форм.
Откройте снова приложение FirstForm. Из окна Toolbox перетащите элемент управления Button на форму. Дважды щелкните на кнопке button1. В коде найдите область Windows Form Designer generated code. В таблице 1.3 сравниваются листинги приложений Event и FirstForm c кнопкой.
Таблица
1.3.
Консольное приложение Event | Windows-приложение FirstForm |
---|---|
using System; |
using System; using System.Drawing; using System.Collections; using System.ComponentModel; using System.Windows.Forms; using System.Data; |
namespace Event { //Объявляем делегат Mydelegate delegate void Mydelegate(); //Создаем класс Button, в котором //будет находится событие //и метод для него class Button { // Объявляем событие Sobitie // на основе делегата public event Mydelegate Sobitie; //Cоздаем метод для события, //который просто будет //обращаться к событию public void MetoddlyaSobitiya() { //Можно вставить проверку наличия события. //if (Sobitie !=null) Sobitie(); } class Class1 { |
namespace FirstForm { public class Form1 : System.Windows.Forms.Form { private System.Windows.Forms.Button button1; private System.ComponentModel.Container components = null; public Form1() { InitializeComponent(); } protected override void Dispose(bool disposing) { if( disposing ) { if (components != null) { components.Dispose(); } } base.Dispose( disposing ); } #region Windows Form Designer generated code private void InitializeComponent() { // Среда автоматически создает экземпляр // button1 класса Button при перетаскивании // элемента управления на форму this.button1 = new System.Windows.Forms.Button(); this.SuspendLayout(); // // button1 // this.button1.Location = new System.Drawing.Point(104, 144); this.button1.Name = "button1"; this.button1.TabIndex = 0; this.button1.Text = "button1"; // Среда автоматически привязывает // обработчик для события Click экземпляра // button1. EventHandler – это делегат. this.button1.Click += new System.EventHandler(this.button1_Click); // // Form1 // this.AutoScaleBaseSize = new System.Drawing.Size(5, 13); this.ClientSize = new System.Drawing.Size(292, 266); this.Controls.Add(this.button1); this.Name = "Form1"; this.Text = "Fom1"; this.ResumeLayout(false); } #endregion |
[STAThread] static void Main(string[] args) { // Создаем экземпляр btn класса Button Button btn = new Button(); //привязываем обработчик для события //Sobitie экземпляра btn. //Когда в скобках укажете //Metodobrabotchik, нажмите //дважды клавишу Tab btn.Sobitie += new Mydelegate(Metodobrabotchik); //Развернутая запись строки выше //btn.Sobitie = btn.Sobitie + // new Mydelegate(Metodobrabotchik); //вызываем метод для события btn.MetoddlyaSobitiya(); } |
[STAThread] static void Main() { Application.Run(new Form1()); } |
// Создаем метод-обработчик, если среда // сгенерировала его сама – // добавляем строку вывода. private static void Metodobrabotchik () { Console.WriteLine("Произошло событие"); } } } } |
// Метод-обработчик для нажатия на кнопку; // когда мы щелкаем по элементу управления // в режиме дизайна, среда генерирует этот //метод и курсор оказывается уже здесь private void button1_Click(object sender, System.EventArgs e) { MessageBox.Show("Произошло событие"); } } } |
Сравнивая листинги, замечаем, что для Windows-приложения First Form не нужно объявлять делегат, событие, метод для обращения к событию и затем вызывать этот метод. Почему же это тогда работает? Дело в том, что среда .NET содержит огромное количество встроенных событий, доступ к которым осуществляется по их названиям. Более того, среда сама привязывает обработчика для события Click (нажатие на кнопку) и нужный метод, используя встроенный делегат EventHandler:
this.button1.Click += new System.EventHandler(this.button1_Click);
Платформа .NET требует точной сигнатуры для любого обработчика событий. button1_Click () и все остальные обработчики событий обязаны выглядеть следующим образом:
void button1_Click (object sender, EventArgs e)//е также может быть производным от EventArgs { // код для обработки события }
Обработчики событий не могут возвращать ничего, кроме void. В них отсутствует точка, которая могла бы служить для возврата значения. Обработчики должны принимать два параметра. Первый параметр является ссылкой на объект, который сгенерировал событие. Второй параметр должен быть ссылкой либо на базовый класс .NET System.EventArgs, либо на производный класс. Класс EventArgs представляет собой общий базовый класс для всех уведомлений о произошедших событиях.
В окне свойств каждого элемента управления на вкладке событий перечислены все доступные события для этого элемента (рис. 1.39).
Рис.
1.39.
Вкладка событий элемента button в окне свойств Properties
Двойной щелчок в поле выбранного свойства перемещает нас в режим дизайна, где уже сгенерированы все объекты для обработки данного события и нам остается только написать код для метода-обработчика. На рис. рис. 1.39 выбрано событие Click, это же событие выбирается по умолчанию при двойном щелчке на элементе управления «кнопка».
События мыши
В Интернете часто встречается шуточная программка, представляющая собой диалоговое окно с двумя кнопками. Для ответа на предлагаемый вопрос следует нажать на одну из двух кнопок, причем вторая кнопка при наведении на нее курсора начинает «убегать» от него. Вы можете встретить реализацию этой шутки, написанную на многих языках — от C до Flash-приложений. Сделаем что-то подобное на C#. Создаем новое Windows—приложение и называем его SocOpros. Из окна Toolbox перетаскиваем на форму две кнопки Button и надпись Label. Устанавливаем следующие свойства элементов управления и формы:
Form1, форма, свойство | Значение |
---|---|
FormBorderStyle | Fixed3D |
Icon | Путь E:\Program Files\Microsoft Visual Studio .NET2003\Common7\Graphics\icons\Computer\W95MBX02.ICO |
Size | 344; 176 |
Text | Социологический опрос |
label1, свойство | Значение |
---|---|
Size | 12 |
Bold | true |
Location | 32; 28 |
Size | 272; 32 |
Text | Вы довольны своей зарплатой? |
Button1, свойство | Значение |
---|---|
Name | btnyes |
Location | 67; 92 |
Text | Да |
Button2, свойство | Значение |
---|---|
Name | btnno |
Location | 195; 92 |
Text | Нет |
Щелкаем дважды по кнопке «Да». В обработчике этой кнопки вставляем следующий код:
private void btnyes_Click(object sender, System.EventArgs e) { MessageBox.Show("Мы и не сомневались, что Вы так думаете!"); }
Выделяем кнопку «Нет». Открываем окно Properties. Переключаемся в окно событий и дважды щелкаем в поле MouseMove (рис. 1.40).
Рис.
1.40.
Событие MouseMove для кнопки btnno Надпись на информационной панели — «Происходит, когда мышь перемещается»
В обработчике этого события связываем движение мыши с координатами кнопки и устанавливаем координаты кнопки, куда она будет возвращаться, если во время своего движения выйдет за указанную область:
private void btnno_MouseMove(object sender, System.Windows.Forms.MouseEventArgs e) { btnno.Top -= e.Y; btnno.Left += e.X; if (btnno.Top < -10 || btnno.Top > 100) btnno.Top = 60; if (btnno.Left < -80 || btnno.Left > 250) btnno.Left = 120; }
Запустите приложение. Теперь, при выборе «Да» появляется окно с надписью, а при попытке нажать на кнопку «Нет» она «убегает» (рис. 1.41).
Рис.
1.41.
Готовое приложение SocOpros
С событиями мыши связано большинство инструментов во многих программах, а для некоторых, например, графических, — это основа всего взаимодействия с пользователем. Другие события мыши — такие как MouseDown, MouseEnter, MouseUp — могут быть использованы для получения необычной реакции на действия пользователя в этом приложении.
На диске, прилагаемом к книге, вы найдете приложение SocOpros (Code\Glava1\ SocOpros ).
Лабораторные работы си шарп. Работа с мышью
Приложения для Windows forms
Лабораторная работа 16
Выполнить: Разработайте приложение «Графический редактор», в котором инструменты не будут похожи на инструменты стандартного графического редактора Paint.
Пример выполнения:
[Название проекта: Lesson_16Lab1
, название файла L16Lab1.cs
]
✍ Выполнение:
-
1. Для вывода графического изображения будем использовать саму форму. Первый инструмент, который мы создадим, будет квадрат, т.е. при перемещении указателя мыши на форме под курсором будет рисоваться квадрат.
2. Для этого необходимо запрограммировать событие MouseMove (перемещение мыши) для формы. Активируйте объект формы, чтобы просмотреть окно свойств и событий. В окне свойств переключитесь на окно событий: а затем из списка событий выберите пункт MouseMove, дважды щелкните по нему. В коде программы появится описание процедуры:
private void Form1_MouseMove(object sender, MouseEventArgs e) { }
3. Теперь опишем необходимые переменные для создания изображений:
Graphics myg = this.CreateGraphics();// создаем холст для рисования int CursorX = Cursor.Position.X; // координата X курсора мыши int CursorY = Cursor.Position.Y; // координата Y курсора мыши Color myColor = Color.FromArgb(100, Color.Red);// Задаем цвет SolidBrush myb = new SolidBrush(myColor); // переменная инструмента Кисть
Класс Graphics предоставляет методы для вывода объектов в устройстве отображения. Объект Graphics связан с конкретным контекстом устройства (this — то есть текущий объект-форма). Используя объект Graphics, можно нарисовать много разных фигур и линий.
SolidBrush – класс, определяющий кисть одного цвета. Кисти используются для заливки графических фигур, таких как прямоугольники, эллипсы, круги, многоугольники и контуры. Этот класс не наследуется.
Color.FromArgb – используется для создания цвета системы Argb, где первый аргумент – прозрачность (от 0 – прозрачный до 100 — непрозрачный).
Cursor.Position.X и Cursor.Position.Y — для распознания текущего положения курсора.
4. Теперь введем процедуру, рисующую прямоугольник высотой и шириной 10 пикселей, с координатами X и Y курсора мыши. Цвет прямоугольника зависит от значения переменной myb:
Rectangle myrect = new Rectangle(CursorX, CursorY, 10, 10); // создаем квадратик, связываем его с координатами мыши
где myb
– наша кисть для заливки красного цвета, CursorX, CursorY – горизонтальная и вертикальная координаты курсора мыши для задания верхней левой точки прямоугольника, 10, 10 – заполнение области прямоугольника.
5. Осталось нарисовать прямоугольник на холсте:
myg.FillRectangle(myb, myrect); // рисуем квадрат кистью на холсте
6. Запустите приложение и поводите мышкой по форме. Под курсором рисуется квадрат. Но в данном случае мы не управляем процессом вывода. Необходимо, чтобы мы могли подавать команды для начала и окончания рисования квадрата. Самый удобный способ – это подавать данные команды мышью, к примеру, чтобы квадрат рисовался при нажатой левой клавише мыши.
7. Для этого в начале модуля формы (перед кодом public Form1()
) необходимо описать переменную КнопкаНажата
логического типа.
8. Затем необходимо запрограммировать два события для формы (выбирая их в списке событий формы): когда кнопка мыши опускается вниз (MouseDown
), и когда кнопка мыши поднимается вверх (MouseUp
):
private void Form1_MouseDown(object sender, MouseEventArgs e) { КнопкаНажата = true; }
9. Теперь осталось в событии перемещения мыши добавить условный оператор, благодаря которому прямоугольники рисуются только в случае, если переменная КнопкаНажата
имеет значение True
:
if (КнопкаНажата==true) { myg.FillRectangle(myb, myrect); // рисуем квадрат кистью на холсте }
10. Для выполнения дополнительного задания добавим на нашей форме меню (menuStrip), назовем его Инструменты, в котором будут перечисляться созданные графические инструменты. Вызывать тот или иной инструмент можно при помощи переменных, описанных в глобальной области формы (или создайте модуль формы для этих целей):
bool ИнструментКвадрат; bool ИнструментЭллипс;
11. В событии Click
каждого пункта меню добавьте необходимый код. К примеру, для пункта Квадрат:
ИнструментКвадрат = true; ИнструментЭллипс = false;
12. В описание MouseMove следует также добавить дополнительные условия. Для рисования квадрата:
if (КнопкаНажата==true && ИнструментКвадрат == true) { myg.FillRectangle(myb, myrect); // рисуем квадрат кистью на холсте }
Контрольное задание:
1. Добавьте инструмент Эллипс (FillEllipse)
myg.FillEllipse(Brush, Int, Int, Int, Int) — заполняет внутреннюю часть эллипса, определяемого ограничивающим прямоугольником, заданным с помощью пары координат (в нашем случае координаты курсора), ширины и высоты.
2. Добавьте в меню пункт Цвет для выбора цвета.
Вопросы для самоконтроля:
1. Когда генерируется событие MouseMove?
2. Когда генерируется событие MouseDown и MouseUp?
Все права защищены. Использование любых материалов сайта возможно только с разрешения правообладателя.
По вопросам размещения рекламы на сайте — обращайтесь: mayersvetlana @ yandex.ru
1.
Основы алгоритмизации и программирование
ФИСТ УлГТУ 1 курс
Власенко Олег Федосович
SimbirSoft
Лекция 8
Windows приложение. Как работает?
Обработка событий – клавиатура, мышь, таймер.
Многомодульные проекты.
Random.
ЛР 14. Работа с клавиатурой и мышью
ЛР 15. Самодвижущиеся фигуры – таймер, случайные
числа
2.
Лабораторная работа №14
Работа с клавиатурой и мышью
3.
Задача 1. Управление через клавиатуру (0)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
4.
Задача 1. Управление через клавиатуру (1)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
5.
Задача 1. Управление через клавиатуру (2)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
6.
Задача 1. Управление через клавиатуру (2)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
7.
Задача 1. Управление через клавиатуру (3)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
8.
Задача 1. Управление через клавиатуру (3)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
case WM_KEYDOWN:
switch (wParam)
{
case VK_LEFT: // стрелка ВЛЕВО
image1_x -= 10;
InvalidateRect(hWnd, NULL, TRUE);
break;
case VK_RIGHT: // стрелка ВПРАВО
image1_x += 10;
InvalidateRect(hWnd, NULL, TRUE);
break;
}
break;
9.
Задача 1. Управление через клавиатуру (4)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
10.
Задача 1. Управление через клавиатуру (4)
1. Нужно создать новый проект Windows
2. Добавить глобальные переменные image1_x и image1_y
3. Добавить отрисовку прямоугольника вокруг точки с координатами image1_x и
image1_y
4. Добавить обработку события WM_KEYDOWN. В ней реализовать изменение image1_x
при помощи клавиш VK_LEFT и VK_RIGHT, и изменение image1_y при помощи
клавиш VK_DOWN и VK_UP.
case VK_DOWN: // стрелка ВНИЗ
image1_y += 10;
InvalidateRect(hWnd, NULL, TRUE);
break;
case VK_UP: // стрелка ВВЕРХ
image1_y -= 10;
InvalidateRect(hWnd, NULL, TRUE);
break;
11.
Задача 2. Создание модуля
В предыдущей лабораторной работе были создано несколько функций отрисовки
изображений следующего вида void Image0(HDC hdc, int cx, int cy, COLORREF color)
Нужно собрать все эти функции в отдельном модуле и включить этот модуль в текущий
проект.
1.
2.
3.
4.
5.
6.
Создать файл Images.cpp и перенести в него все реализованные вами функции вида void Image0(HDC hdc, int
cx, int cy, COLORREF color) (из предыдущей лабораторной работы!)
Создать файл Images.h и перенести в него все заголовки функций
Файл Images.h включить посредством директивы #include в файл Images.cpp
Файл Images.h включить посредством директивы #include в основной файл проекта ( в примере это
Lab14_Win.cpp)
Собрать и запустить проект – чтобы убедиться что все собрано корректно.
Заменить в коде Задачи 1 вызов Rectangle() на вызов Image0()
12.
Задача 2. Создание модуля (1)
В предыдущей лабораторной работе были создано несколько функций отрисовки
изображений следующего вида void Image0(HDC hdc, int cx, int cy, COLORREF color)
Нужно собрать все эти функции в отдельном модуле и включить этот модуль в текущий
проект.
1.
2.
3.
4.
5.
6.
Создать файл Images.cpp и перенести в него все реализованные вами функции вида void Image0(HDC hdc, int
cx, int cy, COLORREF color) (из предыдущей лабораторной работы!)
Создать файл Images.h и перенести в него все заголовки функций
Файл Images.h включить посредством директивы #include в файл Images.cpp
Файл Images.h включить посредством директивы #include в основной файл проекта ( в примере это
Lab14_Win.cpp)
Собрать и запустить проект – чтобы убедиться что все собрано корректно.
Заменить в коде Задачи 1 вызов Rectangle() на вызов Image0()
13.
Задача 2. Создание модуля (2)
В предыдущей лабораторной работе были создано несколько функций отрисовки
изображений следующего вида void Image0(HDC hdc, int cx, int cy, COLORREF color)
Нужно собрать все эти функции в отдельном модуле и включить этот модуль в текущий
проект.
1.
2.
3.
4.
5.
6.
Создать файл Images.cpp и перенести в него все реализованные вами функции вида void Image0(HDC hdc, int
cx, int cy, COLORREF color) (из предыдущей лабораторной работы!)
Создать файл Images.h и перенести в него все заголовки функций
Файл Images.h включить посредством директивы #include в файл Images.cpp
Файл Images.h включить посредством директивы #include в основной файл проекта ( в примере это
Lab14_Win.cpp)
Собрать и запустить проект – чтобы убедиться что все собрано корректно.
Заменить в коде Задачи 1 вызов Rectangle() на вызов Image0()
14.
Задача 2. Создание модуля (3)
В предыдущей лабораторной работе были создано несколько функций отрисовки
изображений следующего вида void Image0(HDC hdc, int cx, int cy, COLORREF color)
Нужно собрать все эти функции в отдельном модуле и включить этот модуль в текущий
проект.
1.
2.
3.
4.
5.
6.
Создать файл Images.cpp и перенести в него все реализованные вами функции вида void Image0(HDC hdc, int
cx, int cy, COLORREF color) (из предыдущей лабораторной работы!)
Создать файл Images.h и перенести в него все заголовки функций
Файл Images.h включить посредством директивы #include в файл Images.cpp
Файл Images.h включить посредством директивы #include в основной файл проекта ( в примере это
Lab14_Win.cpp)
Собрать и запустить проект – чтобы убедиться что все собрано корректно.
Заменить в коде Задачи 1 вызов Rectangle() на вызов Image0()
15.
Задача 2. Создание модуля (4)
В предыдущей лабораторной работе были создано несколько функций отрисовки
изображений следующего вида void Image0(HDC hdc, int cx, int cy, COLORREF color)
Нужно собрать все эти функции в отдельном модуле и включить этот модуль в текущий
проект.
1.
2.
3.
4.
5.
6.
Создать файл Images.cpp и перенести в него все реализованные вами функции вида void Image0(HDC hdc, int
cx, int cy, COLORREF color) (из предыдущей лабораторной работы!)
Создать файл Images.h и перенести в него все заголовки функций
Файл Images.h включить посредством директивы #include в файл Images.cpp
Файл Images.h включить посредством директивы #include в основной файл проекта ( в примере это
Lab14_Win.cpp)
Собрать и запустить проект – чтобы убедиться что все собрано корректно.
Заменить в коде Задачи 1 вызов Rectangle() на вызов Image0()
16.
Задача 2. Создание модуля (5)
В предыдущей лабораторной работе были создано несколько функций отрисовки
изображений следующего вида void Image0(HDC hdc, int cx, int cy, COLORREF color)
Нужно собрать все эти функции в отдельном модуле и включить этот модуль в текущий
проект.
1.
2.
3.
4.
5.
6.
Создать файл Images.cpp и перенести в него все реализованные вами функции вида void Image0(HDC hdc, int
cx, int cy, COLORREF color)
Создать файл Images.h и перенести в него все заголовки функций
Файл Images.h включить посредством директивы #include в файл Images.cpp
Файл Images.h включить посредством директивы #include в основной файл проекта ( в примере это
Lab14_Win.cpp)
Собрать и запустить проект – чтобы убедиться что все собрано корректно.
Заменить в коде Задачи 1 вызов Rectangle() на вызов Image0(
17.
Задача 3. Выбор отображаемой фигуры
Добавить возможность менять отображаемую фигуру – при помощи нажатия пробела
1. Добавить глобальную переменную type в которой хранится номер отображаемой
фигуры.
2. В обработку события WM_KEYDOWN добавить обработку клавиши пробела VK_SPACE.
3. По нажатию пробела значение глобальной переменной type увеличивается на 1.
4. В обработку события WM_PAINT добавить логику выбора вызова функций Image0(),
Image1(), Image2() и т.д. в зависимости от значения глобальной переменной type
18.
Задача 3. Выбор отображаемой фигуры
Добавить возможность менять отображаемую фигуру – при помощи нажатия пробела
1. Добавить глобальную переменную type в которой хранится номер отображаемой
фигуры.
2. В обработку события WM_KEYDOWN добавить обработку клавиши пробела VK_SPACE.
3. По нажатию пробела значение глобальной переменной type увеличивается на 1.
4. В обработку события WM_PAINT добавить логику выбора вызова функций Image0(),
Image1(), Image2() и т.д. в зависимости от значения глобальной переменной type
19.
Задача 4. Управление мышкой
При нажатии левой кнопки мышки перемещать отрисованную фигуру в точку, где была
нажата мышь
1. Добавить обработку события WM_LBUTTONDOWN.
2. Координаты мышки присвоить переменным image1_x и image1_y
20.
Задача 4. Управление мышкой (1)
При нажатии левой кнопки мышки перемещать отрисованную фигуру в точку, где была
нажата мышь
1. Добавить обработку события WM_LBUTTONDOWN.
2. Координаты мышки присвоить переменным image1_x и image1_y
21.
Задача 4. Управление мышкой (2)
При нажатии левой кнопки мышки перемещать отрисованную фигуру в точку, где была
нажата мышь
1. Добавить обработку события WM_LBUTTONDOWN.
2. Координаты мышки присвоить переменным image1_x и image1_y
case WM_LBUTTONDOWN:
{
WORD xPos, yPos;
// Сохраняем координаты курсора мыши
xPos = LOWORD(lParam);
yPos = HIWORD(lParam);
image1_x = xPos;
image1_y = yPos;
InvalidateRect(hWnd, NULL, TRUE);
}
break;
22.
Задача 5*. Изменяем количеством строк и столбцов
При помощи клавиатуры увеличивается/уменьшается количество отрисованных
строк/столбцов
1. Добавить глобальные переменные image1_n и image1_m в которых хранится
количество строк и столбцов соответственно.
2. В обработку события WM_KEYDOWN добавить обработку клавиш I, O, U, N.
3. В обработку события WM_PAINT добавить циклы для отрисовки нескольких рядов и
нескольких столбцов фигур.
Где найти коды клавиш:
«Операционная система Microsoft Windows 3.1 для программиста» https://www.frolovlib.ru/books/bsp/v11/ch5_2.htm
23.
Домашнее задание по ЛР14
1) Доделать задачи 1-4.
1) Задача 6*. Добавить возможность изменения цвета
отображаемых фигур при помощи нажатия клавиш
(конкретные клавиши и способ изменения цвета нужно
выбрать самостоятельно).
2) Задача 7*. Все ранее созданные картинки (во всех
предыдущих лабораторных работах) собрать в один единый
проект и организовать переключение картинок при помощи
клавиатуры. (Например, нажимая на клавишу СТРЕЛКА_ВЛЕВО
показывается предыдущая картинка, СТРЕЛКА_ВПРАВО –
следующая картинка)
3) Задача 8**. Все картинки, созданные в предыдущих
лабораторных работах, поместить в отдельный модуль
Pictures.cpp/Pictures.h.
24.
ИТОГО по ЛР14
1. Научились управлять программой через клавиатуру и мышь.
Попробовали создавать модули в Си программе.
25.
26.
ТЕОРЕТИЧЕСКИЙ БЛОК
27.
Компиляция программы на Си
28.
Компиляция
https://ru.wikipedia.org/wiki/%D0%9A%D0%BE%D0%BC%D0%BF%D0%B8
%D0%BB%D1%8F%D1%82%D0%BE%D1%80
Компиля́тор — программа, переводящая текст, написанный на языке
программирования, в набор машинных кодов
Трансляция программы как неотъемлемая составляющая компиляции включает в себя:
1.Лексический анализ. На этом этапе последовательность символов исходного файла
преобразуется в последовательность лексем.
2.Синтаксический (грамматический) анализ. Последовательность лексем преобразуется в
древо разбора.
3.Семантический анализ. На этой фазе древо разбора обрабатывается с целью
установления его семантики (смысла) — например, привязка идентификаторов к их
объявлениям, типам данных, проверка совместимости, определение типов выражений
и т. д. Результат обычно называется «промежуточным представлением/кодом», и может
быть дополненным древом разбора, новым деревом, абстрактным набором команд или
чем-то ещё, удобным для дальнейшей обработки.
4.Оптимизация. Выполняется удаление излишних конструкций и упрощение кода с
сохранением его смысла. Оптимизация может быть на разных уровнях и этапах —
например, над промежуточным кодом или над конечным машинным кодом.
5.Генерация кода. Из промежуточного представления порождается код на целевом
машинно-ориентированном языке.
29.
Процесс компиляции
«Процесс компиляции программ на C++» — https://habr.com/ru/post/478124/
1) Препроцессинг (#define , #include, etc подстановка в Си код)
Препроцессор — это макро процессор, который преобразовывает вашу программу для
дальнейшего компилирования. На данной стадии происходит происходит работа с
препроцессорными директивами. Например, препроцессор добавляет хэдеры в код
(#include), убирает комментирования, заменяет макросы (#define) их значениями,
выбирает нужные куски кода в соответствии с условиями #if, #ifdef и #ifndef.
2) Компиляция (Си код ASM)
На данном шаге компилятор выполняет свою главную задачу — компилирует, то есть
преобразует полученный на прошлом шаге код без директив в ассемблерный код. Это
промежуточный шаг между высокоуровневым языком и машинным (бинарным) кодом.
3) Ассемблирование (ASM OBJ)
Так как процессоры исполняют команды на бинарном коде, необходимо перевести
ассемблерный код в машинный с помощью ассемблера. Ассемблер преобразовывает
ассемблерный код в машинный код, сохраняя его в объектном файле.
4) Компоновка (OBJ EXE)
Компоновщик (линкер) связывает все объектные файлы и статические библиотеки в
единый исполняемый файл, который мы и сможем запустить в дальнейшем.
30.
Препроцессор
«Директивы препроцессора в Си» — https://prog-cpp.ru/c-directives/
Препроцессор — это специальная программа, являющаяся частью
компилятора языка Си. Она предназначена для предварительной
обработки текста программы. Препроцессор позволяет включать в текст
программы файлы и вводить макроопределения.
Работа препроцессора осуществляется с помощью специальных
директив (указаний). Они отмечаются знаком решетка #.
31.
#include
Директива #include
Директива #include позволяет включать в текст программы указанный
файл. Если заголовочный файл содержит описание библиотечных
функций и находится в папке компилятора, он заключается в угловые
скобки <>.
Если файл находится в текущем каталоге проекта, он указывается в
кавычках «». Для файла, находящегося в другом каталоге необходимо в
кавычках указать полный путь.
#include <stdio.h>
#include «func.c»
32.
#define (1)
Директива #define
Директива #define позволяет вводить в текст программы константы и макроопределения.
Общая форма записи
#define Идентификатор Замена
Поля Идентификатор и Замена разделяются одним или несколькими пробелами.
Директива #define указывает компилятору, что нужно подставить строку, определенную
аргументом Замена, вместо каждого аргумента Идентификатор в исходном файле.
Идентификатор не заменяется, если он находится в комментарии, в строке или как часть
более длинного идентификатора.
#include <stdio.h>
#define A 3
int main()
{
printf(«%d + %d = %d», A, A, A+A); // 3 + 3 = 6
return 0;
}
33.
#define (2)
Вторая форма синтаксиса определяет макрос, подобный функции, с параметрами. Эта форма допускает
использование необязательного списка параметров, которые должны находиться в скобках. После
определения макроса каждое последующее вхождение
идентификатор(аргумент1, …, агрументn)
замещается версией аргумента замена, в которой вместо формальных аргументов подставлены
фактические аргументы.
Пример на Си: Вычисление синуса угла
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#define PI 3.14159265
#define SIN(x) sin(PI*x/180)
int main()
{
int c;
system(«chcp 1251»);
system(«cls»);
printf(«Введите угол в градусах: «);
scanf(«%d», &c);
printf(«sin(%d)=%lf», c, SIN(c));
getchar(); getchar();
return 0;
}
34.
Основные директивы препроцессора
#include — вставляет текст из указанного файла
#define — задаёт макроопределение (макрос) или символическую константу
#undef — отменяет предыдущее определение
#if — осуществляет условную компиляцию при истинности константного выражения
#ifdef — осуществляет условную компиляцию при определённости символической
константы
#ifndef — осуществляет условную компиляцию при неопределённости
символической константы
#else — ветка условной компиляции при ложности выражения
#elif — ветка условной компиляции, образуемая слиянием else и if
#endif — конец ветки условной компиляции
#line — препроцессор изменяет номер текущей строки и имя компилируемого
файла
#error — выдача диагностического сообщения
#pragma — действие, зависящее от конкретной реализации компилятора.
35.
Создание модулей в Си
36.
1. Структура файлов
Главный модуль:
Main.c – главный файл – в нем находится функция main()
Модуль Unit:
Unit.c – файл, где находятся определения
Unit.h – заголовочный файл, где находятся объявления
37.
2. Файл модуля (Unit.c)
#include «Unit.h»
// Определение глобальной переменной cnt
int cnt = 0;
// Определение функции unitF
void unitF() {
printf(«unitF() start!\n»);
cnt++;
printf(«unitF:cnt = %d\n», cnt);
printf(«unitF() finish!\n»);
}
38.
3. Заголовочный файл (Unit.h)
#pragma once
// Объявление функции unitF
void unitF();
// Объявление глобальной переменной cnt
extern int cnt;
39.
4. Главный файл (Main.c)
#include <stdio.h>
#include «Unit.h»
void main() {
printf(«main() start!\n»);
printf(«cnt = %d\n», cnt); // Использование cnt
unitF(); // Вызов unitF
unitF(); // Вызов unitF
unitF(); // Вызов unitF
printf(«main:cnt = %d\n», cnt); // Использование cnt
printf(«main() finish!\n»);
}
40.
41.
Solution & Project в MS VS
42.
«Пустой проект»
43.
Проект, созданный на основе «пустого»
44.
«Классическое приложение Windows»
45.
Solution
46.
47.
Как работает Windows Application
48.
События Windows
List Of Windows Messages — https://wiki.winehq.org/List_Of_Windows_Messages
49.
Как работает программа Windows (1)
«Архитектура программ Windows» http://netlib.narod.ru/library/book0031/ch02_01.htm
Архитектура программ Windows
Если вы до Windows работали с другой операционной системой, такой как UNIX,
Linux или DOS, новый стиль программирования может показаться несколько
необычным. Сначала придется отказаться от функции main(), которая будет
заменена функцией с именем WinMain(). Так же как в других операционных
системах требовалось наличие функции main(), программам работающим в
Windows необходима функция WinMain().
Работа, управляемая событиями
Следующее отличие программирования в Windows заключается в том, что
программы для Windows управляются событиями. Это значит, что программа,
вместо того, чтобы бежать за информацией, может бездельничать и ждать
сообщений, поступающих ей через очередь сообщений. Все сообщения получает и
обрабатывает обработчик сообщений (message handler). Элементы,
обрабатываемые в обработчике сообщений обычно называются событиями (events).
50.
Как работает программа Windows (2)
51.
Как устроен код автоматически
сгенерированного Windows
приложения
52.
Код Windows приложения (1)
53.
Код Windows приложения (2)
54.
Код Windows приложения (3)
55.
Код Windows приложения (4)
56.
Код Windows приложения (5)
57.
Код Windows приложения (6)
58.
Код Windows приложения (2’)
59.
Код Windows приложения (7)
https://firststeps.ru/mfc/winapi/r.php?54
60.
61.
Лабораторная работа №15
Самодвижущиеся фигуры – таймер,
случайные числа
62.
Задача 0. Создать заготовку для ЛР15
1. Нужно создать новый проект Windows
2. Добавить в этот проект модуль Images.cpp / Images.h созданный в предыдущей
лабораторной работе.
3. Убедиться что все собирается и работает – на примере отрисовки Image0()
63.
Задача 1. Добавить самодвижущуюся фигуру
1. Добавить в код определение структуры Image
2. Добавить переменную im1 имеющую тип struct Image
3. Задать переменной im1 положение фигуры (примерно) в центре окна, и задать ей
перемещение вправо
4. Добавить таймер в программу
5. По таймеру изменять координаты фигуры и вызывать перерисовку фигуры
6. В обработчик WM_PAINT добавить код отрисовки фигуры Image0() по координатам
заданным в im1
64.
Задача 1. Добавить самодвижущуюся фигуру (1)
1. Добавить в код определение структуры Image
2. Добавить переменную im1 имеющую тип struct Image
3. Задать переменной im1 положение фигуры (примерно) в центре окна, и задать ей
перемещение вправо
4. Добавить таймер в программу
5. По таймеру изменять координаты фигуры и вызывать перерисовку фигуры
6. В обработчик WM_PAINT добавить код отрисовки фигуры Image0() по координатам
заданным в im1
struct Image {
int x;
int y;
int vx;
int vy;
};
struct Image im1 = { 100, 200, 10, 0 };
65.
Задача 1. Добавить самодвижущуюся фигуру (2)
1. Добавить в код определение структуры Image
2. Добавить переменную im1 имеющую тип struct Image
3. Задать переменной im1 положение фигуры (примерно) в центре окна, и задать ей
перемещение вправо
4. Добавить таймер в программу
5. По таймеру изменять координаты фигуры и вызывать перерисовку фигуры
6. В обработчик WM_PAINT добавить код отрисовки фигуры Image0() по координатам
заданным в im1
case WM_CREATE:
SetTimer(hWnd, 1, 500, 0);
break;
66.
Задача 1. Добавить самодвижущуюся фигуру (3)
1. Добавить в код определение структуры Image
2. Добавить переменную im1 имеющую тип struct Image
3. Задать переменной im1 положение фигуры (примерно) в центре окна, и задать ей
перемещение вправо
4. Добавить таймер в программу
5. По таймеру изменять координаты фигуры и вызывать перерисовку фигуры
6. В обработчик WM_PAINT добавить код отрисовки фигуры Image0() по координатам
заданным в im1
case WM_TIMER:
im1.x += im1.vx;
im1.y += im1.vy;
InvalidateRect(hWnd, NULL, TRUE);
break;
67.
Задача 1. Добавить самодвижущуюся фигуру (4)
1. Добавить в код определение структуры Image
2. Добавить переменную im1 имеющую тип struct Image
3. Задать переменной im1 положение фигуры (примерно) в центре окна, и задать ей
перемещение вправо
4. Добавить таймер в программу
5. По таймеру изменять координаты фигуры и вызывать перерисовку фигуры
6. В обработчик WM_PAINT добавить код отрисовки фигуры Image0() по координатам
заданным в im1
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = BeginPaint(hWnd, &ps);
Image0(hdc, im1.x, im1.y, RGB(128, 128, 0));
EndPaint(hWnd, &ps);
}
break;
68.
Задача 2. Добавить еще одну самодвижущуюся
фигуру (0)
1. Добавить определение «псевдонима типа» IMAGE.
2. Добавить переменную im2 имеющую тип IMAGE
3. Задать переменной im2 положение фигуры (примерно) в правой части окна, и задать
ей перемещение влево
4. В обработчик таймера добавить изменение координат фигуры im2
5. В обработчик WM_PAINT добавить код отрисовки фигуры Image1() по координатам
заданным в im2
69.
Задача 2. Добавить еще одну самодвижущуюся
фигуру (1)
1. Добавить определение «псевдонима типа» IMAGE.
2. Добавить переменную im2 имеющую тип IMAGE
3. Задать переменной im2 положение фигуры (примерно) в правой части окна, и задать
ей перемещение влево
4. В обработчик таймера добавить изменение координат фигуры im2
5. В обработчик WM_PAINT добавить код отрисовки фигуры Image1() по координатам
заданным в im2
typedef struct Image IMAGE;
IMAGE im2 = { 400, 200, -10, 0 };
70.
Задача 2. Добавить еще одну самодвижущуюся
фигуру (2)
1. Добавить определение «псевдонима типа» IMAGE.
2. Добавить переменную im2 имеющую тип IMAGE
3. Задать переменной im2 положение фигуры (примерно) в правой части окна, и задать
ей перемещение влево
4. В обработчик таймера добавить изменение координат фигуры im2
5. В обработчик WM_PAINT добавить код отрисовки фигуры Image1() по координатам
заданным в im2
case WM_TIMER:
im1.x += im1.vx;
im1.y += im1.vy;
im2.x += im2.vx;
im2.y += im2.vy;
InvalidateRect(hWnd, NULL, TRUE);
break;
71.
Задача 2. Добавить еще одну самодвижущуюся
фигуру (3)
1. Добавить определение «псевдонима типа» IMAGE.
2. Добавить переменную im2 имеющую тип IMAGE
3. Задать переменной im2 положение фигуры (примерно) в правой части окна, и задать
ей перемещение влево
4. В обработчик таймера добавить изменение координат фигуры im2
5. В обработчик WM_PAINT добавить код отрисовки фигуры Image1() по координатам
заданным в im2
case WM_PAINT:
{
PAINTSTRUCT ps;
HDC hdc = BeginPaint(hWnd, &ps);
Image0(hdc, im1.x, im1.y, RGB(128, 128, 0));
Image1(hdc, im2.x, im2.y, RGB(128, 128, 0));
EndPaint(hWnd, &ps);
}
break;
72.
Задача 3. Добавить еще одну самодвижущуюся
фигуру
1. Добавить переменную im3 имеющую тип IMAGE
2. Задать переменной im3 положение фигуры (примерно) в верхней части окна, и
задать ей перемещение вниз
3. В обработчик таймера добавить изменение координат фигуры im3
4. В обработчик WM_PAINT добавить код отрисовки фигуры Image2() по координатам
заданным в im3
73.
Задача 4. Добавить еще одну самодвижущуюся
фигуру
1. Добавить переменную im4 имеющую тип IMAGE
2. Задать переменной im4 положение фигуры (примерно) в нижней части окна, и
задать ей перемещение вверх
3. В обработчик таймера добавить изменение координат фигуры im4
4. В обработчик WM_PAINT добавить код отрисовки фигуры Image3() по координатам
заданным в im4
74.
Задача 5. Случайное перемещение фигуры
1. Добавить переменную im5 имеющую тип IMAGE
2. Задать переменной im5 положение фигуры (примерно) в центре окна, и задать ей
перемещение 0,0 (стоит на месте)
3. В обработчик таймера добавить изменение координат фигуры im5 случайным
образом
4. В обработчик WM_PAINT добавить код отрисовки фигуры Image4() по координатам
заданным в im5
75.
Задача 5. Случайное перемещение фигуры
1. Добавить переменную im5 имеющую тип IMAGE
2. Задать переменной im5 положение фигуры (примерно) в центре окна, и задать ей
перемещение 0,0 (стоит на месте)
3. В обработчик таймера добавить изменение координат фигуры im5 случайным
образом
4. В обработчик WM_PAINT добавить код отрисовки фигуры Image4() по координатам
заданным в im5
case WM_TIMER:
// Изменение координат другие фигур
…
// Случайное изменение координат фигуры №5
int dx5 = rand() % 10;
int dy5 = rand() % 21 – 10;
im5.x += dx5;
im5.y += dy5;
InvalidateRect(hWnd, NULL, TRUE);
break;
76.
Задача 6*. Массив фигур
1.
2.
3.
4.
Добавить переменную imA имеющую тип массив IMAGE
Задать всем элементам массива imA координаты и направления перемещение
В обработчик таймера добавить изменение координат элементов массива imA
В обработчик WM_PAINT добавить код отрисовки всех элементов imA через вызов
Image5()
77.
Задача 6*. Массив фигур (1)
1.
2.
3.
4.
Добавить переменную imA имеющую тип массив IMAGE
Задать всем элементам массива imA координаты и направления перемещение
В обработчик таймера добавить изменение координат элементов массива imA
В обработчик WM_PAINT добавить код отрисовки всех элементов imA через вызов
Image5()
78.
Задача 6*. Массив фигур (2)
1.
2.
3.
4.
Добавить переменную imA имеющую тип массив IMAGE
Задать всем элементам массива imA координаты и направления перемещение
В обработчик таймера добавить изменение координат элементов массива imA
В обработчик WM_PAINT добавить код отрисовки всех элементов imA через вызов
Image5()
79.
Задача 6*. Массив фигур (3)
1.
2.
3.
4.
Добавить переменную imA имеющую тип массив IMAGE
Задать всем элементам массива imA координаты и направления перемещение
В обработчик таймера добавить изменение координат элементов массива imA
В обработчик WM_PAINT добавить код отрисовки всех элементов imA через вызов
Image5()
80.
81.
Домашнее задание по ЛР15
1) Доделать задачи 1-4.
2) Задача 7*. Добавить еще один массив фигур – в количестве 20100 штук. Фигуры из этого массива перемещаются случайным
образом.
3) Задача 8*. Добавить цвет к каждой фигуре.
4) Задача 9**. Сделать так, чтобы фигуры сталкиваясь с краем
окна разворачивались и двигались после столкновения в
обратную сторону (от границы окна).
82.
ИТОГО по ЛР15
1. Познакомились с таймером.
2. Применили массивы к отрисовке множества объектов.
3. Познакомились с генератором случайных чисел.
83.
ЛИТЕРАТУРА
Где найти коды клавиш:
«Операционная система Microsoft Windows 3.1 для программиста»
https://www.frolov-lib.ru/books/bsp/v11/ch5_2.htm
84.
ИТОГО по лекции 8
1.
2.
3.
4.
5.
Узнали про процесс сборки Си программы.
Узнали про препроцессор.
Узнали как создаются модули в Си.
Узнали как работает Windows программа.
Узнали про сообщения WM_KEYDOWN, WM_LBUTTONDOWN,
WM_CREATE, WM_TIMER
6. Узнали про генератор случайных чисел
7. Узнали что нужно сделать в ЛР14 и ЛР15