Mail.ruПочтаМой МирОдноклассникиВКонтактеИгрыЗнакомстваНовостиКалендарьОблакоЗаметкиВсе проекты

Змейка на C++ в консоли.

~hephest ~ Ученик (103), закрыт 1 год назад
Не могу разобраться как реализовать отрисовку змейки и обработку нажатия на стрелки. То есть всё работает, змейка движется и поворачивает, но с использованием sleep() не всегда обрабатываются нажатия и std::this_thread::sleep_for(std::chrono::milliseconds(200)) та же история. Погуглив, понял, что программа грубо говоря засыпает и нажатия попавшие в это время не обрабатываются. Я так понимаю нужно в зависимости от прошедшего времени отрисовывать змейку и обрабатывать нажатия, не используя sleep. Только вот не могу понять как это просто реализовать. Возможно есть какие книги или статьи (можно на англ.) в которых описана суть игрового процесса и создания правильного игрового цикла. Полазив в интернете я понял что, sleep() лучше не использовать в играх. Нужен игровой таймер, но у меня возникли трудности с этим. Буду благодарен за помощь и советы.
Лучший ответ
Сергей Гений (60615) 1 год назад
Решается очень просто созданием второго потока, которые отлавливает нажатия клавиш. Первый поток просыпается, и опрашивает второй, была ли нажата кнопка, делает отрисовку и засыпает.
 void command_thread(char& ch) //функция для отлова кнопок
{
char input;
while (true) //цикл опроса работает непрерывно
{
input = _getch(); //я через метод conio.h считывал
switch (input)
{
case 'w': ch = 'u'; break;
case 's': ch = 'd'; break;
case 'a': ch = 'l'; break;
case 'd': ch = 'r';
}
}
}
в функции main:
 #include 
int main(){
char command = 'u'; //переменная для направления змеи
thread comand(command_thread, ref(command)); //запускаем поток,
//передаем в него нашу функцию отлова кнопок и направление по ссылке //ref.
comand.detach(); //отцепляем поток, теперь он самостоятельно будет cчитывать и обновлять
//переменную command в основном потоке
...
ваш код
...
}
Остальные ответы
D P Мудрец (18454) 1 год назад
Функции ввода Си++ вообще малопригодны для подобных выкрутасов.
sleep тут вообще не в тему.
Почитайте про следующие функции
 select или poll для мониторинга событий на файловом дескрипторе
clock_gettime для измерения времени
Основная идея интерактивных программ типа игр и т.п.
Есть постоянный цикл отрисовки игрового мира
Есть получение информации о событиях (нажатие клавиш и т.п.). Это можно сделать как в основном потоке (как раз при помощи select или poll), так и в дополнительных.
Для создания разного рода пауз используют вычисление разницы между двумя точками времени а не блокирующие поток выполнения функции типа sleep
D PМудрец (18454) 1 год назад
Вот тут пример работы с poll для считывания стандартного ввода.
В вашем случае таймаут вообще не нужен, надо просто посмотреть, появилась ли информация, которую можно считывать, или нет.
А вообще, на мой взгляд, лучше использовать для динамических игр специально предназначенные для этого вещи, типа SDL. Потому что, по хорошему, для игр нужна обработка низкоуровневого ввода. Во времена игр DOS можно было просто напрямую работать с клавиатурой, но сейчас уже такой фокус просто так не пройдет.
Похожие вопросы