Скролінг ігрового світу

Автор блогу Хі3 досить зрозуміло роз'яснив принцип переміщення карти. Але, зізнаюся чесно, такий підхід особисто мені не подобається. Я вважаю, що він не є універсальним, оскільки через такий підхід можуть виникнути різні складності в майбутньому. Тому я розповім про дещо інший підхід.

Для початку розберемося прокрутка карти. Фактично в будь-якій грі, де ігровий рівень виходить за межі ігрового екрану, необхідна реалізація прокручування карти. А частіше потрібно, щоб карта рухалася на протилежний бік від персонажа, коли той переміщається. Тобто начебто камера стежить за героєм.

ігрового

Оскільки у Flash немає ніяких камер, то рухати нам доведеться весь ігровий світ. Тобто насправді виходить так, ніби ми дивимося у віконце на якийсь світ, і коли персонаж тікає з виду, нам треба підсунути весь світ так, щоб персонаж знову потрапив в область видимості нашого віконця — «камери».

світу

Таким чином, все зводиться до того, що весь ігровий світ має бути одним великим об'єктом — так його простіше рухатиме і при цьому світ навіть не підозрюватиме про те, що його переміщують. Всі ігрові об'єкти живуть усередині карти, і їх становище визначається відповідно до її внутрішніх координат, що зводить виникнення різних незручностей до мінімуму.

Почнемо приклад із простого переміщення ігрової карти. Реалізуємо у класу ігрової карти два простих методи, через які буде здійснюватися запуск прокручування картки.

Тут все досить просто_speedX та_speedY - це локальні змінні ігрової карти з поточною швидкістю руху. Тепер треба реалізувати метод руху карти, який її рухатиме.

Швидкість руху додаємо до положення карти, а потім виконуємо уповільнення швидкості, щоб після того, як виклик методівhScroll() абоvScroll() припинився, карта ще деякий час продовжувала рухатися по енерції.

Використання прокручування виглядає так:

Результат виглядає так:

Клацніть у сітку та використовуйте клавіші зі стрілками для переміщення карти.

Як зупинити прокручування при виході видимої області за межі картки?

Зазвичай в іграх не допускається виїзд «камери» за межі карти — це не тільки допомагає гравцеві зрозуміти, що він уперся в межу рівня і далі нічого немає, а й дозволяє розробнику не морочитися деталізацією непотрібних частин рівня. Обмеження переміщення карти зробити досить легко. Необхідно лише перевіряти положення ігрової карти та не допускати її зміщення далі за встановлені межі. Для цього нам треба знати розміри ігрової карти та розміри вікна. Метод руху карти переробляємо так:

_mapWidth - ширина ігрової карти;_mapHeight - висота ігрової карти;SCR_WIDTH - ширина ігрового екрану;SCR_HEIGHT — висота ігрового екрану.

Тепер результат виглядає так:

Клацніть у сітку та використовуйте клавіші зі стрілками для переміщення карти.

Як змусити камеру слідкувати за персонажем?

Переміщення карти з обмеженнями руху ми реалізували, а тепер найцікавіше — це реалізація «камери» за персонажем.

Не знаю, як вам, а мене особисто дратує, коли в іграх реалізують мертву прив'язку камери до персонажа. Зазвичай це виглядає так: персонаж біжить і весь світ у цей час також рухається. Я волію реалізовувати більш щадну прокручування. Виявляється це в тому, що коли персонаж ненамагається залишити межі екрана і залишається в межах видимості, камера не рухається за ним і тим самим не втомлює гравця зайвими рухами. Можливо, деякі не здогадуються, але таку камеру дуже просто реалізувати. Потрібно лише додати умовні межі на ігровому екрані і при їхньому перетині героєм включати прокручування в необхідну сторону.

світу

Спостережуваний об'єкт намагається залишити область видимості, не проґавити його! :)

Перевірку перетинів з межами необхідно виконувати безпосередньо в коді руху об'єкта, за яким повинна стежити камера і якщо він виходить за встановлені межі викликати методи карткиhScroll() абоvScroll(). Я додав у приклад об'єкт, який постійно рухається і відскакує від кордонів карти. Метод його руху виглядає так:

Перевірку виходу об'єкта за допустимі межі винесено в окремий методupdMapPos(). Він виглядає так:

Принцип дії простий. Єдиний показник прокручування карти – це її координати, причому вони завжди негативні. Знаючи координати карти ми можемо знайти поточне положення екрана на ній і порахувати межі перетинаючи які об'єкт включає прокручування. У змінній_border знаходиться розмір кордону.

Тепер приклад має такий вигляд:

Кулька завжди в області видимості. Карту можна спробувати переміщати клавішами зі стрілками.

Це власна вся основа прокручування карти, змінюючи розмір кордонів, швидкість прокручування та уповільнення руху карти можна налаштувати прокручування практично під будь-які завдання.

До речі, якщо літаючий об'єкт із прикладу замінити курсором миші, то вийде скролінг мишкою як у більшості сучасних стратегій.

Для охочих поколупатися і розібратися з вихідником прикладу пропоную завдання: створитискролінг мишкою, або управління літаючої кулькою з клавіатури.