Ввод и взаимодействие с пользователем
тем изменение текущего значения, заполнение дисплейного списка примитивами, а затем восстановление значений параметров- извлечение их из стеков. Поэтому в начале процедуры формирования стека вы часто увидите вызовы функций
glPushAttrib(GL_ALL_ATTRIВ_ВITS); glPushMatrix(); В конце процедуры в таком случае должны присутствовать вызовы функций
glPopAttrib(); glPopMatrix();
При описании методов построения иерархических графических моделей в главе 8 мы будем очень часто обращаться к стекам матриц и атрибутов.
В составе OpenGL есть еще несколько функций, облегчающих работу с дисплейным списком. Когда приходится работать со множеством дисплейных списков, то для формирования последовательных значений идентификаторов списков можно воспользоваться функцией glGenLists{<количество>), которая возвращает первое целочисленное значение в последовательности из <количество>, еще не использованное в программе в качестве идентификатора. Функция glCallLists ( ) позволяет запустить процесс отображения сразу нескольких дисплейных списков. Очень хорошим примером использования возможностей, которые открывают дисплейные списки, является формирование текста. В следующем разделе будет подробно описана технология формирования текста с помощью средств OpenGL, но вы можете при чтении этой главы и опустить этот материал, а вернуться к нему позже. Однако хочу обратить ваше внимание на то, что описанная методика демонстрирует, какими гибкими возможностями обладает API и как это облегчает прикладному программисту решение множества проблем. К теме дисплейных списков мы вернемся еще раз в главе 8, когда будем обсуждать использование графических приложений в сети World Wide Web.
3.4.2. Дисплейные списки и формирование текста В главе 2 были описаны два способа формирования текстовых символов - растровый и штриховой. Независимо от того, какой из этих методов выбран, нам понадобится определенная программа, описывающая весь набор символов определенного шрифта. Предположим, что мы остановились на растровом шрифте, в котором каждый символ должен быть описан матрицей битов размером 12x10. В результате для хранения каждого символа нужно выделить память объемом 15 байт. Проще всего формировать изображение строки, отсылая на сервер матрицу битов каждого очередного символа в порядке их появления в строке. Таким образом, придется отсылать по 15 байт на каждый символ строки. Если же сформировать штриховой шрифт, состоящий из отрезков, то на каждый символ "уйдет" разное количество отрезков и соответственно потребуется разный объем памяти. Можно пойти дальше и сформировать шрифт из многоугольников с заливкой, как показано на рис. 3.14. Для буквы "I" много труда не потребуется, но чтобы получить плавное изображение буквы "О", придется аппроксимировать ее контур множеством коротких отрезков. В среднем на полный комплект букв такого шрифта потребуется гораздо больше памяти, чем 15 байт на символ. Если приложение должно выводить на экран достаточно длинный текст, то на сервер придется пересылать очень много информации, что приведет к значительной загрузке сети.