Uploaded by Алена Гринь

ПЗ с 8 стр

advertisement
8
ВСТУП
В наш час швидкими темпами розвивається тривимірна графіка зокрема інтерактивна. Свого часу було зроблено безліч спроб створити
універсальну мову опису тривимірних сцен. Найвдалішою виявилася спроба
компанії Silicon Graphics – її мова OPENGL отримала всесвітнє визнання. Всі
найкрасивіші спецефекти, а також майже вся промислова 3D графіка
рендерітся у форматі OPENGL. Цей формат, був розроблений Silicon
Graphics і у даний час, став стандартом для тривимірного моделювання.
OPENGL оперує графічними примітивами "початкового рівня", такими як
крапки тривимірного простору (вертекси, вершини), відрізки прямих, опуклі
полігони і растрові зображення. Підтримуються й проектні перетворення,
обчислення освітлення.
Штучний інтелект (ШІ) означає апаратне або програмне забезпечення,
яке дозволяє комп'ютеру "думати", тобто обробляти інформацію подібно до
людини. Застосування систем ШІ почалося не так давно, але розвивається з
експоненціальною швидкістю. Сьогодні технології штучного інтелекту стали
можливі завдяки штучним нейронним мережам, генетичним алгоритмам і
нечіткій логіці. Нейронні мережі є грубою моделлю людського мозку, а
генетичні алгоритми - безліч методів і гіпотез, що використовуються для
еволюції програмної системи, заснованої на біологічних парадигмах.
9
1 ОСНОВНІ ТЕОРЕТИЧНІ ПОЛОЖЕННЯ
1.1 Технологія OPENGL
Сучасній світ вже немислимий без тривимірної графіки - зокрема
інтерактивною. Свого часу було зроблено безліч спроб створити
універсальну мову опису тривимірних сцен. Найвдалішою виявилася спроба
компанії Silicon Graphics – її мова OPENGL отримала всесвітнє визнання.
Багато хто з вас знає, що всі найкрасивіші спец ефекти, а також майже
вся промислова 3D графіка рендерітся у форматі OPENGL. Цей формат був
розроблений Silicon Graphics і у даний час ставши стандартом для
тривимірного моделювання.
Для будь-якого протоколу, будь то мережевий протокол або мова опису
сцен, важливим є питання рівня абстракції – тобто того, на якому рівні
працює дана система або протокол, що є вхідними даними і що вихідними,
які компоненти взаємодіятимуть як постачальники і приймачі даних. Кажучи
просто, потрібно визначитися з питання "що ми робимо і чого не робимо".
Творці OPENGL планували свою мову з явним наміром створити
"віртуальний графічний акселератор", так щоб примітиви OPENGL
максимально відповідали примітивам сучасних графічних карт і вимагали
мінімум коду для трансляції з однієї системи команд в іншу. Фактично
більшість сучасних графічних процесорів (зазвичай наваних відеокартами,
хоча до відео мають лише дотичне відношення) безпосередньо сприймають
OPENGL як мову вхідного рівня без якої-небудь (або з мінімумом)
трансляції.
OPENGL оперує графічними примітивами "початкового рівня", такими
як крапки тривимірного простору (вертекси, вершини), відрізки прямих,
опуклі полігони і растрові зображення. Підтримуються й проектні
перетворення, обчислення освітлення. До "просунутих" функцій можна
віднести меппінг текстур (натягування бітових карт на тривимірні поверхні) і
антіаліасинг (згладжування колірних переходів - як локальне, в рамках
окремого об'єкту, так і глобальне, по всій сцені). Передбачається, що додаток
більш високого рівня виконуватиме операції, які бракує в OPENGL, наприклад, декомпозицію не опуклих полігонів.
З погляду програміста, OPENGL – це система викликів процедур з
передачею ним параметрів, тобто ця мова є Call Level API. Ключовим
моментом з погляду продуктивності, особливо в мережевому оточенні є
10
наявність двох режимів: покрокового і пакетного. Пакетний групує команди
опису об'єктів і режими в пакет, звань списком відображення (display list).
Подібна техніка застосовується, наприклад, при описі сторінок в PostScript
або, в дещо іншому контексті, при створенні процедур, що зберігаються, в
SQL. Сенс ясний – інкапсуляція функціональності (у даному випадку об'єктів для подальшого багатократного використання). При цьому можна
провести декілька оптимізацій: заздалегідь один раз перевірити синтаксис, а
також кеширувати готовий об'єкт при передачі по мережі на цільовій машині.
Недолік списку відображення виявляється при частому внесенні до
нього змін – при цьому, зрозуміло, жоден метод оптимізації не працюватиме.
Для роботи з такими "мінливими" об'єктами і сценами в OPENGL
передбачений режим прямого відображення, коли кожна пропозиція
інтерпретується у порядку надходження, не чекаючи того, що закриває
список тієї або якоїсь подібної команди на відмальовку. У практиці обидва
методи знайшли широке застосування.
1.1.1 Архітектура OPENGL
Більш глибоко занурюючись в технологію OPENGL, ми виявимо
струнку і гармонійну архітектуру, загальний вид показаний на рисунку 1.1.
Рисунок 1.1 - Архітектура OPENGL
Точно так, як і процесор має два типи конвеєрів – для цілочисельних
обчислень і чисел з плаваючою крапкою, OPENGL має два конвеєри для
піксельних даних і вертексних операцій, тобто для операцій з векторними
даними. Кожен з потоків обробляється окремо, до тих пір, поки це можливо –
11
тобто до стадії меппинга, коли піксельні растри як фактури "натягаються" на
площини і складніші поверхні.
Перший етап – апроксимація кривих і поверхонь обчисленням
поліномів від вхідних значень. Другий прохід оперує з примітивами типу
крапок, відрізань і полігонів – вони перетворяться по правилах афінних
перетворень, поєднуються і сцена відсікається в підготовці до растрування.
Растрування як результат створює список об'єктів (крапок, відрізків і
трикутників) в двовимірній площині. Над окремими об'єктами може бути
виконана операція розфарбовування, градієнтної заливки або застосування
меппинга, тобто накладення фактури.
Готові фрагменти остаточно обробляються перед тим, як вони реально
будуть внесені до frame buffer. Зокрема, фрагменти сортуються залежно від
значень "глибини" – і ці значення порівнюються з відомими на предмет
рекомпозиції. Застосування блендинга приводить до того, що прозорі
фрагменти приймають колір, що складається з їх власного і кольорів "нижче
лежачих" фрагментів. Додатково може бути реалізоване маскування і інші
ефекти.
Піксельний процесор в ході растрування вбудовує двовимірні бітові
фрагменти прямо в кадр. Частина готового кадру також може бути прочитана
для повторного використання як масив пікселів – так що дані, що
відображаються в буфері, можуть стати частиною інших сцен.
1.1.2 Пріоритети OPENGL
При реалізації додатку існує п'ять орієнтирів, важливих з погляду
отримуваних результатів.
Продуктивність. Із самого початку в OPENGL була закладена "украй
бажана" можливість відмальовки динамічних сцен. Для отримання потрібних
результатів в систему введено безліч параметрів, або, як то кажуть, режимів
малювання. Якщо деякий режим або комбінація режимів на даному
устаткуванні не в змозі забезпечити інтерактивної взаємодії і необхідної
частоти оновлення сцени, то користувач або сама програма повинні бути в
змозі відключати так багато додаткових функцій, скільки потрібно для
отримання "живої" картинки.
Ортогональність. По можливості всі функції OPENGL є
ортогональними, тобто незалежними. Ви можете використовувати їх в
довільній комбінації, наприклад використання меппинга не обмежує
можливостей застосування світлотіні.
12
Повнота. Наскільки це представляється можливим, OPENGL відповідає
набору функцій, що надається сучасними апаратними засобами графічної
акселерації. OPENGL прагне уникати всього, що повинне бути реалізоване
програмно. З іншого боку, принаймні, гарантується отримання робочої
картинки, навіть якщо продуктивність і не дозволяє отримати її зі всіма
подробицями. Тобто, якщо щось працює на одній платформі, то цей же код
працюватиме і на іншій – хоча, можливо, і з іншим результатом.
Інтероперабельність. У мережевому оточенні важливо передавати дані
між різними платформами. Тому OPENGL заздалегідь орієнтований на
роботу в режимі клієнт-сервер, навіть якщо і клієнт і сервер розташовані на
одному комп'ютері.
Розширюваність. Оскільки OPENGL розрахований на максимальну
відповідність можливостям апаратури (а апаратура, як відомо, має тенденцію
розвиватися), то в OPENGL також вбудовані механізми включення нових
функцій. З іншого боку, нестабільний інтерфейс ускладнює життя
розробників, тому нові можливості накопичуються достатній час і
застосовуються погоджено з виходом нової версії.
1.1.3 Функції OPENGL
Нижче перераховані основні функції OPENGL, про деяких з них вже
згадувалося. По ним ви можете оцінити рівень мови і використовувані
примітиви:
- альфа-канал – дозволяє робити предмети прозорими, рівень
прозорості від 0 до 100%;
- антиаліасінг – згладжування колірних переходів, реалістичніше
зображення;
- буфер акумулятора – додатковий буфер для 2,5-мірних ефектів,
спецефектів і глобального згладжування по всій сцені;
- градієнтна заливка (gouraud shading) – лінійно-градієнтна заливка
полігонів і відрізків;
- графічні примітиви – в просторі: крапка, відрізок, полігон, бітове
зображення або зображення в іншому форматі;
- подвійна буферизація – застосовується для згладжування ефектів
анімації, коли нове зображення будується на задньому плані і потім
відображається цілком. При цьому користувач не бачить самого процесу
створення зображення в неузгодженому стані, наприклад різних "виворотів
об'єктів", "дірок в просторі", "граней світу" і подібних небажаних деталей;
13
- заливка і освітленість фактур – до фактур застосовуються ефекти
освітленості і затінювання залежно від характеристик "матеріалу";
- маскування – можна маскувати деякі кольори по трафарету;
- масиви вершин – для підвищення продуктивності задавати вершини
масивами, а не окремо;
- зворотний зв'язок – дані після растрування можуть бути повернені в
додаток замість передачі з/в frame buffer або паралельно з нею;
- перетини – автоматичне визначення того, чи перетинає той або інший
об'єкт заданий просторовий регіон;
- піксельні операції – маштабування і інші перетворення бітових
образів;
- під діапазони – можливість працювати з частиною матриці вершин;
застосовується як метод оптимізації;
- поліноміальні операції – підтримка нерівномірних раціональних
бісплайнів для опису кривих поверхонь;
- повно кольорове відображення – уявлення в режимі RGBA, тобто
трьома кольорами і значенням альфа-каналу. Починаючи з версії 1.2,
підтримуються також схеми BGRA і схеми з упакованими кольорами для
швидкої обробки популярних типів графічних файлів;
- просторові перетворення – масштабування, обертання і переміщення
об'єктів в просторі;
- режим індексованих кольрів – представлення кольорів не RGBтриплетами, а індексами в таблиці кольорів. Застосовується для стиснення
розміну зображень "по глибині кольору" і ефектів швидкої заміни одного
кольору іншим;
- режим прямої відмальовки – малювання у міру надходження команд,
без використання списків відображення;
- змішування кольорів – дозволяє встановлювати декілька режимів
накладення одного зображення на інше. За допомогою цієї операції, зокрема,
реалізується альфа-канал і інші ефекти;
- список відображення (display list) – пакет опису об'єктів сцени для
попереднього розбору і оптимізації кешування;
- текстури – накладення двомірних зображень на об'ємні поверхні для
додання сцені реалізму. Починаючи з версії 1.2, підтримуються тривимірні
текстури. Крім того, починаючи з цієї ж версії, підтримується рівень текстур,
що дозволяє завантажувати їх тільки до певного ступеня деталізації, – в цілях
економії пам'яті текстур;
- Z-буфер – поняття про видалення об'єктів і їх частин від спостерігача,
14
частина алгоритму видалення прихованих поверхонь.
1.2 Історія створення ігор
Все почалося десь в 1960-х роках, за часів перших мейнфреймів,
першою комп'ютерною грою була Core Wars ("Війни в пам'яті") на машинах
під управлінням Unix. У 1970-х роках з'явилася безліч текстових і графічних
(втім, це була дуже "сира" графіка) пригодницьких (так званих бродилок)
ігор для різних типів мейнфреймів і міні-комп'ютерів.
Як не дивно, але більшість ігор були мережевими. До 90% ігор
складали розраховані на багато користувачів ігри типу MUD, імітатори на
зразок Star Trek або військові імітатори. Проте широкі маси не звідували
смаку ігор до тих пір, поки не з'явилася гра Нолана Башнелла (Nolan
Bushnell) Pong, яка і відкрила еру відеоігор.
Тоді, в 1976-78-х роках, TRS-80, Apple і Atari 800 представляли весь
ринок комп'ютерів. Кожен з них мав свої за і проти. Atari 800 був
наймогутнішим, TRS-80 найбільшою мірою підходив для бізнесу, а Apple був
самим "розкрученим". Помалу ігри завойовували ринок програмного
забезпечення для цих систем, і все більше число підлітків грали в них ночі
безперервно. У ті дні комп'ютерні ігри виглядали саме як комп'ютерні ігри, і
лише небагато програмістів знали, як вони створюються. Книг на цю тему не
було зовсім. Все, що було, - це самовідавничі брошури, що містили деякі
частини величезної мозаїки, та рідкісні статті в журналі Byte.
Восьмидесяті роки ознаменувалися виходом на сцену 16-бітових
комп'ютерів типу IBM РС (і сумісних з ним), Mac, Atari ST, Amiga 500 і т.п.
Прийшов час, коли ігри стали виглядати добре. З'явилися навіть перші
тривимірні (3D) ігри типу Wing Commander і Flight Simulator, але РС у той
час не можна було назвати ігровим комп'ютером. У 1985 році цю нішу міцно
займали Amiga 500 і Atari ST. Але РС поступово набирав популярність
завдяки дешевизні і використання в бізнесі. Висновок зі всього цього: кінець
з кінцем завжди перемагає комп'ютер, що захопив ринок, незалежно від його
технологічності або якості.
На початку 90-х років безперечним лідером на ринку став IBM РСсумісний комп'ютер. З виходом Microsoft Windows 3.1 він остаточно
перевершив Apple Macintosh, ставши "комп'ютером ділової людини". Та все
ж РС відставав від своїх конкурентів в частині графіки і аудіо, що ніяк не
давало іграм виглядати так само добре, як іграм на Amiga.
В кінці 1993 року Id Software випустила продовження гри Wolfenstein
15
3D (одна з перших ЗD-ігор, також розроблена Id Software) – DOOM. РС став
комп'ютером, на якому можна не тільки працювати, але і грати, комп'ютером
для роботи і для дому. DOOM довів, що РС можна примусити робити все.
Немає ніякої заміни уяві і рішучості. Якщо ви вірите в те, що щось можливе.
Після неймовірного успіху DOOM Microsoft почала перегляд своєї
позиції щодо ігор і їх програмування. Стало очевидне, що індустрія розваг
величезна і буде тільки рости, і Microsoft вирішила зайняти гідне місце в цій
індустрії. Проблема була в тому, що навіть Windows 95 мала дуже слабкі
видео- і аудіо можливості, так що Microsoft розробила спеціальне програмне
забезпечення WIN-G для вирішення питань, пов'язаних з відео. WIN-G була
заявлена як основна підсистема програмування ігор і графіки. По суті, вона
була всього лише набором графічних викликів для виведення растрових
зображень, і приблизно через рік Microsoft заперечувала її існування.
Проте на той час вже щосили йшла робота над новою системою, яка
повинна була об'єднувати графіку, звук, введення інформації, мережеві
можливості і ЗD-системи, Так народився продукт DIRECTX. Як завжди,
маркетологи Microsoft негайно заявили, що DIRECTX і є остаточне рішення
всіх проблем програмування ігор на платформі РС і що ігри в Windows
будуть такими ж швидкими, чим ігри під DOS32.
Перші версії DIRECTX потерпіли фіаско, але як програмний продукт, а
не як технологія. Microsoft просто недооцінила складність програмування
відеоігор. Але вже з DIRECTX 3.0 цей продукт починає працювати краще,
ніж DOS. Проте більшість компаній, розробляючи ігри, в ті роки (1996-1997)
продовжували працювати з DOS32 і не поспішали переходити KDirectX,
поки не вийшла версія 5.0 цього продукту.
Використовуючи технологію DIRECTX, ви можете створити
віртуальну DOS-подібну машину з адресним простором в 4 Гбайт і лінійною
пам'яттю і програмувати так, як ви б це робили, працюючи під DOS.
Але що набагато важливіше, тепер у вас є можливість негайно
працювати з технологіями графіки і звуку, що знов з'являються, завдяки
особливостям розробки DIRECTX.
Першою грою нового покоління була DOOM, що використала
програмне растеризування. Наступне покоління ЗD-ігор, наприклад Quake I,
Quake II або Unreal, по суті, стало "квантовим стрибком" в технології.
1.2.1 Типи ігор
В даний час існує безліч ігор, які можна розділити на декілька типів.
16
DOOM-подібні ігри. В більшості своїй це повністю тривимірні ігри,
типовими прикладами яких є DOOM, Hexen, Quake, Unreal, Duke Nukem 3D і
Dark Forces. Технологічно це найбільш складні в розробці ігри, що
вимагають хорошого знання різних технологій.
Спортивні ігри. Можуть бути як двомірними, так і тривимірними, але
все частіше і частіше вони стають тривимірними. У будь-якому випадку
спортивні ігри бувають як для команди, так і для однієї людини. Графіка в
спортивних іграх пройшла довгий шлях, і хоча вона не така вражаюча, як в
DOOM-подібних іграх, від цього вона не стає такою, що менш захоплює.
Проте найбільш сильною стороною спортивних ігор є система штучного
інтелекту, який в іграх цього класу зазвичай найбільш розвинений в
порівнянні з іншими іграми.
Бойові ігри. Зазвичай призначені для одного або двох гравців, і їх дії
розглядаються з боку або при допомозі рухомої ЗD-камери. Зображення
може бути двомірним, 2.5D (множинні растрові 2D-зображення тривимірних
об'єктів) або повністю тривимірним. Ігри цього типу не так популярні на
платформі РС, ймовірно, із-за проблем інтерфейсу з контролерами і у зв'язку
з призначенням ігор для двох гравців.
Лабіринти. Типові представники цієї старої школи ігор – Asteroids, Рас
Man, Jazz Jackrabbit. Звичайно це двомірні ігри, хоча останнім часом
з'явилися їх тривимірні версії; але сценарій таких ігор той же, що і у
двомірних.
Механічні імітатори. Це ігри, що здійснюють деякий вид водіння,
польоту, плавання і подібних дій. В більшості випадків це тривимірні ігри, і
такими вони були завжди.
Імітатори екосистем. Це новий клас ігор, що не мають аналогів в
реальному світі. Як приклад можна привести Populous, SimCity, SimAnt,
Civilization і ін. Ці ігри дозволять вам переконатися, чи важко бути Богом і
управляти якоюсь штучною системою – містом, колонією або цілим світом.
Сюди ж входять ігри – імітатори економічної системи.
Стратегічні або військові ігри. Підрозділяються на ряд підтипів,
перераховувати які тут не має сенсу. Сюди входять такі ігри, як Warcraft,
Diablo, Final Fantasy і т.п. Деякі з цих ігор є іграми реального часу, але при
цьому вимагають наявність стратегічного мислення; інші – типові
представники ігор, в яких дія здійснюється на основі ходів супротивників.
Інтерактивні повісті. Зазвичай ці ігри містять заздалегідь створену
графіку і відео, і ви подорожуєте по заздалегідь створених дорогах і
17
розглядаєте заздалегідь створені види, відгадувавши різні головоломки.
Зазвичай такі ігри не дають особливої свободи вибору переміщень.
Ретро-ігри. Це ігри для тих, хто пам'ятає старі добрі часи і віддає
перевагу іграм тих років. Часто це переробки старих ігор на новий лад, тобто
ігри з тим же змістом, але з використанням сучасних можливостей.
Головоломки і настільні ігри. Тут може бути все, що завгодно:
двомірність, тривимірність, попередній рендеринг і т.п. Tetris, Monopoly,
Mahjong – ось деякі з величезного списку ігор, що входять в цю категорію.
1.2.2 Розробка документації і сценарію
Після того, як у вас з'явилася ідея, ви повинні викласти її на папері. В
основному документація є картою або нарисом гри. У ній повинна бути
перерахована якомога більше детальної інформації про гру, її рівні, правила і
т.д. Тоді ви точно знаєте, чого хочете, і можете слідувати викладеному на
папері плану. Інакше деталі весь час змінюватимуться, і кінець кінцем ваша
гра виявиться непослідовною і незв'язною.
1.2.3 Структура тривимірного ігрового процесора
Оскільки нас цікавить програмування ігор, головна мета тривимірного
ігрового процесора — візуалізація тривимірної гри. Це означає, що ігровий
процесор, фізична система, система штучного інтелекту і інші складові
частини гри повинні бути тісно пов'язані з тривимірним процесором. Інакше
проблем у нас буде значно більше, чим їх рішень.
Таким чином, при розробці тривимірного процесора треба чи не в
першу чергу думати про його взаємодію з ігровим процесором. На рисунку
1.2 представлена зразкова схема тривимірного ігрового процесора, завдяки
якій стає очевидно, що в тривимірну гру повинні входити наступні складові:
- тривимірний процесор;
- ігровий процесор;
- система введення і роботи в мережі;
- система анімації;
- система навігації і виявлення зіткнень;
- фізичний процесор;
- система штучного інтелекту;
- база даних тривимірних моделей і зображень.
18
Тривимірний
процесор
Штучний інтелект
Анімація
Игровий процесор
Базова логіка
Фізичні моделі
Навігація
Данні гри
.bmp, .3ds, .wav
ЛВС/Телефон
джойстик
миша
клавіатура
Система введення
Периферія/
Мережа
Рисунок 1.2 - Узагальнена структура тривимірного ігрового процесора
У простій двовимірній грі виявлення зіткнень, система штучного
інтелекту і база даних гри були достатньо прості і зрозумілі, але над
реалізацією всього перерахованого в тривимірному випадку треба міцно
поламати голову. Спочатку докладніше ознайомимося з різним і частинами
ігрового процесора.
1.2.4 Тривимірний процесор
Тривимірний процесор є програмне забезпечення, яке обробляє
структури даних тривимірного світу (включаючи джерела освітлення,
дійових осіб, загальну інформацію про стан гри і т.п.) і візуалізує ігровий світ
з погляду гравця або камери. Рішення цієї задачі відносне просте і без
вишукувань, якщо ігровий процесор розробляється модульним, так що є не
так багато зв'язків між тривимірним процесором і іншим і ігровим і
підсистемами. Одна з найбільших помилок, яку можна зробити при
написанні тривимірного процесора, — це зробити його відповідальним не
тільки за тривимірну візуалізацію. Наприклад, спроба внести фізичне
моделювання до коду тривимірного процесора разом з кодом тривимірної
графіки є дуже великою помилкою. Іншим прикладом може бути розміщення
в процесорі мережевого перехоплення для спрощення роботи в мережі.
19
Тривимірний процесор вирішує одну єдину задачу — тривимірну
візуалізацію.
1.2.5 Ігровий процесор
Ігровий процесор тривимірної гри в більшості випадків є модулем, що
управляє, який шле команди всім іншим підсистемам. Отже, ігровий
процесор слід розробляти так, щоб він міг підключатися до будь-якої іншої
підсистеми гри. Часто допускається помилка, що полягає в тому, що
тривимірну гру починають з розробки тривимірного процесора, а потім в
деякий момент процесу розробки перетворюють частину тривимірного
процесора в підсистему управління. Це не кращий спосіб розробки гри. Із
самого початку треба розробляти модуль управління рештою всіх модулів,
тобто ігровий процесор. Його можна представити також у вигляді
контейнера, що містить решту всіх частин гри.
1.2.6 Система введення і роботи в мережі
Система введення-виводу і роботи з мережею в тривимірній грі
користується поганою славою самої проблемної підсистеми, і користується
заслужено. Проблема в тому, що потенційно по мережі повинна пересилатися
така величезна кількість даних, що це робить працюючу мережеву
тривимірну гру справді дивом. На рисунку 1.3 показано дві різні моделі
мережевих ігор.
20
Рисунок 1.3 - Моделей мережевих ігор
Головне правило при створенні мережевої тривимірної гри полягає в
тому, що в першу чергу треба думати про гру, а не про підтримку мережі, і
гра повинна бути відокремлена від мережі. Підтримка мережі не може бути
частиною тривимірного процесора, штучного інтелекту, фізичного
моделювання — словом, це абсолютно окреме питання про те, які структури
даних слід використовувати, як забезпечити синхронізацію, причому все
повинно бути узгоджено з принципами самої гри. Тому питання мережевої
підтримки і питання дизайну гри повинні розглядатися одночасно і з самого
початку її розробки.
При написанні двовимірної гри ви можете спробувати додати мережеву
підтримку на завершальному етапі — правда, це приведе до різкого
збільшення трудовитрат і появи величезної кількості повторного коду. Але
в тривимірній грі додати мережеву підтримку на останньому етапі роботи
просто неможливо. Це рішення повинне ухвалюватися спочатку, причому від
21
вас буде потрібна серйозна робота із створення мережевої моделі і її
усестороннього тестування.
1.2.7 Ази штучного інтелекту
У академічному сенсі термін "штучний інтелект" (ШІ) означає апаратне
або програмне забезпечення, яке дозволяє комп'ютеру "думати", тобто
обробляти інформацію подібно до людини. Застосування систем ШІ почалося
не так давно, але росте з експоненціальною швидкістю.
Технології ШІ сталі можливі завдяки штучним нейронним мережам,
генетичним алгоритмам і нечіткій логіці. Нейронні мережі є грубою моделлю
людського мозку, а генетичні алгоритми — безліч методів і гіпотез, що
використовуються для еволюції програмної системи, заснованої на
біологічних парадигмах.
Нечітка логіка є теорією множин, заснованою на нечітких гіпотезах.
Але всі ці технології наближаються до реального світу і працюють все краще
і краще. Врешті-решт, ще не так давно клонування було всього лише
фантастикою, а сьогодні це науковий факт. Спускаючись з надхмарних висот
на грішну Землю, скажемо відразу: ми не збираємося створювати реальний
штучний інтелект для ігор. Натомість ми розглядатимемо спрощені методи,
використовувані програмістами для створення розумних персонажів,
вірніше, що виглядають розумними. Як не дивно, але дуже багато
програмістів знайомі з питаннями ШІ лише поверхнево, і в результаті
виходять ігри, в яких прекрасна тривимірна графіка поєднується з повним
ідіотизмом персонажів.
Після того, як ви прочитаєте розділ і випробуєте всі демонстраційні
програми, запам'ятаєте, що всі описані тут технології залишаються тільки
технологіями і не більш. Важливе не те, вірний або невірний спосіб рішення
задачі, важливо, щоб завдання було вирішене.
Врешті-решт, якщо керований комп'ютером танк може виїхати із
засідки і вистрілити вам в спину, значить, ви отримали бажане. Якщо немає
— слід продовжувати роботу.
Незалежно від того, наскільки примітивні використовувані вашим
штучним інтелектом технології, гравець завжди наділятиме своїх
комп'ютерних супротивників індивідуальністю. Найголовнішу частину
роботи гравець зробить за вас — адже він віритиме, що його супротивники
дійсно думають, планують, хитрять, принаймні зовні це виглядатиме саме
так.
22
1.2.8 Детерміновані алгоритми штучного інтелекту
Детерміновані алгоритми означають зумовлену і заздалегідь
запрограмовану поведінку об'єктів. Наприклад, якщо ви розглянете систему
ШІ в демонстраційній грі Asteroids (рисунок 1.4), то побачите, що він вкрай
простий.
Рисунок 1.4 - Штучний інтелект гри Asteroids
Штучний інтелект створює астероїд, який потім відправляє в політ у
випадковому напрямі з випадковою швидкістю. Вся математика ШІ
зводиться до двох рядків програми:
asteroicLx += asteroid_x_velocity;
asteroid. _y+= asteroid_y_velocity;
У астероїда одна мета: рухатися по своєму курсу. Все. Тому штучний
інтелект астероїда гранично простий — йому не потрібно обробляти якесь
зовнішнє введення інформації, змінювати курс і т.п. Поведінка астероїдів
повністю детермінована і передбачена.
Саме такі, прості і передбачені алгоритми ШІ і складають перший клас
алгоритмів, які я хочу розглянути. У цьому класі є ряд технологій, які були
розроблені ще в часи ігор типу РасМаn.
1.2.9 Випадковий рух
У описаний вище алгоритм досить внести мінімальні зміни, щоб
отримати хаотичне переміщення об'єкту (або зміна його властивостей), як
показано на рисунку 1.5
23
Рисунок 1.5 - Випадковий рух об'єкту
Наприклад, якщо ви хочете змоделювати броунівський рух атома або
якийсь інший об'єкт з хаотичним рухом, можна поступити так. Спочатку
випадковим чином змінюється швидкість об'єкту:
fly_x_velocity = -84 rand(} % 16;
fly_y_velocity = -8 -t rand() % 16;
Потім об'єкт якийсь час рухається з обчисленою швидкістю:
// Рух із заданою швидкістю протягом 10 циклів
for(intfly_ count = 0; fly_coijnt< 10; ++fly_count)
fly_x += fly _x_ velocity;
fly_y += Hy_y_ velocity;
// ... Обчислення нової швидкості об'єкту ...
У даному прикладі спочатку вибирається випадковий напрям руху і
швидкість, після чого протягом 10 циклів об'єкт переміщається з
використанням вибраного вектора швидкості. Потім вибирається новий
напрям і швидкість, і цикл повторюється. Очевидно, що в даний алгоритм
можна внести додатковий рівень хаотичності, наприклад вибираючи деяке
випадкове число замість 10 циклів переміщення. Крім того, можна віддати
перевагу вибору одних напрямів перед іншими (тим самим, наприклад,
можна зімітувати наявність вітру). Даний приклад показує, що можна
добитися достатньо цікавих результатів за допомогою дуже невеликого коду.
Випадковий рух є важливою частиною поведінкової моделі
інтелектуальних об'єктів гри. Невелика примітка про інтелектуальність: я
живу в Кремнієвій Долині, і можу засвідчити, що водії тут часто поводяться
24
відповідно до описаного алгоритму: хаотично змінює смуги руху, а іноді і
просто рухаються по стрічній смузі.
1.2.10 Алгоритм проходження за об'єктом
Хоча випадкове переміщення і є абсолютно непередбачуваним,
зазвичай від нього мало користі. Наступним кроком в розвитку ШІ є
алгоритми, які враховують стан зовнішнього середовища і реагують на нього.
Як приклад я вибрав алгоритм проходження за об'єктом (tracking algorithm).
Штучний інтелект на основі інформації про положення деякого
(відстежуваного) об'єкту змінює траєкторію нашого об'єкту так, щоб він
рухався у напрямку до відстежуваного.
Рух може бути направлений як безпосередньо на відстежуваний об'єкт,
так і (у реалістичнішій моделі) по деякій кривій, направленій до об'єкту (на
зразок траєкторії самонавідної ракети), що показане на рисунку 1.6
Рисунок 1.6 - Методи відстежування переміщення
Як грубий приклад проходження за об'єктом можна привести
наступний алгоритм:
// Координати гравця - pLayer_x, player^
// Координати персонажа - monster^x, monster_y
// Перевірка відносного розміщення по осі X
if (player_x > monster_x) ++monster_x;
if (player_x < monster_x) --monster^x;
// Перевірка відносного розміщення по осі Y
if (player_y > monster^y) ++monster_y;
if (pLayer_y < monster_y) --monster_y;
25
Якщо ви використовуєте цей алгоритм ШІ в простій демонстраційній
програмі, то отримаєте такого термінатора, постійно і що неухильно прямує
до мети. Приведений код дуже простий, але вельми ефективний. До речі,
практично аналогічний алгоритм використаний в грі РасМаn (звичайно, з
певними змінами, що дозволяють обходити перешкоди і рухатися тільки по
прямих лініях). У цій грі, управляючи приведенням за допомогою клавіш
переміщення курсору, ви можете подивитися, як слухняно слідує за ним
кажан. Цей алгоритм проходження непоганий, але представляється не дуже
інтелектуальним; більш природним чином був би рух з урахуванням напряму
вектора від центру нашого об'єкту до центру об'єкту, за яким ми слідуємо.
1.2.11 Шаблони
Створення шаблону для об'єкту гри може виявитися як складним, так і
дуже простим, залежно від того, для якого об'єкту створюється шаблон.
Наприклад, шаблон для управління рухом реалізується дуже просто. Уявимо,
що ми розробляємо гру типу Phoenix або Galaxian. Чужі рухаються по певній
траєкторії і в деякий момент атакують вас, слідуючи деякому шаблону атаки.
Штучний інтелект такого роду може використовувати безліч різних
технологій, але особисто мені простим представляється спосіб, заснований на
трансляції інструкцій руху.
Кожен шаблон руху зберігається у вигляді послідовності інструкцій.
Разом з кожною інструкцією можуть використовуватися додаткові дані, що
уточнюють її, наприклад вказуючи, на яку відстань слід переміститися. В
результаті формат інструкції мови шаблону можна записати таким чином:
інструкція операнд. Інструкція є однією з код з приведеного вище списку, а
операнд — числове значення, яке дозволяє уточнити поведінку об'єкту, що
викликається інструкцією. Використовуючи цей простий формат інструкції,
ви можете створити програму (послідовність інструкцій), що визначає
шаблон. Потім ви створюєте транслятор, який в процесі гри виконує розбір
шаблону і відповідно управляє діями персонажа гри.
Шаблони — достатньо могутня, проте повністю детермінована
технологія. А це означає, що як тільки гравець запам'ятає шаблон, він стає
даремний: гравець завжди знає, що відбудеться далі. Рішення цієї проблеми
(як і ряду інших проблем, пов'язаних з шаблонами) полягає в додаванні до
логіки обробки шаблонів умовних операторів, що дозволяє враховувати стан
гри і дії гравця.
Шаблони з умовними операторами дають вам ще один рівень контролю
26
над системою ШІ, дозволяючи створювати шаблони з розгалуженням. Вона
перевіряє відстань від гравця до об'єкту, що виконує шаблон. Якщо дистанція
дуже велика (або, навпаки, мала або виконується ще деякі умова, що
накладається на відстань від гравця до об'єкту), то система ШІ може змінити
свою поведінку. Ви можете помістити інструкцію test_distance в шаблон
точно так, як і будь-яку іншу.
turn_right_90, go_forward test_distance...
turn_left_90 testjjistance go_backward
При виконанні шаблону кожна інструкція test_distance, що
зустрічається, примушує систему ШІ визначити відстань від гравця до
об'єкту і порівняти його з відстанню, заданою як операнд інструкції
test_distance. Якщо відстань дуже велика, штучний інтелект може
перемкнутися, наприклад, на виконання іншого шаблону, який
цілеспрямовано знижуватиме вказану відстань. Погляньте на наступний код:
if (instruction_stream[instruction_ptr++]= test_distance)
// Набуваємо значення операнда інструкції test__distance
// і відстань від гравця до об'єкту і порівнюємо їх
int min_.distance = instruction_stream[instruction_ptr++];
if (Distance(ptayer.object)> min_distance)
// Змінюємо внутрішній стан системи
// штучного інтелекту...
ai_State = track_player;
// ...або перемикаємося на виконання іншого шаблону
1.2.12 Моделювання систем із станами
У цьому розділі розглядаються кінцеві автомати (які іменують також
машинами станів). Моя мета — формалізувати застосування кінцевих
автоматів при розробці систем ШІ в ігрових програмах.
Для створення стійкого кінцевого автомата потрібне наступне:
- розумна кількість станів, кожне з яких представляє різні цілі або
мотиви;
- вхідна інформація для кінцевого автомата, така, як пролягання
середовища і інших об'єктів в ній.
Вимога розумної кількості станів досить просто і зрозуміло. У нас,
людей, є сотні, якщо не тисячі, емоційних станів, і в кожному з них — безліч
підстанів.
А персонаж гри повинен всього лише виглядати розумним, так що і
27
станів у нього не повинно бути занадто багато. Наприклад, простій
персонаж гри може мати декілька станів:
- стан 1: Рухатися вперед;
- стан 2: Рухатися назад;
- стан 3: Поворот;
- стан 4: Зупинка;
- стан 5: Стрілянина;
- стан 6: Погоня за гравцем;
- стан 7: Втеча від гравця.
Стани 1—4 прості і очевидні, проте для коректного моделювання
поведінки персонажа в станах 5—7 можуть потрібні додаткові підстани.
Наприклад, погоня за гравцем може включати рух вперед і повороти. Проте
не слід вважати, що під стани можуть бути засновані тільки на вже наявних
станах; під стани можуть бути штучно введені для кожного з даних станів.
Висновок з цього обговорення такий: станів не повинно бути дуже багато,
інакше буде просто неможливо написати відповідну програму, і в той же час
не повинно бути дуже мало, інакше об'єкт не здаватиметься достатньо
розумним. Якщо у об'єкту тільки два стани, наприклад стояти і рухатися
вперед, то важко добитися враження розумності такого об'єкту. Станів
повинно бути рівно стільки, скільки потрібно для отримання бажаного
ефекту розумності, і не більше. Що стосується другої вимоги, то вам
необхідно забезпечити отримання інформації від інших об'єктів в грі, від
гравця і ігрового середовища. Якщо об'єкт просто входить в деякий стан і
знаходиться в ньому до кінця гри, це не штучний інтелект, а штучна дурість.
Стан міг бути вибраний цілком розумно, але це було 100 мілісекунд тому. З
того часу ігрова обстановка істотно змінилася, а гравець виконав ряд дій, на
які потрібно дати розумну відповідь. Кінцевий автомат повинен відстежувати
стан гри і мати можливість при необхідності вийти з поточного стану і увійти
до іншого. Взявши до уваги все викладене, ви зможете розробити кінцевий
автомат, який добре моделює розумну поведінку об'єкту. Щоб не бути
голослівним, розглянемо деякі конкретні приклади, починаючи з простого
кінцевого автомата.
1.2.13 Створення реальних систем ШІ для ігор
От і все, що я хотів розповісти вам про ази використання штучного
інтелекту в іграх. Я розповів вам про деякі використовувані для цього
технології виключно для того, щоб вам було з чого почати. Ви можете
28
розгубитися і не знати, які технології використовувати в тому або іншому
конкретному випадку. Ось декілька порад на цю тему:
- для об'єктів з простою поведінкою, таких, як камені, ракети і т.п.,
використовуйте прості детерміновані системи ШІ;
- для об'єктів, які передбачаються розумними, але є швидше частиною
навколишнього середовища, чим об'єктами (наприклад, птахи, що літають
навколо, якщо пролітає поряд космічний корабель), що діють,
використовуйте детермінований ШІ з елементами рандомізації;
- для важливих персонажів ігор, що взаємодіють з гравцями, вам,
безумовно, необхідно використовувати кінцеві автомати разом з іншими
допоміжними методами. Проте деякі персонажі можуть бути не дуже
розумними — у такому разі не слід витрачати зайві зусилля на їх
персоналізацію за допомогою спеціалізованих розподілів вірогідності або
втрачати час на розробку самонавчальних систем;
- при реалізації дуже розумного персонажа гри ви повинні зібрати всі
разом. Його ШІ повинен бути кінцевим автоматом із застосуванням великої
кількості умовної логіки, вірогідності, із запам'ятовуванням переходів між
станами. Не забувайте, що дуже складна система може складатися з маси
дуже простих складових. Іншими словами, навіть коли штучний інтелект
кожного індивідуального персонажа зовсім нескладний, їх взаємодія створює
величезну поведінкову систему, запрограмувати яку "з нуля" представляється
абсолютно непосильним завданням (у чомусь це схоже на мозок людини —
надзвичайно складну систему, що складається з гранично простих нейронів).
Дуже важливу роль в таких складних системах грає обмін інформацією між її
складовими; у іграх це реалізується як обмін інформацією між персонажами,
що опинилися на близькій відстані.
1.3 Основи фізичного моделювання
Абсолютно неможливо уявити собі гри з використанням реальної
фізики в 1970—80-х роках. В більшості своїй це були ігри типу "стрелялок",
де треба було знайти і знищити всіх ворогів. Проте з приходом 1990-х років і
ери тривимірних ігор фізичне моделювання стає все більш і більш важливим.
Зараз важко уявити собі гру, в якій рух об'єктів не реалістичний або хоч би не
зроблена спроба наблизити його до такого, В цьому розділі представлені
основні концепції фізичного моделювання:
- фундаментальні закони фізики;
- гравітація;
29
- тертя;
- зіткнення;
- кінематика;
- системи частинок.
Якщо Всесвіт — всього лише модель на деякому неймовірно
складному комп'ютері, то Бог — її програміст. А значить, закони фізики
відмінно працюють на всіх рівнях — від квантового до космогонії. Краса
фізики в тому, що Всесвітом управляють не так вже багато законів фізики.
Інша справа — обмеженість наших знань про ці закони; проте для створення
комп'ютерної моделі, здатної обдурити майже будь-якого спостерігача своїм
реалізмом, знань у нас достатньо. Більшість моделей ігор використовують
моделі на базі стандартної класичної фізики Ньютона, яка цілком
справедлива для опису руху об'єктів в розумних межах мас, розмірів і
швидкостей (тобто швидкість повинна бути значно менше швидкості світла,
об'єкти — значно більше окремого атома, але значно менше галактики). Але
навіть таке моделювання на основі фізики Ньютона вимагає чималих витрат
комп'ютерних сил. Проста імітація більярда, виконана повністю коректно,
але зажадає, як мінімум, потужности Pentium IV. Проте ми не раз бачили в
іграх і дощ і більярд. Програмісти цих ігор усвідомлювали, що фізика, яку
вони повинні змоделювати, дуже складна і слід обмежитися дуже
наближеними моделями, що дають результати, близькі до тих, з якими
гравець стикається в реальному житті. У таких програмах безліч різних
прийомів, оптимізацій і спрощень модельованої системи. Наприклад,
набагато простіше обчислити результат зіткнення двох сфер, чим результат
зіткнення астероїдів неправильної форми, тому програміст може
апроксимувати астероїди в грі простими сферами. Невистачить і тисяч
сторінок, щоб описати дійсно серйозну адекватну фізичну модель, оскільки в
ній повинні буде висловлюватися не тільки фізика, але і математика, яку слід
вивчити, щоб хоч би розуміти, про що йде мова. Тому я обмежуся тільки
найпростішими фізичними моделями, вивчивши які, а потім освоївши в
необхідному об'ємі відповідні розділи фізики і математики, ви зможете
створювати власні моделі для своїх ігор.
1.3.1 Фундаментальні закони фізики
Почнемо подорож в світ фізики з опису деяких базових концепцій і
властивостей простору, часу і матерії. Ці концепції познайомлять вас з
використовуваною термінологією і допоможуть зрозуміти наступний за цим
30
розділом складніший матеріал. Все, про що я говоритиму, не цілком вірно на
квантовому або космологічному рівнях, але достатньо коректно на рівні
нашого обговорення. Зрозуміло, це не підручник фізики і говорити про повну
строгість у викладі матеріалу тут не доводиться.
1.3.2 Маса
Вся матерія має масу, яка є характеристикою її інертності і, як правило,
визначає, яку кількість атомів складає даний об'єкт. Багато хто плутає
поняття маси і ваги і говорить, що вони важать на Землі 75 kg1. Почнемо з
того, що кілограм — це одиниця вимірювання маси, тобто того, скільки
матерії містить об'єкт. Одиницею вимірювання ваги є Ньютон (N). Матерія
сама по собі не має ваги; тільки будучи поміщена в гравітаційне поле, яке і
викликає ефект, названий вагою. Отже, маса є абстрактнішою ідеєю, ніж
вага, яка змінюється від планети до планети. У іграх концепція маси
використовується в більшості випадків абстрактно, як відносна величина.
Наприклад, я можу вказати, що маса корабля — 100 одиниць, а маса
астероїда — 10000. Я можу використовувати для опису маси кілограми, але
поки я не приступаю до реального фізичного моделювання, ніякого значення
це не має.
Маса також є мірою опору об'єкту зміні його швидкості (перший закон
Ньютона). Перший закон Ньютона свідчить, що у відсутність зовнішніх сил
нерухомий об'єкт залишається в стані спокою, а рухомий — рухається
прямолінійно і з постійною швидкістю.
1.3.3 Час
Час є абстрактною концепцією. Подумайте про те, як можна пояснити,
що таке час, не удаючись до нього в процесі пояснення? Без циклічності у
визначенні роз'яснити, що таке час, не вдасться. Але, на щастя, всі і так
знають, що це таке, а тому і говорити ні про що, хіба що про те, як концепція
часу пов'язана з іграми.
Час в реальному житті вимірюється в секундах, хвилинах, годиннах і
т.д. Якщо вам потрібно вимірювати час більш точно — до ваших послуг
мілісекунди (1ms=10-3s), мікросекунди (1µs=106s), нано-, піко-, фемто- (10-9,
10-12 і 10-15 відповідно) і інші долі секунди. Проте в більшості відеоігор
ніякої кореляції між реальним часом і часом в грі не спостерігається.
Алгоритми, що розробляються, більшою мірою прив'язані до частоти кадрів,
31
чим до реального часу і секунд (за винятком ігор, де моделюється реальний
час). У більшості ігор один кадр — це і є одна віртуальна секунда, іншими
словами, найменша помітна кількість часу.
Проте при створенні реальних складних тривимірних ігор вам, мабуть,
все ж таки доведеться працювати з реальним часом. Всі алгоритми в таких
іграх не повинні прив'язуватися до частоти кадрів, наприклад танк, що йде із
швидкістю 70 km/h, повинен йти саме з цією швидкістю, чи впаде частота
кадрів до двох в секунду або підскочить до 60... Моделювання часу в таких
умовах — суще покарання, але, якщо ви хочете створити реалістичну гру, без
нього неможливо обійтися і фізичні події не повинні залежати від зміни
частоти кадрів. У будь-якому випадку в наших прикладах час
вимірюватиметься в секундах (s) або у віртуальних секундах (які просто
означають зміну одного кадру).
1.3.4 Положення в просторі
Кожен об'єкт має певне положення (x, y, z) в тривимірному просторі (х,
у) — в двомірному, просто х (іноді використовується позначення s) — в
одновимірному. Проте іноді незрозуміло, що вважати положенням об'єкту,
навіть коли відомо, де саме він знаходиться. Наприклад, вибираючи крапку,
яка визначає положення сфери, ви напевно виберете її центр. Проте в іграх
концепція положення в просторі набагато простіша. Більшість програмістів
просто описують навколо об'єкту прямокутник, коло (паралелепіпед, сферу,
залежно від розмірності гри), і використовують центр описаного об'єкту як
центр даного об'єкту. В більшості випадків такий опис положення об'єкту
цілком прийнятний особливо коли основна маса об'єкту розташована в його
центрі; але при виконанні обчислень відповідно до фізичної моделі це
наближення є дуже грубим і неадекватним.
Єдиний шлях рішення даної проблеми полягає в тому, щоб вибрати як
крапку, що представляє положення об'єкту, його центр мас. Обчислити центр
мас досить просто — потрібно тільки розбити об'єкт на елементарні малі за
розміром осередки і обчислити їх вагу. Якщо ж об'єкт складений з
багатокутників, то кожному з них можна зіставити його точну обчислену
вагу і центр мас, і обчислити центр мас об'єкту в точності. Припускаючи, що
двомірний об'єкт складається з n частин, маса i-й частини при цьому, а
координати її центру мас — (xiyi), обчислити координати центру мас об'єкту
можна по формулах.
32
1.3.5 Швидкість
Швидкість є миттєвою мірою поступальної ходи об'єкту і вимірюється
як відношення пройденої об'єктом відстані до часу, за який воно було
пройдене. Одиниця вимірювання швидкості — m/s. Математично швидкість
є першою похідною за часом радіус-вектора рухомої крапки.
Іншими словами, швидкість — це відношення миттєвої зміни
положення крапки в просторі до витраченого на це часу. У відеоіграх
концепція швидкості одна з найбільш поширених, проте використовувані при
цьому одиниці, як правило, достатньо довільні і відносні.
Отже, об'єкт в наший грі переміщається з швидкістю, вимірюваною в
пікселях в секунду. Звичайно, якщо хочете, то можете оцінити, скільки
метрів міститься в одному пікселі вашого віртуального ігрового простору, і
виразити отриману швидкість в звичних метрах в секунду. У будь-якому
випадку, знаючи швидкість об'єкту і його положення в одному кадрі, ви
можете обчислити, яке положення він займатиме в наступному кадрі. Так,
якщо зараз положення об'єкту хі він рухається з постою швидкістю 4 пікселі
за кадр, то через 30 кадрів його положення буде х0 + 4x30 = х0 + 120
пікселів. Отже, головна формула поступальної ходи з постійною швидкістю:
xt – x0 + vt.
(1.1)
Ця формула свідчить, що якщо об'єкт, розташований в точці х
рухається з постійною швидкістю v протягом часу t, то до цього моменту
його положення буде рівне положенню в початковий момент плюс добуток
швидкості на час руху vt (рисунок 1.7).
Рисунок 1.7 - Рух з постійною швидкістю
33
1.3.6 Прискорення
Прискорення схоже на швидкість, але визначає швидкість зміни
швидкості. Погляньте на рисунку 1.8 — на ньому проілюстровані об'єкт,
рухомий з постійною швидкістю, і об'єкти, рухаючись з прискоренння.
Графіком залежності швидкості від часу для об'єкту, рухомого з постійною
швидкістю, буде горизонтальна пряма. Для об'єкту, рухомого з
прискоренням, залежність швидкості від часу є похилою прямою (при
постійному прискоренні) або кривою.
Рисунок 1.8 - Швидкість і прискорення
Математично прискорення визначається так само, як і швидкість, з тією
різницею, що радіус-вектор об'єкту замінюється вектором його швидкості:
a
dv
dt
(1.2)
у одновимірному випадку відповідно:
a
dv
dt
(1.3)
Одиниця вимірювання прискорення, як видно з його визначення, —
m/s2. Одновимірний рівноприскорений прямолінійний рух дає наступні
формули для залежності швидкості і положення об'єкту від часу (у момент
часу t=0 об'єкт знаходився в положенні х, а його швидкість складала v0;
прискорення об'єкту постійне і рівною а):
vt  v0  at ,
at 2
xt  x0  v0t 
2
(1.4)
(1.5)
34
Розглянемо рівноприскорений рух в грі, де початкове положення
об'єкту — х=50 пікселів, початкова швидкість — 4 пікселі за кадр, а
прискорення — 2 пикселя/кадр2. Щоб знайти положення об'єкту у будь-який
момент часу, можна використовувати вираз C/C++.
x=50+4*t+(2*t*t) /2;
де t — номер кадру.
1.3.7 Сила
Однією з найважливіших концепцій фізики є сила. На рисунку 1.9
показаний один з варіантів ілюстрації сили. На ньому зображений об'єкт з
масою т, що знаходиться на площині в полі тяжіння Землі, прискорення
вільного падіння в якому позначається як g.
Рисунок 1.9 - Сила і вага
Зв'язок між силою, масою і прискоренням описується другим законом
Ньютона; F=mа. Іншими словами, сила, що додається до об'єкту для його
руху з прискоренням а, рівна добутку маси на це прискорення. Другий закон
Ньютона може бути переписаний в іншому вигляді: a=F/m, що визначає
прискорення руху тіла під дією сили.
Тепер розглянемо одиницю вимірювання сили. Виходячи з другого
закону Ньютона, очевидно, що розмірність сили рівна kg = m/s2 . Для цієї
одиниці є окрема назва — Ньютон (N). Так, наприклад, уявимо, що об'єкт
масою 100kg рухається з прискоренням 2 m/s2. У такому разі можна
стверджувати, що до тіла прикладена сила 200kg*2m/s2 = 200N.
35
1.4 Мультимедійна бібліотека MMSystem
Для роботи із звуковим адаптером в середовищі операційної системи
Windows вам не потрібно буде програмувати на рівні портів
введення/виводу, переривань і каналів прямого доступу. Важкий необхідний
інтерфейс (високого або низького рівня) надається додатку DLL-бібліотекою
mmsystem.dll. Цю бібліотеку можна розглядати як розширення Windows для
забезпечення можливості роботи з мультимедіа.
Бібліотека mmsystem.dll з’являється у складі Windows версії 3.1 (версія
3.0 не могла працювати з мультимедіа, проте можна було придбати продукт
Microsoft Multimedia Extension, що містить цю бібліотеку і додатки,
призначені для роботи із звуком). Всі функції, що входять в бібліотеку
mmsystem.dll, описані у файлі mmsystem.h, який поставляється зі всіма
системами розробки додатків для Windows і знаходиться в каталозі include
разом з файлом windows.h.
У бібліотеці mmsystem.dll визначені функції двох рівнів: функції
низького рівня (Low-Level Functions ) і функції високого рівня, що є
інтерфейсом управління середовищем MCI (Media Control Interface).
Функції низького рівня працюють безпосередньо з драйверами
пристроїв введення/виводу, такими, як драйвери звукового адаптера,
джойстика або пристрою введення/виводу MIDI.
Функції інтерфейсу MCI працюють з драйверами пристроїв MCI
(наприклад, драйверами пристроїв читання компакт-дисків або лазерних
відеодисків) і викликають функції низького рівня.
У будь-якому випадку для роботи з пристроями мультимедіа додаток
повинен викликати ту або іншу функцію, визначену в бібліотеці
mmsystem.dll, незалежно від рівня інтерфейсу.
Що ж до драйверів звукових пристроїв, то можна виділити чотири типи
таких драйверів:
- драйвер для введення звуку;
- драйвер для виведення звуку;
- драйвер для введення музики в стандарті MIDI;
- драйвер для виведення музики в стандарті MIDI.
1.5 Середовище розробки Delphi
Delphi - це комбінація декількох найважливіших технологій:
- високопродуктивний компілятор в машинний код;
36
- об'єктно-орієнтована модель компонент;
- візуальна (а, отже, і швидкісне) побудова додатків з програмних
прототипів;
- масштабовані засоби для побудови баз даних.
1.5.1 Об'єктно-орієнтована модель програмних компонент
Основний напрям цієї моделі в Delphi робиться на максимальному
ревиконанні коду. Це дозволяє розробникам будувати додатки вельми
швидко із заздалегідь підготовлених об'єктів, а також дає їм можливість
створювати свої власні об'єкти для середовища Delphi. Ніяких обмежень по
типах об'єктів, які можуть створювати розробники, не існує. Дійсно, все в
Delphi написано на ньому же, тому розробники мають доступ до тих же
об'єктів і інструментів, які використовувалися для створення середовища
розробки. В результаті немає ніякої різниці між об'єктами, Borland, що
поставляються, або третіми фірмами, і об'єктами, які ви можете створити.
У стандартне постачання Delphi входять основні об'єкти, які
утворюють вдало підібрану ієрархію з 270 базових класів. Спершу непогано. Але якщо виникне необхідність в рішенні якоїсь специфічної
проблеми на Delphi, радимо, перш ніж спробувати починати вирішувати
проблему “з нуля”, проглянути список вільно поширюваних або комерційних
компонент, розроблених третіми фірмами, кількість цих фірм в даний час
перевищує число 250, хоча, можливо, я не про всіх знаю. Скептики, можливо,
не повірять мені, коли я скажу, що на Delphi можна однаково добре писати як
додатку до корпоративних баз даних, так і, наприклад, ігрові програми.
Проте, це так. Багато в чому це пояснюється тим, що традиційно в
середовищі Windows було досить складно реалізовувати призначений для
користувача інтерфейс. Діюча модель в Windows завжди була складна для
розуміння і відладки. Але саме розробка інтерфейсу в Delphi є найпростішим
завданням для програміста.
1.5.2 Delphi for Windows
Delphi for Windows вдає із себе підмножину Delphi Client-Server і
призначений
для
розробників
високопродуктивних
персональних
застосувань, що працюють з локальними СКБД типу dBase і Paradox.Delphi
Desktop Edition пропонує таке ж середовище для швидкої розробки і
першокласний компілятор як і клієнт-серверна версія (Client/Server Edition).
37
Це середовище дозволяє розробникові швидко виготовляти персональні
застосування, що працюють з персональними СКБД типу dBase і Paradox.
Delphi дозволяє також створювати розробникові DLL, яка може бути
викликана з Paradox, dBase, C++ або яких-небудь інших готових програм.
У Delphi for Windows, як і в Delphi Client-Server, входять:
- компілятор Object Pascal (ця мова є розширенням мови Borland Pascal
7.0);
- генератор звітів ReportSmith 2.5 (у якого, правда, відсутня можливість
роботи з SQL-серверами);
- середовище візуального будівника додатків;
- бібліотека візуальних компонентів;
- локальний сервер InterBase.
1.5.3 Для кого призначений Delphi
В першу чергу Delphi призначений для професіоналів-розробників
корпоративних інформаційних систем. Можливо, тут слід пояснити, що
конкретно мається на увазі. Не секрет, що деякі вдалі продукти, призначені
для швидкісної розробки додатків (RAD - rapid application development)
чудово працюють при виготовленні достатньо простих застосувань, проте,
розробник стикається з непередбаченими складнощами, коли намагається
зробити щось дійсно складне. Буває, що в продукті розкриваються властиві
йому обмеження тільки після деякого часу.
Delphi такі обмеження не властиві. Хороший доказ тому - це той факт,
що сам Delphi розроблений на Delphi. Можете робити виводи. Проте Delphi
призначений не тільки для програмістів-професіоналів. Я читав в
електронній конференції абсолютно несподівані для мене листи, де вчителі,
лікарі, викладачі вузів, бізнесмени, все ті, хто використовують комп'ютер з
чисто прикладною метою, розповідали про те, що придбали Delphi for
Windows для того, щоб швидко вирішити якісь свої завдання, не
привертаючи для цього програмістів з боку. В більшості випадків їм це
вдається.
Керівники підприємств, плануючі виділення засобів на придбання
програмних продуктів, повинні бути упевнені в тому, що плановані
інвестиції окупляться. Тому одним з оцінюваних чинників повинне бути
питання - а чи легко знайти фахівця з Delphi і скільки коштуватиме його
навчання, скільки часу фахівець витратить на оволодіння продуктом.
Відповідь тут отримати вельми просто - будь-який програміст на паскалі
38
здатний практично відразу професійно освоїти Delphi. Фахівцеві, що раніше
використав інші програмні продукти, доведеться важче, проте найперше
працююче застосування він зможе написати протягом першої ж години
роботи на Delphi. І, звичайно ж, відкрита технологія Delphi є могутнім
гарантом того, що інвестиції, зроблені в Delphi, будуть збережені протягом
багатьох років.
1.5.4 Особливості Delphi
Локальний сервер InterBase - слід відмітити, що цей інструмент
призначений тільки для автономної відладки додатків. Насправді він вдає із
себе скорочений варіант обробника SQL-запитів InterBase, в якого не
включені деякі можливості справжнього сервера InterBase. Відсутність цих
можливостей з лишком компенсується перевагою автономної відладки
програм.
Team Development Support - засіб підтримки розробки проекту в групі.
Дозволяє істотно полегшити управління крупними проектами. Це зроблено у
вигляді можливості підключення такого продукту як Intersolve PVCS 5.1
безпосередньо до середовища Delphi.
Високопродуктивний компілятор в машинний код - на відміну від
більшості Паскаль-компіляторов, що транслюють в p-код, в Delphi
програмний текст компілюється безпосередньо в машинний код, внаслідок
чого Delphi- додатку виконуються в 10-20 разів швидше (особливо додатки,
що використовують математичні функції). Готове застосування може бути
виготовлене або у вигляді виконуваного модуля, або у вигляді динамічної
бібліотеки, яку можна використовувати в додатках, написаних на інших
мовах програмування.
39
2
ПРОГРАМНА РЕАЛІЗАЦІЯ ДОДАТКУ
Дипломна робота реалізована на мові програмування Delphi 7.0 і
складається з двох програм: MapBilder.exe і Tanks.exe, які включають
5 основних модулів:
- MapBilder.pas – містить процедури і функції для створення і
редагування ігрового простору;
- Unit_tank.pas – забезпечує взаємодію користувача і програми;
- TankEngine.pas – містить обширну кількість функцій для
маніпулювання ігровим простором (ландшафти, рослинність, танки, вода,
дорогі і т.д.);
- Rwin_xfile.pas – містить набір процедур і функцій для завантаження
файлів типу *.х, а також їх візуалізація;
- Kwav.pas – бібліотека для завантаження аудіо звуків і потокового
виведення 3Д звуку.
2.1 Реалізація ландшафтів
Ландшафт є динамічний двомірний масив довільного розміру
фіксованою дискретності, кожен елемент якого містить висоту, а також тип
поверхні ландшафту. При чому кожен осередок ландшафту відображає
1\GroundTextureSplit частину текстури, і якщо в сусідньому осередку інша
текстура поверхні, то текстура градаційно змінюється між цими осередками,
що підвищує реалістичність зображення. Приклад побудови ландшафту
зображений на рисунку 2.1.
Для збільшення швидкодії на екран виводиться не весь ландшафт, а
тільки його частина – фрагменти рівновіддалені від камери на відстань менш
GroundPartOutPutRadius.
При побудові рівнів, ті частини ландшафту, які нижче встановленого
рівня води, – утворюють області покриті водою.
При необхідності зміни погодних умов існує можливість застосування
таких ефектів як туман різної щільності і кольору, джерело світла з різними
спектральними і дифузійними характеристиками, приклад використання
погодних умов. Приклад погодних умов наведений на рисунку 2.2.
40
Рисунок 2.1 - Приклад побудови ландшафту
Рисунок 2.2 - Візуалізація погодних умов
41
На комп'ютерах з високою швидкодією можливе використання
додаткового ефекту – дзеркального віддзеркалення у воді.
Рисунок 2.3 - Ефект дзеркального віддзеркалення у воді
Ефект дзеркального віддзеркалення у воді досягається за допомогою
Stencil буфера і площини відсікання:
- вода вимальовується в буфері Stencil;
-проводиться
вимальовка
частин
ландшафту
відсічених
горизонтальною площиною нижче за рівень води, використовуючи маску
Stencil;
- очищається Z-буфер і використовуючи маску вимальовується верхня
(дзеркально-відбита) частина ландшафту;
- потім рисується вода, а після чого – вся решта ландшафту.
Рух танка обумовлений поверхнею ландшафту. Дискретність цієї
поверхні приводить до нереального розташування об'єктів на ній. Рішення
цієї проблеми – використання білінійної інтерполяції і обчислення крапки на
площині.
Обчислення крапки на площині здійснюється таким чином: знаю
координати вершин суміжних осередків масиву висот ландшафту(х1,y1,z1,
х2,y2,z2, х3,y3,z3) будується рівняння площини, потім підставивши необхідні
значення х, y отримаємо висоту в цій крапці.
a:= ((y2-y3)*(z3-z1)-(y3-y1)*(z2-z3));
42
b:=-((x2-x3)*(z3-z1)-(x3-x1)*(z2-z3));
c:= ((x2-x3)*(y3-y1)-(x3-x1)*(y2-y3));
z:=z1+(-a*(x-x1)-b*(y-y1)) /c;
Обчислення кутів розташування танка (Gama, Beta) в осередку
(i,j,inx=|i+1|,jnx=|j+1|):
a1:=(map^.mapCalc[i,j].Normal.a*(GroundPartSize-di)/
(GroundPartSize))+(map^.mapCalc[inx,j ].Normal.a*(di)/(GroundPartSize));
b1:=(map^.mapCalc[i,j].Normal.b*(GroundPartSize-di)/
(GroundPartSize))+(map^.mapCalc[inx,j ].Normal.b*(di)/(GroundPartSize));
c1:=(map^.mapCalc[i,j].Normal.c*(GroundPartSize-di)/
(GroundPartSize))+(map^.mapCalc[inx,j].Normal.c*(di)/(GroundPartSize));
Обчислення другого кута:
a2:=(map^.mapCalc[i,jnx].Normal.a*(GroundPartSize-di)/
(GroundPartSize))+(map^.mapCalc[inx,jnx].Normal.a*(di)/(GroundPartSize));
b2:=(map^.mapCalc[i,jnx].Normal.b*(GroundPartSize-di)/
(GroundPartSize))+(map^.mapCalc[inx,jnx].Normal.b*(di)/(GroundPartSize));
c2:=(map^.mapCalc[i,jnx].Normal.c*(GroundPartSize-di)/
(GroundPartSize))+(map^.mapCalc[inx,jnx].Normal.c*(di)/(GroundPartSize));
Обчислення третього кута:
a3:=(a1*(GroundPartSize-dj)/
(GroundPartSize))+(a2*(dj)/(GroundPartSize));
b3:=(b1*(GroundPartSize-dj)/
(GroundPartSize))+(b2*(dj)/(GroundPartSize));
c3:=(c1*(GroundPartSize-dj)/
(GroundPartSize))+(c2*(dj)/(GroundPartSize));
Gama := a3*90;
Beta := -b3*90;
де а1,b1,c1 – лінійно інтерпольовані значення по ширині верхньої
частини осередку, а2,b2,c2 – лінійно інтерпольовані значення по ширині
нижньої частини осередку, а3,b3,c3 – лінійно інтерпольовані значення по
ширині нижньої частини осередку;
GroundPartSize – ширина і висота осередку;
dj, di – положення танка усередині осередку.
43
2.2 Реалізація рослинності
Перелік об'єктів рослинності знаходиться у файлі object\plant\plant.cfg.
Це файл де кожен об'єкт – файл у форматі *.х. Спеціальна опція в імені
файлу non_bind указує що об'єкт ніяк не взаємодіє з танком(для кущів,
трави). Програма створює список екземплярів рослинності і кожен екземпляр
рослинності має індивідуальні розміри, координати, кути, а також посилання
на модель об'єкту. Використання альфа тесту використовується для
маскування невидимих частин текстур, що використовується при малюванні
гілок дерев, чагарників і т.д. Приклад рослинності показаний на рисунку 2.4 .
Рисунок 2.4 - Рослинність в ігровому застосуванні
Для збільшення швидкодії на екран виводиться не вся рослинність, а
тільки частина – фрагменти рівновіддалені від камери на відстань менш
GroundPartOutPutRadius.
У програмі будівнику рівнів для візуалізації рослинності на панелі
використовується вимальовка кожного виду рослинності в текстуру при
завантаженні програми.
44
2.3 Розробка імітаційної моделі танка
Імітаційна модель танка ієрархічна структура геометричних об'єктів
зв'язаних між собою об'єктами заміщення, як показано на рисунку 2.5
Рисунок 2.5 Імітаційна модель танка
Список всіх елементів знаходиться у файлі tanks.cfg, де виділений клас
об'єктів:
- main – основа, основна частина танка на якій знаходиться решта
частин(wheel, weapon);
- wheel – частина призначена для переміщення танка по поверхні,
також при русі кут повороту може мінятися залежно від швидкості руху і
розміру, прикріпляється до основної частини за допомогою об'єкту
з'єднувача 1;
- weapon – знаряддя(башта) призначена для кріплення ствола гармати,
для наведення знаряддя в мету в горизонтальній площині, тобто при
натисненні на певну клавішу башта повертається, прикріпляється за
допомогою об'єкту з'єднувача 2;
- barrel – стовбур, кріпиться на башті і призначений відтворувати
постріл (при пострілі снаряди з'являються у позиції об'єкту 4), наведення
знаряддя у вертикальній площині, при натисненні на певну клавішу стовбур
може опускатися і підніматися. Вектор швидкості снаряда обчислюється
виходячи з суми векторів: одиничний вектор повороту башти і одиничного
вектора нахилу стволу.
45
Програма створює список екземплярів танків і кожен екземпляр має
індивідуальні координати, кути, швидкість пересування, різні складові
(колеса, гусениці, башти, стовбур), технічні стани (рівень життя). При малій
кількості життя у танка з'являються сліди пошкоджень, при попаданні в танк
з нього йде дим.
При пересуванні танка по ландшафту його швидкість залежить від
кутів нахилу поверхні (якщо підйом, то танк пересувається значно
повільніше, ніж при спуску його з схилу). Швидкість пересування танка по
ландшафту обчислюється по формулах:
k:=1.0;
Dx:=pl.Speed*cos(pi*pl.Alfa/180);
Dy:=pl.speed*sin(pi*pl.Alfa/180);
Kdx:=(dx*k*sin(pi*pl.Gama/180))*cos(pi*pl.Alfa/180);
Kdy:=(dy*k*sin(pi*pl.Beta/180))*sin(pi*pl.Alfa/180);
if Abs(dx) >Abs(Kdx) then pl.vx := -(dx+Kdx);
if Abs(dy) >Abs(Kdy) then pl.vz:=(dy+Kdy);
де k – коефіцієнт подолання нахилів; чим менше коефіцієнт, тим менше
значущість кутів нахилу поверхні;
pl.Speed – лінійна швидкість танка;
Dx, Dy – векторна швидкість танка;
pl.Alfa – кут повороту в горизонтальній площині танка;
pl.Gama, pl.Beta – кут нахилу танка у вертикальній площині;
Kdx, Kdy – компенсація вектора швидкості прямо пропорційна
коефіцієнту до; залежно від напряму руху танка вектор компенсації може
додаватися або відніматися від основної швидкості;
pl.vx, pl.vz – результуючий вектор швидкості танка на площині.
При пересуванні танка по місцевості він взаємодіє з рослинністю, тобто
при зіткненні з крупною рослинністю швидкість танка перераховується:
f := (pl.Level * Plant_down_level - p.Scale);
if f < 0 then f := 0;
if f > 1 then f := 1;
p.Alfa := p.Alfa + pl.vz * (f)*3;
p.Gama := p.Gama - pl.vx * (f)*3;
l := sqrt( sqr(p.X - pl.Posx)+ sqr(p.Z - pl.Posz));
а := (p.X - pl.Posx)/l;
с := (p.Z - pl.Posz)/l;
plV := pl.vx*a + pl.vz*c;
pl.vx := (pl.vx*(f))+(1-f)*(pl.vx - a*plv)/3;
46
pl.vz := (pl.vz*(f))+(1-f)*(pl.vz - c*plv)/3;
де f – коефіцієнт дії екземпляра танка(pl) з екземпляром рослинності(p),
тобто танк з великим рівнем(pl.Level) зможе легше подолати перешкоди
рослинності розміром(p.Scale);
p.Alfa, p.Gama – кути нахилу рослини у вертикальній площині, на них
впливає вектор швидкості pl.vx, pl.vz залежно від коефіцієнта f, якщо f=0 –
кут не міняється;
l – відстань між центром танка(pl.Posx, pl.Posz) і центром екземпляра
рослини(p.X, p.Z);
(а, с) – одиничний вектор з’єднуючий центр танка з центром рослини;
plV – довжина перпендикуляра опущеного з центру танка в напрям
центру рослини, а проекція рівна (pl.vz - а*plv, pl.vz - c*plv).
Всі ігрові танки підрозділяються на декілька груп тих, що
розрізняються між собою кольором і кожен танк має пізнавальні знаки
певного кольору. Групи створюються в будівнику карт, кожному танку
призначається своя певна група.
Танком можна управляти таким чином:
- Player control – танку керується посилання на список кнопок по
натисненню яких здійснюється маніпулювання танком. Маніпуляція танком
можлива з клавіатури, маніпулятора миші, а також всіляких типів
джойстиків;
- CPU control – програмне управління танком, екземпляр танка містить
посилання на спеціальну структуру в якій зберігається стан штучного
інтелекту;
- Net control – управління танками з видаленого терміналу, він
зв'язаний через player control через мережу і є віддзеркаленням клієнта на
сервері.
При створенні танка в будівнику карт йому може призначатися тільки 2
типи управління: управління гравцем і автоматичне управління.
Представлене при запуску гри, кожен гравець посилає запит на створення
танка і йому виділяється вільний танк із списку танків з типом управління
контролю гравцем.
2.4 Мережевий режим гри
У даному додатку також реалізовано мережевий режим гри, який
дозволяє об’єднати зусилля декількох гравців за допомогою мережі.
Мережевий режим гри можна використовувати тільки в локальній
47
мережі. Сервером може бути будь-який комп'ютер, який запускає гру в
одиночному режимі, а клієнтський під’єднується до нього шляхом вказівки
локальної адреси і порту. Також клієнт шукає сервер в локальній мережі за
допомогою розсилки широкомовного повідомлення.
Ця програма описана з використанням Socket по протоколу UDP/IP.
Програма включає 2 сокети: серверний (ініціалізується на початку одиночної
гри і знищується по її завершенню) і клієнтський (створюється відразу після
запуску гри і знищується завершення програми).
Для обміну даними між клієнтом і сервером використовується
спеціальний набір повідомлень, який організований за принципом: спочатку
відсилається заголовок повідомлення, а потім по заголовку визначається який
потік даних потрібно прийняти.
Повідомлення передаваємі від клієнта до сервера:
- chunk_get_server – відсилається всім серверам за широкомовною
адресою;
- chunk_send_server_info – сервер відповідає на запит клієнта якщо
сервер запущений і далі посилає відомості про сервер (ім'я сервера, назва
рівня, кількість гравців);
- chunk_join_to_server – клієнт посилає запит на підключення до
сервера;
- chunk_client_join – сервер підтверджує запит на з'єднання, після чого
посилає відомості про поточну гру і передає всю інформацію про запущену
гру; при цьому додається запис про клієнтів на сервері (локальна адреса,
порт);
- chunk_send_control_to_server – кожен клієнт посилає бітові значення
управління танком;
- chunk_send_frame_to_client – сервер посилає дані клієнту про
системний час (для синхронізації) і інформацію про гравців;
- chunk_close – може посилає клієнт або сервер по завершенню або
перериванню гри.
Щоб синхронізувати сервер і клієнт разом з передачею даних про
відомості управління і системний час передається спеціальний ідентифікатор.
Якщо клієнт одержує данні з ідентифікатором за більше очікуване – це
означає, що дані були загублені в мережі і клієнт повторює запит на
отримання кадру даних. Для цього на сервері створюється список кадрів
даних за невеликий проміжок часу. Якщо кадр на сервері не існує, то сервер
посилає повідомлення про розрив зв'язку. Клієнт обробляє повідомлення і
48
змінює стан ігрового простору до тих пір, поки не закінчить прийом всіх
даних. Тільки після всього цього можлива перересовка екрану.
2.5 Реалізація частинок
Частинка – об'єкт, що створюється при вибуху, рухома по законах
фізики (визначаються зіткнення і перераховуються швидкості). Специфічний
вид частинок – призовий вектор, бонус. Кожна частинка створює певну
кількість диму залежно від часу життя частинки і типу частинки (по
завершенню життя частинки – кількість диму зменшується).
Реалізація фізики в програмі приведена нижче:
l := Sqrt((fp.vx * fp.vx) + (fp.vy * fp.vy) + (fp.vz * fp.vz));
if l = 0 then COSalpha := 1 else
COSalpha := (fp.vx*(-na) + fp.vy*(-nc) + fp.vz*(-nb))/l;
pa := na*COSalpha*l;
pb := nb*COSalpha*l;
pc := nc*COSalpha*l;
oa := fp.vx + pa;
ob := fp.vz + pb;
ос := fp.vy + pc;
fp.vx := KS*oa + KN*pa;
fp.vz := KS*ob + KN*pb;
fp.vy := KS*oc + KN*pc;
fp.wa := fp.wa * KS;
fp.wb := fp.wb * KS;
fp.wc := fp.wc * KS;
де, fp – екземпляр частинки;
fp.x, fp.y, fp.z – координати частинки;
fp.vx, fp.vy, fp.vz – вектор швидкості частинки;
fp.wa, fp.wb, fp.wc – кутовий вектор швидкості;
l – довжина вектора швидкості;
na, nb, nc –вектор сполучаючий центр частинки і точку удару;
COSalpha – косинус кута між вектором з’єднуючий центр частинки і
точку удару і вектором швидкості частинки;
pa, pb, pc – відбитий вектор швидкості від поверхні;
oa, ob, ос – вектор швидкості ковзання;
KS, KN – коефіцієнт ковзання і опору поверхні відповідно.
49
Даний блок програми виконується після визначення того, що частинка
зіткнулася з поверхнею. При потраплянні частинки у воду на неї діє сила
Архімеда. Це виражено нижче таким чином:
if fp.vy < 0 then
fp.vy := fp.vy + fp.WaterDrown * 13 * Gravity* SystemSpeed else
fp.vy := fp.vy + fp.WaterDrown * 10.8 * Gravity* SystemSpeed;
fp.vx := fp.vx - fp.vx * 0.01*SystemSpeed;
fp.vz := fp.vz - fp.vz * 0.01*SystemSpeed;
fp.wa := fp.wa - fp.wa * 0.01*SystemSpeed;
fp.wb := fp.wb - fp.wb * 0.01*SystemSpeed;
fp.wc := fp.wc - fp.wc * 0.01*SystemSpeed;
де, fp.WaterDrown – коефіцієнт інертності об'єкту (0 для важких
об'єктів, 1 - для легких).
2.6 Візуалізація диму
Дим – плоский напівпрозорий об'єкт повернений до монітора. Кожен
екземпляр диму описується координатами, розміром, кадром текстури,
швидкістю руху і швидкістю зміни розміру. Із-за напівпрозорої виникає
необхідність сортування частинок диму (об'єкти розташовані ближчим
частково перекривають, а частково колір змішується з розташованими далі
об'єктами сцени). Це здійснюється таким чином:
1)координати частинок диму перетворяться в екранні, при цьому
визначається мінімальне і максимальне значення координати z (віддаленість
від монітора);
2) всі елементи розбиваються на n груп для певного інтервалу значень z
(створюється n списків, вміст яких – покажчики на відповідні частинку
елементу);
3) кожен список сортується;
4) послідовне виведення списків і їх елементів.
Орієнтація частинки диму до площини монітора реалізована таким
чином:
glGetDoublev (GL_MODELVIEW_MATRIX, @matrix);
xn:=x*matrix[0,0]+y*matrix[0,1]+z*matrix[0,2];
yn:=x*matrix[1,0]+y*matrix[1,1]+z*matrix[1,2];
zn:=x*matrix[2,0]+y*matrix[2,1]+z*matrix[2,2];
де,
glGetDoublev
–
отримання
матриці
перетворення
gl_modelview_matrix у матрицю matrix;
50
x, у, z – координати вершини площини диму;
xn, yn, zn – перетворені координати.
2.7 Основні процедури функцій
Основні процедури функцій приведені у таблиці 2.1
Таблиця 2.1 - Основні процедури функцій
Назва процедури
Опис процедури
Procedure InitTankEngine;
Ініціалізація усіх змінних та черг
об’єктів, ігрового простору
Procedure DestroyTankEngine;
Видалення усіх змінних та черг
об’єктів, ігрового простору
Function CreatePlayer:Pointer;
Створення та додавання в чергу
гравця
Function JoinPlayer : Pointer;
Знаходження вільного гравця у черзі
Procedure ControlPlayers;
Керування любим типом гравця
Procedure LoadTanks(Fname:String);
Загрузка танків з файлу-списку всіх
танків
Procedure LoadPlant(Fname:String);
Загрузка з файлу-списку рослинності
Procedure OutAllPlant;
Візуалізація рослинності
Procedure LoadRoadLib(Fname:String); Візуалізація дороги
Procedure LoadMap
Загрузка ігрового простору
(Fname:String;var map:Pmap);
Procedure SaveMap(Fname:String;
Збереження ігрового простору
map:Pmap);
Procedure CalcMapNormals (var
Обчислення нормалей ландшафту
map:Pmap);
51
Продовження Таблиці 2.1 - Основні процедури функцій
Procedure OutMap(map:Pmap);
Вивід ландшафту
Procedure GetMapPart (x,y:single;var
Отримання висоти по координаті на
z,n1,n2,n3:single);
ландшафті
Procedure GetMapNormal
Отримання нормалі у точці
(x,y:single;var n1,n2,n3:single);
Function CreateShell(x, y, z, vx, vy, vz, Створення снаряда в точці x, у, z зі
Power: single; owner : Pplayer) : Pshell; швидкістю vx, vy, vz
Procedure ControlShell(map : Pmap);
Управління снарядом Shell
Procedure OutAllShell;
Візуалізація усіх снарядів
Function LoadXFile (var obj:PXfileObj; Завантаження файлу тривимірної
Fname:string;TexturePath:string):
геометрії
boolean;
procedure LoadTexture (var
Завантаження однієї текстури з
Texture:GLuint; Fname: string);
файлу Fname
procedure InitMenus;
Ініціалізація меню гри
Procedure DrawMenu (m : Pmenu);
Промальовування меню на екрані
Procedure ControlMenu (m : Pmenu);
Управління геометрії меню
Function PlayWav (Fname: string):
Програвання мультимедійного аудіо
boolean;
файлу з файлу Fname
Procedure SoundControl;
Управління всіма звуками
Function InitNetPlay : boolean;
Ініціалізація мережевого інтерфейсу
Procedure CloseNetPlay;
Деініціалізация мережевого
інтерфейсу
function InitServer : boolean;
Ініціалізація сервера гри
Procedure CloseServer;
Завершення роботи сервера
Procedure Server_Action;
Контроль управління сервером
Procedure Client_Action;
Контроль управління клієнтом
Procedure RefreshServers;
Очищення списку серверів і посилка
широкомовного повідомлення
52
3 КЕРІВНИЦТВО ПО ВИКОРИСТАННЮ
Ігровий додаток складається з двох програм:
- MapBilder.exe – використовується для побудови ігрових рівнів;
- Tanks.exe – файл запуску гри.
Ці програми використовують однакові модулі (Rwin3D.pas,
TankEngine.pas, Queue.pas), загружають однакові зовнішні файли (геометрія,
текстури), що значно економить місто на жорсткому диску. Додаток не
використовує ніякі специфічні динамічні бібліотеки, що значно підвищує
переносимість і сумісність на різних платформах. Загальний розмір архіву
додатку складає менш 1МБ, що дозволяє легко розмістити архів в
середовищіІнтернет. Для розпаковування архіву використовується архіватор
WinRar .
3.1 Будівник карт
Будівник використовується для створення і редагування ігрових рівнів.
Зручне
меню дозволяє легко і швидко створювати ігровий простір.
Програма складається з 2 форм: основна і форма настройок. На основній
формі розташовані: панель інструментів, панель опцій, панель елементів,
вікно і рядок станів. Основна форма програми показана на рисунку 3.1.
53
Рисунок 3.1 - Основна форма програми
3.2 Головне меню
Як і у усіх програмах, рядок меню розташований під рядком заголовку.
У головному меню знаходятьсяменю File, Settings і View.
У меню File є такі підменю:
- new – це меню дозволяє створити новий рівень;
- open – меню за допомогою якого можна відкрити вже існуючий рівень
для подальшого його перегляду або редагування;
- save – меню збереження рівня;
- save аs – меню збереження рівня під іншим ім'ям;
- exit – меню виходу з програми.
Меню Settings викликає вікно настройок в якому надається можливість
редагування рівня.
Меню View містить настройки управління відображення ігрового
простору:
- light – включає відображення освітлення рівня;
- cube map – включає відображення оточення (задній план).
54
3.3 Вікно виведення ігрового простору
Вікно показує навігацію в тривимірному просторі, також можна
виділяти об'єкти і створювати нові. Переміщатися по рівню можливо за
допомогою затиснутої лівої клавіші миші в різні боки. Права клавіша миші
дозволяє провести обертання, змінити кут огляду. При натисненні на
середню клавішу миші (скрол) можна наближати, або рівень, змінюється
висота.
3.4 Рядок станів
Рядок станів призначений для виведення додаткової інформації.
Показує координати об'єкту в просторі при його переміщенні, також показує
допоміжну інформацію (допомога).
3.5 Панель інструментів
Панель інструментів необхідна для вибору одного з наданих
інструментів. При виборі будь-якого інструменту змінюється вміст панелі
настройок, панелі елементів і рядка станів. Панель інструментів має вигляд
(рисунок 3.2)
Рисунок 3.2 - Панель інструментів
Інструмент навігація – використовується для переміщення, поворотів, і
наближення по рівню за допомогою клавіш миші.
Інструмент рельєф – служить для зміни поверхні ландшафту. Спочатку
потрібно вибрати необхідну ділянку поверхні, а потім за допомогою лівої
клавіші миші змінити його висоту; якщо опустити ділянку нижче за рівень
води, то на цій ділянці з'являється вода, а якщо підняти ділянку вище за
рівень води, то на цій ділянці утворюється гора . Панель настройок
інструменту рельєфу приведена нижче на рисунку 3.3.
Рисунок 3.3 - Інструмент рельєф
55
1)
жорсткий радіус – змінює радіус області виділення, на якому
поверхня змінюється не плавно залежно від радіусу;
2)
гладкий радіус - змінює радіус області виділення, на якому
змінюється плавно поверхня залежно від радіусу.
Інструмент згладжування – при натисненні лівої клавіші миші згладжує
вибрану ділянку поверхні, роблячи її плоскою. На панелі опцій можна
змінити радіус виділення поверхні. Інструмент згладжування зображений
нижче на рисунку 3.4.
Рисунок 3.4 - Інструмент згладжування
Інструмент малювання - призначений для зміни типу поверхні
виділеної ділянки. Інструмент малювання показаний на рисунку 3.5
Рисунок 3.5 - Інструмент малювання
На панелі елементів розташовані зразки всіх типів поверхні, які можна
використовувати при побудові рівня. Приклад зразків поверхні показаний на
рисунку 3.6.
Рисунок 3.6 - Зразки поверхонь
56
Інструмент рослинність - призначений для створення різних типів
рослинності. Спочатку потрібно вибрати на панелі елементів потрібний тип
рослинності, потім виділити на вікні висновку вказану область, де потрібно
розташувати рослинність, також на панелі опцій можна вибрати (кількість
даного типа рослинності, мінімальний і максимальний розмір рослинності) і
лише після цього на екрані з'явиться рослинність. Інструмент рослинність
зображений на рисунку 3.7.
Рисунок 3.7 - Інструмент рослинність
Інструмент дорога - використовується для малювання дороги на
поверхні ландшафту. На панелі елементів вибирається тип дороги і за
допомогою миші малюється дорога.
Інструмент танк - призначений для створення, редагування і видалення
танків. Існує 3 режими інструменту танк: створення, редагування і створення
генератора танків. При створенні танка потрібно вибрати кількість життів,
тип танка, тип управління танків, кут повороту танку, а також групу танка.
При редагуванні танка потрібно вибрати потрібний нам танк і змінити його
параметри. Інструмент танк зображений нижче на рисунку 3.8.
Рисунок 3.8 - Інструмент танк
57
4 ЕКОНОМІЧНЕ ОБГРУНТУВАННЯ ДИПЛОМНОЇ РОБОТИ
При розробці програмного продукту необхідно описати призначення
програми, яка розробляється в даному проекті. Потрібно охарактеризувати
можливості, які надає використання цієї програми. Також, доцільно буде
обґрунтувати та описати язик програмування та характеристику ПЕОМ,
потрібні для розробки програми.
4.1 Визначення трудомісткості робіт
Встановлення програмного забезпечення потребують певних витрат
часу та праці. Показником, який узагальнює ці витрати є – трудомісткість.
Для розрахунку загальної трудомісткості необхідно визначити етапи
робіт та трудомісткість цих робіт. Всі розрахунки загальної трудомісткості
робіт зводяться до таблиці 4.1.
Таблиця 4.1 – Розрахунок загальної трудомісткості робіт
Назва етапів
Трудомісткість
Виконавець(спеціальність)
Тшт., год
Постановка задачі
2
Програміст
Формування і аналіз
2
Програміст
фізичної задачі
Розробка математичної
4
Програміст
моделі
Розробка
алгоритму
8
Програміст
програми
Аналіз графіки
2
Дизайнер
Створення макету гри
8
Дизайнер
Розробка графічного
8
Дизайнер
інтерфейсу
Створення графічних
22
Дизайнер
структур гри
Написання
тексту
42
Програміст
програми
Введення
тексту
8
Програміст
програми в комп’ютер
58
Продовження таблиці 4.1 – Розрахунок загальної трудомісткості робіт
Синтаксична
12
Програміст
налагодження програми
Тестування і синтаксична
4
Програміст
налагодження
Запуск готової програми
8
Програміст
та
аналіз
отриманих
результатів
Загальна трудомісткість
130
Тзаг., год.
З урахуванням рівня язику програмування трудомісткість розробки
програми повинна бути скорегована наступним чином:
Тпр = Кпр * Тзаг н.год.
(4.1)
де Кпр – коефіцієнт зміни трудомісткості залежно від рівня язику
програмування (дивись табл. 4.2.)
Таблиця 4.2 – Коефіцієнт зміни трудомісткості залежно від язику
програмування
Рівень язику
Характер язику
Коефіцієнт
програмування
програмування
зміни
трудомісткості
I
По командний язик – Асемблер
1
II
Макроасемблер
0,95
III
Алгоритмічні язики високого
рівня
0,8 – 0,9
IV
Алгоритмічні язики найвисокого
рівня
0,7 – 0,8
Далі розраховуємо трудомісткість. Коефіцієнт трудомісткості брався
0.8, так як програма виконана на алгоритмах високого рівня – на мові
програмування Delphi.
Тпр.прог.=0,8*90=72 н.год.
Тпр.диз. = 0,8 * 40 = 32 н.год.
59
4.2 Розрахунок чисельності персоналу
Дійсний фонд робочого часу виконання приймаємо за 13 робочих днів,
тобто за 104 години.
Чисельність персоналу приведена у таблиці 4.3.
Таблиця 4.3 – Склад і кількість виконавців
Назва спеціальності
Програміст
Дизайнер
Загальна кількість виконавців, чол.
Кількість, чол.
1
1
2
4.3 Розрахунок витрат на оплату праці
Витрати на оплату праці – це запланована на визначений термін часу
сума грошових коштів, призначених для виплати працюючим за виконану
роботу.
Витрати на оплату праці (Вопл.) включає:
- витрати на основну заробітну плату, Зосн.;
- витрати на додаткову заробітну плату, Здод..
Витрати на основну заробітну плату включають тарифну заробітну
плату, яка визначається тарифними ставками, відрядними розцінками,
посадовими окладами, а також надбавками і доплатами у розмірах, не вище
встановлених чинним законодавством.
Витрати на додаткову заробітну плату включають доплати, надбавки,
гарантійні і компенсаційні виплати, передбачені чинним законодавством,
премії за виконання виробничих завдань і функцій.
Всі виконавці знаходяться на погодинно-преміальній системі оплати
праці.
Витрати на оплату праці розраховуються за формулою:
Вопл. = ∑Зосн. + ∑Здод.
(4.2)
де ∑Зосн. – сума основної заробітної плати всіх виконавців;
∑Здод. – сума додаткової заробітної плати всіх виконавців.
Основна заробітна плата для спеціалістів, керівників розраховується за
формулою:
60
Зосн. = Окл.∙ Тшт. / Фд.
(4.3)
де Окл. – величина окладу спеціаліста згідно штатному розкладу
підприємства;
Тшт. – трудомісткість виконання етапу робіт за і-ю спеціальністю;
Фд – дійсний (місячний) фонд робочого часу одного виконавця.
Зосн.прог = (1900 * 72) / 178 = 768,54 грн.
Зосн.диз = (1800 * 32) / 178 = 323,6 грн.
Додаткова заробітна плата розраховується за формулою:
Здод. = Зосн.∙ Д.
(4.4)
де Зосн. – основна заробітна плата;
Д – сума доплат, надбавок та інших виплат, передбачених чинним
законодавством (0,4 – 0,5).
Здод. = 768,54 * 50% = 768,54 * 0,5 = 384,27 грн.
Здод. = * 50% = 323,6 * 0,5 = 161,8 грн.
Отже, виплати на оплату праці складуть 1638,21 гривню.
Вопл. = (768,54 + 323,6) + (384,27+ 161,8) = 1092,14 + 546,07 = 1638,21 грн.
4.4 Відрахування на соціальні заходи
Відрахування на соціальні заходи включають: відрахування на пенсійне
забезпечення, на соціальне страхування, страхування на випадок безробіття,
страхування від нещасних випадків. Величина відрахувань встановлюється у
відсотках від витрат на оплату праці, так:
- пенсійний фонд – 32.3%;
- фонд зайнятості – 1.6%;
- фонд соціального страхування – 2.9%;
- фонд страхування від нещасних випадків для галузі радіоелектроніки
– 1,5%.
Отже, загальний відсоток відрахувань згідно чинного законодавства
складає 38,3%.
61
Таким чином відрахування на соціальні заходи визначаються за
формулою:
Всоц.з. = 0,383 ∙ Вопл.
(4.5)
де Всоц.з. – відрахування на соціальні заходи;
Вопл. – витрати на оплату праці.
Всоц.з. = 0,383 * 1638,21 = 627,43 грн.
4.5 Витрати на утримання та експлуатацію обладнання
Витрати на утримання та експлуатацію обладнання відносяться до
непрямих витрат.
При розробці програмного забезпечення витрати на утримання і
експлуатацію обчислювального комплексу розраховуються за формулою:
Ву.е. = Sм.год.∙ Фм,
(4.6)
де Sм.год. – вартість одного машинного часу;
Фм – фонд часу роботи на ПЕОМ (дані беруться із таблиці 4.1;
зазвичай фонд часу роботи на ПЕОМ складається з витрат часу на процес
програмування та налагодження програмного продукту).
Ву.е.о = 130 * 1,3 = 169 грн.
Вартість машинного часу розраховується за наступною формулою:
Sм.год. = (Вел.р. + Ар. + Врем.р.) / Фпк,
(4.7)
де Вел.р. – витрати на річні відрахування за електроенергію, яку
використовує один персональний комп’ютер (ПК);
Ар. – витрати на річну амортизацію ПК;
Врем.р. – річні витрати на поточний ремонт ПК;
Фпк – річний дійсний фонд часу роботи ПК.
Sм.год. = (620,25 + 1400+ 200) / 1734 = 1,3
62
Дійсний фонд часу роботи ПК за рік розраховується за формулою:
Фпк. = Фном.∙ Кпроф.
(4.8)
де Фном. – номінальний фонд часу роботи одного ПК (за рік складає
2040 год.);
Кпроф. – коефіцієнт витрат часу на профілактичні заходи (Кпроф. =
0,85);
Фпк = 2040 * 0,85 = 1734 грн.
Річні відрахування за електроенергію, яку використовує один ПК,
визначаються за формулою:
Вел.р. = S ∙ Рс ∙ Фпк,
(4.9)
де S – вартість однієї квт./год. (0,75грн.);
Рс – споживча потужність ПК (0,5 квт./год.);
Фпк – дійсний фонд часу роботи ПК за рік.
Вел. р. = 0,75 * 0,5 * 1734 = 650,25 грн.
Річна амортизація розраховується як добуток балансової вартості
основних фондів та встановленої для відповідної групи основних фондів
норми амортизації і розраховується за формулою:
Ар. = Sб ∙ На,
(4.10)
де Sб – балансова вартість відповідної групи основних фондів на
початок року (ПЕОМ відноситься до IV групи);
На – річна норма амортизації (по ступеню зносу для ПК На=35%).
Ар. = 4000 * 0,35 = 1400 грн.
Річні витрати на поточний ремонт ПК визначаються пропорційно до
балансової вартості основних фондів і розраховуються за формулою:
Врем.р. = Sб ∙ Прем.,
(4.11)
63
де Sб – балансова вартість основних фондів (ПК) на початок року;
Прем. – відсоток витрат на поточні ремонти від вартості основних
фондів (для ПК Прем.=5%).
Врем.р. = 4000 * 0,05 = 200 грн.
4.6 Загальновиробничі витрати
Загальновиробничі витрати відносяться до непрямих і включають
витрати, пов’язані з утриманням та експлуатацією будівель і споруд
виробничого призначення і визначаються пропорційно до витрат на основну
заробітну плату за формулою:
Взаг.вир. = Зосн.∙(Пзаг.вир./100%)
(4.12)
де Зосн. – витрати на основну заробітну плату;
Пзаг.вир. – відсоток витрат на утримання та експлуатацію обладнання
(на базовому підприємстві складає 80%).
Взаг.вир. = 1092,14 * 0,8 = 873,71 грн.
4.7 Матеріальні витрати
До матеріальних витрат відносяться витрати на матеріали та
комплектуючі, транспотно-заготівельні витрати, а також витрати на
електроенергію під час монтажних та налагоджувальних робіт.
Витрати на матеріали та комплектуючі розраховуються за формулою:
Вм = ∑Цмі ∙Нмі,
де Вм, Вк – витрати відповідно на матеріали та комплектуючі;
Цмі – ціна відповідно за одиницю і-го матеріалу;
Нмі – норма витрат відповідно матеріалу.
Вм. = 40 + 5 + 70 = 115 грн.
(4.13)
64
Всі розрахунки зводяться до таблиці 4.4.
Таблиця 4.4 – Витрати на матеріали та комплектуючі
Найменування матеріалів
Одиниці
Кількість
Ціна
та комплектуючих
виміру
(грн.)
Папір
пачка
1
40
Диск CD-RW
шт.
1
5
Картридж для принтера
шт.
1
70
Всього
3
115
Вартість
(грн.)
40
5
70
115
Вся сума матеріальних витрат розраховується за формулою:
Вмат = Вм + Вк + Втз + Вел
(4.14)
де Вм – витрати на матеріали;
Вк – витрати на комплектуючі;
Втз – транспортно-заготівельні витрати;
Вел – витрати на електроенергію для монтажних та налагоджувальних
робіт.
Після підрахунку можна побачити, що витрати на матеріали склали
Вмат. = 115 грн.
4.8 Калькуляція собівартості
Калькуляція – це розрахунок собівартості одиниці продукції,
виконаних робіт та послуг. При калькулюванні встановлюють об’єкти
калькулювання, вибирають калькуляційні одиниці, визначають калькуляційні
статті витрат та методики їх обчислення.
Об’єкт калькулювання – продукція (робота, послуга), собівартість якої
обчислюється. Для кожного об’єкта калькулювання вибирається
калькуляційна одиниця – одиниця його кількісного вимірювання (штуках,
тоннах, кіловат-годинах тощо).
При калькулюванні продукції (робіт, послуг) витрати групуються за
калькуляційними статтями, перелік і склад яких установлюється
підприємством самостійно.
Згідно типового положення для більшості підприємств, виробнича
собівартість групується за наступними калькуляційними статтями і
65
визначається за формулою:
Свир = Вм + Зосн + Здод + Всоц.з. + Ву.е. + Взаг.вир.
(4.15)
де Вм – сума витрат на матеріали та комплектуючі;
Зосн – основна заробітна плата;
Здод – додаткова заробітна плата;
Всоц.з. – відрахування на соціальні заходи;
Ву.е. – витрати на утримання та експлуатацію обладнання;
Взаг.вир. – Загальновиробничі витрати.
Свир. = 115 + 1092,14 + 546,07 + 627,43+ 169 + 873,71= 3423,35 грн.
Групування витрат за статтями калькуляції та визначення виробничої
собівартості зводиться до таблиці 4.5.
Таблиця 4.5 – Калькуляція собівартості
№
п/п
1
Найменування статей витрат
Витрати на матеріали та комплектуючі
2
3
4
5
6
7
Основна заробітна плата
Додаткова заробітна плата
Відрахування на соціальні заходи
Витрати на утримання та експлуатацію обладнання
Загальновиробничі витрати
Виробнича собівартість
Позначення статті
Вм
Зосн
Здод
Всоц.з.
Ву.е.о.
Взаг.вир.
Свир
Сума,
грн
115
1092,14
546,07
627,43
169
873,71
3423,35
4.9 Обґрунтування економічної доцільності наданих пропозицій
Якщо обґрунтування економічної доцільності техніко-організаційних
нововведень потребує більш повного визначення затрат, а також ціни на
виконання даного виду робіт, то проводяться розрахунки показників повної
собівартості, оптової та відпускної ціни.
Повна
собівартість включає окрім виробничої собівартості
адміністративні витрати та витрати на збут і визначається за формулою:
С пов = С вир + Вадм + Взб
(4.16)
66
де Свир – виробнича собівартість;
Вадм – адміністративні витрати (непряма комплексна стаття витрат,
яка включає витрати, пов’язані з утриманням апарату управління;
утриманням транспортних мереж і мереж зв’язку і визначаються за
формулою:
Вад = Зосн∙( %Вад / 100)
(4.17)
де Зосн – основна заробітна плата;
%Вадм – процент відрахувань на адміністративні витрати (близько 80%
основної заробітної плати основних робітників).
Взб = Свир ∙ (%Взб / 100)
(4.18)
де Свир – виробнича собівартість;
%Взб – процент відрахувань на витрати на збут (близько 3 – 5% Свир).
Спов. = 3423,35 + 873,71 + 171,17 = 4468,23 грн.
Вад. = 1092,14* 0,8 = 873,71 грн.
Взб. = 3423,35 * 0,05 = 171,17 грн.
Оптова ціна визначається за формулою:
Цопт = Спов + П ,
(4.19)
де Спов – повна собівартість;
П – прибуток, який дорівнює: П = 0,5 * Спов.
Цопт. = 4468,23 + (0,5 * 4468,23) = 6702,35 грн.
Відпускна ціна визначається за формулою:
Цвідп = Цопт + ПДВ;
(4.20)
де Цопт – оптова ціна;
ПДВ – податок на додану вартість:
ПДВ=20% ∙ Цопт
(4.21)
67
ПДВ = 0.2 * 6702,35 = 1340,47 грн.
Цвідп = 1340,47 + 6702,35 = 8042,82 грн.
Обґрунтування економічної доцільності виконання даного виду робіт
власними спеціалістами проводимо шляхом порівняння витрат на ці роботи
(собівартості) із ринковою вартістю аналогічних робіт (послуг). При цьому
економію розраховуємо за формулою:
Е = Ц – С,
(4.22)
де Ц – ціна аналогічної роботи (послуги) на ринку;
С – виробнича собівартість на даний вид робіт (послуг).
Отриманий розмір економії і є підтвердженням економічної вигоди і
доцільності виконання даних робіт власними спеціалістами.
Е = 8042,82 – 3423,35 = 4619,47 грн.
68
5 ОХОРОНА ПРАЦІ
У даній дипломній роботі в розділі охорони праці винесено питання:
«Чинники, які впливають на тяжкість ураження людини електричним
електрострумом». На даний момент електробезпека одне із найважливіших
питань на виробництві, так як порушення правил безпеки поводження з
електрострумом приводить до нещасних і навіть фатальних наслідків.
5.1 Основні поняття електробезпеки
Електробезпека — це система організаційних та технічних заходів і
засобів, що забезпечують захист людей від шкідливого та небезпечного
впливу електричного струму, електричної дуги, електромагнітного поля і
статичної електрики.
Електротравма — це травма, викликана дією електричного струму або
електричної дуги. Електротравми поділяються на два види: струмові і
дугові.
Електротравматизм — це явище, котре характеризується сукупністю
електротравм, котрі виникають та повторюються в аналогічних виробничих,
побутових умовах та ситуаціях. Осередок, джерело електротравматизму — та
чи інша тимчасова або навіть постійна ситуація при експлуатації
електроустановок, коли мають місце аналогічні випадки ураження людини
струмом.
Проходячи через тіло людини, електричний струм справляє термічну,
електричну та механічну (динамічну) дію. Ці фізико-хімічні процеси
притаманні живій та неживій матерії. Одночасно електричний струм
здійснює і біологічну дію, котра є специфічним процесом, властивим лише
живій тканині.
Термічна дія струму проявляється через опіки окремих ділянок тіла,
нагрівання до високої температури кровоносних судин, нервів, серця, мозку
та інших органів, котрі знаходяться на шляху струму, що викликає в них
суттєві функціональні розлади.
Електролітична дія струму характеризується розкладом органічної
рідини, в тому числі і крові, що супроводжується значними порушеннями їх
фізико-хімічного складу.
Механічна (динамічна) дія — це розшарування, розриви та інші подібні
ушкодження тканин організму, в тому числі м’язової тканини, стінок
69
кровоносних судин, судин легеневої тканини внаслідок електродинамічного
ефекту, а також миттєвого вибухоподібного утворення пари від перегрітої
струмом тканинної рідини та крові.
Біологічна дія струму проявляється через подразнення та збудження
живих тканин організму, а також через порушення внутрішніх біологічних
процесів, що відбуваються в організмі і котрі тісно пов’язані з його
життєвими функціями.
5.2 Види електричних травм
Різноманітність впливу електричного струму на організм людини
призводять до електротравм, котрі умовно поділяються на два види:
місцеві електротравми, котрі означають місцеве ушкодження
організму;
загальні електротравми (електричні удари), коли уражається (або
виникає загроза ураження) весь організм внаслідок порушення
нормальної діяльності життєво важливих органів та систем.
Згідно зі статистичними даними орієнтовний розподіл нещасних
випадків внаслідок дії електричного струму в промисловості за вказаними
видами травм має наступний вигляд:
місцеві електротравми - 20%;
електричні удари - 25%;
змішані травми (одночасно місцеві електричні травми та
електричні удари) - 55%.
Місцева електротравма - яскраво виявлене порушення щільності
тканин тіла, в тому числі кісток, викликане впливом електричного струму або
електричної дуги. Найчастіше - це поверхневі ушкодження, тобто
ушкодження шкіри, а інколи й інших м’яких тканин, зв’язок та кісток.
Небезпека місцевих електротравм та складність їх лікування залежать від
місця, характеру та ступеня ушкодження тканин, а також від реакції
організму на це ушкодження. Місцеві електротравми виліковуються і
працездатність потерпілого відновлюється повністю або частково. Однак при
важких опіках людина помирає. При цьому безпосередньою причиною
смерті є не електричний струм, а місцеве ушкодження організму, викликане
струмом. Характерні місцеві електротравми-електричні опіки, електричні
знаки, металізація шкіри, механічні пошкодження та електроофтальмія.
Приблизно 75% випадків ураження людей струмом супроводжується
виникненням місцевих електротравм.
70
За видами травм ці випадки розподіляються наступним чином, %:
електричні опіки - 40;
електричні знаки - 7;
металізація шкіри - 3;
механічні пошкодження - 0,5;
електрофтальмія - 1,5;
змішані травми - 23;
всього - 75.
Електричні опіки - це ушкодження поверхні тіла під дією електричної
дуги або великих струмів, що проходять через тіло людини. Опіки бувають
двох видів: струмові, копи струм проходить через тіло людини, та дугові (під
дією електричної дуги температурою понад 3500 °С).
Електричний знак - це чітко окреслена пляма діаметром 1-5 мм сірого
або блідо-жовтого кольору, що з’являється на поверхні шкіри людини, яка
зазнала дії струму. В більшості випадків електричні знаки безболісні, з часом
верхній шар шкіри сходить, а уражене місце набуває початкового кольору,
відновлює пластичність та чутливість.
Електрометалізація - проникнення в шкіру частинок металу внаслідок
його розбризкування та випаровування під дією струму. Вона може статися
при коротких замиканнях, від’єднаннях роз’єднувачів та рубильників під
навантаженням. При цьому дрібні частинки розплавленого металу під
впливом динамічних сил та теплового потоку розлітаються у всі сторони з
великою швидкістю. Кожна з цих частинок має високу температуру, але
малий запас теплоти, і тому не здатна пропалити одяг. Тому ушкоджуються
відкриті частини тіла - руки та обличчя. Уражена ділянка тіла має шорстку
поверхню.
З плином часу хвора шкіра сходить, уражена ділянка набуває
нормального вигляду та еластичності, зникають і всі хворобливі відчуття,
пов’язані з цією травмою. Лише при пошкодженні очей лікування може
виявитись тривалим та складним, а в деяких випадках потерпілий може
позбутись зору. Тому роботи, при котрих можливе виникнення електричної
дуги, повинні виконуватись в захисних окулярах. Металізація шкіри
спостерігається у 10% потерпілих від електричного струму. Одночасно з
металізацією виникає дуговий опік, котрий майже завжди викликає більш
важкі ураження, ніж металізація.
Механічні ушкодження є в більшості випадків наслідком різких
судомних скорочень м’язів під впливом струму, котрий проходить через тіло
людини. Внаслідок цього можуть відбутися розриви сухожиль, шкіри,
71
кровоносних судин та нервової тканини і навіть переломи кісток.
Електротравмами не вважаються аналогічні травми, викликані падінням
людини з висоти, ударами об предмети внаслідок впливу струму. Механічні
ушкодження мають місце при роботі в установках напругою до 1000 В при
тривалому перебуванні людини під напругою. Механічні ушкодження
виникають приблизно у 1% осіб, що зазнали впливу струму. Такі
ушкодження завжди створюють електричні удари, оскільки їх викликає
струм, що проходить через тіло людини. Деякі з них супроводжуються, крім
того, контактними опіками тіла. На ступінь ураження людини струмом
істотно впливають рід та величина струму, час його дії, шлях по тілу людини.
Електроофтальмія - це запалення зовнішніх оболонок очей, що
виникає під впливом потужного потоку ультрафіолетових променів. Таке
опромінення можливе при утворенні електричної дуги (при короткому
замиканні). Електроофтальмія спостерігається приблизно у 3% потерпілих
від струму.
Інфрачервоні (теплові) промені також шкідливі для очей, але лише на
близькій відстані або при інтенсивному і тривалому опроміненні. У випадку
ж короткотривалої дуги основним фактором, що впливає на очі, є
ультрафіолетові промені, хоч і в цьому випадку не виключена небезпека
ураження очей інфрачервоними променями, а також потужним потоком
світла та бризками розплавленого металу.
Електроофтальмія
розвивається
через
4-8
годин
після
ультрафіолетового опромінення. При цьому мають місце почервоніння та
запалення шкіри, слизових оболонок повік, сльози, гнійні виділення з очей,
судоми повік та часткова втрата зору. Потерпілий відчуває головний біль та
різкий біль в очах, що посилюється на світлі.
Запобігання електроофтальмії при обслуговуванні електроустановок
забезпечується застосуванням захисних окулярів зі звичайним склом, котре
майже не пропускає ультрафіолетових променів і одночасно захищає очі від
інфрачервоного опромінення та бризок розплавленого металу при
виникненні електричної дуги.
Електричний удар - збудження живих тканин організму електричним
струмом, що супроводжується судомним скороченням м’язів. Такий удар
може призвести до порушення і навіть повного припинення роботи легенів та
серця. При цьому зовнішніх місцевих ушкоджень, тобто електричних травм,
людина може і не мати.
Ступінь негативного впливу на організм електричних ударів різний.
Найслабший електричний удар викликає ледь відчутні скорочення м’язів
72
поблизу місця входу або виходу струму. Може порушитись і навіть
припинитися діяльність легенів та серця, тобто призвести до загибелі
організму.
В залежності від наслідку ураження електричні удари можна умовно
розділити на 5 ступенів:
I - судомні ледь відчутні скорочення м’язів;
II - судомні скорочення м’язів, що супроводжуються сильним болем,
що ледь переноситься без втрати свідомості;
III - судомне скорочення м’язів з втратою свідомості, але зі
збереженням дихання і роботи серця;
IV - втрата свідомості та порушення серцевої діяльності або дихання
(або одного і другого разом);
V - клінічна смерть, тобто відсутність дихання та кровообігу.
5.3 Фактори, що впливають на наслідки ураження електричним
струмом
Сила струму. Зі зростанням сили струму небезпека ураження ним тіла
людини зростає. Розрізняють порогові значення струму (при частоті 50 Гц):
пороговий відчутний струм - 0,5-1,5 мА при змінному струмі і
5-7 мА при постійному струмі;
пороговий невідпускний струм (струм, що викликає при
проходженні через тіло людини нездоланні судомні скорочення м’язів
руки, в котрій затиснений провідник) - 10-15 мА при змінному струмі і 50-80
мА при постійному струмі;
пороговий фібриляційний струм (струм, що викликає при
проходженні через організм фібриляцію серця) - 100 мА при змінному
струмі і 300 мА при постійному струмі.
Опір тіла людини проходженню струму. Електричний опір тіла людини
- це опір струму, котрий проходить по ділянці тіла між двома електродами,
прикладеними до поверхні тіла. Він складається з опору тонких зовнішніх
шарів шкіри, котрі контактують з електродами, і з опору внутрішніх тканин
тіла. Найбільший опір струму чинить шкіра. На місці контакту електродів з
тілом утворюється своєрідний конденсатор, однією обкладкою котрого є
електрод, другою - внутрішні струмопровідні тканини, а діелектриком зовнішній
шар
шкіри.
Електричні
властивості
конденсатора
характеризуються напругою, на котру він розрахований, та його ємністю.
Ємність конденсатора - відношення його заряду до напруги, при котрій він
73
може отримати даний заряд.
Таким чином, опір тіла людини складається з ємнісного та активного
опорів. Величина електричного опору тіла залежить від стану рогового шару
шкіри, наявності на її поверхні вологи та забруднень, від місця прикладання
електродів, частоти струму, величини напруги, тривалості дії струму.
Ушкодження рогового шару (порізи, подряпини, волога, потовиділення)
зменшують опір тіла, а відтак - збільшують небезпеку ураження. Опір тіла
людини в практичних розрахунках приймається рівним 1000 Ом.
5.4 Вид та частота струму
Змінний струм. Через наявність в опорі тіла людини ємнісної складової
зростання частоти прикладеної напруги супроводжується зменшенням
повного опору тіла та зростанням струму, що проходить через тіло людини.
Можна було б припустити, що зростання частоти призведе до підвищення
цієї небезпеки. Однак це припущення справедливе лише в діапазоні частот до
50 Гц. Подальше ж підвищення частоти, незважаючи на зростання струму,
що проходить через людину, супроводжується зниженням небезпеки
ураження, котра повністю зникає при частоті 450-500 Гц, тобто струм такої
та більшої частоти - не може викликати смертельного ураження внаслідок
припинення роботи серця або легенів, а також інших життєво важливих
органів. Однак ці струми зберігають небезпеку опіків при виникненні
електричної дуги та при проходженні їх безпосередньо через тіло людини.
Значення фібриляційного струму при частотах 50-100 Гц практично однакові;
при частоті 200 Гц фібриляційний струм зростає приблизно в два рази в
порівнянні з його значенням при 50-100 Гц, а при частоті 400 Гц-більше, ніж
в 3 рази.
Постійний струм. Постійний струм приблизно в 4-5 разів безпечніший,
ніж змінний струм частотою 50 Гц. Цей висновок випливає з порівняння
значень порогових невідпускаючих струмів (50 - 80 мА для постійного та 1015 мА для струму частотою 50 Гц) і гранично витримуваних напруг: людина,
тримаючи циліндричні електроди в руках, в змозі витримати (за больовими
відчуттями) прикладену до неї напругу не більше 21-22 В при 50 Гц і не
більше 100-105 В для постійного струму. Постійний струм, проходячи через
тіло людини, викликає слабші скорочення м’язів і менш неприємні відчуття
порівняно зі змінним того ж значення. Лише в момент замикання і
розмикання ланки струму людина відчуває короткочасні болісні відчуття
внаслідок судомного скорочення м’язів. Порівняльна оцінка постійного та
74
змінного струмів справедлива лише для напруг до 500 В. Вважається, що при
більш високих напругах постійний струм стає небезпечнішим, ніж змінний
частотою 50 Гц.
Тривалість проходження струму через організм істотно впливає на
наслідок ураження: зі зростанням тривалості дії струму зростає ймовірність
важкого або смертельного наслідку. Така залежність пояснюється тим, що зі
зростанням часу впливу струму на живу тканину підвищується його
значення, накопичуються наслідки впливу струму на організм. Зростає також
імовірність співпадання моменту проходження струму через серце з
уразливою фазою серцевого циклу (кардіоциклу). Зростання сили струму зі
зростанням часу його дії пояснюється зниженням опору тіла людини
внаслідок місцевого нагрівання шкіри та подразнювальної дії на тканини. Це
викликає рефлекторну, тобто через центральну нервову систему, швидку
зворотну реакцію організму у вигляді розширення судин шкіри, а відтак посилення постачання її кров’ю і підвищення потовиділення, що й
призводить до зниження електричного опору шкіри в цьому місці.
Наслідки впливу струму на організм полягають в порушенні функцій
центральної нервової системи, зміні складу крові, місцевому руйнуванні
тканин організму під впливом тепла, що виділяється, в порушенні роботи
серця, легенів. Зі зростанням часу дії струму ці негативні фактори
накопичуються, а згубний їх вплив на стан організму посилюється.
Встановлено, що чутливість серця до електричного струму неоднакова
протягом різних фаз його діяльності. Найбільш уразливе серце в фазі Т,
тривалість котрої близько 0,2 с. Тому, якщо протягом фази Т через серце
проходить струм, то при деякому його значенні виникає фібриляція серця.
Якщо ж час проходження цього струму не співпадає з фазою Т, то
ймовірність фібриляції різко знижується.
Шлях протікання струму через людину. Практика та експерименти
показують, що шлях протікання струму через тіло людини має велике
значення з огляду на. наслідки ураження. Якщо на шляху струму
виявляються життєво важливі органи - серце, легені, головний мозок, то
небезпека ураження досить велика, оскільки струм безпосередньо впливає на
ці органи. Якщо ж струм проходить іншими шляхами, то його вплив на
життєво важливі органи може бути лише рефлекторним, а не безпосереднім.
При цьому, хоч небезпека важкого ураження і зберігається, але ймовірність
його знижується. До того ж, оскільки шлях струму визначається місцем
прикладання струмопровідних частин (електродів) до тіла потерпілого, то
його вплив на наслідок ураження зумовлюється ще й різним опором шкіри на
75
різних ділянках шкіри.
Індивідуальні властивості людини. Відомо, що здорові та фізично міцні
люди легше переносять електричні удари, ніж хворі та слабкі. Особливо
сприйнятливими до електричного струму є особи, котрі нездужають на
захворювання шкіри, серцево-судинної системи, органів внутрішньої
секреції, легенів, мають нервові хвороби.
Важливе значення має психічна підготовленість до можливої небезпеки
ураження струмом. В переважній більшості випадків несподіваний
електричний удар навіть за низької напруги призводить до важких наслідків.
Проте за умови, коли людина очікує удару, то ступінь ураження значно
знижується. В цьому контексті великого значення набувають ступінь уваги,
зосередженість людини на виконуваній роботі, втома. Кваліфікація людини
також суттєво відбивається на наслідках впливу електричного струму.
Досвід, вміння адекватно оцінити ситуацію щодо небезпеки, що виникла, а
також застосувати раціональні способи звільнення від струму дозволяють
уникнути важкого ураження. В зв’язку з цим правила техніки безпеки
передбачають обов’язкову медичну перевірку персоналу, котрий обслуговує
електроустановки при початку роботи та періодичні перевірки.
Висновок. Після детального ознайомлення із даним розділом можна
зробити висновок, що потрібне не нехтувати елементарними правилами
техніки безпеки при роботи із електричним струмом. Постійне зростає
виробництво та споживання електроенергії, а відтак і кількість людей, які в
процесі своєї життєдіяльності використовують (експлуатують) електричні
пристрої та установки. Тому питання електробезпеки набувають особливої
ваги.
76
ВИСНОВКИ
В ході розробки даної дипломної роботи були проаналізовані
можливості і створено тривимірний додаток з використанням 3D графіки на
основі технології OPENGL. Спочатку була зібрана інформація по
можливостях реалізації конкретних методів. Проаналізувавши тенденції у
використанні 3D графіки було вирішено створити ігровий додаток „3D
Танк”. У даній програмі модульовано ігровий простір з використанням
різноманітних ландшафтів, дерев, рослинності, доріг, води, споруд, ефектів
диму та вогню. Користувачеві надається можливість вибирати режими
настройки відео, аудіо, управління за допомогою інтерактивного меню.
Впровадження розробленого програмного продукту є економічно вигідним.
Доцільніше розробку та створення даного додатку зробити власноруч, тому
що ця робота буде коштувати на ринку приблизно 8042,82 гривень. А
створити її на своєму підприємстві коштує 4619,47 гривень.
Також в ході розробки були розглянуті чинники, які впливають на
тяжкість ураження людини електричним електрострумом. На даний момент
електробезпека одне із найважливіших питань на виробництві, так як
порушення правил безпеки поводження з електрострумом приводить до
нещасних і навіть фатальних наслідків.
77
ПЕРЕЛІК ПОСИЛАНЬ
1. Андре Ламот „Программирование игр для Windows. Советы
профессионала”, 2-е издание, 2004. – 881 с;
2. Андре Ламот „Программирование трехмерных игр для Windows.
Советы профессионала по трехмерной графике и растеризации”, 2004. – 1422
с.;
3. Randi J. Rost “OpenGL® Shading Language”, 2006. – 800c.;
4. Михаил Краснов ”OpenGL. Графика в проектах Delphi”, 2002. –
275c.;
5. Френсис Хилл “OpenGL. Программирование компьютерной графики.
Для профессионалов”, 2002. – 1088c.;
6. Кандзюба С. П. Громов В. “Delphi 6/7 Базы данных и приложения.”,
2004. – 527c.;
7. Грибачев К.Г. “Delphi и Model Driven Architecture”, 2004. – 348c.;
8. П. Дарахвелидзе и Е. Маркова “Иллюстрированный самоучитель по
Delphi 7 для профессионалов”, 2005. – 740c.;
9. Петр Дарахвелидзе, Евгений Марков “Программирование в
Delphi 7”, 2003. – 854c.;
10. Дмитрий Кузан, Владимир Шапоров “Программирование Win32
API в Delphi”, 2005. – 476c.;
11. Галисеев Г.В. “Программирование в среде Delphi 8 for .NET.
Самоучитель”, 2004. – 563c.;
12. Валерий Фаронов “Delphi 2005. Разработка приложений для баз
данных и Интернета”, 2006 – 608c.;
13. Чарльз Калверт “Delphi 2. Энциклопедия пользователя”, 1996. –
736c.;
14. Виктор Пестриков, Артур Маслобоев “Delphi на примерах”, 2005. –
496c.;
15. Василий Корняков “Программирование документов и приложений
MS Office в Delphi”, 2005. – 496c.;
16. Культин Н.Б. “Delphi 6. Программирование на Object pascal”, 2001.
– 526c.;
17. В.Пономарев “COM и ActiveX в Delphi”, 2001. – 320c.;
18. Рэй Конопка “Создание оригинальных компонент в среде Delphi”,
1996. – 512c.;
78
19. Юрий Ревич “Нестандартные приемы програмирования на
DELPHI”, 2002. – 365c.;
20. Евгений Марков, Владимир Никифоров “Delphi 2005 для .NET”,
2005. – 896c.;
21. В. В. Шупрута “Delphi 2005. Учимся программировать”, 2005. –
352c.;
22. Михаил Фленов “Delphi 2005. Секреты программирования”, 2005. –
272c.;
23. Михаил Фленов “Программирование в Delphi глазами хакера”,
2003, – 362c.;
24. www.gamedev.ru
25. www.3dcenter.ru
26. www.delphisourses.ru
27. www.delphiworld.narod.ru
28. www.aimatrix.nm.ru
29. www.tuman-delphi.narod.ru
30. www.citforum.ru/programming/delphi
31. www.delphi.int.ru
32. www.delphi.vov.ru
33. www.wcs.ru
34. www.delphid.dax.ru
35. www.delphirus.com.ru
36. www.delphimaster.ru
Download