Увеличение / уменьшение и рисование в openGL - PullRequest
1 голос
/ 08 ноября 2010

У меня недавно были некоторые проблемы с реализацией функции масштабирования в приложении рисования. Пожалуйста, позвольте мне начать с предоставления некоторой справочной информации.

Сначала я начал с изменения демо-приложения Apple glPaint. Я думаю, что это отличный источник, так как он показывает вам, как настроить EAGLView и т. Д ...

Теперь, что я хотел сделать дальше, это реализовать функцию масштабирования. Проведя некоторые исследования, я попробовал два разных подхода.

1) использовать glOrthof

2) изменить размер кадра моего EAGLView.

Хотя оба способа позволяют мне идеально увеличивать / уменьшать масштаб, у меня возникают различные проблемы, когда речь идет о рисовании при увеличении.

Когда я использую (1), я должен визуализировать вид следующим образом:

glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrthof(left, right, bottom, top, -1.0f, 1.0f); //those values have been previously calculated
glDisable(GL_BLEND);
//I'm using Apple's Texture2D class here to render an image
[_textures[kTexture_MyImage] drawInRect:[self bounds]];
glEnable(GL_BLEND);
[self swapBuffers];

Теперь, давайте предположим, что я немного увеличил масштаб, ТО я рисую, а после этого хочу снова уменьшить масштаб. Чтобы заставить это работать, мне нужно убедиться, что «kTexture_MyImage» всегда содержит последние изменения. Для этого мне нужно захватить содержимое экрана после внесения изменений и объединить их с исходным изображением. Проблема в том, что когда я увеличиваю, на моем экране отображается только часть изображения (увеличенная), и я еще не нашел подходящего способа справиться с этим.

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

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

Что касается подхода (2), я могу избежать большинства вышеперечисленного, поскольку я изменяю только размер моего окна EAGLView. Тем не менее, при рисовании штрихи находятся далеко от их ожидаемого положения. Возможно, мне нужно учитывать уровень масштабирования при рисовании и пересчитывать CGPoints другим способом.

Однако, если вы делали подобные вещи в прошлом или можете дать мне подсказку, как я могу реализовать масштабирование в моем приложении для рисования, я был бы очень признателен.

Заранее спасибо.

1 Ответ

1 голос
/ 09 ноября 2010

Да, это определенно возможно.

Когда дело доходит до программ рисования, вы должны хранить связанный список или дерево объектов для рисования для легкой вставки / удаления.Когда пользователь прекращает рисовать (то есть touchesEnded), вы добавляете объекты в структуру данных, содержащую вашу сцену.

Когда ваш пользователь увеличивает масштаб, вам нужно модулировать координаты объектов, которые вы рисуете, относительно текущего видового экрана., проекция и трансформация вида модели.В вашем случае вы не изменяете область просмотра или преобразования модели, поэтому вам нужно только учитывать преобразование проекции.Вы также можете реализовать масштабирование с помощью перевода и масштаба в матрице вида модели, но я проигнорирую этот случай для простоты, поскольку он включает в себя инвертирование преобразований.

Хорошая новость заключается в том, что вы используете ортографическую проекцию, поэтомукоординаты соответствуют координатам окна, когда масштабирование не действует.«Мир» в вашем случае - это простой холст, который, вероятно, соответствует размеру устройства в координатах окна.

Прежде чем добавить объект в структуру данных сцены, преобразуйте все координаты, используя текущийпроекционное преобразование (т.е. параметры для вызова glOrthof ()) в мировые координаты (т. е. полные координаты холста).Вы останетесь в здравом уме, только если будете хранить все вещи в своей модели в одном и том же координатном пространстве.

Чтобы преобразовать координаты, предполагая, что вы никогда не сможете уменьшить масштаб до полного размера устройства в вызове glOrtho (), выПридется уменьшать их пропорционально отношениям ваших увеличенных ортогональных измерений к вашим увеличенным ортогональным измерениям, а затем смещать их по разнице между вашим увеличенным ортогональным нижним, левым значениями и значениями оригинальных не увеличенных ортогональных значений.

...