2009-08-25 5 views
4

Я изучаю немного функционального программирования в Gambit-C Scheme, ограничиваясь тем, что не использовал set !. Я подумал, что было бы интересно написать небольшую игру OpenGL, используя эту среду, которая, похоже, хорошо подходит для разработки игр.Функциональный GLUT?

Однако при использовании OpenGL и GLUT, кажется, трудно придерживаться функционального стиля и избегать глобального состояния. Я не думаю, что это фундаментальное ограничение игрового программирования, по сути, но API-интерфейс, основанный на обратном вызове, такой как GLUT, похоже, не работает с функциональным программированием.

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

В идеале мне нужно что-то вроде «снаружи» GLUT, основной функции, которая каким-то образом зависит (возможно, монадически) от различных функций GLUT, которые были выполнены в какой-то момент. Как можно создать такой стиль игрового движка вокруг GLUT, или еще один способ спросить, как я могу наиболее успешно изолировать GLUT от моего движка? Возможно ли, чтобы GLUT генерировал такой чередующийся список событий для внешней процедуры? Как Haskell справляется с этим, например?

ответ

3

Вам будет очень сложно реализовать функциональную графическую систему. Даже привязки Haskell к GLUT используют императивное программирование через монаду IO. Самое близкое, что я слышал от того, что вы пытаетесь сделать, это Functional Reactive Programming, но библиотеки еще не готовы к прайм-тайм, и для него существует серьезная нехватка учебников по реальности.

1

Это довольно фундаментальный для конечной машины, такой как openGL, что она имеет состояние!

Я не вижу, как вы можете иметь бесплатное функциональное программирование с побочным эффектом, когда побочный эффект рисует набор материалов на экран.

+0

Проблема здесь не столько в побочных эффектах, сколько в том, как обращаться с тем, что GLUT асинхронно перезвонит, когда ему нужно что-то сделать, вместо этого установления отношения функциональной зависимости. Мне интересно, есть ли способ сделать его похожим на определенную внешнюю перспективу, но, возможно, это не очень четкая идея. – Steve

+0

Извините, я не использовал GLUT за добавлением шрифта для openGL. Я думал о состоянии openGL pop/push. Не может вам помочь. –

+0

> Я не вижу, как вы можете иметь бесплатное функциональное программирование с побочным эффектом, когда побочный эффект рисует набор материалов на экран. Мы программируем чисто функциональным способом с числами, хотя конечный шаг вывода рисует материал («печать»). Аналогично, ключ к функциональной графике состоит в том, чтобы предоставить тип данных, который имеет богатую и полезную алгебру, где происходит составление (модель программирования), с четкой и доступной семантикой и без побочных эффектов.И тогда не беспокойтесь о том, чтобы рисовать больше, чем беспокоиться о том, как печатать цифры. – Conal

2

Вы можете посмотреть библиотеку FieldTrip на некоторые идеи по функциональной графике.

0

Написав этот вопрос, я подумал об этом немного, и я начинаю задаваться вопросом, лежит ли ответ на использование совместных процедур. Если игра представляет собой функциональную совместную процедуру, которая запускается бездействием GLUT и отображает вызовы, это очень хорошо отделяет логику игры от архитектуры GLUT. Например, это очень вероятно, что набор! нельзя избежать, но если используются обратные вызовы GLUT! только для изменения потока, который подается в совместную процедуру, это может создать очень приятную границу. Любые мысли по этому поводу? Мне нужно будет получить больше опыта с совместными занятиями, прежде чем узнавать больше.

+0

Из того, что я помню, когда я читал реализации совместных подпрограмм с использованием call/cc, я думаю, вам все равно придется использовать 'set !' путь глубоко в вашей библиотеке сопутствующих программ. Я бы не стал это беспокоить вас. :) Скрытие как можно большего количества изменений состояния, вероятно, по-прежнему будет очень сильно очищать ваш код. –

+0

Да, я думаю, что мне начинает нравиться идея. Если я не могу избавиться от set !, то лучше всего держать его как можно ближе к GLUT, а дистанцировать мой код, выражая его как нечто, представляющее собой единственную функцию ленивого списка. Часть GLUT - это просто генератор ленивого списка событий. Работая над ним, во всяком случае .. :) – Steve