Форум программистов, компьютерный форум, киберфорум
Кроссплатфор­менная разработка
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.71/68: Рейтинг темы: голосов - 68, средняя оценка - 4.71
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562

Змейка

17.10.2010, 06:00. Показов 13564. Ответов 95
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
wxWidgets - вот и пошло первое написание игры. Ну относительно игры конечно. Проблема вот в чем. Нам препод показал как сделать, чтобы "змейка" двигалась. Поднастроил, чтобы она двигалась правильно. Влево - влево, вниз - вертикально вниз и т.п. Но есть проблемка. При таком коде, что соответственно:

C++
1
2
3
    m_coord +=
        wxGetKeyState(WXK_UP)? wxPoint(0, -10) : wxGetKeyState(WXK_DOWN) ? wxPoint(0, 10) : 
        wxGetKeyState(WXK_LEFT)? wxPoint(-10, 0) : wxGetKeyState(WXK_RIGHT)? wxPoint(10, 0) : wxPoint(10, 0);
Координата точки изменяется, только если держать кнопку. По дефолту идет вправо. Не коммильфо. Как запомнить последнюю нажатую кнопку и перемещать именно в ту сторону, какая кнопка была нажата?
0
Лучшие ответы (1)
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
17.10.2010, 06:00
Ответы с готовыми решениями:

Змейка не работает
Неправильно работает хвост (add_hvost) . Что не так ? #include <iostream> #include <conio.h> #include <cstdlib> #include...

Змейка. Нужен совет как доработать программу
Недавно я зашел в тупик, работая над программой "Змейка". Но несмотря на то, что в общем и целом программа работает (змея двигается по...

Змейка на QT C++
Доброго времени суток! Начал изучение с++ QT и параллельно пробую писать игру змейка. Сама реализация игры почти готова - змейка...

95
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
29.10.2010, 19:35  [ТС]
Студворк — интернет-сервис помощи студентам
На картинке выделена область которой быть не должно. Итог: выходит за пределы экрана и змейка и еда.
И это не есть коммильфо, размер экрана фиксированный, это прекрасно, но все же не хочется выхода за пределы экрана абсолютно. То есть размер клиентки должен быть почти такой же как размер фрейма. Как такое прикрутить?
Миниатюры
Змейка  
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
29.10.2010, 19:57
C++
1
2
3
4
5
// в конструкторе фрейма
mycanvas = new MyCanvas(this);
boxSizer = new wxBoxSizer(wxVERTICAL);
boxSizer->Add(mycanvas, 1, wxEXPAND | wxALL, 0);
SetSizer(boxSizer);
Так ты хочешь сделать? Это на всю область фрейма.
0
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
29.10.2010, 20:05  [ТС]
rangerx, М... Не помогает. Все та же долбанная область.
C++
1
2
3
4
    MyCanvas* Ob= new MyCanvas(this);
    wxSizer* Sizer=new wxBoxSizer(wxVERTICAL);
    Sizer->Add(Ob, 1, wxEXPAND | wxALL, 0);
    SetSizer(Sizer);
Во фрейме
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
29.10.2010, 20:29
C++
1
boxSizer->Add(mycanvas, 0, 0, 0);
Так сможешь подогнать размер самого клиентского окна. Т.е. параметры отвечающие за размер окна будут учитываться.
А так, клиентское окно плюс ко всему бедет центроваться на фрейме.
C++
1
boxSizer->Add(mycanvas, 0, wxCENTER, 0);
1
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
29.10.2010, 20:37  [ТС]
rangerx, ммм... после этого размер клиентки стал примерно 1 на 1. То есть не айс совершенно.
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
29.10.2010, 20:39
Так размер окна в конструкторе какой у тебя указан?
1
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
29.10.2010, 20:41  [ТС]
rangerx, wxDefaultSize. Сейчас менял на 700 на 700 - фрейм растягивается на 700 на 700, а клиентка 1 на 1
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
29.10.2010, 20:42
Размер клиентки меняй как тебе нужно.
1
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
29.10.2010, 21:06  [ТС]
rangerx, Огромное спасибо. Все шикарно работает. Теперь пожалуй можно даже оставить изменение размера.
А для разного размера так можно сделать? Т.е. оба параметра как wxDefaultSize и в констре фрейма и в констре клиентки и при этом размер клиентки всегда равен размеру фрейма, как бы его не растягивать?
Да и кстати. Если мы растягиваем окно - размер фрейма программно меняется?

Добавлено через 16 минут
М. Почему происходит так?

У нас есть две константы
C++
1
2
const int VERT_SIZE=500;
const int HOR_SIZE=500;
Их мы подаем в конструктор фрейма как размер и в конструктор клиенского окна. В итоге с какой-то стороны все таки выходим за пределы.

Если мы подаем их в конструктор фрейма, а каждая из них -50 в конструктор клиентского окна - все гуд, кроме того, что видно серую область за клиенткой. Фиг бы с ним конечно, но как-то неэстетично...
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
29.10.2010, 21:53
Честно говоря не совсем, понимаю что ты пытаешься сделать. То ты хочешь сделать фиксированный размер главного окна, то хочешь его ресейзить... Покажи скрин в момент выхода за пределы.
P.S. скачай wxFormBuilder и посмотри как работаю сейзеры(уже несколько раз тебе об этом говорил).
1
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
30.10.2010, 00:00  [ТС]
rangerx, Да... Скачаю посмотрю.
Единственное, что мне хочется, чтобы программа работала корректно и дальше будет возможность ее развивать, по мере изучения wxWidgets. Так как я фактически нифига в этом еще не знаю, кроме нескольких функций, классов, которые нам говорил препод и еще нескольких которые использую в змейке.
Когда был выход за пределы окна, было совсем не то. Сейчас впринципе все хорошо, кроме некоторой серой части окна. Она маленькая конечно, но все же. Хотя это тоже не суть вцелом.

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

Сейчас думаю над реализацией изменения скорости движения змейки (читай тика таймера). Как это лучше будет реализовать?
У меня есть две идеи - первая, забиндить увеличение/снижение скорости на две разные кнопки.
Вторая - сделать менюшку, в которой выбираем скорость от 1 до 7, в зависимости от выбора в программе к значению тика прибавляется/убавляется нужное колличество.
Ну и третья, которую я пока затрагивать наверное не буду - сделать это на панельке.

Добавлено через 1 час 7 минут
Елки палки... Не понимаю в чем проблема.

Сделал такую функцию:
C++
1
2
3
4
5
6
7
void MyFrame::OnStart(wxCommandEvent& event)
{
    Ob=new MyCanvas(this);
    wxBoxSizer* Sizer=new wxBoxSizer(wxVERTICAL);
    Sizer->Add(Ob, 0, 0, 0);
    SetSizer(Sizer);
}
Чтобы игра не начиналась сразу и была бы возможность почитать хелп по игре. Работает. Но перестало реагировать на нажатие кнопок, дебагом проверял, перестал прыгать в обработчик событий от клавиатуры. С чем это может быть связано? Если переношу обратно в конструктор фрейма - все окей.
Хотя пробежался еще раз дебагом - при нажатии на кнопку - прыгает в обработчик. Во время игры - нет.

Добавлено через 46 минут
Етить. Клавиши начинают работать только после выбора меню информация, в момент игры оО
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
30.10.2010, 00:32
Сейчас думаю над реализацией изменения скорости движения змейки (читай тика таймера). Как это лучше будет реализовать?
Вообще скорость обычно меняется автоматически при наборе определённого количества очков ) Разве что можно ещё с уровнем сложности что-то придумать...
Етить. Клавиши начинают работать только после выбора меню информация, в момент игры оО
Возможно надо просто установить фокуc на канву... Попробуй Ob->SetFocus(); А там уж не знаю...
1
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
30.10.2010, 00:42  [ТС]
rangerx, Что бы я без тебя делал! Помогло!
Ну да. Про скорость помню.
Но я сделал так для начала:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
    case WXK_SHIFT:
        {
            int old_timer_value=timer_value;
            timer_value+=50;
            m_timer.Start(timer_value<=300 ? timer_value : timer_value=old_timer_value);
        }
        break;
    case WXK_CONTROL:
        {
            int old_timer_value=timer_value;
            timer_value-=50;
            m_timer.Start(timer_value>= 50 ? timer_value : timer_value=old_timer_value);
        }
        break;
0
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
30.10.2010, 02:39  [ТС]
Лучший ответ Сообщение было отмечено как решение

Решение

Итак. На пару деньков я пожалуй законсервирую дальнейшее развитие этой программы. Стоит отдохнуть от нее.

Скидываю сюда экзешник и сорсы, если кому будет интересно.

Огромное спасибо rangerx!
Вложения
Тип файла: rar minimal.rar (359.7 Кб, 35 просмотров)
Тип файла: rar Sources.rar (7.6 Кб, 34 просмотров)
3
 Аватар для papochka
33 / 33 / 0
Регистрация: 14.11.2009
Сообщений: 137
30.10.2010, 19:33
подправь немного. Иногда не поймешь, куда вести змейку - не видно.. точнее плохо видно.

Как можно заметить, красную точку вообще плохо видно))

и ещё кое-что нашел: вобщем, если жмём резко клавишу влево и вверх(возможны и другие вариации), сразу же вылетает табличка игра окончена. Врезаться, она не может, тк состоит из 3-х звеньев. Даже не знаю, как описать, чтобы можно было повторить ..
Миниатюры
Змейка  
1
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
30.10.2010, 20:10
Замечания по коду(и не только):
1) У тебя практически в каждой строке комментарий... Не следует комментировать очевидные вещи.
2) По файлам ты так ничего и не разбил... Всё в куче. И MyCanvas(кстати все эти приставки "My" не мешало бы убрать и дать классам нормальные имена), и MyApp(читай функция main), и MyFrame... И самое интересное, что этот единственный файл называется minimal.cpp(?).
3) Cтроку
C++
1
dc.SelectObject(wxBitmap(CS.GetHeight(), CS.GetWidth()));
лучше переписать так
C++
1
2
3
wxMemoryDC dc;
wxBitmap bitmap(CS.GetHeight(), CS.GetWidth());
dc.SelectObject(bitmap);
потому как, начиная с версии 2.9, параметром SelectObject является уже неконстантная ссылка...
4) Змейка у тебя появляется на половину за пределами окна(см. скрин постом выше). Это надо исправить(исправляется элементарно...)
5) Использовать wxMessageBox для выдачи сообщений не годится(особенно это касается паузы). Используй функцию, которую я написал. Исправь там, что считаешь нужным и всё.
6) Используй короткие(типа Sn) имена только для переменных c коротким временем жизни(циклы и т.д.), для всего остального подбирай нормальные(значащие) имена.
7) Змейку не мешало бы оживить. Т.е. поставить фон какой-нибудь и т.д.(но для начала следует привести в порядок код).
P.S. Какая кодировка у тебя стоит в редакторе студии? Уже все нормальнын(и не очень) IDE давно понимают UTF-8. Используй её.

Добавлено через 1 минуту
и ещё кое-что нашел: вобщем, если жмём резко клавишу влево и вверх(возможны и другие вариации), сразу же вылетает табличка игра окончена.
Да, у меня тоже самое...
2
2 / 2 / 1
Регистрация: 01.05.2009
Сообщений: 25
30.10.2010, 20:26
Цитата Сообщение от papochka Посмотреть сообщение
и ещё кое-что нашел: вобщем, если жмём резко клавишу влево и вверх(возможны и другие вариации), сразу же вылетает табличка игра окончена. Врезаться, она не может, тк состоит из 3-х звеньев. Даже не знаю, как описать, чтобы можно было повторить ..
Змейка поворачивается на 180 градусов и врезается в себя. У меня такое было, когда я писал змейку.
Лечится созданием 2 переменных направления (текущее и новое). В новом храниться новое направление движения змейки, полученное от стрелок. Перед прорисовкой нового шага копируем значение из нового в текущее и перерисовываем. При нажатии стhелок проверяем: новое направление не может быть противоположно текущему.
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
30.10.2010, 22:13
-Deadly-, он это сделал, тут дело не в этом.
Lavroff, Получается, что при движении змейки, например, вправо и быстром(быстрее, чем тик таймера) нажатии клавиш "вниз" и "влево", напраление движения меняется как раз на противоположное ) Т.e. проверка в SetDir выполняется, как и должна(направление-то меняется вниз, а затем влево), но т.к. после нажатия клавиши "вниз" тик таймера ещё не успел произойти и метод DoMotion не вызывался, то координаты змейки, когда идёт попытка движения влево остаются те же, что и были при движении вправо. Попробуй блокировать возможность изменения направления до того как будет сделан шаг(можно завести булеву переменную lockChangeDir и устанавливать/проверять её состояние).
1
В астрале
Эксперт С++
 Аватар для ForEveR
8049 / 4806 / 655
Регистрация: 24.06.2010
Сообщений: 10,562
31.10.2010, 00:41  [ТС]
Цитата Сообщение от rangerx Посмотреть сообщение
1) У тебя практически в каждой строке комментарий... Не следует комментировать очевидные вещи.
Хотел прокомментировать только скользкие моменты, но увлекся. Надо подправить.



Цитата Сообщение от rangerx Посмотреть сообщение
2) По файлам ты так ничего и не разбил... Всё в куче. И MyCanvas(кстати все эти приставки "My" не мешало бы убрать и дать классам нормальные имена), и MyApp(читай функция main), и MyFrame... И самое интересное, что этот единственный файл называется minimal.cpp(?).
Дело в том, что проект не мой по сути. Он построен на базе сэмпла минимал. Не знаю зачем, но препод просил сделать так, видимо, чтобы пока не заморачиваться с деталями вроде подключения нужных либ. Но разбить действительно стоит.

Цитата Сообщение от rangerx Посмотреть сообщение
Потому как, начиная с версии 2.9, параметром SelectObject является уже неконстантная ссылка...
Да. Был такой ворн. Поправлю.

Цитата Сообщение от rangerx Посмотреть сообщение
4) Змейка у тебя появляется на половину за пределами окна(см. скрин постом выше). Это надо исправить(исправляется элементарно...)
Сделаю.

Цитата Сообщение от rangerx Посмотреть сообщение
) Использовать wxMessageBox для выдачи сообщений не годится(особенно это касается паузы). Используй функцию, которую я написал. Исправь там, что считаешь нужным и всё.
Просто понимаешь, хочется свое. То, что понял сам. Это все же не какой-то грандиозный проект, а всего-навсего змейка. Но да. С этим я согласен и подумаю. Но разве для сообщения о проигрыше меседжбокс не годится?
Цитата Сообщение от rangerx Посмотреть сообщение
6) Используй короткие(типа Sn) имена только для переменных c коротким временем жизни(циклы и т.д.), для всего остального подбирай нормальные(значащие) имена.
+

Цитата Сообщение от rangerx Посмотреть сообщение
7) Змейку не мешало бы оживить. Т.е. поставить фон какой-нибудь и т.д.(но для начала следует привести в порядок код).
P.S. Какая кодировка у тебя стоит в редакторе студии? Уже все нормальнын(и не очень) IDE давно понимают UTF-8. Используй её.
Покопаюсь в редакторе - посмотрю. На тему оживления да, было бы неплохо. Приведу в порядок код и подумаю.

Цитата Сообщение от rangerx Посмотреть сообщение
Lavroff, Получается, что при движении змейки, например, вправо и быстром(быстрее, чем тик таймера) нажатии клавиш "вниз" и "влево", напраление движения меняется как раз на противоположное ) Т.e. проверка в SetDir выполняется, как и должна(направление-то меняется вниз, а затем влево), но т.к. после нажатия клавиши "вниз" тик таймера ещё не успел произойти и метод DoMotion не вызывался, то координаты змейки, когда идёт попытка движения влево остаются те же, что и были при движении вправо. Попробуй блокировать возможность изменения направления до того как будет сделан шаг(можно завести булеву переменную lockChangeDir и устанавливать/проверять её состояние).
Да. Хорошая идея.

В ближайших планах:
1) Избавится от сайзеров (тупо изменить родителя клиенского окна на wxCanvas или wxPanel) и разблокировать изменение размера.
2) Ловить изменение размера методом EVT_SIZE.
3) Убрать поимку события от клавы (препод сказал, что это нехорошо, тормозит весь процесс).
4) Если мигание не уберется выбрать другой порядок отрисовки (т.е. не перерисовывать все окно, а перерисовывать прямоугольник в котором змейка + еду).
0
2022 / 1621 / 489
Регистрация: 31.05.2009
Сообщений: 3,005
31.10.2010, 02:00
Дело в том, что проект не мой по сути. Он построен на базе сэмпла минимал.
Да, я догадался.
Просто понимаешь, хочется свое. То, что понял сам.
Другими словами, ты принципиально будешь делать "не так"? Теперь понятна истинная причина почему ты решил использовать вектор и swap вместо того что я предложил.
Но разве для сообщения о проигрыше меседжбокс не годится?
Если говорить об единообразии интерфейса, то не годится. А так, можешь делать как угодно, главное чтобы у пользователя это не вызывало неудобств.
1) Избавится от сайзеров
Зачем? Если в дальнейшем ты собираешься ставить ещё и панель, то без сейзеров ты этого не сделаешь. Так что советую разобраться с этим. И кстати говоря ты Layout(); не вызвал для фрейма поэтому сейзеры у тебя скорее всего не работали должным образом. Вызови Layout(); после SetSizer(Sizer); А сам сейзер оформи так Sizer->Add(Ob, 0, wxALIGN_CENTER, 0); может быть такой вариант это не то, что тебе нужно, но по крайней мере увидишь, что они работают
3) Убрать поимку события от клавы (препод сказал, что это нехорошо, тормозит весь процесс).
В смысле? Что значит убрать события клавы?
4) Если мигание не уберется выбрать другой порядок отрисовки (т.е. не перерисовывать все окно, а перерисовывать прямоугольник в котором змейка + еду).
У тебя холст мерцает при перерисовке ты имеешь в виду?
1
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
31.10.2010, 02:00

Ошибка undefined reference to в игре "Змейка"
В главном файле такие ошибки: #include &lt;QApplication&gt; #include &quot;Game.h&quot; Game* game; int main(int argc, char *argv) { ...

Прокомментировать код игры "змейка" в QT
Помогите прокомментировать код игры (подписать как, что и для чего).

Ошибки в игре "Змейка"
Не получается исправить ошибки в коде :(

Игра "Змейка": чтобы змейка не съедала сама себя
Здравствуйте! Пишу змейку на VB 2010. Не получается составить условие того, что бы змейка не ползла в направлении обратному...

Змейка
Написал только движение квадрата влево,вправо,вверх,вниз ,но не могу им управлять он движется до конца поля ,а только потом можно...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
80
Ответ Создать тему
Новые блоги и статьи
Запустил конкурс "тем и промптов для текстовых квестов созданных почти чисто ИИ"
Adler 06.10.2026
Всем привет! За последние три-четыре дня я создал более 16 текстовых квестовых игр используя преимущественно по одному запросу к ИИ на игру. Мне так понравилось смотреть все ветки/ сцены во всех. . .
ИИ не может найти нужный язык в списке
Supersumestria 05.10.2026
Я ему даю вот такое изображение и прошу найти и подчеркнуть немецкий язык. Возвращает он вот это: https:/ / i. **********/ vqBWLe2. png Нужную строчку в 3й колонке просто выдумал. . Это. . .
Новая последняя моя музыка в SUNO
zorxor 05.10.2026
Здравствуйте, дорогие мои друзья! С большой радостью я хотел бы представить вам свою новую последнею музыку, которую сгенерировала мне по моей просьбе нейросеть SUNO. С уважением, zorxor. Это. . .
Программный домашний кинотеатр
russiannick 27.09.2026
Сподобился на программный домашний кинотеатр. В качестве ЯВУ по традиции выбрал js. В помощники взял Яндекс-Алису. Было создано три зала на разные интересы. исторические и ретро сериал Хичкок. . .
Беседа с ИИ о программистах, недопускающих к созданию и правке кода генеративные ИИ и причины этого
zorxor 21.09.2026
Раньше я радовался или получал некоторые эмоции, пусть небольшие, но всё же, от самого процесса написания кода, рекомпиляции и запуска, видя постепенное развитие программы и прочее. А теперь лень. . .
Мобильное приложение ColorStep
pavlinmavlin 17.09.2026
Реализовал приложение Красный, Зеленый, Синий в Unity3d + c#. Название изменил на ColorStep. Приложение прошло модерацию и теперь доступно для скачивания. Делал его сам, шаг за шагом — и вот,. . .
Запрет дублирования строк в табличной части
Maks 13.09.2026
Реализация из решения ниже выполнена на нетиповом справочнике "Нормы ТО" с табличной часть "Виды ТО", разработанного в КА2, со следующими реквизитами: - ВидТО (СправочникСсылка. ВидыТО); - ВидГСМ. . .
Скрипты Tampermonkey для CyberForum, ChatGPT, Claude и пр.
Jin X 06.09.2026
Скрипты Tampermonkey для CyberForum, ChatGPT, Claude и пр. Работая с форумом и нейросетями в браузере часто хочется что-то подкорректировать или добавить какого-то функционала. Ниже прикреплён. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru