How-To For GDNative

These steps most likely will not work correctly as the branch is still under development. Please note that the GDNative version does not allow for default arguments in functions, thus some functions may have odd behaviors. If you are using this version of GodotSteam you are required to pass any argument that has a default in the module version. Also, there are no enums in the GDNative version due to how it is structured. I will attempt re-writing the whole thing once Godot 4 is released.


1. Preparing

  • Create a new folder and call it GDNative (or whatever you want).
  • Download this repository.
    • Unpack this repo and place it inside the GDNative folder.
  • Download the Steamworks SDK; this requires a Steam developer account.
    • Unpack the Steamworks SDK then copy the public and redistributable_bin to the /godotsteam/sdk folder in the unpacked repo folder.
  • Download the Godot 3.3.3 binary, if you do not have it already.
    • Preferably you use the Godot 3.3.3 binary, at this time of writing.
    • Unpack it and place it in the root of the GDNative folder.
  • Download the Godot cpp, the 3.3 branch preferably.
    • Unpack the godot_cpp into the GDNative folder.
    • Alternatively, you can just use these commands inside the GDNative folder to clone them:
      git clone --recursive -b 3.3 https://github.com/godotengine/godot-cpp

Alternate Preparation Option

Once you have the pre-compiles and Steamworks SDK, skip ahead to Step 5 in this tutorial.


2. Compiling Bindings

CD into the godot-cpp folder and compile the bindings (make sure your slashes are OS appropriate):

scons platform= generate_bindings=yes

3. Folder Layout

You should end up with a GDNative folder that looks something like this:

Godot_v3.3.3-stable_x11.64 (or whatever your binary is for your platform)
godot-cpp/
--- bin/*
--- godot-headers/*
--- include/*
--- misc/*
--- src/*
--- test/*
--- binding_generator.py
--- CMakeLists.txt
--- LICENSE
--- Makefile
--- README.md
--- SConstruct
godotsteam/
--- sdk/
--- --- public/steam/*
--- --- redistributable_bin/*
--- godotsteam.h
--- godotsteam.cpp
--- init.cpp
SConstruct
README.md
LICENSE.txt

4. Compile It

Windows users, follow these steps for Visual Studio (big thanks to willnationsdev):

  • Create a new Visual Studio project.
  • Name it GDNative and make sure it DOES NOT create a directory.
    • Uncheck the box here.
  • Select the GDNative folder we were working in.
  • Choose Win32 Desktop Wizard template.
  • Select options for both a dynamic library (.dll) and an empty project.
  • Things should look like this:
    GDNative -cpp_bindings -godot_headers -lib -GDNative --.vs --GDNative.sln --GDNative.vcxproj --GDNative.vcsproj.filters -src
  • Make sure you have a debug, x64 configuration for the solution.
    • The options are located in the toolbar at the top left.
  • Go to Project > GDNative Properties to open the project properties.
  • Ensure you are on the x64 Debug configurations at the top and make these changes:
    • VC++ Directories > Include Directories. Add 'GDNative\godot-cpp\include', 'GDNative\godot-cpp\include\core', and 'GDNative\godot-cpp\godot-headers' to the list.
    • VC++ Directories > Library Directories. Add 'GDNative\godotsteam'.
    • VC++ Directories > Source Directories. Add 'GDNative\godotsteam'.
    • C/C++ > Linker > System. Subsystem = "Console (/SUBSYSTEM:CONSOLE)"
    • C/C++ > Linker > Input. Add cpp_bindings.windows.64.lib to the Additional Dependencies parameter.
  • Click on Apply and then Save.
  • Now build the solution.
  • Alternatively, you can also run the following in the VS Command Prompt:
    scons platform=windows production=yes target=release

Linux and Mac users, follow these steps:

  • Simply CD into the root of the GDNative folder and run:
    scons platform= production=yes target=release

5. Adding It To Your Project

Copy the resulting file from your /bin/win64 or /bin/linuxbsd or /bin/osx folder and copy the matching Steam API file into an /addons/godotsteam folder inside your game's project folder. For example:

  • For Windows: /addons/godotsteam/win64/, you want godotsteam.dll and steam_api64.dll.
  • For Linux: /addons/godotsteam/linux/, you want libgodotsteam.so and libsteam_api.so.
  • For Mac: /addons/godotsteam/osx, you want libgodotsteam.dylib and libsteam_api.dylib.

In a text editor, create a file called godotsteam.gdnlib (this may need to be renamed as such if using Windows). Place the following inside this file and save it in the root of your project (game) folder:

[general]
singleton=false
load_once=true
symbol_prefix="godot_"
reloadable=true

[entry]
(read below)

[dependencies]
(read below)

If using Windows:

[entry]
Windows.64="res://godotsteam.dll"

[dependencies]
Windows.64=["res://steam_api64.dll"]

If using Linux:

[entry]
X11.64="res://libgodotsteam.so"

[dependencies]
X11.64=["res://libsteam_api.so"]

To double-check this worked, in your Godot project, open the .gdnlib file in the Inspector. It will have the correct data in the GUI editor that pops up in the bottom panel.

In the Script Editor, cerate a new script.

  • Set the type as NativeScript.
  • Set the Inherits as Reference.
  • Set the class as Steam.
  • Set the filename as godotsteam.gdns.
  • Hit create to save it.

Open the new godotsteam.gdns file in the Inspector.

  • It will have a null GDNativeLibrary field.
  • Click the arrow and select Load to add the godotsteam.gdnlib file.
  • Click the save icon in the Inspector.

Create a new scene in your game project.

  • Add a Node node with a built-in GDScript as the script.
  • Add the following code:
    extends Node

    onready var Steam = preload("godotsteam.gdns").new()

    func _ready():
      Steam.steamInit()

Save the scene as godotsteam.tscn and place it where ever you want.


6. Adding Singleton

Go to Project > Project Settings then click on Autoload. Add your godotsteam.tscn as a singleton, with the node name of godotsteam. Done!


7. Use It

Now you should be able to call functions from GodotSteam like you would normally with the GodotSteam module. They will, however, have to be added to your script in the godotsteam.tscn like this:

name = Steam.getPersonaName()
country = Steam.getIPCountry()
running = Steam.isSteamRunning()

func setAchievement(achieve):
  Steam.setAchievement(achieve)

These can then be called in any other script (since godotsteam.tscn is a singleton) like this:

print(godosteam.name)
print(godotsteam.country)

if godotsteam.running:
  runFunction()

godotsteam.setAchievement(achieve)

A New How-To Soon

I found GDNative to actually be more work than just compiling the module version of GodotSteam or just using pre-compiles, so I highly recommend either of those two instead. At least, for now. After this is rebuilt and working reliably, I will probably add GodotSteam to the Asset Library in Godot Engine for folks.