Особенности C#¶
На этой странице представлен обзор наиболее часто используемых функций C# и Godot, а также того, как они используются вместе.
Превращение типов и кастинг¶
C# - это статически типизированный язык. Следовательно, вы не можете сделать следующее:
var mySprite = GetNode("MySprite");
mySprite.SetFrame(0);
Метод GetNode()
возвращает экземпляр Node
. Вы должны однозначно преобразовать его в желаемый производный тип, Sprite
в данном случае.
Для этого в C# имеются различные опции.
Приведение и проверка типа
Выдает `` InvalidCastException``, если возвращаемый узел не может быть приведен к Sprite. Вы можете использовать его вместо оператора `` as``, если уверены, что он не потерпит неудачу.
Sprite mySprite = (Sprite)GetNode("MySprite");
mySprite.SetFrame(0);
** Использование оператора AS **
Оператор as
возвращает null
, если узел не может быть приведен к Sprite, и по этой причине его нельзя использовать с типами значений.
Sprite mySprite = GetNode("MySprite") as Sprite;
// Only call SetFrame() if mySprite is not null
mySprite?.SetFrame(0);
** Использование универсальных методов **
Общие методы также предоставляются, чтобы сделать это преобразование типов прозрачным.
GetNode<T>()
преобразует узел перед его возвратом. Он выдаст InvalidCastException
, если узел не может быть приведен к нужному типу.
Sprite mySprite = GetNode<Sprite>("MySprite");
mySprite.SetFrame(0);
GetNodeOrNull<T>()
использует оператор as
и вернет null
, если узел не может быть приведен к нужному типу.
Sprite mySprite = GetNodeOrNull<Sprite>("MySprite");
// Only call SetFrame() if mySprite is not null
mySprite?.SetFrame(0);
** Проверка типа с использованием оператора IS **
Чтобы проверить, может ли узел быть приведен к Sprite, вы можете использовать оператор is
. Оператор is
возвращает false, если узел не может быть приведен к Sprite, в противном случае он возвращает true.
if (GetNode("MySprite") is Sprite)
{
// Yup, it's a sprite!
}
Для более сложной проверки типов вы можете посмотреть в Сопоставление шаблонов.
Сигналы C#¶
Для полного C# примера см. Раздел ** Обработка сигнала ** в пошаговом руководстве Языки скрипта.
Объявление сигнала в C# выполняется с помощью атрибута [Signal]
делегата.
[Signal]
delegate void MySignal();
[Signal]
delegate void MySignalWithArguments(string foo, int bar);
Эти сигналы затем могут быть подключены либо в редакторе, либо из кода с помощью `` Connect``. Если вы хотите подключить сигнал в редакторе, вам нужно собрать проект, чтобы увидеть новый сигнал. Эту сборку можно запустить вручную, нажав кнопку «Построить» в верхнем правом углу окна редактора.
public void MyCallback()
{
GD.Print("My callback!");
}
public void MyCallbackWithArguments(string foo, int bar)
{
GD.Print("My callback with: ", foo, " and ", bar, "!");
}
public void SomeFunction()
{
instance.Connect("MySignal", this, "MyCallback");
instance.Connect(nameof(MySignalWithArguments), this, "MyCallbackWithArguments");
}
Излучение сигналов осуществляется методом EmitSignal
.
public void SomeFunction()
{
EmitSignal(nameof(MySignal));
EmitSignal("MySignalWithArguments", "hello there", 28);
}
Обратите внимание, что вы всегда можете сослаться на имя сигнала используя ключевое слово nameof
(применяется к самому делегату).
Возможно связывать значения при установке соединения передавая массив Godot.
public int Value { get; private set; } = 0;
private void ModifyValue(int modifier)
{
Value += modifier;
}
public void SomeFunction()
{
var plusButton = (Button)GetNode("PlusButton");
var minusButton = (Button)GetNode("MinusButton");
plusButton.Connect("pressed", this, "ModifyValue", new Godot.Collections.Array { 1 });
minusButton.Connect("pressed", this, "ModifyValue", new Godot.Collections.Array { -1 });
}
Сигналы поддерживают параметры и связанные значения всех встроенных типов и Классов, полученных из Godot.Object. Следовательно, любой Node
или Reference
будут совместимы автоматически, но пользовательские объекты данных должны наследоваться из Godot.Object или одного из его подклассов.
public class DataObject : Godot.Object
{
public string Field1 { get; set; }
public string Field2 { get; set; }
}
Наконец, сигналы могут быть созданы путем вызова `` AddUserSignal``, но имейте в виду, что он должен выполниться перед любым использованием указанных сигналов (с помощью `` Connect`` или `` EmitSignal``).
public void SomeFunction()
{
AddUserSignal("MyOtherSignal");
EmitSignal("MyOtherSignal");
}
Препроцессорные определения¶
Godot имеет набор определений, которые позволяют изменять код C# в зависимости от среды, в которую вы компилируете.
Примечание
Если вы создали свой проект до Godot 3.2, вам придется изменить или регенерировать свой файл csproj, чтобы использовать эту функцию (сравните <DefineConstants>
с новым проектом 3.2+).
Примеры¶
Например, вы можете изменять код в зависимости от платформы:
public override void _Ready()
{
#if GODOT_SERVER
// Don't try to load meshes or anything, this is a server!
LaunchServer();
#elif GODOT_32 || GODOT_MOBILE || GODOT_WEB
// Use simple objects when running on less powerful systems.
SpawnSimpleObjects();
#else
SpawnComplexObjects();
#endif
}
Или вы можете определить, в каком движке будет находиться ваш код, что полезно для создания кросс-движковых библиотек:
public void MyPlatformPrinter()
{
#if GODOT
GD.Print("This is Godot.");
#elif UNITY_5_3_OR_NEWER
print("This is Unity.");
#else
throw new InvalidWorkflowException("Only Godot and Unity are supported.");
#endif
}
Полный список определений¶
GODOT
всегда объявлен в проектах Godot.Один из
GODOT_64
илиGODOT_32
определяется в зависимости от того, если архитектура будет 64-bit или 32-bit соответственно.Один из
GODOT_X11
,GODOT_WINDOWS
,GODOT_OSX
,GODOT_ANDROID
,GODOT_IOS
,GODOT_HTML5
, илиGODOT_SERVER
определяется в зависимости от операционной системы. В будущем эти названия могут измениться. Они создаются из методаget_name()
синглтона :ref:OS <class_OS>
, но не каждая возможная ОС, возвращаемая методом, является ОС, на которой работает Godot с Mono.
При экспорте также могут быть определены следующие параметры в зависимости от особенностей экспорта:
Один из
GODOT_PC
,GODOT_MOBILE
, илиGODOT_WEB
в зависимости от типа платформы.Один из
GODOT_ARM64_V8A
илиGODOT_ARMEABI_V7A
на Android только в зависимости от архитектуры.Один из
GODOT_ARM64
илиGODOT_ARMV7
на iOS только в зависимости от архитектуры.Любой из
GODOT_S3TC
,GODOT_ETC
, иGODOT_ETC2
в зависимости от типа сжатия текстур.Любые пользовательские функции, добавленные в меню экспорта, будут написаны заглавными буквами и с префиксом:
foo
->GODOT_FOO
.
Чтобы увидеть пример проекта, см. демонстрационную версию тестирования ОС: https://github.com/godotengine/godot-demo-projects/tree/master/misc/os_test