Development/ru: Difference between revisions

From DDraceNetwork
Created page with "Прежде всего, DDNet написан с использованием языка программирования C++, вам необходимо быть достаточно знакомым с ним, но вы также можете знать основы и научиться большему с его помощью."
 
Был пропущен символ
 
(28 intermediate revisions by 3 users not shown)
Line 1: Line 1:
{{MigrateTranslation}}
<languages />
<languages/>
 
Цель этой статьи - познакомить вас с DDNet '''''разработкой''''', поскольку это игра с открытым исходным кодом, она полагается на случайных людей, готовых внести в нее свой вклад в свободное время.
Цель этой статьи - познакомить вас с DDNet '''''разработкой''''', поскольку это игра с открытым исходным кодом, она полагается на случайных людей, готовых внести в нее свой вклад в свободное время.


Line 12: Line 12:
* Эта статья пока не имеет версии для Windows и ориентирована на Linux.
* Эта статья пока не имеет версии для Windows и ориентирована на Linux.


Прежде всего, DDNet написан с использованием языка программирования C++, вам необходимо быть достаточно знакомым с ним, но вы также можете знать основы и научиться большему с его помощью.
Прежде всего, DDNet написан на языке программирования C++, и вам потребуется достаточно глубокое знакомство с ним, но вы также можете узнать основы и научиться большему с его помощью.


Некоторые полезные ресурсы для изучения C++:
Некоторые полезные ресурсы для изучения C++:
Line 39: Line 39:
Для Arch Linux:
Для Arch Linux:


<code>sudo pacman -S --needed base-devel cmake curl freetype2 git glew gmock libnotify opusfile python sdl2 sqlite wavpack</code>
<syntaxhighlight lang="bash">
sudo pacman -S --needed base-devel cmake curl ffmpeg freetype2 git glew glslang gmock libnotify libpng opusfile python rust sdl2 spirv-tools sqlite vulkan-headers vulkan-icd-loader wavpack x264
</syntaxhighlight>
 
Для Debian:


<syntaxhighlight lang="bash">
sudo apt install build-essential cargo cmake git glslang-tools google-mock libavcodec-extra libavdevice-dev libavfilter-dev libavformat-dev libavutil-dev libcurl4-openssl-dev libfreetype6-dev libglew-dev libnotify-dev libogg-dev libopus-dev libopusfile-dev libpng-dev libsdl2-dev libsqlite3-dev libssl-dev libvulkan-dev libwavpack-dev libx264-dev python3 rustc spirv-tools
</syntaxhighlight>


<span id="Compiling_DDNet"></span>
<span id="Compiling_DDNet"></span>
Line 67: Line 74:
== Расположение исходного кода ==
== Расположение исходного кода ==


Теперь, когда вы можете создать DDNet, вы можете приступить к его редактированию.
Теперь, когда вы можете собрать DDNet, вы можете приступить к его редактированию.




Line 97: Line 104:
К числу важных структур относятся:
К числу важных структур относятся:


* [https://github.com/ddnet/ddnet/blob/master/src/game/server/entities/character.h CCharacter]: Представляет собой [[Special:MyLanguage/Common_Terminology#Tee|тии]], который является живым, он создается при порождении тии и удаляется при его смерти. Информацию о том, как игрок сохраняется между смертями, см. в [https://github.com/ddnet/ddnet/blob/master/src/game/server/player.h CPlayer].
*[https://github.com/ddnet/ddnet/blob/master/src/game/server/entities/character.h CCharacter]: Представляет собой [[Special:MyLanguage/Common_Terminology#Tee|тии]], который жив, он создаётся при спавне тии и удаляется при его смерти.
* [https://github.com/ddnet/ddnet/blob/master/src/game/server/player.h CPlayer] содержит информацию, не относящуюся к [[Common Terminology/fr#Tee|Тии]] (никнейм, флаг, и тд).




Line 103: Line 111:
==== Клиентская сторона ====
==== Клиентская сторона ====


Клиентская сторона состоит из компонентов, это классы, которые наследуют <code>CComponent</code>: Эти компоненты могут реализовывать виртуальные методы, такие как <code>OnInit</code>, <code>OnMessage</code> и т.д., чтобы обеспечить их функциональность.
Клиентская часть состоит из компонентов - классов, наследующих [https://github.com/ddnet/ddnet/blob/master/src/game/client/component.h CComponent], определенных в <code>src/game/client/component.h</code>. Эти компоненты могут реализовывать виртуальные методы, такие как <code>OnInit</code>, <code>OnMessage</code> и т.д, для обеспечения их функциональности.




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Networking"></span>
==== Networking ====
==== Сетевое взаимодействие ====
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Сетевой протокол в основном генерируется скриптами python, которые выводят код C++, например, <code>datasrc/network.py</code> определяет все сетевые пакеты.
The network protocol is mostly generated by python scripts that output C++ code, for example, <code>datasrc/network.py</code> defines all network packets.
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Code_conventions"></span>
== Code conventions ==
== Кодовые конвенции ==
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Продолжающаяся дискуссия о кодовых соглашениях находится здесь: [https://github.com/ddnet/ddnet/issues/2945 ddnet#2945].
The ongoing discussion on code conventions is located here: [https://github.com/ddnet/ddnet/issues/2945 ddnet#2945]
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
В настоящее время применяется следующее:
Currently, the following applies:
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Indentation_style"></span>
=== Indentation style ===
=== Indentation стиль ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
[https://en.wikipedia.org/wiki/Indentation_style#Allman_style Allman style] используется.
[https://en.wikipedia.org/wiki/Indentation_style#Allman_style Allman style] is used.
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<blockquote>
<blockquote>
This style puts the brace associated with a control statement on the next line, indented to the same level as the control statement. Statements within the braces are indented to the next level.
Этот стиль помещает скобку, связанную с управляющим оператором, на следующую строку с отступом на том же уровне, что и управляющий оператор. Утверждения внутри скобок отступают на следующий уровень.
</blockquote>
</blockquote>
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
while(x == y)
while(x == y)
Line 149: Line 143:
     SomethingElse();
     SomethingElse();
}
}
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
FinalThing();
Finalthing();
</syntaxhighlight>
</syntaxhighlight>
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Classes_and_Structs"></span>
=== Classes and Structs ===
=== Классы и структуры ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Должен иметь префикс <code>C</code> (по устаревшим причинам это игнорируется для структур в некоторых местах, например, в графическом коде) или <code>I</code> для интерфейсов. Новая структуры должны иметь префикс <code>S</code>.
Must be prefixed by <code>C</code> (for legacy reasons this is ignored for structs in some places, such as in graphics code) or <code>I</code> for interfaces. New <code>struct</code>s should be prefixed by <code>S</code>.
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Пример:
Example:
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
class CCharacter : public CEntity
class CCharacter : public CEntity
Line 176: Line 160:
}
}
</syntaxhighlight>
</syntaxhighlight>
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Enums_and_constants"></span>
=== Enums and constants ===
=== Перечисления и константы ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Должен быть ''screaming snake case [https://en.wikipedia.org/wiki/Snake_case]'', например: <code>MAX_PLAYERS</code>
Should be screaming snake case, for example: <code>MAX_PLAYERS</code>
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
enum
enum
Line 200: Line 179:
};
};
</syntaxhighlight>
</syntaxhighlight>
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Variable_naming"></span>
=== Variable naming ===
=== Именование переменных ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
* Имена переменных содержат 3 части: классификатор, префикс и имя.
* The names of variables contain 3 parts: qualifier, prefix and name.
* Имена переменных должны начинаться с прописной буквы, если только они не имеют длину в 1 символ без какого-либо префикса или определителя, например: <code>i</code>, <code>x</code>, <code>y</code>.
* Variable names should start with uppercase unless they are 1 char long without any prefix or qualifier, for example: <code>i</code>, <code>x</code>, <code>y</code>.
* Переменные могут иметь более 1 классификатора (или нуля) и более 1 префикса (или нуля).
* Variables can have more than 1 qualifier (or zero) and more than 1 prefix (or zero).
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Они расположены следующим образом: <code>[qualifiers]_[prefixes][Name]</code>
These are laid out like this: <code>[qualifiers]_[prefixes][Name]</code>
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Qualifiers"></span>
==== Qualifiers ====
==== Классификаторы ====
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
* <code>m</code> для переменных-членов: <code>m_MyVariable</code>.
* <code>m</code> for member variables: <code>m_MyVariable</code>.
* <code>s</code> для статических переменных: <code>s_MyStaticVariable</code>, <code>ms_MyStaticMemberVariable</code>.
* <code>s</code> for static variables: <code>s_MyStaticVariable</code>, <code>ms_MyStaticMemberVariable</code>.
* <code>g</code> для глобальных переменных с внешней связью: <code>gs_MyGlobalStaticVar</code>.
* <code>g</code> for global variables with external linkage: <code>gs_MyGlobalStaticVar</code>.
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Prefixes"></span>
==== Prefixes ====
==== Префиксы ====
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
* <code>p</code> для указателей: <code>pMyPointer</code>, <code>m_pCharacter</code>, <code>ppMyPointerToPointer</code>.
* <code>p</code> for pointers: <code>pMyPointer</code>, <code>m_pCharacter</code>, <code>ppMyPointerToPointer</code>.
* <code>a</code> для массивов: <code>aMyArray</code>, <code>aBuf</code>.
* <code>a</code> for arrays: <code>aMyArray</code>, <code>aBuf</code>.
* <code>v</code> для <code>std::vector</code>s: <code>vMyVector</code>, <code>vpvMyVectorOfPointersToVectors</code>.
* <code>v</code> for <code>std::vector</code>s: <code>vMyVector</code>, <code>vpvMyVectorOfPointersToVectors</code>.
* <code>fn</code> для функций: <code>pfnMyCallback</code>, <code>m_papfnMyPointerToArrayOfCallbacks</code>.
* <code>fn</code> for functions: <code>pfnMyCallback</code>, <code>m_papfnMyPointerToArrayOfCallbacks</code>.
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Common_snippets"></span>
== Common snippets ==
== Общие фрагменты ==
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Вот список кода, который вы можете часто встретить в кодовой базе:
Here is a list of code that you may frequently see across the codebase:
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Formatting_text"></span>
=== Formatting text ===
=== Форматирование текста ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
char aBuf[128];
char aBuf[128];
str_format(aBuf, sizeof(aBuf), "number: %d", 2);
str_format(aBuf, sizeof(aBuf), "number: %d", 2);
</syntaxhighlight>
</syntaxhighlight>
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Список всех спецификаторов форматирования см. в [https://cplusplus.com/reference/cstdio/printf/ документации по printf].
=== Iterating over all players ===
=== Итерация по всем игрокам ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
for(int i = 0; i < MAX_CLIENTS; i++)
for(int i = 0; i < MAX_CLIENTS; i++)
Line 274: Line 232:
}
}
</syntaxhighlight>
</syntaxhighlight>
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Printing_to_the_game_console"></span>
=== Printing to the game console ===
=== Печать на игровой консоли ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "wikiprint", "Hello from the ddnet wiki!");
Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "wikiprint", "Hello from the ddnet wiki!");
</syntaxhighlight>
</syntaxhighlight>
</div>




<div lang="en" dir="ltr" class="mw-content-ltr">
<span id="Debug_printing"></span>
=== Debug printing ===
=== Отладочная печать ===
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
<syntaxhighlight lang="cpp">
<syntaxhighlight lang="cpp">
int i = 2;
int i = 2;
dbg_msg("wikiprint", "Hello from the ddnet wiki: %d", i);
dbg_msg("wikiprint", "Hello from the ddnet wiki: %d", i);
</syntaxhighlight>
</syntaxhighlight>
</div>


=== Перевод текста в клиенте ===
<code>Localize</code> можно использовать в клиенте игры, чтобы получить перевод для определенной строки из языкового файла, выбранного пользователем.
<syntaxhighlight lang="cpp">
DoButton(..., Localize("Connect"), ...);
</syntaxhighlight>Строка может также содержать спецификаторы формата. Переведенная строка должна содержать те же спецификаторы форматирования.<syntaxhighlight lang="cpp">
char aBuf[128];
str_format(aBuf, sizeof(aBuf), Localize("%d of %d servers"), NumServers, TotalServers);
</syntaxhighlight>Скрипт используется для сканирования кода на наличие вызовов <code>Localize</code> и сбора строк для обновления файлов перевода. По этой причине вызов <code>Localize</code> не должен содержать никакого другого кода, иначе скрипт не сможет правильно определить текст.
<syntaxhighlight lang="cpp">
// НЕ делайте этого:
const char *pStr = Localize(Team == TEAM_RED ? "Red team" : "Blue team");
// Вместо этого сделайте следующее:
const char *pStr = Team == TEAM_RED ? Localize("Red team") : Localize("Blue team");
</syntaxhighlight>
<span id="External_resources"></span>
== Внешние ресурсы ==
*[https://edgarluque.com/blog/ui-code-ddnet/ Код пользовательского интерфейса в DDraceNetwork] от [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
*[https://edgarluque.com/blog/intro-to-ddnet/ Знакомство с исходным кодом игры DDraceNetwork] от [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
*[https://edgarluque.com/blog/code-conventions-in-ddnet/ Соглашения по коду в DDraceNetwork] от [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
*[https://edgarluque.com/blog/chat-command-ddracenetwork/ Реализация команды чата в DDraceNetwork] от [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
*[https://codedoc.ddnet.org/ Автоматически сгенерированная документация]
*[https://ddnet.org/libtw2-doc/ Техническая документация по форматам файлов Teeworlds и сетевому протоколу]
*[https://heinrich5991.github.io/blog/blog/one-tick-unfreeze Анатомия размораживания одного тика]
*[https://www.youtube.com/playlist?list=PLhJkqAQmOh5LyYOfnMy4PJB6CSZltQyTc YouTube-учебник по программированию Teeworlds] от [[User:ChillerDragon|ChillerDragon]]
*[https://chillerdragon.github.io/teeworlds-protocol/ Документация по сетевому протоколу Teeworlds 0.6/0.7] от [[User:ChillerDragon|ChillerDragon]]
<span id="About_Tee_Skin_Rendering"></span>
== О рендеринге скинов ==


<div lang="en" dir="ltr" class="mw-content-ltr">
В этом разделе описано, как выполнить рендеринг скина тии.
== External resources ==
</div>


<div lang="en" dir="ltr" class="mw-content-ltr">
Значения собраны вместе Patiga
* [https://edgarluque.com/blog/intro-to-ddnet/ An intro to the DDraceNetwork game source code]  by [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
Особая благодарность компании Jupstar
* [https://edgarluque.com/blog/code-conventions-in-ddnet/ Code conventions in DDraceNetwork] by [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
* [https://edgarluque.com/blog/chat-command-ddracenetwork/ Implementing a chat command in DDraceNetwork] by [[Special:MyLanguage/User:Ryozuki|Ryozuki]]
Масштабирование сегментов:
* [https://codedoc.ddnet.org/ Auto generated docs]
    тело: 100%
* [https://ddnet.org/libtw2-doc/ Technical documentation of Teeworlds file formats and network protocol]
    ноги: 150%
* [https://heinrich5991.github.io/blog/blog/one-tick-unfreeze The Anatomy of a One Tick Unfreeze]
    глаза: 120%
* [https://www.youtube.com/playlist?list=PLhJkqAQmOh5LyYOfnMy4PJB6CSZltQyTc Teeworlds programming YouTube tutorial] by ChillerDragon
    моргание глаз: 45%
</div>
    рука: 93,75%
  Позиционирование:
    64/64 = 1 = ширина или высота сегмента тела
    туловище: 4/64 вверх
    ноги:
        10/64 вниз
        7/64 влево/вправо
    глаза:
        0,125 вверх
        0,05 влево/вправо
   
    движение глаз:
        dir = угол наклона глаз (угол обзора), правый = 0
        глаза:
            x: cos(dir) * 0.125
            y: sin(dir) * 0.1
        каждый глаз (в сторону от другого):
            x: abs(cos(dir)) * 0.01

Latest revision as of 21:40, 23 September 2024

Цель этой статьи - познакомить вас с DDNet разработкой, поскольку это игра с открытым исходным кодом, она полагается на случайных людей, готовых внести в нее свой вклад в свободное время.


Ваша среда разработки

Крайне рекомендуется установить среду Linux для начала программирования в DDNet по следующим причинам (на данный момент):

  • Большинство участников DDNet на самом деле используют Linux для внесения вклада.
  • Более простое управление пакетами, вы можете легко установить все необходимые библиотеки и начать вносить свой вклад.
  • Эта статья пока не имеет версии для Windows и ориентирована на Linux.

Прежде всего, DDNet написан на языке программирования C++, и вам потребуется достаточно глубокое знакомство с ним, но вы также можете узнать основы и научиться большему с его помощью.

Некоторые полезные ресурсы для изучения C++:

Исходный код DDNet управляется с помощью Git, системы контроля версий, важного инструмента для совместной работы с несколькими разработчиками.

Если в вашем дистрибутиве Linux еще нет git, обязательно установите его, например, в большинстве дистрибутивов на базе debian/ubuntu: sudo apt install git.


Получение исходного кода

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

Если вы не знакомы с git/github, вы можете изучить основы здесь: Hello World - Github.


Установка зависимостей

Если вы работаете на Linux, вы можете установить все необходимые зависимости, прочитав README на странице DDNet на github: https://github.com/ddnet/ddnet#dependencies-on-linux--macos.

Для Arch Linux:

sudo pacman -S --needed base-devel cmake curl ffmpeg freetype2 git glew glslang gmock libnotify libpng opusfile python rust sdl2 spirv-tools sqlite vulkan-headers vulkan-icd-loader wavpack x264

Для Debian:

sudo apt install build-essential cargo cmake git glslang-tools google-mock libavcodec-extra libavdevice-dev libavfilter-dev libavformat-dev libavutil-dev libcurl4-openssl-dev libfreetype6-dev libglew-dev libnotify-dev libogg-dev libopus-dev libopusfile-dev libpng-dev libsdl2-dev libsqlite3-dev libssl-dev libvulkan-dev libwavpack-dev libx264-dev python3 rustc spirv-tools

Компиляция DDNet

Мы используем CMake для управления процессом компиляции, если у вас установлены все зависимости, это так же просто, как выполнить следующие команды (убедитесь, что вы находитесь в папке DDNet):

mkdir build
cd build
cmake ..
make -j$(nproc)


Общая информация

Вот некоторые общие сведения:

  • В настоящее время исходный код скомпилирован в соответствии со стандартом C++17, но вы увидите, что многие части кода больше похожи на C, поскольку только в основном новый код использует материал C++17.
  • std::string используется редко, массивы символов плюс использование system.h методы для их обработки являются нормой.
  • Большая часть кода ввода-вывода, форматирования и печати выполняется с использованием методов, предоставляемых system.h.


Расположение исходного кода

Теперь, когда вы можете собрать DDNet, вы можете приступить к его редактированию.


Каталог src/base

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


Каталог src/engine

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


Каталог src/game

Весь код, связанный с геймплеем, находится здесь, разделенный на клиентский и серверный.


Серверная сторона

Эта игра использует свою собственную иерархическую объектно-ориентированную систему сущностей, основным классом, от которого происходят все остальные сущности, является CEntity located in src/game/server/entity.h.

Эти сущности управляются игровым миром, расположенным здесь src/game/server/gameworld.h.

К числу важных структур относятся:

  • CCharacter: Представляет собой тии, который жив, он создаётся при спавне тии и удаляется при его смерти.
  • CPlayer содержит информацию, не относящуюся к Тии (никнейм, флаг, и тд).


Клиентская сторона

Клиентская часть состоит из компонентов - классов, наследующих CComponent, определенных в src/game/client/component.h. Эти компоненты могут реализовывать виртуальные методы, такие как OnInit, OnMessage и т.д, для обеспечения их функциональности.


Сетевое взаимодействие

Сетевой протокол в основном генерируется скриптами python, которые выводят код C++, например, datasrc/network.py определяет все сетевые пакеты.


Кодовые конвенции

Продолжающаяся дискуссия о кодовых соглашениях находится здесь: ddnet#2945.

В настоящее время применяется следующее:


Indentation стиль

Allman style используется.

Этот стиль помещает скобку, связанную с управляющим оператором, на следующую строку с отступом на том же уровне, что и управляющий оператор. Утверждения внутри скобок отступают на следующий уровень.

while(x == y)
{
    Something();
    SomethingElse();
}

FinalThing();

Классы и структуры

Должен иметь префикс C (по устаревшим причинам это игнорируется для структур в некоторых местах, например, в графическом коде) или I для интерфейсов. Новая структуры должны иметь префикс S.

Пример:

class CCharacter : public CEntity
{
    // ...
}


Перечисления и константы

Должен быть screaming snake case [1], например: MAX_PLAYERS

enum
{
	FAKETUNE_FREEZE = 1,
	FAKETUNE_SOLO = 2,
	FAKETUNE_NOJUMP = 4,
	FAKETUNE_NOCOLL = 8,
	FAKETUNE_NOHOOK = 16,
	FAKETUNE_JETPACK = 32,
	FAKETUNE_NOHAMMER = 64,
};


Именование переменных

  • Имена переменных содержат 3 части: классификатор, префикс и имя.
  • Имена переменных должны начинаться с прописной буквы, если только они не имеют длину в 1 символ без какого-либо префикса или определителя, например: i, x, y.
  • Переменные могут иметь более 1 классификатора (или нуля) и более 1 префикса (или нуля).

Они расположены следующим образом: [qualifiers]_[prefixes][Name]


Классификаторы

  • m для переменных-членов: m_MyVariable.
  • s для статических переменных: s_MyStaticVariable, ms_MyStaticMemberVariable.
  • g для глобальных переменных с внешней связью: gs_MyGlobalStaticVar.


Префиксы

  • p для указателей: pMyPointer, m_pCharacter, ppMyPointerToPointer.
  • a для массивов: aMyArray, aBuf.
  • v для std::vectors: vMyVector, vpvMyVectorOfPointersToVectors.
  • fn для функций: pfnMyCallback, m_papfnMyPointerToArrayOfCallbacks.


Общие фрагменты

Вот список кода, который вы можете часто встретить в кодовой базе:


Форматирование текста

char aBuf[128];
str_format(aBuf, sizeof(aBuf), "number: %d", 2);

Список всех спецификаторов форматирования см. в документации по printf.

Итерация по всем игрокам

for(int i = 0; i < MAX_CLIENTS; i++)
{
    // Server-side
    CPlayer *pPlayer = GameServer()->m_apPlayers[i];
}


Печать на игровой консоли

Console()->Print(IConsole::OUTPUT_LEVEL_STANDARD, "wikiprint", "Hello from the ddnet wiki!");


Отладочная печать

int i = 2;
dbg_msg("wikiprint", "Hello from the ddnet wiki: %d", i);

Перевод текста в клиенте

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

DoButton(..., Localize("Connect"), ...);

Строка может также содержать спецификаторы формата. Переведенная строка должна содержать те же спецификаторы форматирования.

char aBuf[128];
str_format(aBuf, sizeof(aBuf), Localize("%d of %d servers"), NumServers, TotalServers);

Скрипт используется для сканирования кода на наличие вызовов Localize и сбора строк для обновления файлов перевода. По этой причине вызов Localize не должен содержать никакого другого кода, иначе скрипт не сможет правильно определить текст.

// НЕ делайте этого:
const char *pStr = Localize(Team == TEAM_RED ? "Red team" : "Blue team");

// Вместо этого сделайте следующее:
const char *pStr = Team == TEAM_RED ? Localize("Red team") : Localize("Blue team");

Внешние ресурсы

О рендеринге скинов

В этом разделе описано, как выполнить рендеринг скина тии.

Значения собраны вместе Patiga
Особая благодарность компании Jupstar

Масштабирование сегментов:
   тело: 100%
   ноги: 150%
   глаза: 120%
   моргание глаз: 45%
   рука: 93,75%

Позиционирование:
   64/64 = 1 = ширина или высота сегмента тела
   туловище: 4/64 вверх
   ноги:
       10/64 вниз
       7/64 влево/вправо
   глаза:
       0,125 вверх
       0,05 влево/вправо

   движение глаз:
       dir = угол наклона глаз (угол обзора), правый = 0
       глаза:
           x: cos(dir) * 0.125
           y: sin(dir) * 0.1
       каждый глаз (в сторону от другого):
           x: abs(cos(dir)) * 0.01