Мы уже разобрались с событиями. Теперь пришло время разобраться с временем. Знание того, как обращаться с временем — ключевой момент при создании игр. В этом уроке мы создадим простой таймер, который можно запускать и останавливать.
Предположим что вам нужно отмерить 30-секундный интервал, но у вас нет таймера. Если бы на стене висели часы с секундной стрелкой, вы бы дождались пока она достигнет положения кратного 15 секундам:
и ждали бы до тех пор, пока она не пройдет 30 секунд от точки отсчета.
Наш таймер работает по этому же принципу. SDL
запускает внутренний таймер в нашей программе, и мы можем получить время в миллисекундах используя SDL_GetTIcks()
. Если вам нужно отмерить 1000 миллисекунд, вы сохраняете время когда вы начали ожидание и ждете до тех пор, пока разница между временем начала и текущем не будет равна 1000.
//Заголовки #include "SDL/SDL.h" #include "SDL/SDL_image.h" #include "SDL/SDL_ttf.h" #include <string> #include <sstream> |
Наряду со стандартными заголовками, мы подключаем строковые потоки. Я объясню что это такое чуть позже.
int main( int argc, char* args[] ) { //Флаг выхода bool quit = false; //Время начала отсчета таймера Uint32 start = 0; //Флаг старта/остановки таймера bool running = true; |
В начале функции main
мы объявляем две переменные, которые мы будем использовать для реализации нашего таймера. start
будет хранить время запуска таймера, а running
— флаг, отслеживающий запущен ли таймер.
//Инициализируем таймер start = SDL_GetTicks(); //Пока пользователь не решил выйти while( quit == false ) { |
После того, как мы инициализировали и загрузили поверхности, пришло время запустить таймер.
Мы начинаем с того, что сохраняем текущее время, используя SDL_GetTicks()
. После этого мы входим в главный цикл.
//Пока есть события для обработки while( SDL_PollEvent( &event ) ) { //Если нажали клавишу if( event.type == SDL_KEYDOWN ) { //Если нажали клавишу 's' if( event.key.keysym.sym == SDLK_s ) { //Если таймер запущен if( running == true ) { //Остановить таймер running = false; start = 0; } else { //Запустить таймер running = true; start = SDL_GetTicks(); } } } |
Здесь мы обрабатываем нажатие клавиши ‘s
‘, которая запускает и останавливает таймер.
Если таймер был запущен, мы выставляем флаг running
в false
, и обнуляем start
, просто потому что я не люблю бродячие значения. Если таймер был остановлен, мы, напротив, присваиваем флагу running
значение true и запускаем таймер, так же, как мы сделали это до входа в главный цикл.
//Если таймер запущен if( running == true ) { //Время таймера в виде строки std::stringstream time; //Преобразовать время в строку time << "Timer: " << SDL_GetTicks() - start; |
После того, как мы выводим фон и сообщение, мы проверяем запущен ли таймер. Если да, то показываем время.
Формула для расчета времени таймера такова:
время = текущее время - время запуска
То есть, если вы запустили таймер, когда значение SDL_GetTicks()
было равно 10 000 и теперь оно 20 000, формула даст нам цифру 10 000, означающую что прошло 10 секунд с момента запуска таймера.
Теперь кладем 'Timer: ' + время таймера
в строковой поток.
Мы создаем строковой поток по имени time
, который хранит сообщение содержащее время таймера. Строковые потоки позволяют создавать строки из нескольких переменных. Как вы могли заметить, они очень похожи на cout
, но вместо того, чтобы выводить все в консоль, они просто сохраняют текст в строковом потоке, чтобы мы могли воспользоваться им впоследствии.
Тем из вас, кто все еще пользуются VC++ 6.0, нужно будет привести (SDL_GetTicks() - start)
к int
.
//Отрисовать время seconds = TTF_RenderText_Solid( font, time.str().c_str(), textColor ); //Вывести время apply_surface( ( SCREEN_WIDTH - seconds->w ) / 2, 50, seconds, screen ); //освободить поверхность SDL_FreeSurface( seconds ); } //Обновить экран if( SDL_Flip( screen ) == -1 ) { return 1; } } |
После мы отрисовываем поверхность с текстом, показывающую время таймера используя текст из строкового потока. После этого мы выводим текст на экран и освобождаем ресурсы.
И, наконец, обновив экран продолжаем главный цикл.
Скачать исходники и материалы
Лагает :(