.
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..0b075ff
--- /dev/null
+++ b/README.md
@@ -0,0 +1,137 @@
+[](https://ci.appveyor.com/project/RektInator/zonetool)
+
+
+
+
+
+
+# zonetool
+zonetool, a fastfile linker for various Call of Duty titles.
+
+## Folder structure
+Call of Duty\
+| - zone_source\
+| - zonetool\
+| - zonetool.exe\
+| - zonetool.dll
+
+## Usage
+Simply put the output DLL in your game directory and run zonetool.exe (For IW3, rename the DLL to zoneiw3.dll)
+
+## Commands
+``buildzone `` - builds the specified zone.\
+``loadzone `` - loads the specified zone into memory.\
+``dumpzone `` - dumps all assets from the specified zone.
+
+## Supported asset types
+The following asset types can be linked by ZoneTool:
+
+| Asset Type | IW4 | IW5 |
+|-------------|-----|-----|
+| PhysPreset | ✔️ | ✔️ |
+| PhysCollmap | ✔️ | ✔️ |
+| XAnimParts | ✔️ | ✔️ |
+| XModelSurfs | ✔️ | ✔️ |
+| XModel | ✔️ | ✔️ |
+| Material | ✔️ | ✔️ |
+| PixelShader | ✔️ | ✔️ |
+| VertexShader | ✔️ | ✔️ |
+| VertexDecl | ✔️ | ✔️ |
+| Techset | ✔️ | ✔️ |
+| Image | ✔️ | ✔️ |
+| Sound | ✔️ | ✔️ |
+| SndCurve | ✔️ | ✔️ |
+| LoadedSound | ✔️ | ✔️ |
+| CollisionMap | ✔️ | ✔️ |
+| ComMap | ✔️ | ✔️ |
+| GlassMap | ✔️ | ✔️ |
+| MapEnts | ✔️ | ✔️ |
+| FxMap | ✔️ | ✔️ |
+| GfxMap | ✔️ | ✔️ |
+| Font | ✔️ | ✔️ |
+| MenuFile | ❌ | ❌ |
+| Menu | ❌ | ❌ |
+| Localize | ✔️ | ✔️ |
+| Attachment | - | ✔️ |
+| Weapon | ✔️ | ✔️ |
+| FxEffectDef | ✔️ | ✔️ |
+| ImpactFx | ❌ | ❌ |
+| RawFile | ✔️ | ✔️ |
+| ScriptFile | - | ✔️ |
+| StringTable | ✔️ | ✔️ |
+| LeaderBoardDef | ✔️ | ✔️ |
+| StructuredDataDef | ✔️ | ✔️ |
+| Tracer | ✔️ | ✔️ |
+| Vehicle | ❌ | ❌ |
+| AddonMapEnts | ❌ | ❌ |
+
+## Supported assets for cross-engine porting
+The following asset types can be ported across different games:
+
+| Asset Type | Supported? |
+|-------------|------------|
+| PhysPreset | ✔️ |
+| PhysCollmap | ✔️ |
+| XAnimParts | ✔️ |
+| XModelSurfs | ✔️ |
+| XModel | ✔️ |
+| Material | ✔️ |
+| PixelShader | ✔️ |
+| VertexShader | ✔️ |
+| VertexDecl | ✔️ |
+| Techset | ✔️ |
+| Image | ✔️ |
+| Sound | ✔️ |
+| SndCurve | ✔️ |
+| LoadedSound | ✔️ |
+| CollisionMap | ✔️ |
+| ComMap | ✔️ |
+| GlassMap | ✔️ |
+| MapEnts | ✔️ |
+| FxMap | ✔️ |
+| GfxMap | ✔️ |
+| Font | ❌ |
+| MenuFile | ❌ |
+| Menu | ❌ |
+| Localize | ✔️ |
+| Attachment | ✔️ |
+| Weapon | ✔️ |
+| FxEffectDef | ✔️ |
+| ImpactFx | ❌ |
+| RawFile | ✔️ |
+| ScriptFile | ✔️ |
+| StringTable | ✔️ |
+| LeaderBoardDef | ❌ |
+| StructuredDataDef | ✔️ |
+| Tracer | ✔️ |
+| Vehicle | ❌ |
+| AddonMapEnts | ❌ |
+
+## Supported clients
+ZoneTool generated fastfiles are compatible with the following clients:
+* IW4x (IW4 client)
+* Plutonium (IW5 client)
+* Oxygen (IW5 client)
+
+## Credits
+Special thanks to the following people:
+* Laupetin
+* NTAuthority
+* momo5502
+* TheApadayo
+* localhost
+* X3RX35
+* homura
+* Sofika
+* Gamecheat13
+
+## Discord
+Join our discord server at https://discord.gg/a6JM2Tv or https://discord.gg/plutonium
+
+## Donate
+If you like my work, feel free to contribute!
+
+bitcoin: 17YZtqKcFP4WiwMRZB5AE57QR4oa3fnFAM\
+eth: 0xf4f73463861eD8Ba72ac422B237c53B720c6608A
+
+[](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=JF352E6E7TL8N)
\ No newline at end of file
diff --git a/appveyor.yml b/appveyor.yml
new file mode 100644
index 0000000..43597f0
--- /dev/null
+++ b/appveyor.yml
@@ -0,0 +1,20 @@
+version: 1.0.{build}
+skip_tags: true
+image: Visual Studio 2019
+configuration: release
+before_build:
+- git submodule update --init --recursive
+- ps: tools\premake5.exe vs2019 --set-version="$env:APPVEYOR_BUILD_VERSION"
+build:
+ project: build/zonetool.sln
+ verbosity: minimal
+test: off
+artifacts:
+- path: build/bin/*.dll
+- path: build/bin/*.pdb
+deploy:
+- provider: GitHub
+ auth_token:
+ secure: IyUTCaq8tOpcOwDfqa2bH2UCEgPNoLpgqZtJOetSchzZcs1rJT8b/oQ/DTq2ecwc
+ on:
+ branch: master
\ No newline at end of file
diff --git a/dep/bin/steam_api.lib b/dep/bin/steam_api.lib
new file mode 100644
index 0000000..c188c64
Binary files /dev/null and b/dep/bin/steam_api.lib differ
diff --git a/dep/libtomcrypt.lua b/dep/libtomcrypt.lua
new file mode 100644
index 0000000..6530536
--- /dev/null
+++ b/dep/libtomcrypt.lua
@@ -0,0 +1,43 @@
+libtomcrypt = {}
+
+function libtomcrypt:include()
+ includedirs {
+ path.join(DependencyFolder(), "libtomcrypt/src/headers")
+ }
+end
+
+function libtomcrypt:link()
+ self:include()
+ links {
+ "libtomcrypt"
+ }
+end
+
+function libtomcrypt:project()
+ local folder = DependencyFolder();
+
+ project "libtomcrypt"
+
+ location "%{wks.location}/dep"
+ kind "StaticLib"
+ language "C"
+
+ files {
+ path.join(folder, "libtomcrypt/src/**.h"),
+ path.join(folder, "libtomcrypt/src/**.c")
+ }
+
+ defines {
+ "_CRT_SECURE_NO_WARNINGS",
+ "_CRT_NONSTDC_NO_DEPRECATE",
+ "LTC_SOURCE",
+ "LTC_NO_TEST",
+ "LTC_NO_PROTOTYPES"
+ }
+
+ self:include()
+ libtommath:include()
+
+ -- Disable warnings. They do not have any value to us since it is not our code.
+ warnings "off"
+end
diff --git a/dep/libtommath.lua b/dep/libtommath.lua
new file mode 100644
index 0000000..e3b5404
--- /dev/null
+++ b/dep/libtommath.lua
@@ -0,0 +1,34 @@
+libtommath = {}
+
+function libtommath:include()
+ includedirs {
+ path.join(DependencyFolder(), "libtommath")
+ }
+end
+
+function libtommath:link()
+ self:include()
+ links {
+ "libtommath"
+ }
+end
+
+function libtommath:project()
+ local folder = DependencyFolder();
+
+ project "libtommath"
+
+ location "%{wks.location}/dep"
+ kind "StaticLib"
+ language "C"
+
+ files {
+ path.join(folder, "libtommath/*.h"),
+ path.join(folder, "libtommath/*.c")
+ }
+
+ self:include()
+
+ -- Disable warnings. They do not have any value to us since it is not our code.
+ warnings "off"
+end
diff --git a/dep/steam_api.lua b/dep/steam_api.lua
new file mode 100644
index 0000000..0e775b1
--- /dev/null
+++ b/dep/steam_api.lua
@@ -0,0 +1,22 @@
+SteamApi = {}
+
+function SteamApi:include()
+ includedirs {
+ path.join(DependencyFolder(), "steam_api")
+ }
+end
+
+function SteamApi:link()
+ self:include()
+
+ syslibdirs {
+ path.join(DependencyFolder(), "bin")
+ }
+
+ links {
+ "steam_api"
+ }
+end
+
+function SteamApi:project()
+end
diff --git a/dep/steam_api/isteamapplist.h b/dep/steam_api/isteamapplist.h
new file mode 100644
index 0000000..d678909
--- /dev/null
+++ b/dep/steam_api/isteamapplist.h
@@ -0,0 +1,63 @@
+//====== Copyright © 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to app data in Steam
+//
+//=============================================================================
+
+#ifndef ISTEAMAPPLIST_H
+#define ISTEAMAPPLIST_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+#include "steamtypes.h"
+
+//-----------------------------------------------------------------------------
+// Purpose: This is a restricted interface that can only be used by previously approved apps,
+// contact your Steam Account Manager if you believe you need access to this API.
+// This interface lets you detect installed apps for the local Steam client, useful for debugging tools
+// to offer lists of apps to debug via Steam.
+//-----------------------------------------------------------------------------
+class ISteamAppList
+{
+public:
+ virtual uint32 GetNumInstalledApps() = 0;
+ virtual uint32 GetInstalledApps( AppId_t *pvecAppID, uint32 unMaxAppIDs ) = 0;
+
+ virtual int GetAppName( AppId_t nAppID, OUT_STRING() char *pchName, int cchNameMax ) = 0; // returns -1 if no name was found
+ virtual int GetAppInstallDir( AppId_t nAppID, char *pchDirectory, int cchNameMax ) = 0; // returns -1 if no dir was found
+
+ virtual int GetAppBuildId( AppId_t nAppID ) = 0; // return the buildid of this app, may change at any time based on backend updates to the game
+};
+
+#define STEAMAPPLIST_INTERFACE_VERSION "STEAMAPPLIST_INTERFACE_VERSION001"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+//---------------------------------------------------------------------------------
+// Purpose: Sent when a new app is installed
+//---------------------------------------------------------------------------------
+DEFINE_CALLBACK( SteamAppInstalled_t, k_iSteamAppListCallbacks + 1 );
+ CALLBACK_MEMBER( 0, AppId_t, m_nAppID ) // ID of the app that installs
+END_DEFINE_CALLBACK_1()
+
+
+//---------------------------------------------------------------------------------
+// Purpose: Sent when an app is uninstalled
+//---------------------------------------------------------------------------------
+DEFINE_CALLBACK( SteamAppUninstalled_t, k_iSteamAppListCallbacks + 2 );
+ CALLBACK_MEMBER( 0, AppId_t, m_nAppID ) // ID of the app that installs
+END_DEFINE_CALLBACK_1()
+
+
+#pragma pack( pop )
+#endif // ISTEAMAPPLIST_H
diff --git a/dep/steam_api/isteamapps.h b/dep/steam_api/isteamapps.h
new file mode 100644
index 0000000..9a97b4a
--- /dev/null
+++ b/dep/steam_api/isteamapps.h
@@ -0,0 +1,176 @@
+//====== Copyright © 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to app data in Steam
+//
+//=============================================================================
+
+#ifndef ISTEAMAPPS_H
+#define ISTEAMAPPS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+const int k_cubAppProofOfPurchaseKeyMax = 240; // max supported length of a legacy cd key
+
+
+//-----------------------------------------------------------------------------
+// Purpose: interface to app data
+//-----------------------------------------------------------------------------
+class ISteamApps
+{
+public:
+ virtual bool BIsSubscribed() = 0;
+ virtual bool BIsLowViolence() = 0;
+ virtual bool BIsCybercafe() = 0;
+ virtual bool BIsVACBanned() = 0;
+ virtual const char *GetCurrentGameLanguage() = 0;
+ virtual const char *GetAvailableGameLanguages() = 0;
+
+ // only use this member if you need to check ownership of another game related to yours, a demo for example
+ virtual bool BIsSubscribedApp( AppId_t appID ) = 0;
+
+ // Takes AppID of DLC and checks if the user owns the DLC & if the DLC is installed
+ virtual bool BIsDlcInstalled( AppId_t appID ) = 0;
+
+ // returns the Unix time of the purchase of the app
+ virtual uint32 GetEarliestPurchaseUnixTime( AppId_t nAppID ) = 0;
+
+ // Checks if the user is subscribed to the current app through a free weekend
+ // This function will return false for users who have a retail or other type of license
+ // Before using, please ask your Valve technical contact how to package and secure your free weekened
+ virtual bool BIsSubscribedFromFreeWeekend() = 0;
+
+ // Returns the number of DLC pieces for the running app
+ virtual int GetDLCCount() = 0;
+
+ // Returns metadata for DLC by index, of range [0, GetDLCCount()]
+ virtual bool BGetDLCDataByIndex( int iDLC, AppId_t *pAppID, bool *pbAvailable, char *pchName, int cchNameBufferSize ) = 0;
+
+ // Install/Uninstall control for optional DLC
+ virtual void InstallDLC( AppId_t nAppID ) = 0;
+ virtual void UninstallDLC( AppId_t nAppID ) = 0;
+
+ // Request legacy cd-key for yourself or owned DLC. If you are interested in this
+ // data then make sure you provide us with a list of valid keys to be distributed
+ // to users when they purchase the game, before the game ships.
+ // You'll receive an AppProofOfPurchaseKeyResponse_t callback when
+ // the key is available (which may be immediately).
+ virtual void RequestAppProofOfPurchaseKey( AppId_t nAppID ) = 0;
+
+ virtual bool GetCurrentBetaName( char *pchName, int cchNameBufferSize ) = 0; // returns current beta branch name, 'public' is the default branch
+ virtual bool MarkContentCorrupt( bool bMissingFilesOnly ) = 0; // signal Steam that game files seems corrupt or missing
+ virtual uint32 GetInstalledDepots( AppId_t appID, DepotId_t *pvecDepots, uint32 cMaxDepots ) = 0; // return installed depots in mount order
+
+ // returns current app install folder for AppID, returns folder name length
+ virtual uint32 GetAppInstallDir( AppId_t appID, char *pchFolder, uint32 cchFolderBufferSize ) = 0;
+ virtual bool BIsAppInstalled( AppId_t appID ) = 0; // returns true if that app is installed (not necessarily owned)
+
+ virtual CSteamID GetAppOwner() = 0; // returns the SteamID of the original owner. If different from current user, it's borrowed
+
+ // Returns the associated launch param if the game is run via steam://run///?param1=value1;param2=value2;param3=value3 etc.
+ // Parameter names starting with the character '@' are reserved for internal use and will always return and empty string.
+ // Parameter names starting with an underscore '_' are reserved for steam features -- they can be queried by the game,
+ // but it is advised that you not param names beginning with an underscore for your own features.
+ virtual const char *GetLaunchQueryParam( const char *pchKey ) = 0;
+
+ // get download progress for optional DLC
+ virtual bool GetDlcDownloadProgress( AppId_t nAppID, uint64 *punBytesDownloaded, uint64 *punBytesTotal ) = 0;
+
+ // return the buildid of this app, may change at any time based on backend updates to the game
+ virtual int GetAppBuildId() = 0;
+
+ // Request all proof of purchase keys for the calling appid and asociated DLC.
+ // A series of AppProofOfPurchaseKeyResponse_t callbacks will be sent with
+ // appropriate appid values, ending with a final callback where the m_nAppId
+ // member is k_uAppIdInvalid (zero).
+ virtual void RequestAllProofOfPurchaseKeys() = 0;
+
+ CALL_RESULT( FileDetailsResult_t )
+ virtual SteamAPICall_t GetFileDetails( const char* pszFileName ) = 0;
+};
+
+#define STEAMAPPS_INTERFACE_VERSION "STEAMAPPS_INTERFACE_VERSION008"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+//-----------------------------------------------------------------------------
+// Purpose: posted after the user gains ownership of DLC & that DLC is installed
+//-----------------------------------------------------------------------------
+struct DlcInstalled_t
+{
+ enum { k_iCallback = k_iSteamAppsCallbacks + 5 };
+ AppId_t m_nAppID; // AppID of the DLC
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: possible results when registering an activation code
+//-----------------------------------------------------------------------------
+enum ERegisterActivationCodeResult
+{
+ k_ERegisterActivationCodeResultOK = 0,
+ k_ERegisterActivationCodeResultFail = 1,
+ k_ERegisterActivationCodeResultAlreadyRegistered = 2,
+ k_ERegisterActivationCodeResultTimeout = 3,
+ k_ERegisterActivationCodeAlreadyOwned = 4,
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: response to RegisterActivationCode()
+//-----------------------------------------------------------------------------
+struct RegisterActivationCodeResponse_t
+{
+ enum { k_iCallback = k_iSteamAppsCallbacks + 8 };
+ ERegisterActivationCodeResult m_eResult;
+ uint32 m_unPackageRegistered; // package that was registered. Only set on success
+};
+
+
+//---------------------------------------------------------------------------------
+// Purpose: posted after the user gains executes a steam url with query parameters
+// such as steam://run///?param1=value1;param2=value2;param3=value3; etc
+// while the game is already running. The new params can be queried
+// with GetLaunchQueryParam.
+//---------------------------------------------------------------------------------
+struct NewLaunchQueryParameters_t
+{
+ enum { k_iCallback = k_iSteamAppsCallbacks + 14 };
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: response to RequestAppProofOfPurchaseKey/RequestAllProofOfPurchaseKeys
+// for supporting third-party CD keys, or other proof-of-purchase systems.
+//-----------------------------------------------------------------------------
+struct AppProofOfPurchaseKeyResponse_t
+{
+ enum { k_iCallback = k_iSteamAppsCallbacks + 21 };
+ EResult m_eResult;
+ uint32 m_nAppID;
+ uint32 m_cchKeyLength;
+ char m_rgchKey[k_cubAppProofOfPurchaseKeyMax];
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: response to GetFileDetails
+//-----------------------------------------------------------------------------
+struct FileDetailsResult_t
+{
+ enum { k_iCallback = k_iSteamAppsCallbacks + 23 };
+ EResult m_eResult;
+ uint64 m_ulFileSize; // original file size in bytes
+ uint8 m_FileSHA[20]; // original file SHA1 hash
+ uint32 m_unFlags; //
+};
+
+
+#pragma pack( pop )
+#endif // ISTEAMAPPS_H
diff --git a/dep/steam_api/isteamappticket.h b/dep/steam_api/isteamappticket.h
new file mode 100644
index 0000000..21fb9e1
--- /dev/null
+++ b/dep/steam_api/isteamappticket.h
@@ -0,0 +1,28 @@
+//====== Copyright 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: a private, but well versioned, interface to get at critical bits
+// of a steam3 appticket - consumed by the simple drm wrapper to let it
+// ask about ownership with greater confidence.
+//
+//=============================================================================
+
+#ifndef ISTEAMAPPTICKET_H
+#define ISTEAMAPPTICKET_H
+#pragma once
+
+//-----------------------------------------------------------------------------
+// Purpose: hand out a reasonable "future proof" view of an app ownership ticket
+// the raw (signed) buffer, and indices into that buffer where the appid and
+// steamid are located. the sizes of the appid and steamid are implicit in
+// (each version of) the interface - currently uin32 appid and uint64 steamid
+//-----------------------------------------------------------------------------
+class ISteamAppTicket
+{
+public:
+ virtual uint32 GetAppOwnershipTicketData( uint32 nAppID, void *pvBuffer, uint32 cbBufferLength, uint32 *piAppId, uint32 *piSteamId, uint32 *piSignature, uint32 *pcbSignature ) = 0;
+};
+
+#define STEAMAPPTICKET_INTERFACE_VERSION "STEAMAPPTICKET_INTERFACE_VERSION001"
+
+
+#endif // ISTEAMAPPTICKET_H
diff --git a/dep/steam_api/isteamclient.h b/dep/steam_api/isteamclient.h
new file mode 100644
index 0000000..f007c63
--- /dev/null
+++ b/dep/steam_api/isteamclient.h
@@ -0,0 +1,520 @@
+//====== Copyright � 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: Main interface for loading and accessing Steamworks API's from the
+// Steam client.
+// For most uses, this code is wrapped inside of SteamAPI_Init()
+//=============================================================================
+
+#ifndef ISTEAMCLIENT_H
+#define ISTEAMCLIENT_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "steamtypes.h"
+#include "steamclientpublic.h"
+
+// Define compile time assert macros to let us validate the structure sizes.
+#define VALVE_COMPILE_TIME_ASSERT( pred ) typedef char compile_time_assert_type[(pred) ? 1 : -1];
+
+#ifndef REFERENCE
+#define REFERENCE(arg) ((void)arg)
+#endif
+
+#if ( defined(STEAM_API_EXPORTS) || defined(STEAM_API_NODLL) ) && !defined(API_GEN)
+#define STEAM_PRIVATE_API( ... ) __VA_ARGS__
+#elif defined(STEAM_API_EXPORTS) && defined(API_GEN)
+#define STEAM_PRIVATE_API( ... )
+#else
+#define STEAM_PRIVATE_API( ... ) protected: __VA_ARGS__ public:
+#endif
+
+#if defined(__linux__) || defined(__APPLE__)
+// The 32-bit version of gcc has the alignment requirement for uint64 and double set to
+// 4 meaning that even with #pragma pack(8) these types will only be four-byte aligned.
+// The 64-bit version of gcc has the alignment requirement for these types set to
+// 8 meaning that unless we use #pragma pack(4) our structures will get bigger.
+// The 64-bit structure packing has to match the 32-bit structure packing for each platform.
+#define VALVE_CALLBACK_PACK_SMALL
+#else
+#define VALVE_CALLBACK_PACK_LARGE
+#endif
+
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error ???
+#endif
+
+typedef struct ValvePackingSentinel_t
+{
+ uint32 m_u32;
+ uint64 m_u64;
+ uint16 m_u16;
+ double m_d;
+} ValvePackingSentinel_t;
+
+#pragma pack( pop )
+
+
+#if defined(VALVE_CALLBACK_PACK_SMALL)
+VALVE_COMPILE_TIME_ASSERT( sizeof(ValvePackingSentinel_t) == 24 )
+#elif defined(VALVE_CALLBACK_PACK_LARGE)
+VALVE_COMPILE_TIME_ASSERT( sizeof(ValvePackingSentinel_t) == 32 )
+#else
+#error ???
+#endif
+
+
+// handle to a communication pipe to the Steam client
+typedef int32 HSteamPipe;
+// handle to single instance of a steam user
+typedef int32 HSteamUser;
+// function prototype
+#if defined( POSIX )
+#define __cdecl
+#endif
+extern "C" typedef void (__cdecl *SteamAPIWarningMessageHook_t)(int, const char *);
+extern "C" typedef uint32 ( *SteamAPI_CheckCallbackRegistered_t )( int iCallbackNum );
+#if defined( __SNC__ )
+ #pragma diag_suppress=1700 // warning 1700: class "%s" has virtual functions but non-virtual destructor
+#endif
+
+// interface predec
+class ISteamUser;
+class ISteamGameServer;
+class ISteamFriends;
+class ISteamUtils;
+class ISteamMatchmaking;
+class ISteamContentServer;
+class ISteamMatchmakingServers;
+class ISteamUserStats;
+class ISteamApps;
+class ISteamNetworking;
+class ISteamRemoteStorage;
+class ISteamScreenshots;
+class ISteamMusic;
+class ISteamMusicRemote;
+class ISteamGameServerStats;
+class ISteamPS3OverlayRender;
+class ISteamHTTP;
+class ISteamUnifiedMessages;
+class ISteamController;
+class ISteamUGC;
+class ISteamAppList;
+class ISteamHTMLSurface;
+class ISteamInventory;
+class ISteamVideo;
+
+//-----------------------------------------------------------------------------
+// Purpose: Interface to creating a new steam instance, or to
+// connect to an existing steam instance, whether it's in a
+// different process or is local.
+//
+// For most scenarios this is all handled automatically via SteamAPI_Init().
+// You'll only need these APIs if you have a more complex versioning scheme,
+// or if you want to implement a multiplexed gameserver where a single process
+// is handling multiple games at once with independent gameserver SteamIDs.
+//-----------------------------------------------------------------------------
+class ISteamClient
+{
+public:
+ // Creates a communication pipe to the Steam client.
+ // NOT THREADSAFE - ensure that no other threads are accessing Steamworks API when calling
+ virtual HSteamPipe CreateSteamPipe() = 0;
+
+ // Releases a previously created communications pipe
+ // NOT THREADSAFE - ensure that no other threads are accessing Steamworks API when calling
+ virtual bool BReleaseSteamPipe( HSteamPipe hSteamPipe ) = 0;
+
+ // connects to an existing global user, failing if none exists
+ // used by the game to coordinate with the steamUI
+ // NOT THREADSAFE - ensure that no other threads are accessing Steamworks API when calling
+ virtual HSteamUser ConnectToGlobalUser( HSteamPipe hSteamPipe ) = 0;
+
+ // used by game servers, create a steam user that won't be shared with anyone else
+ // NOT THREADSAFE - ensure that no other threads are accessing Steamworks API when calling
+ virtual HSteamUser CreateLocalUser( HSteamPipe *phSteamPipe, EAccountType eAccountType ) = 0;
+
+ // removes an allocated user
+ // NOT THREADSAFE - ensure that no other threads are accessing Steamworks API when calling
+ virtual void ReleaseUser( HSteamPipe hSteamPipe, HSteamUser hUser ) = 0;
+
+ // retrieves the ISteamUser interface associated with the handle
+ virtual ISteamUser *GetISteamUser( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // retrieves the ISteamGameServer interface associated with the handle
+ virtual ISteamGameServer *GetISteamGameServer( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // set the local IP and Port to bind to
+ // this must be set before CreateLocalUser()
+ virtual void SetLocalIPBinding( uint32 unIP, uint16 usPort ) = 0;
+
+ // returns the ISteamFriends interface
+ virtual ISteamFriends *GetISteamFriends( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns the ISteamUtils interface
+ virtual ISteamUtils *GetISteamUtils( HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns the ISteamMatchmaking interface
+ virtual ISteamMatchmaking *GetISteamMatchmaking( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns the ISteamMatchmakingServers interface
+ virtual ISteamMatchmakingServers *GetISteamMatchmakingServers( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns the a generic interface
+ virtual void *GetISteamGenericInterface( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns the ISteamUserStats interface
+ virtual ISteamUserStats *GetISteamUserStats( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns the ISteamGameServerStats interface
+ virtual ISteamGameServerStats *GetISteamGameServerStats( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns apps interface
+ virtual ISteamApps *GetISteamApps( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // networking
+ virtual ISteamNetworking *GetISteamNetworking( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // remote storage
+ virtual ISteamRemoteStorage *GetISteamRemoteStorage( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // user screenshots
+ virtual ISteamScreenshots *GetISteamScreenshots( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Deprecated. Applications should use SteamAPI_RunCallbacks() or SteamGameServer_RunCallbacks() instead.
+ STEAM_PRIVATE_API( virtual void RunFrame() = 0; )
+
+ // returns the number of IPC calls made since the last time this function was called
+ // Used for perf debugging so you can understand how many IPC calls your game makes per frame
+ // Every IPC call is at minimum a thread context switch if not a process one so you want to rate
+ // control how often you do them.
+ virtual uint32 GetIPCCallCount() = 0;
+
+ // API warning handling
+ // 'int' is the severity; 0 for msg, 1 for warning
+ // 'const char *' is the text of the message
+ // callbacks will occur directly after the API function is called that generated the warning or message.
+ virtual void SetWarningMessageHook( SteamAPIWarningMessageHook_t pFunction ) = 0;
+
+ // Trigger global shutdown for the DLL
+ virtual bool BShutdownIfAllPipesClosed() = 0;
+
+ // Expose HTTP interface
+ virtual ISteamHTTP *GetISteamHTTP( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Exposes the ISteamUnifiedMessages interface
+ virtual ISteamUnifiedMessages *GetISteamUnifiedMessages( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Exposes the ISteamController interface
+ virtual ISteamController *GetISteamController( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Exposes the ISteamUGC interface
+ virtual ISteamUGC *GetISteamUGC( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // returns app list interface, only available on specially registered apps
+ virtual ISteamAppList *GetISteamAppList( HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Music Player
+ virtual ISteamMusic *GetISteamMusic( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Music Player Remote
+ virtual ISteamMusicRemote *GetISteamMusicRemote(HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion) = 0;
+
+ // html page display
+ virtual ISteamHTMLSurface *GetISteamHTMLSurface(HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion) = 0;
+
+ // Helper functions for internal Steam usage
+ STEAM_PRIVATE_API( virtual void DEPRECATED_Set_SteamAPI_CPostAPIResultInProcess( void (*)() ) = 0; )
+ STEAM_PRIVATE_API( virtual void DEPRECATED_Remove_SteamAPI_CPostAPIResultInProcess( void (*)() ) = 0; )
+ STEAM_PRIVATE_API( virtual void Set_SteamAPI_CCheckCallbackRegisteredInProcess( SteamAPI_CheckCallbackRegistered_t func ) = 0; )
+
+ // inventory
+ virtual ISteamInventory *GetISteamInventory( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+
+ // Video
+ virtual ISteamVideo *GetISteamVideo( HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char *pchVersion ) = 0;
+};
+
+
+#define STEAMCLIENT_INTERFACE_VERSION "SteamClient017"
+
+//-----------------------------------------------------------------------------
+// Purpose: Base values for callback identifiers, each callback must
+// have a unique ID.
+//-----------------------------------------------------------------------------
+enum { k_iSteamUserCallbacks = 100 };
+enum { k_iSteamGameServerCallbacks = 200 };
+enum { k_iSteamFriendsCallbacks = 300 };
+enum { k_iSteamBillingCallbacks = 400 };
+enum { k_iSteamMatchmakingCallbacks = 500 };
+enum { k_iSteamContentServerCallbacks = 600 };
+enum { k_iSteamUtilsCallbacks = 700 };
+enum { k_iClientFriendsCallbacks = 800 };
+enum { k_iClientUserCallbacks = 900 };
+enum { k_iSteamAppsCallbacks = 1000 };
+enum { k_iSteamUserStatsCallbacks = 1100 };
+enum { k_iSteamNetworkingCallbacks = 1200 };
+enum { k_iClientRemoteStorageCallbacks = 1300 };
+enum { k_iClientDepotBuilderCallbacks = 1400 };
+enum { k_iSteamGameServerItemsCallbacks = 1500 };
+enum { k_iClientUtilsCallbacks = 1600 };
+enum { k_iSteamGameCoordinatorCallbacks = 1700 };
+enum { k_iSteamGameServerStatsCallbacks = 1800 };
+enum { k_iSteam2AsyncCallbacks = 1900 };
+enum { k_iSteamGameStatsCallbacks = 2000 };
+enum { k_iClientHTTPCallbacks = 2100 };
+enum { k_iClientScreenshotsCallbacks = 2200 };
+enum { k_iSteamScreenshotsCallbacks = 2300 };
+enum { k_iClientAudioCallbacks = 2400 };
+enum { k_iClientUnifiedMessagesCallbacks = 2500 };
+enum { k_iSteamStreamLauncherCallbacks = 2600 };
+enum { k_iClientControllerCallbacks = 2700 };
+enum { k_iSteamControllerCallbacks = 2800 };
+enum { k_iClientParentalSettingsCallbacks = 2900 };
+enum { k_iClientDeviceAuthCallbacks = 3000 };
+enum { k_iClientNetworkDeviceManagerCallbacks = 3100 };
+enum { k_iClientMusicCallbacks = 3200 };
+enum { k_iClientRemoteClientManagerCallbacks = 3300 };
+enum { k_iClientUGCCallbacks = 3400 };
+enum { k_iSteamStreamClientCallbacks = 3500 };
+enum { k_IClientProductBuilderCallbacks = 3600 };
+enum { k_iClientShortcutsCallbacks = 3700 };
+enum { k_iClientRemoteControlManagerCallbacks = 3800 };
+enum { k_iSteamAppListCallbacks = 3900 };
+enum { k_iSteamMusicCallbacks = 4000 };
+enum { k_iSteamMusicRemoteCallbacks = 4100 };
+enum { k_iClientVRCallbacks = 4200 };
+enum { k_iClientGameNotificationCallbacks = 4300 };
+enum { k_iSteamGameNotificationCallbacks = 4400 };
+enum { k_iSteamHTMLSurfaceCallbacks = 4500 };
+enum { k_iClientVideoCallbacks = 4600 };
+enum { k_iClientInventoryCallbacks = 4700 };
+enum { k_iClientBluetoothManagerCallbacks = 4800 };
+
+//-----------------------------------------------------------------------------
+// The CALLBACK macros are for client side callback logging enabled with
+// log_callback
+// Do not change any of these.
+//-----------------------------------------------------------------------------
+
+#ifdef STEAM_CALLBACK_INSPECTION_ENABLED
+
+#define DEFINE_CALLBACK( callbackname, callbackid ) \
+struct callbackname { \
+ typedef callbackname SteamCallback_t; \
+ enum { k_iCallback = callbackid }; \
+ static callbackname *GetNullPointer() { return 0; } \
+ static const char *GetCallbackName() { return #callbackname; } \
+ static uint32 GetCallbackID() { return callbackname::k_iCallback; }
+
+#define CALLBACK_MEMBER( varidx, vartype, varname ) \
+ public: vartype varname ; \
+ static void GetMemberVar_##varidx( unsigned int &varOffset, unsigned int &varSize, uint32 &varCount, const char **pszName, const char **pszType ) { \
+ varOffset = (unsigned int)(size_t)&GetNullPointer()->varname; \
+ varSize = sizeof( vartype ); \
+ varCount = 1; \
+ *pszName = #varname; *pszType = #vartype; }
+
+#define CALLBACK_ARRAY( varidx, vartype, varname, varcount ) \
+ public: vartype varname [ varcount ]; \
+ static void GetMemberVar_##varidx( unsigned int &varOffset, unsigned int &varSize, uint32 &varCount, const char **pszName, const char **pszType ) { \
+ varOffset = (unsigned int)(size_t)&GetNullPointer()->varname[0]; \
+ varSize = sizeof( vartype ); \
+ varCount = varcount; \
+ *pszName = #varname; *pszType = #vartype; }
+
+
+#define END_CALLBACK_INTERNAL_BEGIN( numvars ) \
+ static uint32 GetNumMemberVariables() { return numvars; } \
+ static bool GetMemberVariable( uint32 index, uint32 &varOffset, uint32 &varSize, uint32 &varCount, const char **pszName, const char **pszType ) { \
+ switch ( index ) { default : return false;
+
+
+#define END_CALLBACK_INTERNAL_SWITCH( varidx ) case varidx : GetMemberVar_##varidx( varOffset, varSize, varCount, pszName, pszType ); return true;
+
+#define END_CALLBACK_INTERNAL_END() }; } };
+
+#define END_DEFINE_CALLBACK_0() \
+ static uint32 GetNumMemberVariables() { return 0; } \
+ static bool GetMemberVariable( uint32 index, uint32 &varOffset, uint32 &varSize, uint32 &varCount, const char **pszName, const char **pszType ) { REFERENCE( pszType ); REFERENCE( pszName ); REFERENCE( varCount ); REFERENCE( varSize ); REFERENCE( varOffset ); REFERENCE( index ); return false; } \
+ };
+
+#else
+
+#define DEFINE_CALLBACK( callbackname, callbackid ) struct callbackname { typedef callbackname SteamCallback_t; enum { k_iCallback = callbackid };
+#define CALLBACK_MEMBER( varidx, vartype, varname ) public: vartype varname ;
+#define CALLBACK_ARRAY( varidx, vartype, varname, varcount ) public: vartype varname [ varcount ];
+#define END_CALLBACK_INTERNAL_BEGIN( numvars )
+#define END_CALLBACK_INTERNAL_SWITCH( varidx )
+#define END_CALLBACK_INTERNAL_END() };
+#define END_DEFINE_CALLBACK_0() };
+
+#endif
+
+#define END_DEFINE_CALLBACK_1() \
+ END_CALLBACK_INTERNAL_BEGIN( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_2() \
+ END_CALLBACK_INTERNAL_BEGIN( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_3() \
+ END_CALLBACK_INTERNAL_BEGIN( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_4() \
+ END_CALLBACK_INTERNAL_BEGIN( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_5() \
+ END_CALLBACK_INTERNAL_BEGIN( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_END()
+
+
+#define END_DEFINE_CALLBACK_6() \
+ END_CALLBACK_INTERNAL_BEGIN( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_7() \
+ END_CALLBACK_INTERNAL_BEGIN( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_8() \
+ END_CALLBACK_INTERNAL_BEGIN( 8 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_9() \
+ END_CALLBACK_INTERNAL_BEGIN( 9 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 8 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_10() \
+ END_CALLBACK_INTERNAL_BEGIN( 10 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 8 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 9 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_11() \
+ END_CALLBACK_INTERNAL_BEGIN( 11 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 8 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 9 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 10 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_12() \
+ END_CALLBACK_INTERNAL_BEGIN( 12 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 8 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 9 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 10 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 11 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_13() \
+ END_CALLBACK_INTERNAL_BEGIN( 13 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 8 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 9 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 10 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 11 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 12 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#define END_DEFINE_CALLBACK_14() \
+ END_CALLBACK_INTERNAL_BEGIN( 14 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 0 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 1 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 2 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 3 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 4 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 5 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 6 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 7 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 8 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 9 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 10 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 11 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 12 ) \
+ END_CALLBACK_INTERNAL_SWITCH( 13 ) \
+ END_CALLBACK_INTERNAL_END()
+
+#endif // ISTEAMCLIENT_H
diff --git a/dep/steam_api/isteamcontroller.h b/dep/steam_api/isteamcontroller.h
new file mode 100644
index 0000000..c39a48b
--- /dev/null
+++ b/dep/steam_api/isteamcontroller.h
@@ -0,0 +1,440 @@
+//====== Copyright 1996-2013, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to valve controller
+//
+//=============================================================================
+
+#ifndef ISTEAMCONTROLLER_H
+#define ISTEAMCONTROLLER_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+#define STEAM_CONTROLLER_MAX_COUNT 16
+
+#define STEAM_CONTROLLER_MAX_ANALOG_ACTIONS 16
+
+#define STEAM_CONTROLLER_MAX_DIGITAL_ACTIONS 128
+
+#define STEAM_CONTROLLER_MAX_ORIGINS 8
+
+// When sending an option to a specific controller handle, you can send to all controllers via this command
+#define STEAM_CONTROLLER_HANDLE_ALL_CONTROLLERS UINT64_MAX
+
+#define STEAM_CONTROLLER_MIN_ANALOG_ACTION_DATA -1.0f
+#define STEAM_CONTROLLER_MAX_ANALOG_ACTION_DATA 1.0f
+
+enum ESteamControllerPad
+{
+ k_ESteamControllerPad_Left,
+ k_ESteamControllerPad_Right
+};
+
+enum EControllerSource
+{
+ k_EControllerSource_None,
+ k_EControllerSource_LeftTrackpad,
+ k_EControllerSource_RightTrackpad,
+ k_EControllerSource_Joystick,
+ k_EControllerSource_ABXY,
+ k_EControllerSource_Switch,
+ k_EControllerSource_LeftTrigger,
+ k_EControllerSource_RightTrigger,
+ k_EControllerSource_Gyro,
+ k_EControllerSource_CenterTrackpad, // PS4
+ k_EControllerSource_RightJoystick, // Traditional Controllers
+ k_EControllerSource_DPad, // Traditional Controllers
+ k_EControllerSource_Count
+};
+
+enum EControllerSourceMode
+{
+ k_EControllerSourceMode_None,
+ k_EControllerSourceMode_Dpad,
+ k_EControllerSourceMode_Buttons,
+ k_EControllerSourceMode_FourButtons,
+ k_EControllerSourceMode_AbsoluteMouse,
+ k_EControllerSourceMode_RelativeMouse,
+ k_EControllerSourceMode_JoystickMove,
+ k_EControllerSourceMode_JoystickMouse,
+ k_EControllerSourceMode_JoystickCamera,
+ k_EControllerSourceMode_ScrollWheel,
+ k_EControllerSourceMode_Trigger,
+ k_EControllerSourceMode_TouchMenu,
+ k_EControllerSourceMode_MouseJoystick,
+ k_EControllerSourceMode_MouseRegion,
+ k_EControllerSourceMode_RadialMenu,
+ k_EControllerSourceMode_SingleButton,
+ k_EControllerSourceMode_Switches
+};
+
+enum EControllerActionOrigin
+{
+ // Steam Controller
+ k_EControllerActionOrigin_None,
+ k_EControllerActionOrigin_A,
+ k_EControllerActionOrigin_B,
+ k_EControllerActionOrigin_X,
+ k_EControllerActionOrigin_Y,
+ k_EControllerActionOrigin_LeftBumper,
+ k_EControllerActionOrigin_RightBumper,
+ k_EControllerActionOrigin_LeftGrip,
+ k_EControllerActionOrigin_RightGrip,
+ k_EControllerActionOrigin_Start,
+ k_EControllerActionOrigin_Back,
+ k_EControllerActionOrigin_LeftPad_Touch,
+ k_EControllerActionOrigin_LeftPad_Swipe,
+ k_EControllerActionOrigin_LeftPad_Click,
+ k_EControllerActionOrigin_LeftPad_DPadNorth,
+ k_EControllerActionOrigin_LeftPad_DPadSouth,
+ k_EControllerActionOrigin_LeftPad_DPadWest,
+ k_EControllerActionOrigin_LeftPad_DPadEast,
+ k_EControllerActionOrigin_RightPad_Touch,
+ k_EControllerActionOrigin_RightPad_Swipe,
+ k_EControllerActionOrigin_RightPad_Click,
+ k_EControllerActionOrigin_RightPad_DPadNorth,
+ k_EControllerActionOrigin_RightPad_DPadSouth,
+ k_EControllerActionOrigin_RightPad_DPadWest,
+ k_EControllerActionOrigin_RightPad_DPadEast,
+ k_EControllerActionOrigin_LeftTrigger_Pull,
+ k_EControllerActionOrigin_LeftTrigger_Click,
+ k_EControllerActionOrigin_RightTrigger_Pull,
+ k_EControllerActionOrigin_RightTrigger_Click,
+ k_EControllerActionOrigin_LeftStick_Move,
+ k_EControllerActionOrigin_LeftStick_Click,
+ k_EControllerActionOrigin_LeftStick_DPadNorth,
+ k_EControllerActionOrigin_LeftStick_DPadSouth,
+ k_EControllerActionOrigin_LeftStick_DPadWest,
+ k_EControllerActionOrigin_LeftStick_DPadEast,
+ k_EControllerActionOrigin_Gyro_Move,
+ k_EControllerActionOrigin_Gyro_Pitch,
+ k_EControllerActionOrigin_Gyro_Yaw,
+ k_EControllerActionOrigin_Gyro_Roll,
+
+ // PS4 Dual Shock
+ k_EControllerActionOrigin_PS4_X,
+ k_EControllerActionOrigin_PS4_Circle,
+ k_EControllerActionOrigin_PS4_Triangle,
+ k_EControllerActionOrigin_PS4_Square,
+ k_EControllerActionOrigin_PS4_LeftBumper,
+ k_EControllerActionOrigin_PS4_RightBumper,
+ k_EControllerActionOrigin_PS4_Options, //Start
+ k_EControllerActionOrigin_PS4_Share, //Back
+ k_EControllerActionOrigin_PS4_LeftPad_Touch,
+ k_EControllerActionOrigin_PS4_LeftPad_Swipe,
+ k_EControllerActionOrigin_PS4_LeftPad_Click,
+ k_EControllerActionOrigin_PS4_LeftPad_DPadNorth,
+ k_EControllerActionOrigin_PS4_LeftPad_DPadSouth,
+ k_EControllerActionOrigin_PS4_LeftPad_DPadWest,
+ k_EControllerActionOrigin_PS4_LeftPad_DPadEast,
+ k_EControllerActionOrigin_PS4_RightPad_Touch,
+ k_EControllerActionOrigin_PS4_RightPad_Swipe,
+ k_EControllerActionOrigin_PS4_RightPad_Click,
+ k_EControllerActionOrigin_PS4_RightPad_DPadNorth,
+ k_EControllerActionOrigin_PS4_RightPad_DPadSouth,
+ k_EControllerActionOrigin_PS4_RightPad_DPadWest,
+ k_EControllerActionOrigin_PS4_RightPad_DPadEast,
+ k_EControllerActionOrigin_PS4_CenterPad_Touch,
+ k_EControllerActionOrigin_PS4_CenterPad_Swipe,
+ k_EControllerActionOrigin_PS4_CenterPad_Click,
+ k_EControllerActionOrigin_PS4_CenterPad_DPadNorth,
+ k_EControllerActionOrigin_PS4_CenterPad_DPadSouth,
+ k_EControllerActionOrigin_PS4_CenterPad_DPadWest,
+ k_EControllerActionOrigin_PS4_CenterPad_DPadEast,
+ k_EControllerActionOrigin_PS4_LeftTrigger_Pull,
+ k_EControllerActionOrigin_PS4_LeftTrigger_Click,
+ k_EControllerActionOrigin_PS4_RightTrigger_Pull,
+ k_EControllerActionOrigin_PS4_RightTrigger_Click,
+ k_EControllerActionOrigin_PS4_LeftStick_Move,
+ k_EControllerActionOrigin_PS4_LeftStick_Click,
+ k_EControllerActionOrigin_PS4_LeftStick_DPadNorth,
+ k_EControllerActionOrigin_PS4_LeftStick_DPadSouth,
+ k_EControllerActionOrigin_PS4_LeftStick_DPadWest,
+ k_EControllerActionOrigin_PS4_LeftStick_DPadEast,
+ k_EControllerActionOrigin_PS4_RightStick_Move,
+ k_EControllerActionOrigin_PS4_RightStick_Click,
+ k_EControllerActionOrigin_PS4_RightStick_DPadNorth,
+ k_EControllerActionOrigin_PS4_RightStick_DPadSouth,
+ k_EControllerActionOrigin_PS4_RightStick_DPadWest,
+ k_EControllerActionOrigin_PS4_RightStick_DPadEast,
+ k_EControllerActionOrigin_PS4_DPad_North,
+ k_EControllerActionOrigin_PS4_DPad_South,
+ k_EControllerActionOrigin_PS4_DPad_West,
+ k_EControllerActionOrigin_PS4_DPad_East,
+ k_EControllerActionOrigin_PS4_Gyro_Move,
+ k_EControllerActionOrigin_PS4_Gyro_Pitch,
+ k_EControllerActionOrigin_PS4_Gyro_Yaw,
+ k_EControllerActionOrigin_PS4_Gyro_Roll,
+
+ // XBox One
+ k_EControllerActionOrigin_XBoxOne_A,
+ k_EControllerActionOrigin_XBoxOne_B,
+ k_EControllerActionOrigin_XBoxOne_X,
+ k_EControllerActionOrigin_XBoxOne_Y,
+ k_EControllerActionOrigin_XBoxOne_LeftBumper,
+ k_EControllerActionOrigin_XBoxOne_RightBumper,
+ k_EControllerActionOrigin_XBoxOne_Menu, //Start
+ k_EControllerActionOrigin_XBoxOne_View, //Back
+ k_EControllerActionOrigin_XBoxOne_LeftTrigger_Pull,
+ k_EControllerActionOrigin_XBoxOne_LeftTrigger_Click,
+ k_EControllerActionOrigin_XBoxOne_RightTrigger_Pull,
+ k_EControllerActionOrigin_XBoxOne_RightTrigger_Click,
+ k_EControllerActionOrigin_XBoxOne_LeftStick_Move,
+ k_EControllerActionOrigin_XBoxOne_LeftStick_Click,
+ k_EControllerActionOrigin_XBoxOne_LeftStick_DPadNorth,
+ k_EControllerActionOrigin_XBoxOne_LeftStick_DPadSouth,
+ k_EControllerActionOrigin_XBoxOne_LeftStick_DPadWest,
+ k_EControllerActionOrigin_XBoxOne_LeftStick_DPadEast,
+ k_EControllerActionOrigin_XBoxOne_RightStick_Move,
+ k_EControllerActionOrigin_XBoxOne_RightStick_Click,
+ k_EControllerActionOrigin_XBoxOne_RightStick_DPadNorth,
+ k_EControllerActionOrigin_XBoxOne_RightStick_DPadSouth,
+ k_EControllerActionOrigin_XBoxOne_RightStick_DPadWest,
+ k_EControllerActionOrigin_XBoxOne_RightStick_DPadEast,
+ k_EControllerActionOrigin_XBoxOne_DPad_North,
+ k_EControllerActionOrigin_XBoxOne_DPad_South,
+ k_EControllerActionOrigin_XBoxOne_DPad_West,
+ k_EControllerActionOrigin_XBoxOne_DPad_East,
+
+ // XBox 360
+ k_EControllerActionOrigin_XBox360_A,
+ k_EControllerActionOrigin_XBox360_B,
+ k_EControllerActionOrigin_XBox360_X,
+ k_EControllerActionOrigin_XBox360_Y,
+ k_EControllerActionOrigin_XBox360_LeftBumper,
+ k_EControllerActionOrigin_XBox360_RightBumper,
+ k_EControllerActionOrigin_XBox360_Start, //Start
+ k_EControllerActionOrigin_XBox360_Back, //Back
+ k_EControllerActionOrigin_XBox360_LeftTrigger_Pull,
+ k_EControllerActionOrigin_XBox360_LeftTrigger_Click,
+ k_EControllerActionOrigin_XBox360_RightTrigger_Pull,
+ k_EControllerActionOrigin_XBox360_RightTrigger_Click,
+ k_EControllerActionOrigin_XBox360_LeftStick_Move,
+ k_EControllerActionOrigin_XBox360_LeftStick_Click,
+ k_EControllerActionOrigin_XBox360_LeftStick_DPadNorth,
+ k_EControllerActionOrigin_XBox360_LeftStick_DPadSouth,
+ k_EControllerActionOrigin_XBox360_LeftStick_DPadWest,
+ k_EControllerActionOrigin_XBox360_LeftStick_DPadEast,
+ k_EControllerActionOrigin_XBox360_RightStick_Move,
+ k_EControllerActionOrigin_XBox360_RightStick_Click,
+ k_EControllerActionOrigin_XBox360_RightStick_DPadNorth,
+ k_EControllerActionOrigin_XBox360_RightStick_DPadSouth,
+ k_EControllerActionOrigin_XBox360_RightStick_DPadWest,
+ k_EControllerActionOrigin_XBox360_RightStick_DPadEast,
+ k_EControllerActionOrigin_XBox360_DPad_North,
+ k_EControllerActionOrigin_XBox360_DPad_South,
+ k_EControllerActionOrigin_XBox360_DPad_West,
+ k_EControllerActionOrigin_XBox360_DPad_East,
+
+ // SteamController V2
+ k_EControllerActionOrigin_SteamV2_A,
+ k_EControllerActionOrigin_SteamV2_B,
+ k_EControllerActionOrigin_SteamV2_X,
+ k_EControllerActionOrigin_SteamV2_Y,
+ k_EControllerActionOrigin_SteamV2_LeftBumper,
+ k_EControllerActionOrigin_SteamV2_RightBumper,
+ k_EControllerActionOrigin_SteamV2_LeftGrip,
+ k_EControllerActionOrigin_SteamV2_RightGrip,
+ k_EControllerActionOrigin_SteamV2_LeftGrip_Upper,
+ k_EControllerActionOrigin_SteamV2_RightGrip_Upper,
+ k_EControllerActionOrigin_SteamV2_LeftBumper_Pressure,
+ k_EControllerActionOrigin_SteamV2_RightBumper_Pressure,
+ k_EControllerActionOrigin_SteamV2_LeftGrip_Pressure,
+ k_EControllerActionOrigin_SteamV2_RightGrip_Pressure,
+ k_EControllerActionOrigin_SteamV2_LeftGrip_Upper_Pressure,
+ k_EControllerActionOrigin_SteamV2_RightGrip_Upper_Pressure,
+ k_EControllerActionOrigin_SteamV2_Start,
+ k_EControllerActionOrigin_SteamV2_Back,
+ k_EControllerActionOrigin_SteamV2_LeftPad_Touch,
+ k_EControllerActionOrigin_SteamV2_LeftPad_Swipe,
+ k_EControllerActionOrigin_SteamV2_LeftPad_Click,
+ k_EControllerActionOrigin_SteamV2_LeftPad_Pressure,
+ k_EControllerActionOrigin_SteamV2_LeftPad_DPadNorth,
+ k_EControllerActionOrigin_SteamV2_LeftPad_DPadSouth,
+ k_EControllerActionOrigin_SteamV2_LeftPad_DPadWest,
+ k_EControllerActionOrigin_SteamV2_LeftPad_DPadEast,
+ k_EControllerActionOrigin_SteamV2_RightPad_Touch,
+ k_EControllerActionOrigin_SteamV2_RightPad_Swipe,
+ k_EControllerActionOrigin_SteamV2_RightPad_Click,
+ k_EControllerActionOrigin_SteamV2_RightPad_Pressure,
+ k_EControllerActionOrigin_SteamV2_RightPad_DPadNorth,
+ k_EControllerActionOrigin_SteamV2_RightPad_DPadSouth,
+ k_EControllerActionOrigin_SteamV2_RightPad_DPadWest,
+ k_EControllerActionOrigin_SteamV2_RightPad_DPadEast,
+ k_EControllerActionOrigin_SteamV2_LeftTrigger_Pull,
+ k_EControllerActionOrigin_SteamV2_LeftTrigger_Click,
+ k_EControllerActionOrigin_SteamV2_RightTrigger_Pull,
+ k_EControllerActionOrigin_SteamV2_RightTrigger_Click,
+ k_EControllerActionOrigin_SteamV2_LeftStick_Move,
+ k_EControllerActionOrigin_SteamV2_LeftStick_Click,
+ k_EControllerActionOrigin_SteamV2_LeftStick_DPadNorth,
+ k_EControllerActionOrigin_SteamV2_LeftStick_DPadSouth,
+ k_EControllerActionOrigin_SteamV2_LeftStick_DPadWest,
+ k_EControllerActionOrigin_SteamV2_LeftStick_DPadEast,
+ k_EControllerActionOrigin_SteamV2_Gyro_Move,
+ k_EControllerActionOrigin_SteamV2_Gyro_Pitch,
+ k_EControllerActionOrigin_SteamV2_Gyro_Yaw,
+ k_EControllerActionOrigin_SteamV2_Gyro_Roll,
+
+ k_EControllerActionOrigin_Count
+};
+
+enum ESteamControllerLEDFlag
+{
+ k_ESteamControllerLEDFlag_SetColor,
+ k_ESteamControllerLEDFlag_RestoreUserDefault
+};
+
+// ControllerHandle_t is used to refer to a specific controller.
+// This handle will consistently identify a controller, even if it is disconnected and re-connected
+typedef uint64 ControllerHandle_t;
+
+
+// These handles are used to refer to a specific in-game action or action set
+// All action handles should be queried during initialization for performance reasons
+typedef uint64 ControllerActionSetHandle_t;
+typedef uint64 ControllerDigitalActionHandle_t;
+typedef uint64 ControllerAnalogActionHandle_t;
+
+#pragma pack( push, 1 )
+
+struct ControllerAnalogActionData_t
+{
+ // Type of data coming from this action, this will match what got specified in the action set
+ EControllerSourceMode eMode;
+
+ // The current state of this action; will be delta updates for mouse actions
+ float x, y;
+
+ // Whether or not this action is currently available to be bound in the active action set
+ bool bActive;
+};
+
+struct ControllerDigitalActionData_t
+{
+ // The current state of this action; will be true if currently pressed
+ bool bState;
+
+ // Whether or not this action is currently available to be bound in the active action set
+ bool bActive;
+};
+
+struct ControllerMotionData_t
+{
+ // Sensor-fused absolute rotation; will drift in heading
+ float rotQuatX;
+ float rotQuatY;
+ float rotQuatZ;
+ float rotQuatW;
+
+ // Positional acceleration
+ float posAccelX;
+ float posAccelY;
+ float posAccelZ;
+
+ // Angular velocity
+ float rotVelX;
+ float rotVelY;
+ float rotVelZ;
+};
+
+#pragma pack( pop )
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Native Steam controller support API
+//-----------------------------------------------------------------------------
+class ISteamController
+{
+public:
+
+ // Init and Shutdown must be called when starting/ending use of this interface
+ virtual bool Init() = 0;
+ virtual bool Shutdown() = 0;
+
+ // Synchronize API state with the latest Steam Controller inputs available. This
+ // is performed automatically by SteamAPI_RunCallbacks, but for the absolute lowest
+ // possible latency, you call this directly before reading controller state.
+ virtual void RunFrame() = 0;
+
+ // Enumerate currently connected controllers
+ // handlesOut should point to a STEAM_CONTROLLER_MAX_COUNT sized array of ControllerHandle_t handles
+ // Returns the number of handles written to handlesOut
+ virtual int GetConnectedControllers( ControllerHandle_t *handlesOut ) = 0;
+
+ // Invokes the Steam overlay and brings up the binding screen
+ // Returns false is overlay is disabled / unavailable, or the user is not in Big Picture mode
+ virtual bool ShowBindingPanel( ControllerHandle_t controllerHandle ) = 0;
+
+ // ACTION SETS
+ // Lookup the handle for an Action Set. Best to do this once on startup, and store the handles for all future API calls.
+ virtual ControllerActionSetHandle_t GetActionSetHandle( const char *pszActionSetName ) = 0;
+
+ // Reconfigure the controller to use the specified action set (ie 'Menu', 'Walk' or 'Drive')
+ // This is cheap, and can be safely called repeatedly. It's often easier to repeatedly call it in
+ // your state loops, instead of trying to place it in all of your state transitions.
+ virtual void ActivateActionSet( ControllerHandle_t controllerHandle, ControllerActionSetHandle_t actionSetHandle ) = 0;
+ virtual ControllerActionSetHandle_t GetCurrentActionSet( ControllerHandle_t controllerHandle ) = 0;
+
+ // ACTIONS
+ // Lookup the handle for a digital action. Best to do this once on startup, and store the handles for all future API calls.
+ virtual ControllerDigitalActionHandle_t GetDigitalActionHandle( const char *pszActionName ) = 0;
+
+ // Returns the current state of the supplied digital game action
+ virtual ControllerDigitalActionData_t GetDigitalActionData( ControllerHandle_t controllerHandle, ControllerDigitalActionHandle_t digitalActionHandle ) = 0;
+
+ // Get the origin(s) for a digital action within an action set. Returns the number of origins supplied in originsOut. Use this to display the appropriate on-screen prompt for the action.
+ // originsOut should point to a STEAM_CONTROLLER_MAX_ORIGINS sized array of EControllerActionOrigin handles
+ virtual int GetDigitalActionOrigins( ControllerHandle_t controllerHandle, ControllerActionSetHandle_t actionSetHandle, ControllerDigitalActionHandle_t digitalActionHandle, EControllerActionOrigin *originsOut ) = 0;
+
+ // Lookup the handle for an analog action. Best to do this once on startup, and store the handles for all future API calls.
+ virtual ControllerAnalogActionHandle_t GetAnalogActionHandle( const char *pszActionName ) = 0;
+
+ // Returns the current state of these supplied analog game action
+ virtual ControllerAnalogActionData_t GetAnalogActionData( ControllerHandle_t controllerHandle, ControllerAnalogActionHandle_t analogActionHandle ) = 0;
+
+ // Get the origin(s) for an analog action within an action set. Returns the number of origins supplied in originsOut. Use this to display the appropriate on-screen prompt for the action.
+ // originsOut should point to a STEAM_CONTROLLER_MAX_ORIGINS sized array of EControllerActionOrigin handles
+ virtual int GetAnalogActionOrigins( ControllerHandle_t controllerHandle, ControllerActionSetHandle_t actionSetHandle, ControllerAnalogActionHandle_t analogActionHandle, EControllerActionOrigin *originsOut ) = 0;
+
+ virtual void StopAnalogActionMomentum( ControllerHandle_t controllerHandle, ControllerAnalogActionHandle_t eAction ) = 0;
+
+ // Trigger a haptic pulse on a controller
+ virtual void TriggerHapticPulse( ControllerHandle_t controllerHandle, ESteamControllerPad eTargetPad, unsigned short usDurationMicroSec ) = 0;
+
+ // Trigger a pulse with a duty cycle of usDurationMicroSec / usOffMicroSec, unRepeat times.
+ // nFlags is currently unused and reserved for future use.
+ virtual void TriggerRepeatedHapticPulse( ControllerHandle_t controllerHandle, ESteamControllerPad eTargetPad, unsigned short usDurationMicroSec, unsigned short usOffMicroSec, unsigned short unRepeat, unsigned int nFlags ) = 0;
+
+ // Tigger a vibration event on supported controllers.
+ virtual void TriggerVibration( ControllerHandle_t controllerHandle, unsigned short usLeftSpeed, unsigned short usRightSpeed ) = 0;
+
+ // Set the controller LED color on supported controllers.
+ virtual void SetLEDColor( ControllerHandle_t controllerHandle, uint8 nColorR, uint8 nColorG, uint8 nColorB, unsigned int nFlags ) = 0;
+
+ // Returns the associated gamepad index for the specified controller, if emulating a gamepad
+ virtual int GetGamepadIndexForController( ControllerHandle_t ulControllerHandle ) = 0;
+
+ // Returns the associated controller handle for the specified emulated gamepad
+ virtual ControllerHandle_t GetControllerForGamepadIndex( int nIndex ) = 0;
+
+ // Returns raw motion data from the specified controller
+ virtual ControllerMotionData_t GetMotionData( ControllerHandle_t controllerHandle ) = 0;
+
+ // Attempt to display origins of given action in the controller HUD, for the currently active action set
+ // Returns false is overlay is disabled / unavailable, or the user is not in Big Picture mode
+ virtual bool ShowDigitalActionOrigins( ControllerHandle_t controllerHandle, ControllerDigitalActionHandle_t digitalActionHandle, float flScale, float flXPosition, float flYPosition ) = 0;
+ virtual bool ShowAnalogActionOrigins( ControllerHandle_t controllerHandle, ControllerAnalogActionHandle_t analogActionHandle, float flScale, float flXPosition, float flYPosition ) = 0;
+
+ // Returns a localized string (from Steam's language setting) for the specified origin
+ virtual const char *GetStringForActionOrigin( EControllerActionOrigin eOrigin ) = 0;
+
+ // Get a local path to art for on-screen glyph for a particular origin
+ virtual const char *GetGlyphForActionOrigin( EControllerActionOrigin eOrigin ) = 0;
+};
+
+#define STEAMCONTROLLER_INTERFACE_VERSION "SteamController005"
+
+#endif // ISTEAMCONTROLLER_H
diff --git a/dep/steam_api/isteamfriends.h b/dep/steam_api/isteamfriends.h
new file mode 100644
index 0000000..29827b6
--- /dev/null
+++ b/dep/steam_api/isteamfriends.h
@@ -0,0 +1,636 @@
+//====== Copyright (C) 1996-2008, Valve Corporation, All rights reserved. =====
+//
+// Purpose: interface to both friends list data and general information about users
+//
+//=============================================================================
+
+#ifndef ISTEAMFRIENDS_H
+#define ISTEAMFRIENDS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+#include "steamclientpublic.h"
+
+
+//-----------------------------------------------------------------------------
+// Purpose: set of relationships to other users
+//-----------------------------------------------------------------------------
+enum EFriendRelationship
+{
+ k_EFriendRelationshipNone = 0,
+ k_EFriendRelationshipBlocked = 1, // this doesn't get stored; the user has just done an Ignore on an friendship invite
+ k_EFriendRelationshipRequestRecipient = 2,
+ k_EFriendRelationshipFriend = 3,
+ k_EFriendRelationshipRequestInitiator = 4,
+ k_EFriendRelationshipIgnored = 5, // this is stored; the user has explicit blocked this other user from comments/chat/etc
+ k_EFriendRelationshipIgnoredFriend = 6,
+ k_EFriendRelationshipSuggested_DEPRECATED = 7, // was used by the original implementation of the facebook linking feature, but now unused.
+
+ // keep this updated
+ k_EFriendRelationshipMax = 8,
+};
+
+// maximum length of friend group name (not including terminating nul!)
+const int k_cchMaxFriendsGroupName = 64;
+
+// maximum number of groups a single user is allowed
+const int k_cFriendsGroupLimit = 100;
+
+// friends group identifier type
+typedef int16 FriendsGroupID_t;
+
+// invalid friends group identifier constant
+const FriendsGroupID_t k_FriendsGroupID_Invalid = -1;
+
+const int k_cEnumerateFollowersMax = 50;
+
+
+//-----------------------------------------------------------------------------
+// Purpose: list of states a friend can be in
+//-----------------------------------------------------------------------------
+enum EPersonaState
+{
+ k_EPersonaStateOffline = 0, // friend is not currently logged on
+ k_EPersonaStateOnline = 1, // friend is logged on
+ k_EPersonaStateBusy = 2, // user is on, but busy
+ k_EPersonaStateAway = 3, // auto-away feature
+ k_EPersonaStateSnooze = 4, // auto-away for a long time
+ k_EPersonaStateLookingToTrade = 5, // Online, trading
+ k_EPersonaStateLookingToPlay = 6, // Online, wanting to play
+ k_EPersonaStateMax,
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: flags for enumerating friends list, or quickly checking a the relationship between users
+//-----------------------------------------------------------------------------
+enum EFriendFlags
+{
+ k_EFriendFlagNone = 0x00,
+ k_EFriendFlagBlocked = 0x01,
+ k_EFriendFlagFriendshipRequested = 0x02,
+ k_EFriendFlagImmediate = 0x04, // "regular" friend
+ k_EFriendFlagClanMember = 0x08,
+ k_EFriendFlagOnGameServer = 0x10,
+ // k_EFriendFlagHasPlayedWith = 0x20, // not currently used
+ // k_EFriendFlagFriendOfFriend = 0x40, // not currently used
+ k_EFriendFlagRequestingFriendship = 0x80,
+ k_EFriendFlagRequestingInfo = 0x100,
+ k_EFriendFlagIgnored = 0x200,
+ k_EFriendFlagIgnoredFriend = 0x400,
+ // k_EFriendFlagSuggested = 0x800, // not used
+ k_EFriendFlagChatMember = 0x1000,
+ k_EFriendFlagAll = 0xFFFF,
+};
+
+
+// friend game played information
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+struct FriendGameInfo_t
+{
+ CGameID m_gameID;
+ uint32 m_unGameIP;
+ uint16 m_usGamePort;
+ uint16 m_usQueryPort;
+ CSteamID m_steamIDLobby;
+};
+#pragma pack( pop )
+
+// maximum number of characters in a user's name. Two flavors; one for UTF-8 and one for UTF-16.
+// The UTF-8 version has to be very generous to accomodate characters that get large when encoded
+// in UTF-8.
+enum
+{
+ k_cchPersonaNameMax = 128,
+ k_cwchPersonaNameMax = 32,
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: user restriction flags
+//-----------------------------------------------------------------------------
+enum EUserRestriction
+{
+ k_nUserRestrictionNone = 0, // no known chat/content restriction
+ k_nUserRestrictionUnknown = 1, // we don't know yet (user offline)
+ k_nUserRestrictionAnyChat = 2, // user is not allowed to (or can't) send/recv any chat
+ k_nUserRestrictionVoiceChat = 4, // user is not allowed to (or can't) send/recv voice chat
+ k_nUserRestrictionGroupChat = 8, // user is not allowed to (or can't) send/recv group chat
+ k_nUserRestrictionRating = 16, // user is too young according to rating in current region
+ k_nUserRestrictionGameInvites = 32, // user cannot send or recv game invites (e.g. mobile)
+ k_nUserRestrictionTrading = 64, // user cannot participate in trading (console, mobile)
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: information about user sessions
+//-----------------------------------------------------------------------------
+struct FriendSessionStateInfo_t
+{
+ uint32 m_uiOnlineSessionInstances;
+ uint8 m_uiPublishedToFriendsSessionInstance;
+};
+
+
+
+// size limit on chat room or member metadata
+const uint32 k_cubChatMetadataMax = 8192;
+
+// size limits on Rich Presence data
+enum { k_cchMaxRichPresenceKeys = 20 };
+enum { k_cchMaxRichPresenceKeyLength = 64 };
+enum { k_cchMaxRichPresenceValueLength = 256 };
+
+// These values are passed as parameters to the store
+enum EOverlayToStoreFlag
+{
+ k_EOverlayToStoreFlag_None = 0,
+ k_EOverlayToStoreFlag_AddToCart = 1,
+ k_EOverlayToStoreFlag_AddToCartAndShow = 2,
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: interface to accessing information about individual users,
+// that can be a friend, in a group, on a game server or in a lobby with the local user
+//-----------------------------------------------------------------------------
+class ISteamFriends
+{
+public:
+ // returns the local players name - guaranteed to not be NULL.
+ // this is the same name as on the users community profile page
+ // this is stored in UTF-8 format
+ // like all the other interface functions that return a char *, it's important that this pointer is not saved
+ // off; it will eventually be free'd or re-allocated
+ virtual const char *GetPersonaName() = 0;
+
+ // Sets the player name, stores it on the server and publishes the changes to all friends who are online.
+ // Changes take place locally immediately, and a PersonaStateChange_t is posted, presuming success.
+ //
+ // The final results are available through the return value SteamAPICall_t, using SetPersonaNameResponse_t.
+ //
+ // If the name change fails to happen on the server, then an additional global PersonaStateChange_t will be posted
+ // to change the name back, in addition to the SetPersonaNameResponse_t callback.
+ CALL_RESULT( SetPersonaNameResponse_t )
+ virtual SteamAPICall_t SetPersonaName( const char *pchPersonaName ) = 0;
+
+ // gets the status of the current user
+ virtual EPersonaState GetPersonaState() = 0;
+
+ // friend iteration
+ // takes a set of k_EFriendFlags, and returns the number of users the client knows about who meet that criteria
+ // then GetFriendByIndex() can then be used to return the id's of each of those users
+ virtual int GetFriendCount( int iFriendFlags ) = 0;
+
+ // returns the steamID of a user
+ // iFriend is a index of range [0, GetFriendCount())
+ // iFriendsFlags must be the same value as used in GetFriendCount()
+ // the returned CSteamID can then be used by all the functions below to access details about the user
+ virtual CSteamID GetFriendByIndex( int iFriend, int iFriendFlags ) = 0;
+
+ // returns a relationship to a user
+ virtual EFriendRelationship GetFriendRelationship( CSteamID steamIDFriend ) = 0;
+
+ // returns the current status of the specified user
+ // this will only be known by the local user if steamIDFriend is in their friends list; on the same game server; in a chat room or lobby; or in a small group with the local user
+ virtual EPersonaState GetFriendPersonaState( CSteamID steamIDFriend ) = 0;
+
+ // returns the name another user - guaranteed to not be NULL.
+ // same rules as GetFriendPersonaState() apply as to whether or not the user knowns the name of the other user
+ // note that on first joining a lobby, chat room or game server the local user will not known the name of the other users automatically; that information will arrive asyncronously
+ //
+ virtual const char *GetFriendPersonaName( CSteamID steamIDFriend ) = 0;
+
+ // returns true if the friend is actually in a game, and fills in pFriendGameInfo with an extra details
+ virtual bool GetFriendGamePlayed( CSteamID steamIDFriend, OUT_STRUCT() FriendGameInfo_t *pFriendGameInfo ) = 0;
+ // accesses old friends names - returns an empty string when their are no more items in the history
+ virtual const char *GetFriendPersonaNameHistory( CSteamID steamIDFriend, int iPersonaName ) = 0;
+ // friends steam level
+ virtual int GetFriendSteamLevel( CSteamID steamIDFriend ) = 0;
+
+ // Returns nickname the current user has set for the specified player. Returns NULL if the no nickname has been set for that player.
+ virtual const char *GetPlayerNickname( CSteamID steamIDPlayer ) = 0;
+
+ // friend grouping (tag) apis
+ // returns the number of friends groups
+ virtual int GetFriendsGroupCount() = 0;
+ // returns the friends group ID for the given index (invalid indices return k_FriendsGroupID_Invalid)
+ virtual FriendsGroupID_t GetFriendsGroupIDByIndex( int iFG ) = 0;
+ // returns the name for the given friends group (NULL in the case of invalid friends group IDs)
+ virtual const char *GetFriendsGroupName( FriendsGroupID_t friendsGroupID ) = 0;
+ // returns the number of members in a given friends group
+ virtual int GetFriendsGroupMembersCount( FriendsGroupID_t friendsGroupID ) = 0;
+ // gets up to nMembersCount members of the given friends group, if fewer exist than requested those positions' SteamIDs will be invalid
+ virtual void GetFriendsGroupMembersList( FriendsGroupID_t friendsGroupID, OUT_ARRAY_CALL(nMembersCount, GetFriendsGroupMembersCount, friendsGroupID ) CSteamID *pOutSteamIDMembers, int nMembersCount ) = 0;
+
+ // returns true if the specified user meets any of the criteria specified in iFriendFlags
+ // iFriendFlags can be the union (binary or, |) of one or more k_EFriendFlags values
+ virtual bool HasFriend( CSteamID steamIDFriend, int iFriendFlags ) = 0;
+
+ // clan (group) iteration and access functions
+ virtual int GetClanCount() = 0;
+ virtual CSteamID GetClanByIndex( int iClan ) = 0;
+ virtual const char *GetClanName( CSteamID steamIDClan ) = 0;
+ virtual const char *GetClanTag( CSteamID steamIDClan ) = 0;
+ // returns the most recent information we have about what's happening in a clan
+ virtual bool GetClanActivityCounts( CSteamID steamIDClan, int *pnOnline, int *pnInGame, int *pnChatting ) = 0;
+ // for clans a user is a member of, they will have reasonably up-to-date information, but for others you'll have to download the info to have the latest
+ virtual SteamAPICall_t DownloadClanActivityCounts( ARRAY_COUNT(cClansToRequest) CSteamID *psteamIDClans, int cClansToRequest ) = 0;
+
+ // iterators for getting users in a chat room, lobby, game server or clan
+ // note that large clans that cannot be iterated by the local user
+ // note that the current user must be in a lobby to retrieve CSteamIDs of other users in that lobby
+ // steamIDSource can be the steamID of a group, game server, lobby or chat room
+ virtual int GetFriendCountFromSource( CSteamID steamIDSource ) = 0;
+ virtual CSteamID GetFriendFromSourceByIndex( CSteamID steamIDSource, int iFriend ) = 0;
+
+ // returns true if the local user can see that steamIDUser is a member or in steamIDSource
+ virtual bool IsUserInSource( CSteamID steamIDUser, CSteamID steamIDSource ) = 0;
+
+ // User is in a game pressing the talk button (will suppress the microphone for all voice comms from the Steam friends UI)
+ virtual void SetInGameVoiceSpeaking( CSteamID steamIDUser, bool bSpeaking ) = 0;
+
+ // activates the game overlay, with an optional dialog to open
+ // valid options are "Friends", "Community", "Players", "Settings", "OfficialGameGroup", "Stats", "Achievements"
+ virtual void ActivateGameOverlay( const char *pchDialog ) = 0;
+
+ // activates game overlay to a specific place
+ // valid options are
+ // "steamid" - opens the overlay web browser to the specified user or groups profile
+ // "chat" - opens a chat window to the specified user, or joins the group chat
+ // "jointrade" - opens a window to a Steam Trading session that was started with the ISteamEconomy/StartTrade Web API
+ // "stats" - opens the overlay web browser to the specified user's stats
+ // "achievements" - opens the overlay web browser to the specified user's achievements
+ // "friendadd" - opens the overlay in minimal mode prompting the user to add the target user as a friend
+ // "friendremove" - opens the overlay in minimal mode prompting the user to remove the target friend
+ // "friendrequestaccept" - opens the overlay in minimal mode prompting the user to accept an incoming friend invite
+ // "friendrequestignore" - opens the overlay in minimal mode prompting the user to ignore an incoming friend invite
+ virtual void ActivateGameOverlayToUser( const char *pchDialog, CSteamID steamID ) = 0;
+
+ // activates game overlay web browser directly to the specified URL
+ // full address with protocol type is required, e.g. http://www.steamgames.com/
+ virtual void ActivateGameOverlayToWebPage( const char *pchURL ) = 0;
+
+ // activates game overlay to store page for app
+ virtual void ActivateGameOverlayToStore( AppId_t nAppID, EOverlayToStoreFlag eFlag ) = 0;
+
+ // Mark a target user as 'played with'. This is a client-side only feature that requires that the calling user is
+ // in game
+ virtual void SetPlayedWith( CSteamID steamIDUserPlayedWith ) = 0;
+
+ // activates game overlay to open the invite dialog. Invitations will be sent for the provided lobby.
+ virtual void ActivateGameOverlayInviteDialog( CSteamID steamIDLobby ) = 0;
+
+ // gets the small (32x32) avatar of the current user, which is a handle to be used in IClientUtils::GetImageRGBA(), or 0 if none set
+ virtual int GetSmallFriendAvatar( CSteamID steamIDFriend ) = 0;
+
+ // gets the medium (64x64) avatar of the current user, which is a handle to be used in IClientUtils::GetImageRGBA(), or 0 if none set
+ virtual int GetMediumFriendAvatar( CSteamID steamIDFriend ) = 0;
+
+ // gets the large (184x184) avatar of the current user, which is a handle to be used in IClientUtils::GetImageRGBA(), or 0 if none set
+ // returns -1 if this image has yet to be loaded, in this case wait for a AvatarImageLoaded_t callback and then call this again
+ virtual int GetLargeFriendAvatar( CSteamID steamIDFriend ) = 0;
+
+ // requests information about a user - persona name & avatar
+ // if bRequireNameOnly is set, then the avatar of a user isn't downloaded
+ // - it's a lot slower to download avatars and churns the local cache, so if you don't need avatars, don't request them
+ // if returns true, it means that data is being requested, and a PersonaStateChanged_t callback will be posted when it's retrieved
+ // if returns false, it means that we already have all the details about that user, and functions can be called immediately
+ virtual bool RequestUserInformation( CSteamID steamIDUser, bool bRequireNameOnly ) = 0;
+
+ // requests information about a clan officer list
+ // when complete, data is returned in ClanOfficerListResponse_t call result
+ // this makes available the calls below
+ // you can only ask about clans that a user is a member of
+ // note that this won't download avatars automatically; if you get an officer,
+ // and no avatar image is available, call RequestUserInformation( steamID, false ) to download the avatar
+ CALL_RESULT( ClanOfficerListResponse_t )
+ virtual SteamAPICall_t RequestClanOfficerList( CSteamID steamIDClan ) = 0;
+
+ // iteration of clan officers - can only be done when a RequestClanOfficerList() call has completed
+
+ // returns the steamID of the clan owner
+ virtual CSteamID GetClanOwner( CSteamID steamIDClan ) = 0;
+ // returns the number of officers in a clan (including the owner)
+ virtual int GetClanOfficerCount( CSteamID steamIDClan ) = 0;
+ // returns the steamID of a clan officer, by index, of range [0,GetClanOfficerCount)
+ virtual CSteamID GetClanOfficerByIndex( CSteamID steamIDClan, int iOfficer ) = 0;
+ // if current user is chat restricted, he can't send or receive any text/voice chat messages.
+ // the user can't see custom avatars. But the user can be online and send/recv game invites.
+ // a chat restricted user can't add friends or join any groups.
+ virtual uint32 GetUserRestrictions() = 0;
+
+ // Rich Presence data is automatically shared between friends who are in the same game
+ // Each user has a set of Key/Value pairs
+ // Note the following limits: k_cchMaxRichPresenceKeys, k_cchMaxRichPresenceKeyLength, k_cchMaxRichPresenceValueLength
+ // There are two magic keys:
+ // "status" - a UTF-8 string that will show up in the 'view game info' dialog in the Steam friends list
+ // "connect" - a UTF-8 string that contains the command-line for how a friend can connect to a game
+ // GetFriendRichPresence() returns an empty string "" if no value is set
+ // SetRichPresence() to a NULL or an empty string deletes the key
+ // You can iterate the current set of keys for a friend with GetFriendRichPresenceKeyCount()
+ // and GetFriendRichPresenceKeyByIndex() (typically only used for debugging)
+ virtual bool SetRichPresence( const char *pchKey, const char *pchValue ) = 0;
+ virtual void ClearRichPresence() = 0;
+ virtual const char *GetFriendRichPresence( CSteamID steamIDFriend, const char *pchKey ) = 0;
+ virtual int GetFriendRichPresenceKeyCount( CSteamID steamIDFriend ) = 0;
+ virtual const char *GetFriendRichPresenceKeyByIndex( CSteamID steamIDFriend, int iKey ) = 0;
+ // Requests rich presence for a specific user.
+ virtual void RequestFriendRichPresence( CSteamID steamIDFriend ) = 0;
+
+ // rich invite support
+ // if the target accepts the invite, the pchConnectString gets added to the command-line for launching the game
+ // if the game is already running, a GameRichPresenceJoinRequested_t callback is posted containing the connect string
+ // invites can only be sent to friends
+ virtual bool InviteUserToGame( CSteamID steamIDFriend, const char *pchConnectString ) = 0;
+
+ // recently-played-with friends iteration
+ // this iterates the entire list of users recently played with, across games
+ // GetFriendCoplayTime() returns as a unix time
+ virtual int GetCoplayFriendCount() = 0;
+ virtual CSteamID GetCoplayFriend( int iCoplayFriend ) = 0;
+ virtual int GetFriendCoplayTime( CSteamID steamIDFriend ) = 0;
+ virtual AppId_t GetFriendCoplayGame( CSteamID steamIDFriend ) = 0;
+
+ // chat interface for games
+ // this allows in-game access to group (clan) chats from in the game
+ // the behavior is somewhat sophisticated, because the user may or may not be already in the group chat from outside the game or in the overlay
+ // use ActivateGameOverlayToUser( "chat", steamIDClan ) to open the in-game overlay version of the chat
+ CALL_RESULT( JoinClanChatRoomCompletionResult_t )
+ virtual SteamAPICall_t JoinClanChatRoom( CSteamID steamIDClan ) = 0;
+ virtual bool LeaveClanChatRoom( CSteamID steamIDClan ) = 0;
+ virtual int GetClanChatMemberCount( CSteamID steamIDClan ) = 0;
+ virtual CSteamID GetChatMemberByIndex( CSteamID steamIDClan, int iUser ) = 0;
+ virtual bool SendClanChatMessage( CSteamID steamIDClanChat, const char *pchText ) = 0;
+ virtual int GetClanChatMessage( CSteamID steamIDClanChat, int iMessage, void *prgchText, int cchTextMax, EChatEntryType *peChatEntryType, OUT_STRUCT() CSteamID *psteamidChatter ) = 0;
+ virtual bool IsClanChatAdmin( CSteamID steamIDClanChat, CSteamID steamIDUser ) = 0;
+
+ // interact with the Steam (game overlay / desktop)
+ virtual bool IsClanChatWindowOpenInSteam( CSteamID steamIDClanChat ) = 0;
+ virtual bool OpenClanChatWindowInSteam( CSteamID steamIDClanChat ) = 0;
+ virtual bool CloseClanChatWindowInSteam( CSteamID steamIDClanChat ) = 0;
+
+ // peer-to-peer chat interception
+ // this is so you can show P2P chats inline in the game
+ virtual bool SetListenForFriendsMessages( bool bInterceptEnabled ) = 0;
+ virtual bool ReplyToFriendMessage( CSteamID steamIDFriend, const char *pchMsgToSend ) = 0;
+ virtual int GetFriendMessage( CSteamID steamIDFriend, int iMessageID, void *pvData, int cubData, EChatEntryType *peChatEntryType ) = 0;
+
+ // following apis
+ CALL_RESULT( FriendsGetFollowerCount_t )
+ virtual SteamAPICall_t GetFollowerCount( CSteamID steamID ) = 0;
+ CALL_RESULT( FriendsIsFollowing_t )
+ virtual SteamAPICall_t IsFollowing( CSteamID steamID ) = 0;
+ CALL_RESULT( FriendsEnumerateFollowingList_t )
+ virtual SteamAPICall_t EnumerateFollowingList( uint32 unStartIndex ) = 0;
+};
+
+#define STEAMFRIENDS_INTERFACE_VERSION "SteamFriends015"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: called when a friends' status changes
+//-----------------------------------------------------------------------------
+struct PersonaStateChange_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 4 };
+
+ uint64 m_ulSteamID; // steamID of the friend who changed
+ int m_nChangeFlags; // what's changed
+};
+
+
+// used in PersonaStateChange_t::m_nChangeFlags to describe what's changed about a user
+// these flags describe what the client has learned has changed recently, so on startup you'll see a name, avatar & relationship change for every friend
+enum EPersonaChange
+{
+ k_EPersonaChangeName = 0x0001,
+ k_EPersonaChangeStatus = 0x0002,
+ k_EPersonaChangeComeOnline = 0x0004,
+ k_EPersonaChangeGoneOffline = 0x0008,
+ k_EPersonaChangeGamePlayed = 0x0010,
+ k_EPersonaChangeGameServer = 0x0020,
+ k_EPersonaChangeAvatar = 0x0040,
+ k_EPersonaChangeJoinedSource= 0x0080,
+ k_EPersonaChangeLeftSource = 0x0100,
+ k_EPersonaChangeRelationshipChanged = 0x0200,
+ k_EPersonaChangeNameFirstSet = 0x0400,
+ k_EPersonaChangeFacebookInfo = 0x0800,
+ k_EPersonaChangeNickname = 0x1000,
+ k_EPersonaChangeSteamLevel = 0x2000,
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: posted when game overlay activates or deactivates
+// the game can use this to be pause or resume single player games
+//-----------------------------------------------------------------------------
+struct GameOverlayActivated_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 31 };
+ uint8 m_bActive; // true if it's just been activated, false otherwise
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when the user tries to join a different game server from their friends list
+// game client should attempt to connect to specified server when this is received
+//-----------------------------------------------------------------------------
+struct GameServerChangeRequested_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 32 };
+ char m_rgchServer[64]; // server address ("127.0.0.1:27015", "tf2.valvesoftware.com")
+ char m_rgchPassword[64]; // server password, if any
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when the user tries to join a lobby from their friends list
+// game client should attempt to connect to specified lobby when this is received
+//-----------------------------------------------------------------------------
+struct GameLobbyJoinRequested_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 33 };
+ CSteamID m_steamIDLobby;
+
+ // The friend they did the join via (will be invalid if not directly via a friend)
+ //
+ // On PS3, the friend will be invalid if this was triggered by a PSN invite via the XMB, but
+ // the account type will be console user so you can tell at least that this was from a PSN friend
+ // rather than a Steam friend.
+ CSteamID m_steamIDFriend;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when an avatar is loaded in from a previous GetLargeFriendAvatar() call
+// if the image wasn't already available
+//-----------------------------------------------------------------------------
+struct AvatarImageLoaded_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 34 };
+ CSteamID m_steamID; // steamid the avatar has been loaded for
+ int m_iImage; // the image index of the now loaded image
+ int m_iWide; // width of the loaded image
+ int m_iTall; // height of the loaded image
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: marks the return of a request officer list call
+//-----------------------------------------------------------------------------
+struct ClanOfficerListResponse_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 35 };
+ CSteamID m_steamIDClan;
+ int m_cOfficers;
+ uint8 m_bSuccess;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: callback indicating updated data about friends rich presence information
+//-----------------------------------------------------------------------------
+struct FriendRichPresenceUpdate_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 36 };
+ CSteamID m_steamIDFriend; // friend who's rich presence has changed
+ AppId_t m_nAppID; // the appID of the game (should always be the current game)
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when the user tries to join a game from their friends list
+// rich presence will have been set with the "connect" key which is set here
+//-----------------------------------------------------------------------------
+struct GameRichPresenceJoinRequested_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 37 };
+ CSteamID m_steamIDFriend; // the friend they did the join via (will be invalid if not directly via a friend)
+ char m_rgchConnect[k_cchMaxRichPresenceValueLength];
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a chat message has been received for a clan chat the game has joined
+//-----------------------------------------------------------------------------
+struct GameConnectedClanChatMsg_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 38 };
+ CSteamID m_steamIDClanChat;
+ CSteamID m_steamIDUser;
+ int m_iMessageID;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a user has joined a clan chat
+//-----------------------------------------------------------------------------
+struct GameConnectedChatJoin_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 39 };
+ CSteamID m_steamIDClanChat;
+ CSteamID m_steamIDUser;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a user has left the chat we're in
+//-----------------------------------------------------------------------------
+struct GameConnectedChatLeave_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 40 };
+ CSteamID m_steamIDClanChat;
+ CSteamID m_steamIDUser;
+ bool m_bKicked; // true if admin kicked
+ bool m_bDropped; // true if Steam connection dropped
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a DownloadClanActivityCounts() call has finished
+//-----------------------------------------------------------------------------
+struct DownloadClanActivityCountsResult_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 41 };
+ bool m_bSuccess;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a JoinClanChatRoom() call has finished
+//-----------------------------------------------------------------------------
+struct JoinClanChatRoomCompletionResult_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 42 };
+ CSteamID m_steamIDClanChat;
+ EChatRoomEnterResponse m_eChatRoomEnterResponse;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: a chat message has been received from a user
+//-----------------------------------------------------------------------------
+struct GameConnectedFriendChatMsg_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 43 };
+ CSteamID m_steamIDUser;
+ int m_iMessageID;
+};
+
+
+struct FriendsGetFollowerCount_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 44 };
+ EResult m_eResult;
+ CSteamID m_steamID;
+ int m_nCount;
+};
+
+
+struct FriendsIsFollowing_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 45 };
+ EResult m_eResult;
+ CSteamID m_steamID;
+ bool m_bIsFollowing;
+};
+
+
+struct FriendsEnumerateFollowingList_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 46 };
+ EResult m_eResult;
+ CSteamID m_rgSteamID[ k_cEnumerateFollowersMax ];
+ int32 m_nResultsReturned;
+ int32 m_nTotalResultCount;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: reports the result of an attempt to change the user's persona name
+//-----------------------------------------------------------------------------
+struct SetPersonaNameResponse_t
+{
+ enum { k_iCallback = k_iSteamFriendsCallbacks + 47 };
+
+ bool m_bSuccess; // true if name change succeeded completely.
+ bool m_bLocalSuccess; // true if name change was retained locally. (We might not have been able to communicate with Steam)
+ EResult m_result; // detailed result code
+};
+
+
+#pragma pack( pop )
+
+#endif // ISTEAMFRIENDS_H
diff --git a/dep/steam_api/isteamgamecoordinator.h b/dep/steam_api/isteamgamecoordinator.h
new file mode 100644
index 0000000..5ab0637
--- /dev/null
+++ b/dep/steam_api/isteamgamecoordinator.h
@@ -0,0 +1,75 @@
+//====== Copyright , Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to the game coordinator for this application
+//
+//=============================================================================
+
+#ifndef ISTEAMGAMECOORDINATOR
+#define ISTEAMGAMECOORDINATOR
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "steamtypes.h"
+#include "steamclientpublic.h"
+
+
+// list of possible return values from the ISteamGameCoordinator API
+enum EGCResults
+{
+ k_EGCResultOK = 0,
+ k_EGCResultNoMessage = 1, // There is no message in the queue
+ k_EGCResultBufferTooSmall = 2, // The buffer is too small for the requested message
+ k_EGCResultNotLoggedOn = 3, // The client is not logged onto Steam
+ k_EGCResultInvalidMessage = 4, // Something was wrong with the message being sent with SendMessage
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for sending and receiving messages from the Game Coordinator
+// for this application
+//-----------------------------------------------------------------------------
+class ISteamGameCoordinator
+{
+public:
+
+ // sends a message to the Game Coordinator
+ virtual EGCResults SendMessage( uint32 unMsgType, const void *pubData, uint32 cubData ) = 0;
+
+ // returns true if there is a message waiting from the game coordinator
+ virtual bool IsMessageAvailable( uint32 *pcubMsgSize ) = 0;
+
+ // fills the provided buffer with the first message in the queue and returns k_EGCResultOK or
+ // returns k_EGCResultNoMessage if there is no message waiting. pcubMsgSize is filled with the message size.
+ // If the provided buffer is not large enough to fit the entire message, k_EGCResultBufferTooSmall is returned
+ // and the message remains at the head of the queue.
+ virtual EGCResults RetrieveMessage( uint32 *punMsgType, void *pubDest, uint32 cubDest, uint32 *pcubMsgSize ) = 0;
+
+};
+#define STEAMGAMECOORDINATOR_INTERFACE_VERSION "SteamGameCoordinator001"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+// callback notification - A new message is available for reading from the message queue
+struct GCMessageAvailable_t
+{
+ enum { k_iCallback = k_iSteamGameCoordinatorCallbacks + 1 };
+ uint32 m_nMessageSize;
+};
+
+// callback notification - A message failed to make it to the GC. It may be down temporarily
+struct GCMessageFailed_t
+{
+ enum { k_iCallback = k_iSteamGameCoordinatorCallbacks + 2 };
+};
+
+#pragma pack( pop )
+
+#endif // ISTEAMGAMECOORDINATOR
diff --git a/dep/steam_api/isteamgameserver.h b/dep/steam_api/isteamgameserver.h
new file mode 100644
index 0000000..e19f1dd
--- /dev/null
+++ b/dep/steam_api/isteamgameserver.h
@@ -0,0 +1,387 @@
+//====== Copyright (c) 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to steam for game servers
+//
+//=============================================================================
+
+#ifndef ISTEAMGAMESERVER_H
+#define ISTEAMGAMESERVER_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+#define MASTERSERVERUPDATERPORT_USEGAMESOCKETSHARE ((uint16)-1)
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for authenticating users via Steam to play on a game server
+//-----------------------------------------------------------------------------
+class ISteamGameServer
+{
+public:
+
+//
+// Basic server data. These properties, if set, must be set before before calling LogOn. They
+// may not be changed after logged in.
+//
+
+ /// This is called by SteamGameServer_Init, and you will usually not need to call it directly
+ virtual bool InitGameServer( uint32 unIP, uint16 usGamePort, uint16 usQueryPort, uint32 unFlags, AppId_t nGameAppId, const char *pchVersionString ) = 0;
+
+ /// Game product identifier. This is currently used by the master server for version checking purposes.
+ /// It's a required field, but will eventually will go away, and the AppID will be used for this purpose.
+ virtual void SetProduct( const char *pszProduct ) = 0;
+
+ /// Description of the game. This is a required field and is displayed in the steam server browser....for now.
+ /// This is a required field, but it will go away eventually, as the data should be determined from the AppID.
+ virtual void SetGameDescription( const char *pszGameDescription ) = 0;
+
+ /// If your game is a "mod," pass the string that identifies it. The default is an empty string, meaning
+ /// this application is the original game, not a mod.
+ ///
+ /// @see k_cbMaxGameServerGameDir
+ virtual void SetModDir( const char *pszModDir ) = 0;
+
+ /// Is this is a dedicated server? The default value is false.
+ virtual void SetDedicatedServer( bool bDedicated ) = 0;
+
+//
+// Login
+//
+
+ /// Begin process to login to a persistent game server account
+ ///
+ /// You need to register for callbacks to determine the result of this operation.
+ /// @see SteamServersConnected_t
+ /// @see SteamServerConnectFailure_t
+ /// @see SteamServersDisconnected_t
+ virtual void LogOn( const char *pszToken ) = 0;
+
+ /// Login to a generic, anonymous account.
+ ///
+ /// Note: in previous versions of the SDK, this was automatically called within SteamGameServer_Init,
+ /// but this is no longer the case.
+ virtual void LogOnAnonymous() = 0;
+
+ /// Begin process of logging game server out of steam
+ virtual void LogOff() = 0;
+
+ // status functions
+ virtual bool BLoggedOn() = 0;
+ virtual bool BSecure() = 0;
+ virtual CSteamID GetSteamID() = 0;
+
+ /// Returns true if the master server has requested a restart.
+ /// Only returns true once per request.
+ virtual bool WasRestartRequested() = 0;
+
+//
+// Server state. These properties may be changed at any time.
+//
+
+ /// Max player count that will be reported to server browser and client queries
+ virtual void SetMaxPlayerCount( int cPlayersMax ) = 0;
+
+ /// Number of bots. Default value is zero
+ virtual void SetBotPlayerCount( int cBotplayers ) = 0;
+
+ /// Set the name of server as it will appear in the server browser
+ ///
+ /// @see k_cbMaxGameServerName
+ virtual void SetServerName( const char *pszServerName ) = 0;
+
+ /// Set name of map to report in the server browser
+ ///
+ /// @see k_cbMaxGameServerName
+ virtual void SetMapName( const char *pszMapName ) = 0;
+
+ /// Let people know if your server will require a password
+ virtual void SetPasswordProtected( bool bPasswordProtected ) = 0;
+
+ /// Spectator server. The default value is zero, meaning the service
+ /// is not used.
+ virtual void SetSpectatorPort( uint16 unSpectatorPort ) = 0;
+
+ /// Name of the spectator server. (Only used if spectator port is nonzero.)
+ ///
+ /// @see k_cbMaxGameServerMapName
+ virtual void SetSpectatorServerName( const char *pszSpectatorServerName ) = 0;
+
+ /// Call this to clear the whole list of key/values that are sent in rules queries.
+ virtual void ClearAllKeyValues() = 0;
+
+ /// Call this to add/update a key/value pair.
+ virtual void SetKeyValue( const char *pKey, const char *pValue ) = 0;
+
+ /// Sets a string defining the "gametags" for this server, this is optional, but if it is set
+ /// it allows users to filter in the matchmaking/server-browser interfaces based on the value
+ ///
+ /// @see k_cbMaxGameServerTags
+ virtual void SetGameTags( const char *pchGameTags ) = 0;
+
+ /// Sets a string defining the "gamedata" for this server, this is optional, but if it is set
+ /// it allows users to filter in the matchmaking/server-browser interfaces based on the value
+ /// don't set this unless it actually changes, its only uploaded to the master once (when
+ /// acknowledged)
+ ///
+ /// @see k_cbMaxGameServerGameData
+ virtual void SetGameData( const char *pchGameData ) = 0;
+
+ /// Region identifier. This is an optional field, the default value is empty, meaning the "world" region
+ virtual void SetRegion( const char *pszRegion ) = 0;
+
+//
+// Player list management / authentication
+//
+
+ // Handles receiving a new connection from a Steam user. This call will ask the Steam
+ // servers to validate the users identity, app ownership, and VAC status. If the Steam servers
+ // are off-line, then it will validate the cached ticket itself which will validate app ownership
+ // and identity. The AuthBlob here should be acquired on the game client using SteamUser()->InitiateGameConnection()
+ // and must then be sent up to the game server for authentication.
+ //
+ // Return Value: returns true if the users ticket passes basic checks. pSteamIDUser will contain the Steam ID of this user. pSteamIDUser must NOT be NULL
+ // If the call succeeds then you should expect a GSClientApprove_t or GSClientDeny_t callback which will tell you whether authentication
+ // for the user has succeeded or failed (the steamid in the callback will match the one returned by this call)
+ virtual bool SendUserConnectAndAuthenticate( uint32 unIPClient, const void *pvAuthBlob, uint32 cubAuthBlobSize, CSteamID *pSteamIDUser ) = 0;
+
+ // Creates a fake user (ie, a bot) which will be listed as playing on the server, but skips validation.
+ //
+ // Return Value: Returns a SteamID for the user to be tracked with, you should call HandleUserDisconnect()
+ // when this user leaves the server just like you would for a real user.
+ virtual CSteamID CreateUnauthenticatedUserConnection() = 0;
+
+ // Should be called whenever a user leaves our game server, this lets Steam internally
+ // track which users are currently on which servers for the purposes of preventing a single
+ // account being logged into multiple servers, showing who is currently on a server, etc.
+ virtual void SendUserDisconnect( CSteamID steamIDUser ) = 0;
+
+ // Update the data to be displayed in the server browser and matchmaking interfaces for a user
+ // currently connected to the server. For regular users you must call this after you receive a
+ // GSUserValidationSuccess callback.
+ //
+ // Return Value: true if successful, false if failure (ie, steamIDUser wasn't for an active player)
+ virtual bool BUpdateUserData( CSteamID steamIDUser, const char *pchPlayerName, uint32 uScore ) = 0;
+
+ // New auth system APIs - do not mix with the old auth system APIs.
+ // ----------------------------------------------------------------
+
+ // Retrieve ticket to be sent to the entity who wishes to authenticate you ( using BeginAuthSession API ).
+ // pcbTicket retrieves the length of the actual ticket.
+ virtual HAuthTicket GetAuthSessionTicket( void *pTicket, int cbMaxTicket, uint32 *pcbTicket ) = 0;
+
+ // Authenticate ticket ( from GetAuthSessionTicket ) from entity steamID to be sure it is valid and isnt reused
+ // Registers for callbacks if the entity goes offline or cancels the ticket ( see ValidateAuthTicketResponse_t callback and EAuthSessionResponse )
+ virtual EBeginAuthSessionResult BeginAuthSession( const void *pAuthTicket, int cbAuthTicket, CSteamID steamID ) = 0;
+
+ // Stop tracking started by BeginAuthSession - called when no longer playing game with this entity
+ virtual void EndAuthSession( CSteamID steamID ) = 0;
+
+ // Cancel auth ticket from GetAuthSessionTicket, called when no longer playing game with the entity you gave the ticket to
+ virtual void CancelAuthTicket( HAuthTicket hAuthTicket ) = 0;
+
+ // After receiving a user's authentication data, and passing it to SendUserConnectAndAuthenticate, use this function
+ // to determine if the user owns downloadable content specified by the provided AppID.
+ virtual EUserHasLicenseForAppResult UserHasLicenseForApp( CSteamID steamID, AppId_t appID ) = 0;
+
+ // Ask if a user in in the specified group, results returns async by GSUserGroupStatus_t
+ // returns false if we're not connected to the steam servers and thus cannot ask
+ virtual bool RequestUserGroupStatus( CSteamID steamIDUser, CSteamID steamIDGroup ) = 0;
+
+
+ // these two functions s are deprecated, and will not return results
+ // they will be removed in a future version of the SDK
+ virtual void GetGameplayStats( ) = 0;
+ CALL_RESULT( GSReputation_t )
+ virtual SteamAPICall_t GetServerReputation() = 0;
+
+ // Returns the public IP of the server according to Steam, useful when the server is
+ // behind NAT and you want to advertise its IP in a lobby for other clients to directly
+ // connect to
+ virtual uint32 GetPublicIP() = 0;
+
+// These are in GameSocketShare mode, where instead of ISteamGameServer creating its own
+// socket to talk to the master server on, it lets the game use its socket to forward messages
+// back and forth. This prevents us from requiring server ops to open up yet another port
+// in their firewalls.
+//
+// the IP address and port should be in host order, i.e 127.0.0.1 == 0x7f000001
+
+ // These are used when you've elected to multiplex the game server's UDP socket
+ // rather than having the master server updater use its own sockets.
+ //
+ // Source games use this to simplify the job of the server admins, so they
+ // don't have to open up more ports on their firewalls.
+
+ // Call this when a packet that starts with 0xFFFFFFFF comes in. That means
+ // it's for us.
+ virtual bool HandleIncomingPacket( const void *pData, int cbData, uint32 srcIP, uint16 srcPort ) = 0;
+
+ // AFTER calling HandleIncomingPacket for any packets that came in that frame, call this.
+ // This gets a packet that the master server updater needs to send out on UDP.
+ // It returns the length of the packet it wants to send, or 0 if there are no more packets to send.
+ // Call this each frame until it returns 0.
+ virtual int GetNextOutgoingPacket( void *pOut, int cbMaxOut, uint32 *pNetAdr, uint16 *pPort ) = 0;
+
+//
+// Control heartbeats / advertisement with master server
+//
+
+ // Call this as often as you like to tell the master server updater whether or not
+ // you want it to be active (default: off).
+ virtual void EnableHeartbeats( bool bActive ) = 0;
+
+ // You usually don't need to modify this.
+ // Pass -1 to use the default value for iHeartbeatInterval.
+ // Some mods change this.
+ virtual void SetHeartbeatInterval( int iHeartbeatInterval ) = 0;
+
+ // Force a heartbeat to steam at the next opportunity
+ virtual void ForceHeartbeat() = 0;
+
+ // associate this game server with this clan for the purposes of computing player compat
+ CALL_RESULT( AssociateWithClanResult_t )
+ virtual SteamAPICall_t AssociateWithClan( CSteamID steamIDClan ) = 0;
+
+ // ask if any of the current players dont want to play with this new player - or vice versa
+ CALL_RESULT( ComputeNewPlayerCompatibilityResult_t )
+ virtual SteamAPICall_t ComputeNewPlayerCompatibility( CSteamID steamIDNewPlayer ) = 0;
+
+};
+
+#define STEAMGAMESERVER_INTERFACE_VERSION "SteamGameServer012"
+
+// game server flags
+const uint32 k_unServerFlagNone = 0x00;
+const uint32 k_unServerFlagActive = 0x01; // server has users playing
+const uint32 k_unServerFlagSecure = 0x02; // server wants to be secure
+const uint32 k_unServerFlagDedicated = 0x04; // server is dedicated
+const uint32 k_unServerFlagLinux = 0x08; // linux build
+const uint32 k_unServerFlagPassworded = 0x10; // password protected
+const uint32 k_unServerFlagPrivate = 0x20; // server shouldn't list on master server and
+ // won't enforce authentication of users that connect to the server.
+ // Useful when you run a server where the clients may not
+ // be connected to the internet but you want them to play (i.e LANs)
+
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+// client has been approved to connect to this game server
+struct GSClientApprove_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 1 };
+ CSteamID m_SteamID; // SteamID of approved player
+ CSteamID m_OwnerSteamID; // SteamID of original owner for game license
+};
+
+
+// client has been denied to connection to this game server
+struct GSClientDeny_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 2 };
+ CSteamID m_SteamID;
+ EDenyReason m_eDenyReason;
+ char m_rgchOptionalText[128];
+};
+
+
+// request the game server should kick the user
+struct GSClientKick_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 3 };
+ CSteamID m_SteamID;
+ EDenyReason m_eDenyReason;
+};
+
+// NOTE: callback values 4 and 5 are skipped because they are used for old deprecated callbacks,
+// do not reuse them here.
+
+
+// client achievement info
+struct GSClientAchievementStatus_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 6 };
+ uint64 m_SteamID;
+ char m_pchAchievement[128];
+ bool m_bUnlocked;
+};
+
+// received when the game server requests to be displayed as secure (VAC protected)
+// m_bSecure is true if the game server should display itself as secure to users, false otherwise
+struct GSPolicyResponse_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 15 };
+ uint8 m_bSecure;
+};
+
+// GS gameplay stats info
+struct GSGameplayStats_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 7 };
+ EResult m_eResult; // Result of the call
+ int32 m_nRank; // Overall rank of the server (0-based)
+ uint32 m_unTotalConnects; // Total number of clients who have ever connected to the server
+ uint32 m_unTotalMinutesPlayed; // Total number of minutes ever played on the server
+};
+
+// send as a reply to RequestUserGroupStatus()
+struct GSClientGroupStatus_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 8 };
+ CSteamID m_SteamIDUser;
+ CSteamID m_SteamIDGroup;
+ bool m_bMember;
+ bool m_bOfficer;
+};
+
+// Sent as a reply to GetServerReputation()
+struct GSReputation_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 9 };
+ EResult m_eResult; // Result of the call;
+ uint32 m_unReputationScore; // The reputation score for the game server
+ bool m_bBanned; // True if the server is banned from the Steam
+ // master servers
+
+ // The following members are only filled out if m_bBanned is true. They will all
+ // be set to zero otherwise. Master server bans are by IP so it is possible to be
+ // banned even when the score is good high if there is a bad server on another port.
+ // This information can be used to determine which server is bad.
+
+ uint32 m_unBannedIP; // The IP of the banned server
+ uint16 m_usBannedPort; // The port of the banned server
+ uint64 m_ulBannedGameID; // The game ID the banned server is serving
+ uint32 m_unBanExpires; // Time the ban expires, expressed in the Unix epoch (seconds since 1/1/1970)
+};
+
+// Sent as a reply to AssociateWithClan()
+struct AssociateWithClanResult_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 10 };
+ EResult m_eResult; // Result of the call;
+};
+
+// Sent as a reply to ComputeNewPlayerCompatibility()
+struct ComputeNewPlayerCompatibilityResult_t
+{
+ enum { k_iCallback = k_iSteamGameServerCallbacks + 11 };
+ EResult m_eResult; // Result of the call;
+ int m_cPlayersThatDontLikeCandidate;
+ int m_cPlayersThatCandidateDoesntLike;
+ int m_cClanPlayersThatDontLikeCandidate;
+ CSteamID m_SteamIDCandidate;
+};
+
+
+#pragma pack( pop )
+
+#endif // ISTEAMGAMESERVER_H
diff --git a/dep/steam_api/isteamgameserverstats.h b/dep/steam_api/isteamgameserverstats.h
new file mode 100644
index 0000000..e7922c9
--- /dev/null
+++ b/dep/steam_api/isteamgameserverstats.h
@@ -0,0 +1,101 @@
+//====== Copyright Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface for game servers to steam stats and achievements
+//
+//=============================================================================
+
+#ifndef ISTEAMGAMESERVERSTATS_H
+#define ISTEAMGAMESERVERSTATS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for authenticating users via Steam to play on a game server
+//-----------------------------------------------------------------------------
+class ISteamGameServerStats
+{
+public:
+ // downloads stats for the user
+ // returns a GSStatsReceived_t callback when completed
+ // if the user has no stats, GSStatsReceived_t.m_eResult will be set to k_EResultFail
+ // these stats will only be auto-updated for clients playing on the server. For other
+ // users you'll need to call RequestUserStats() again to refresh any data
+ CALL_RESULT( GSStatsReceived_t )
+ virtual SteamAPICall_t RequestUserStats( CSteamID steamIDUser ) = 0;
+
+ // requests stat information for a user, usable after a successful call to RequestUserStats()
+ virtual bool GetUserStat( CSteamID steamIDUser, const char *pchName, int32 *pData ) = 0;
+ virtual bool GetUserStat( CSteamID steamIDUser, const char *pchName, float *pData ) = 0;
+ virtual bool GetUserAchievement( CSteamID steamIDUser, const char *pchName, bool *pbAchieved ) = 0;
+
+ // Set / update stats and achievements.
+ // Note: These updates will work only on stats game servers are allowed to edit and only for
+ // game servers that have been declared as officially controlled by the game creators.
+ // Set the IP range of your official servers on the Steamworks page
+ virtual bool SetUserStat( CSteamID steamIDUser, const char *pchName, int32 nData ) = 0;
+ virtual bool SetUserStat( CSteamID steamIDUser, const char *pchName, float fData ) = 0;
+ virtual bool UpdateUserAvgRateStat( CSteamID steamIDUser, const char *pchName, float flCountThisSession, double dSessionLength ) = 0;
+
+ virtual bool SetUserAchievement( CSteamID steamIDUser, const char *pchName ) = 0;
+ virtual bool ClearUserAchievement( CSteamID steamIDUser, const char *pchName ) = 0;
+
+ // Store the current data on the server, will get a GSStatsStored_t callback when set.
+ //
+ // If the callback has a result of k_EResultInvalidParam, one or more stats
+ // uploaded has been rejected, either because they broke constraints
+ // or were out of date. In this case the server sends back updated values.
+ // The stats should be re-iterated to keep in sync.
+ CALL_RESULT( GSStatsStored_t )
+ virtual SteamAPICall_t StoreUserStats( CSteamID steamIDUser ) = 0;
+};
+
+#define STEAMGAMESERVERSTATS_INTERFACE_VERSION "SteamGameServerStats001"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: called when the latests stats and achievements have been received
+// from the server
+//-----------------------------------------------------------------------------
+struct GSStatsReceived_t
+{
+ enum { k_iCallback = k_iSteamGameServerStatsCallbacks };
+ EResult m_eResult; // Success / error fetching the stats
+ CSteamID m_steamIDUser; // The user for whom the stats are retrieved for
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: result of a request to store the user stats for a game
+//-----------------------------------------------------------------------------
+struct GSStatsStored_t
+{
+ enum { k_iCallback = k_iSteamGameServerStatsCallbacks + 1 };
+ EResult m_eResult; // success / error
+ CSteamID m_steamIDUser; // The user for whom the stats were stored
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback indicating that a user's stats have been unloaded.
+// Call RequestUserStats again to access stats for this user
+//-----------------------------------------------------------------------------
+struct GSStatsUnloaded_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 8 };
+ CSteamID m_steamIDUser; // User whose stats have been unloaded
+};
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMGAMESERVERSTATS_H
diff --git a/dep/steam_api/isteamhtmlsurface.h b/dep/steam_api/isteamhtmlsurface.h
new file mode 100644
index 0000000..ccfc6af
--- /dev/null
+++ b/dep/steam_api/isteamhtmlsurface.h
@@ -0,0 +1,453 @@
+//====== Copyright 1996-2013, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to display html pages in a texture
+//
+//=============================================================================
+
+#ifndef ISTEAMHTMLSURFACE_H
+#define ISTEAMHTMLSURFACE_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+typedef uint32 HHTMLBrowser;
+const uint32 INVALID_HTMLBROWSER = 0;
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for displaying HTML pages and interacting with them
+//-----------------------------------------------------------------------------
+class ISteamHTMLSurface
+{
+public:
+ virtual ~ISteamHTMLSurface() {}
+
+ // Must call init and shutdown when starting/ending use of the interface
+ virtual bool Init() = 0;
+ virtual bool Shutdown() = 0;
+
+ // Create a browser object for display of a html page, when creation is complete the call handle
+ // will return a HTML_BrowserReady_t callback for the HHTMLBrowser of your new browser.
+ // The user agent string is a substring to be added to the general user agent string so you can
+ // identify your client on web servers.
+ // The userCSS string lets you apply a CSS style sheet to every displayed page, leave null if
+ // you do not require this functionality.
+ //
+ // YOU MUST HAVE IMPLEMENTED HANDLERS FOR HTML_BrowserReady_t, HTML_StartRequest_t,
+ // HTML_JSAlert_t, HTML_JSConfirm_t, and HTML_FileOpenDialog_t! See the CALLBACKS
+ // section of this interface (AllowStartRequest, etc) for more details. If you do
+ // not implement these callback handlers, the browser may appear to hang instead of
+ // navigating to new pages or triggering javascript popups.
+ //
+ CALL_RESULT( HTML_BrowserReady_t )
+ virtual SteamAPICall_t CreateBrowser( const char *pchUserAgent, const char *pchUserCSS ) = 0;
+
+ // Call this when you are done with a html surface, this lets us free the resources being used by it
+ virtual void RemoveBrowser( HHTMLBrowser unBrowserHandle ) = 0;
+
+ // Navigate to this URL, results in a HTML_StartRequest_t as the request commences
+ virtual void LoadURL( HHTMLBrowser unBrowserHandle, const char *pchURL, const char *pchPostData ) = 0;
+
+ // Tells the surface the size in pixels to display the surface
+ virtual void SetSize( HHTMLBrowser unBrowserHandle, uint32 unWidth, uint32 unHeight ) = 0;
+
+ // Stop the load of the current html page
+ virtual void StopLoad( HHTMLBrowser unBrowserHandle ) = 0;
+ // Reload (most likely from local cache) the current page
+ virtual void Reload( HHTMLBrowser unBrowserHandle ) = 0;
+ // navigate back in the page history
+ virtual void GoBack( HHTMLBrowser unBrowserHandle ) = 0;
+ // navigate forward in the page history
+ virtual void GoForward( HHTMLBrowser unBrowserHandle ) = 0;
+
+ // add this header to any url requests from this browser
+ virtual void AddHeader( HHTMLBrowser unBrowserHandle, const char *pchKey, const char *pchValue ) = 0;
+ // run this javascript script in the currently loaded page
+ virtual void ExecuteJavascript( HHTMLBrowser unBrowserHandle, const char *pchScript ) = 0;
+
+ enum EHTMLMouseButton
+ {
+ eHTMLMouseButton_Left = 0,
+ eHTMLMouseButton_Right = 1,
+ eHTMLMouseButton_Middle = 2,
+ };
+
+ // Mouse click and mouse movement commands
+ virtual void MouseUp( HHTMLBrowser unBrowserHandle, EHTMLMouseButton eMouseButton ) = 0;
+ virtual void MouseDown( HHTMLBrowser unBrowserHandle, EHTMLMouseButton eMouseButton ) = 0;
+ virtual void MouseDoubleClick( HHTMLBrowser unBrowserHandle, EHTMLMouseButton eMouseButton ) = 0;
+ // x and y are relative to the HTML bounds
+ virtual void MouseMove( HHTMLBrowser unBrowserHandle, int x, int y ) = 0;
+ // nDelta is pixels of scroll
+ virtual void MouseWheel( HHTMLBrowser unBrowserHandle, int32 nDelta ) = 0;
+
+ enum EMouseCursor
+ {
+ dc_user = 0,
+ dc_none,
+ dc_arrow,
+ dc_ibeam,
+ dc_hourglass,
+ dc_waitarrow,
+ dc_crosshair,
+ dc_up,
+ dc_sizenw,
+ dc_sizese,
+ dc_sizene,
+ dc_sizesw,
+ dc_sizew,
+ dc_sizee,
+ dc_sizen,
+ dc_sizes,
+ dc_sizewe,
+ dc_sizens,
+ dc_sizeall,
+ dc_no,
+ dc_hand,
+ dc_blank, // don't show any custom cursor, just use your default
+ dc_middle_pan,
+ dc_north_pan,
+ dc_north_east_pan,
+ dc_east_pan,
+ dc_south_east_pan,
+ dc_south_pan,
+ dc_south_west_pan,
+ dc_west_pan,
+ dc_north_west_pan,
+ dc_alias,
+ dc_cell,
+ dc_colresize,
+ dc_copycur,
+ dc_verticaltext,
+ dc_rowresize,
+ dc_zoomin,
+ dc_zoomout,
+ dc_help,
+ dc_custom,
+
+ dc_last, // custom cursors start from this value and up
+ };
+
+ enum EHTMLKeyModifiers
+ {
+ k_eHTMLKeyModifier_None = 0,
+ k_eHTMLKeyModifier_AltDown = 1 << 0,
+ k_eHTMLKeyModifier_CtrlDown = 1 << 1,
+ k_eHTMLKeyModifier_ShiftDown = 1 << 2,
+ };
+
+ // keyboard interactions, native keycode is the virtual key code value from your OS
+ virtual void KeyDown( HHTMLBrowser unBrowserHandle, uint32 nNativeKeyCode, EHTMLKeyModifiers eHTMLKeyModifiers ) = 0;
+ virtual void KeyUp( HHTMLBrowser unBrowserHandle, uint32 nNativeKeyCode, EHTMLKeyModifiers eHTMLKeyModifiers ) = 0;
+ // cUnicodeChar is the unicode character point for this keypress (and potentially multiple chars per press)
+ virtual void KeyChar( HHTMLBrowser unBrowserHandle, uint32 cUnicodeChar, EHTMLKeyModifiers eHTMLKeyModifiers ) = 0;
+
+ // programmatically scroll this many pixels on the page
+ virtual void SetHorizontalScroll( HHTMLBrowser unBrowserHandle, uint32 nAbsolutePixelScroll ) = 0;
+ virtual void SetVerticalScroll( HHTMLBrowser unBrowserHandle, uint32 nAbsolutePixelScroll ) = 0;
+
+ // tell the html control if it has key focus currently, controls showing the I-beam cursor in text controls amongst other things
+ virtual void SetKeyFocus( HHTMLBrowser unBrowserHandle, bool bHasKeyFocus ) = 0;
+
+ // open the current pages html code in the local editor of choice, used for debugging
+ virtual void ViewSource( HHTMLBrowser unBrowserHandle ) = 0;
+ // copy the currently selected text on the html page to the local clipboard
+ virtual void CopyToClipboard( HHTMLBrowser unBrowserHandle ) = 0;
+ // paste from the local clipboard to the current html page
+ virtual void PasteFromClipboard( HHTMLBrowser unBrowserHandle ) = 0;
+
+ // find this string in the browser, if bCurrentlyInFind is true then instead cycle to the next matching element
+ virtual void Find( HHTMLBrowser unBrowserHandle, const char *pchSearchStr, bool bCurrentlyInFind, bool bReverse ) = 0;
+ // cancel a currently running find
+ virtual void StopFind( HHTMLBrowser unBrowserHandle ) = 0;
+
+ // return details about the link at position x,y on the current page
+ virtual void GetLinkAtPosition( HHTMLBrowser unBrowserHandle, int x, int y ) = 0;
+
+ // set a webcookie for the hostname in question
+ virtual void SetCookie( const char *pchHostname, const char *pchKey, const char *pchValue, const char *pchPath = "/", RTime32 nExpires = 0, bool bSecure = false, bool bHTTPOnly = false ) = 0;
+
+ // Zoom the current page by flZoom ( from 0.0 to 2.0, so to zoom to 120% use 1.2 ), zooming around point X,Y in the page (use 0,0 if you don't care)
+ virtual void SetPageScaleFactor( HHTMLBrowser unBrowserHandle, float flZoom, int nPointX, int nPointY ) = 0;
+
+ // Enable/disable low-resource background mode, where javascript and repaint timers are throttled, resources are
+ // more aggressively purged from memory, and audio/video elements are paused. When background mode is enabled,
+ // all HTML5 video and audio objects will execute ".pause()" and gain the property "._steam_background_paused = 1".
+ // When background mode is disabled, any video or audio objects with that property will resume with ".play()".
+ virtual void SetBackgroundMode( HHTMLBrowser unBrowserHandle, bool bBackgroundMode ) = 0;
+
+ // CALLBACKS
+ //
+ // These set of functions are used as responses to callback requests
+ //
+
+ // You MUST call this in response to a HTML_StartRequest_t callback
+ // Set bAllowed to true to allow this navigation, false to cancel it and stay
+ // on the current page. You can use this feature to limit the valid pages
+ // allowed in your HTML surface.
+ virtual void AllowStartRequest( HHTMLBrowser unBrowserHandle, bool bAllowed ) = 0;
+
+ // You MUST call this in response to a HTML_JSAlert_t or HTML_JSConfirm_t callback
+ // Set bResult to true for the OK option of a confirm, use false otherwise
+ virtual void JSDialogResponse( HHTMLBrowser unBrowserHandle, bool bResult ) = 0;
+
+ // You MUST call this in response to a HTML_FileOpenDialog_t callback
+ IGNOREATTR()
+ virtual void FileLoadDialogResponse( HHTMLBrowser unBrowserHandle, const char **pchSelectedFiles ) = 0;
+};
+
+#define STEAMHTMLSURFACE_INTERFACE_VERSION "STEAMHTMLSURFACE_INTERFACE_VERSION_003"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The browser is ready for use
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_BrowserReady_t, k_iSteamHTMLSurfaceCallbacks + 1 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // this browser is now fully created and ready to navigate to pages
+END_DEFINE_CALLBACK_1()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: the browser has a pending paint
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK(HTML_NeedsPaint_t, k_iSteamHTMLSurfaceCallbacks + 2)
+CALLBACK_MEMBER(0, HHTMLBrowser, unBrowserHandle) // the browser that needs the paint
+CALLBACK_MEMBER(1, const char *, pBGRA ) // a pointer to the B8G8R8A8 data for this surface, valid until SteamAPI_RunCallbacks is next called
+CALLBACK_MEMBER(2, uint32, unWide) // the total width of the pBGRA texture
+CALLBACK_MEMBER(3, uint32, unTall) // the total height of the pBGRA texture
+CALLBACK_MEMBER(4, uint32, unUpdateX) // the offset in X for the damage rect for this update
+CALLBACK_MEMBER(5, uint32, unUpdateY) // the offset in Y for the damage rect for this update
+CALLBACK_MEMBER(6, uint32, unUpdateWide) // the width of the damage rect for this update
+CALLBACK_MEMBER(7, uint32, unUpdateTall) // the height of the damage rect for this update
+CALLBACK_MEMBER(8, uint32, unScrollX) // the page scroll the browser was at when this texture was rendered
+CALLBACK_MEMBER(9, uint32, unScrollY) // the page scroll the browser was at when this texture was rendered
+CALLBACK_MEMBER(10, float, flPageScale) // the page scale factor on this page when rendered
+CALLBACK_MEMBER(11, uint32, unPageSerial) // incremented on each new page load, you can use this to reject draws while navigating to new pages
+END_DEFINE_CALLBACK_12()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The browser wanted to navigate to a new page
+// NOTE - you MUST call AllowStartRequest in response to this callback
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK(HTML_StartRequest_t, k_iSteamHTMLSurfaceCallbacks + 3)
+CALLBACK_MEMBER(0, HHTMLBrowser, unBrowserHandle) // the handle of the surface navigating
+CALLBACK_MEMBER(1, const char *, pchURL) // the url they wish to navigate to
+CALLBACK_MEMBER(2, const char *, pchTarget) // the html link target type (i.e _blank, _self, _parent, _top )
+CALLBACK_MEMBER(3, const char *, pchPostData ) // any posted data for the request
+CALLBACK_MEMBER(4, bool, bIsRedirect) // true if this was a http/html redirect from the last load request
+END_DEFINE_CALLBACK_5()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The browser has been requested to close due to user interaction (usually from a javascript window.close() call)
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK(HTML_CloseBrowser_t, k_iSteamHTMLSurfaceCallbacks + 4)
+CALLBACK_MEMBER(0, HHTMLBrowser, unBrowserHandle) // the handle of the surface
+END_DEFINE_CALLBACK_1()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: the browser is navigating to a new url
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_URLChanged_t, k_iSteamHTMLSurfaceCallbacks + 5 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface navigating
+CALLBACK_MEMBER( 1, const char *, pchURL ) // the url they wish to navigate to
+CALLBACK_MEMBER( 2, const char *, pchPostData ) // any posted data for the request
+CALLBACK_MEMBER( 3, bool, bIsRedirect ) // true if this was a http/html redirect from the last load request
+CALLBACK_MEMBER( 4, const char *, pchPageTitle ) // the title of the page
+CALLBACK_MEMBER( 5, bool, bNewNavigation ) // true if this was from a fresh tab and not a click on an existing page
+END_DEFINE_CALLBACK_6()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: A page is finished loading
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_FinishedRequest_t, k_iSteamHTMLSurfaceCallbacks + 6 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchURL ) //
+CALLBACK_MEMBER( 2, const char *, pchPageTitle ) //
+END_DEFINE_CALLBACK_3()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a request to load this url in a new tab
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_OpenLinkInNewTab_t, k_iSteamHTMLSurfaceCallbacks + 7 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchURL ) //
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: the page has a new title now
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_ChangedTitle_t, k_iSteamHTMLSurfaceCallbacks + 8 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchTitle ) //
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: results from a search
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_SearchResults_t, k_iSteamHTMLSurfaceCallbacks + 9 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, uint32, unResults ) //
+CALLBACK_MEMBER( 2, uint32, unCurrentMatch ) //
+END_DEFINE_CALLBACK_3()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: page history status changed on the ability to go backwards and forward
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_CanGoBackAndForward_t, k_iSteamHTMLSurfaceCallbacks + 10 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, bool, bCanGoBack ) //
+CALLBACK_MEMBER( 2, bool, bCanGoForward ) //
+END_DEFINE_CALLBACK_3()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: details on the visibility and size of the horizontal scrollbar
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_HorizontalScroll_t, k_iSteamHTMLSurfaceCallbacks + 11 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, uint32, unScrollMax ) //
+CALLBACK_MEMBER( 2, uint32, unScrollCurrent ) //
+CALLBACK_MEMBER( 3, float, flPageScale ) //
+CALLBACK_MEMBER( 4, bool , bVisible ) //
+CALLBACK_MEMBER( 5, uint32, unPageSize ) //
+END_DEFINE_CALLBACK_6()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: details on the visibility and size of the vertical scrollbar
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_VerticalScroll_t, k_iSteamHTMLSurfaceCallbacks + 12 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, uint32, unScrollMax ) //
+CALLBACK_MEMBER( 2, uint32, unScrollCurrent ) //
+CALLBACK_MEMBER( 3, float, flPageScale ) //
+CALLBACK_MEMBER( 4, bool, bVisible ) //
+CALLBACK_MEMBER( 5, uint32, unPageSize ) //
+END_DEFINE_CALLBACK_6()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: response to GetLinkAtPosition call
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_LinkAtPosition_t, k_iSteamHTMLSurfaceCallbacks + 13 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, uint32, x ) // NOTE - Not currently set
+CALLBACK_MEMBER( 2, uint32, y ) // NOTE - Not currently set
+CALLBACK_MEMBER( 3, const char *, pchURL ) //
+CALLBACK_MEMBER( 4, bool, bInput ) //
+CALLBACK_MEMBER( 5, bool, bLiveLink ) //
+END_DEFINE_CALLBACK_6()
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: show a Javascript alert dialog, call JSDialogResponse
+// when the user dismisses this dialog (or right away to ignore it)
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_JSAlert_t, k_iSteamHTMLSurfaceCallbacks + 14 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchMessage ) //
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: show a Javascript confirmation dialog, call JSDialogResponse
+// when the user dismisses this dialog (or right away to ignore it)
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_JSConfirm_t, k_iSteamHTMLSurfaceCallbacks + 15 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchMessage ) //
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: when received show a file open dialog
+// then call FileLoadDialogResponse with the file(s) the user selected.
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_FileOpenDialog_t, k_iSteamHTMLSurfaceCallbacks + 16 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchTitle ) //
+CALLBACK_MEMBER( 2, const char *, pchInitialFile ) //
+END_DEFINE_CALLBACK_3()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a new html window has been created
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_NewWindow_t, k_iSteamHTMLSurfaceCallbacks + 21 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the current surface
+CALLBACK_MEMBER( 1, const char *, pchURL ) // the page to load
+CALLBACK_MEMBER( 2, uint32, unX ) // the x pos into the page to display the popup
+CALLBACK_MEMBER( 3, uint32, unY ) // the y pos into the page to display the popup
+CALLBACK_MEMBER( 4, uint32, unWide ) // the total width of the pBGRA texture
+CALLBACK_MEMBER( 5, uint32, unTall ) // the total height of the pBGRA texture
+CALLBACK_MEMBER( 6, HHTMLBrowser, unNewWindow_BrowserHandle ) // the handle of the new window surface
+END_DEFINE_CALLBACK_7()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: change the cursor to display
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_SetCursor_t, k_iSteamHTMLSurfaceCallbacks + 22 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, uint32, eMouseCursor ) // the EMouseCursor to display
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: informational message from the browser
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_StatusText_t, k_iSteamHTMLSurfaceCallbacks + 23 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchMsg ) // the EMouseCursor to display
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: show a tooltip
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_ShowToolTip_t, k_iSteamHTMLSurfaceCallbacks + 24 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchMsg ) // the EMouseCursor to display
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: update the text of an existing tooltip
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_UpdateToolTip_t, k_iSteamHTMLSurfaceCallbacks + 25 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+CALLBACK_MEMBER( 1, const char *, pchMsg ) // the EMouseCursor to display
+END_DEFINE_CALLBACK_2()
+
+
+//-----------------------------------------------------------------------------
+// Purpose: hide the tooltip you are showing
+//-----------------------------------------------------------------------------
+DEFINE_CALLBACK( HTML_HideToolTip_t, k_iSteamHTMLSurfaceCallbacks + 26 )
+CALLBACK_MEMBER( 0, HHTMLBrowser, unBrowserHandle ) // the handle of the surface
+END_DEFINE_CALLBACK_1()
+
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMHTMLSURFACE_H
diff --git a/dep/steam_api/isteamhttp.h b/dep/steam_api/isteamhttp.h
new file mode 100644
index 0000000..8fab537
--- /dev/null
+++ b/dep/steam_api/isteamhttp.h
@@ -0,0 +1,210 @@
+//====== Copyright © 1996-2009, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to http client
+//
+//=============================================================================
+
+#ifndef ISTEAMHTTP_H
+#define ISTEAMHTTP_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+#include "steamhttpenums.h"
+
+// Handle to a HTTP Request handle
+typedef uint32 HTTPRequestHandle;
+#define INVALID_HTTPREQUEST_HANDLE 0
+
+typedef uint32 HTTPCookieContainerHandle;
+#define INVALID_HTTPCOOKIE_HANDLE 0
+
+//-----------------------------------------------------------------------------
+// Purpose: interface to http client
+//-----------------------------------------------------------------------------
+class ISteamHTTP
+{
+public:
+
+ // Initializes a new HTTP request, returning a handle to use in further operations on it. Requires
+ // the method (GET or POST) and the absolute URL for the request. Both http and https are supported,
+ // so this string must start with http:// or https:// and should look like http://store.steampowered.com/app/250/
+ // or such.
+ virtual HTTPRequestHandle CreateHTTPRequest( EHTTPMethod eHTTPRequestMethod, const char *pchAbsoluteURL ) = 0;
+
+ // Set a context value for the request, which will be returned in the HTTPRequestCompleted_t callback after
+ // sending the request. This is just so the caller can easily keep track of which callbacks go with which request data.
+ virtual bool SetHTTPRequestContextValue( HTTPRequestHandle hRequest, uint64 ulContextValue ) = 0;
+
+ // Set a timeout in seconds for the HTTP request, must be called prior to sending the request. Default
+ // timeout is 60 seconds if you don't call this. Returns false if the handle is invalid, or the request
+ // has already been sent.
+ virtual bool SetHTTPRequestNetworkActivityTimeout( HTTPRequestHandle hRequest, uint32 unTimeoutSeconds ) = 0;
+
+ // Set a request header value for the request, must be called prior to sending the request. Will
+ // return false if the handle is invalid or the request is already sent.
+ virtual bool SetHTTPRequestHeaderValue( HTTPRequestHandle hRequest, const char *pchHeaderName, const char *pchHeaderValue ) = 0;
+
+ // Set a GET or POST parameter value on the request, which is set will depend on the EHTTPMethod specified
+ // when creating the request. Must be called prior to sending the request. Will return false if the
+ // handle is invalid or the request is already sent.
+ virtual bool SetHTTPRequestGetOrPostParameter( HTTPRequestHandle hRequest, const char *pchParamName, const char *pchParamValue ) = 0;
+
+ // Sends the HTTP request, will return false on a bad handle, otherwise use SteamCallHandle to wait on
+ // asynchronous response via callback.
+ //
+ // Note: If the user is in offline mode in Steam, then this will add a only-if-cached cache-control
+ // header and only do a local cache lookup rather than sending any actual remote request.
+ virtual bool SendHTTPRequest( HTTPRequestHandle hRequest, SteamAPICall_t *pCallHandle ) = 0;
+
+ // Sends the HTTP request, will return false on a bad handle, otherwise use SteamCallHandle to wait on
+ // asynchronous response via callback for completion, and listen for HTTPRequestHeadersReceived_t and
+ // HTTPRequestDataReceived_t callbacks while streaming.
+ virtual bool SendHTTPRequestAndStreamResponse( HTTPRequestHandle hRequest, SteamAPICall_t *pCallHandle ) = 0;
+
+ // Defers a request you have sent, the actual HTTP client code may have many requests queued, and this will move
+ // the specified request to the tail of the queue. Returns false on invalid handle, or if the request is not yet sent.
+ virtual bool DeferHTTPRequest( HTTPRequestHandle hRequest ) = 0;
+
+ // Prioritizes a request you have sent, the actual HTTP client code may have many requests queued, and this will move
+ // the specified request to the head of the queue. Returns false on invalid handle, or if the request is not yet sent.
+ virtual bool PrioritizeHTTPRequest( HTTPRequestHandle hRequest ) = 0;
+
+ // Checks if a response header is present in a HTTP response given a handle from HTTPRequestCompleted_t, also
+ // returns the size of the header value if present so the caller and allocate a correctly sized buffer for
+ // GetHTTPResponseHeaderValue.
+ virtual bool GetHTTPResponseHeaderSize( HTTPRequestHandle hRequest, const char *pchHeaderName, uint32 *unResponseHeaderSize ) = 0;
+
+ // Gets header values from a HTTP response given a handle from HTTPRequestCompleted_t, will return false if the
+ // header is not present or if your buffer is too small to contain it's value. You should first call
+ // BGetHTTPResponseHeaderSize to check for the presence of the header and to find out the size buffer needed.
+ virtual bool GetHTTPResponseHeaderValue( HTTPRequestHandle hRequest, const char *pchHeaderName, uint8 *pHeaderValueBuffer, uint32 unBufferSize ) = 0;
+
+ // Gets the size of the body data from a HTTP response given a handle from HTTPRequestCompleted_t, will return false if the
+ // handle is invalid.
+ virtual bool GetHTTPResponseBodySize( HTTPRequestHandle hRequest, uint32 *unBodySize ) = 0;
+
+ // Gets the body data from a HTTP response given a handle from HTTPRequestCompleted_t, will return false if the
+ // handle is invalid or is to a streaming response, or if the provided buffer is not the correct size. Use BGetHTTPResponseBodySize first to find out
+ // the correct buffer size to use.
+ virtual bool GetHTTPResponseBodyData( HTTPRequestHandle hRequest, uint8 *pBodyDataBuffer, uint32 unBufferSize ) = 0;
+
+ // Gets the body data from a streaming HTTP response given a handle from HTTPRequestDataReceived_t. Will return false if the
+ // handle is invalid or is to a non-streaming response (meaning it wasn't sent with SendHTTPRequestAndStreamResponse), or if the buffer size and offset
+ // do not match the size and offset sent in HTTPRequestDataReceived_t.
+ virtual bool GetHTTPStreamingResponseBodyData( HTTPRequestHandle hRequest, uint32 cOffset, uint8 *pBodyDataBuffer, uint32 unBufferSize ) = 0;
+
+ // Releases an HTTP response handle, should always be called to free resources after receiving a HTTPRequestCompleted_t
+ // callback and finishing using the response.
+ virtual bool ReleaseHTTPRequest( HTTPRequestHandle hRequest ) = 0;
+
+ // Gets progress on downloading the body for the request. This will be zero unless a response header has already been
+ // received which included a content-length field. For responses that contain no content-length it will report
+ // zero for the duration of the request as the size is unknown until the connection closes.
+ virtual bool GetHTTPDownloadProgressPct( HTTPRequestHandle hRequest, float *pflPercentOut ) = 0;
+
+ // Sets the body for an HTTP Post request. Will fail and return false on a GET request, and will fail if POST params
+ // have already been set for the request. Setting this raw body makes it the only contents for the post, the pchContentType
+ // parameter will set the content-type header for the request so the server may know how to interpret the body.
+ virtual bool SetHTTPRequestRawPostBody( HTTPRequestHandle hRequest, const char *pchContentType, uint8 *pubBody, uint32 unBodyLen ) = 0;
+
+ // Creates a cookie container handle which you must later free with ReleaseCookieContainer(). If bAllowResponsesToModify=true
+ // than any response to your requests using this cookie container may add new cookies which may be transmitted with
+ // future requests. If bAllowResponsesToModify=false than only cookies you explicitly set will be sent. This API is just for
+ // during process lifetime, after steam restarts no cookies are persisted and you have no way to access the cookie container across
+ // repeat executions of your process.
+ virtual HTTPCookieContainerHandle CreateCookieContainer( bool bAllowResponsesToModify ) = 0;
+
+ // Release a cookie container you are finished using, freeing it's memory
+ virtual bool ReleaseCookieContainer( HTTPCookieContainerHandle hCookieContainer ) = 0;
+
+ // Adds a cookie to the specified cookie container that will be used with future requests.
+ virtual bool SetCookie( HTTPCookieContainerHandle hCookieContainer, const char *pchHost, const char *pchUrl, const char *pchCookie ) = 0;
+
+ // Set the cookie container to use for a HTTP request
+ virtual bool SetHTTPRequestCookieContainer( HTTPRequestHandle hRequest, HTTPCookieContainerHandle hCookieContainer ) = 0;
+
+ // Set the extra user agent info for a request, this doesn't clobber the normal user agent, it just adds the extra info on the end
+ virtual bool SetHTTPRequestUserAgentInfo( HTTPRequestHandle hRequest, const char *pchUserAgentInfo ) = 0;
+
+ // Set that https request should require verified SSL certificate via machines certificate trust store
+ virtual bool SetHTTPRequestRequiresVerifiedCertificate( HTTPRequestHandle hRequest, bool bRequireVerifiedCertificate ) = 0;
+
+ // Set an absolute timeout on the HTTP request, this is just a total time timeout different than the network activity timeout
+ // which can bump everytime we get more data
+ virtual bool SetHTTPRequestAbsoluteTimeoutMS( HTTPRequestHandle hRequest, uint32 unMilliseconds ) = 0;
+
+ // Check if the reason the request failed was because we timed it out (rather than some harder failure)
+ virtual bool GetHTTPRequestWasTimedOut( HTTPRequestHandle hRequest, bool *pbWasTimedOut ) = 0;
+};
+
+#define STEAMHTTP_INTERFACE_VERSION "STEAMHTTP_INTERFACE_VERSION002"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+struct HTTPRequestCompleted_t
+{
+ enum { k_iCallback = k_iClientHTTPCallbacks + 1 };
+
+ // Handle value for the request that has completed.
+ HTTPRequestHandle m_hRequest;
+
+ // Context value that the user defined on the request that this callback is associated with, 0 if
+ // no context value was set.
+ uint64 m_ulContextValue;
+
+ // This will be true if we actually got any sort of response from the server (even an error).
+ // It will be false if we failed due to an internal error or client side network failure.
+ bool m_bRequestSuccessful;
+
+ // Will be the HTTP status code value returned by the server, k_EHTTPStatusCode200OK is the normal
+ // OK response, if you get something else you probably need to treat it as a failure.
+ EHTTPStatusCode m_eStatusCode;
+
+ uint32 m_unBodySize; // Same as GetHTTPResponseBodySize()
+};
+
+
+struct HTTPRequestHeadersReceived_t
+{
+ enum { k_iCallback = k_iClientHTTPCallbacks + 2 };
+
+ // Handle value for the request that has received headers.
+ HTTPRequestHandle m_hRequest;
+
+ // Context value that the user defined on the request that this callback is associated with, 0 if
+ // no context value was set.
+ uint64 m_ulContextValue;
+};
+
+struct HTTPRequestDataReceived_t
+{
+ enum { k_iCallback = k_iClientHTTPCallbacks + 3 };
+
+ // Handle value for the request that has received data.
+ HTTPRequestHandle m_hRequest;
+
+ // Context value that the user defined on the request that this callback is associated with, 0 if
+ // no context value was set.
+ uint64 m_ulContextValue;
+
+
+ // Offset to provide to GetHTTPStreamingResponseBodyData to get this chunk of data
+ uint32 m_cOffset;
+
+ // Size to provide to GetHTTPStreamingResponseBodyData to get this chunk of data
+ uint32 m_cBytesReceived;
+};
+
+
+#pragma pack( pop )
+
+#endif // ISTEAMHTTP_H
\ No newline at end of file
diff --git a/dep/steam_api/isteaminventory.h b/dep/steam_api/isteaminventory.h
new file mode 100644
index 0000000..692c62d
--- /dev/null
+++ b/dep/steam_api/isteaminventory.h
@@ -0,0 +1,382 @@
+//====== Copyright 1996-2014 Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to Steam Inventory
+//
+//=============================================================================
+
+#ifndef ISTEAMINVENTORY_H
+#define ISTEAMINVENTORY_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+// Every individual instance of an item has a globally-unique ItemInstanceID.
+// This ID is unique to the combination of (player, specific item instance)
+// and will not be transferred to another player or re-used for another item.
+typedef uint64 SteamItemInstanceID_t;
+
+static const SteamItemInstanceID_t k_SteamItemInstanceIDInvalid = (SteamItemInstanceID_t)~0;
+
+// Types of items in your game are identified by a 32-bit "item definition number".
+// Valid definition numbers are between 1 and 999999999; numbers less than or equal to
+// zero are invalid, and numbers greater than or equal to one billion (1x10^9) are
+// reserved for internal Steam use.
+typedef int32 SteamItemDef_t;
+
+
+enum ESteamItemFlags
+{
+ // Item status flags - these flags are permanently attached to specific item instances
+ k_ESteamItemNoTrade = 1 << 0, // This item is account-locked and cannot be traded or given away.
+
+ // Action confirmation flags - these flags are set one time only, as part of a result set
+ k_ESteamItemRemoved = 1 << 8, // The item has been destroyed, traded away, expired, or otherwise invalidated
+ k_ESteamItemConsumed = 1 << 9, // The item quantity has been decreased by 1 via ConsumeItem API.
+
+ // All other flag bits are currently reserved for internal Steam use at this time.
+ // Do not assume anything about the state of other flags which are not defined here.
+};
+
+struct SteamItemDetails_t
+{
+ SteamItemInstanceID_t m_itemId;
+ SteamItemDef_t m_iDefinition;
+ uint16 m_unQuantity;
+ uint16 m_unFlags; // see ESteamItemFlags
+};
+
+typedef int32 SteamInventoryResult_t;
+
+static const SteamInventoryResult_t k_SteamInventoryResultInvalid = -1;
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Steam Inventory query and manipulation API
+//-----------------------------------------------------------------------------
+class ISteamInventory
+{
+public:
+
+ // INVENTORY ASYNC RESULT MANAGEMENT
+ //
+ // Asynchronous inventory queries always output a result handle which can be used with
+ // GetResultStatus, GetResultItems, etc. A SteamInventoryResultReady_t callback will
+ // be triggered when the asynchronous result becomes ready (or fails).
+ //
+
+ // Find out the status of an asynchronous inventory result handle. Possible values:
+ // k_EResultPending - still in progress
+ // k_EResultOK - done, result ready
+ // k_EResultExpired - done, result ready, maybe out of date (see DeserializeResult)
+ // k_EResultInvalidParam - ERROR: invalid API call parameters
+ // k_EResultServiceUnavailable - ERROR: service temporarily down, you may retry later
+ // k_EResultLimitExceeded - ERROR: operation would exceed per-user inventory limits
+ // k_EResultFail - ERROR: unknown / generic error
+ METHOD_DESC(Find out the status of an asynchronous inventory result handle.)
+ virtual EResult GetResultStatus( SteamInventoryResult_t resultHandle ) = 0;
+
+ // Copies the contents of a result set into a flat array. The specific
+ // contents of the result set depend on which query which was used.
+ METHOD_DESC(Copies the contents of a result set into a flat array. The specific contents of the result set depend on which query which was used.)
+ virtual bool GetResultItems( SteamInventoryResult_t resultHandle,
+ OUT_ARRAY_COUNT( punOutItemsArraySize,Output array) SteamItemDetails_t *pOutItemsArray,
+ uint32 *punOutItemsArraySize ) = 0;
+
+ // In combination with GetResultItems, you can use GetResultItemProperty to retrieve
+ // dynamic string properties for a given item returned in the result set.
+ //
+ // Property names are always composed of ASCII letters, numbers, and/or underscores.
+ //
+ // Pass a NULL pointer for pchPropertyName to get a comma - separated list of available
+ // property names.
+ //
+ // If pchValueBuffer is NULL, *punValueBufferSize will contain the
+ // suggested buffer size. Otherwise it will be the number of bytes actually copied
+ // to pchValueBuffer. If the results do not fit in the given buffer, partial
+ // results may be copied.
+ virtual bool GetResultItemProperty( SteamInventoryResult_t resultHandle,
+ uint32 unItemIndex,
+ const char *pchPropertyName,
+ OUT_STRING_COUNT( punValueBufferSizeOut ) char *pchValueBuffer, uint32 *punValueBufferSizeOut ) = 0;
+
+ // Returns the server time at which the result was generated. Compare against
+ // the value of IClientUtils::GetServerRealTime() to determine age.
+ METHOD_DESC(Returns the server time at which the result was generated. Compare against the value of IClientUtils::GetServerRealTime() to determine age.)
+ virtual uint32 GetResultTimestamp( SteamInventoryResult_t resultHandle ) = 0;
+
+ // Returns true if the result belongs to the target steam ID, false if the
+ // result does not. This is important when using DeserializeResult, to verify
+ // that a remote player is not pretending to have a different user's inventory.
+ METHOD_DESC(Returns true if the result belongs to the target steam ID or false if the result does not. This is important when using DeserializeResult to verify that a remote player is not pretending to have a different users inventory.)
+ virtual bool CheckResultSteamID( SteamInventoryResult_t resultHandle, CSteamID steamIDExpected ) = 0;
+
+ // Destroys a result handle and frees all associated memory.
+ METHOD_DESC(Destroys a result handle and frees all associated memory.)
+ virtual void DestroyResult( SteamInventoryResult_t resultHandle ) = 0;
+
+
+ // INVENTORY ASYNC QUERY
+ //
+
+ // Captures the entire state of the current user's Steam inventory.
+ // You must call DestroyResult on this handle when you are done with it.
+ // Returns false and sets *pResultHandle to zero if inventory is unavailable.
+ // Note: calls to this function are subject to rate limits and may return
+ // cached results if called too frequently. It is suggested that you call
+ // this function only when you are about to display the user's full inventory,
+ // or if you expect that the inventory may have changed.
+ METHOD_DESC(Captures the entire state of the current users Steam inventory.)
+ virtual bool GetAllItems( SteamInventoryResult_t *pResultHandle ) = 0;
+
+
+ // Captures the state of a subset of the current user's Steam inventory,
+ // identified by an array of item instance IDs. The results from this call
+ // can be serialized and passed to other players to "prove" that the current
+ // user owns specific items, without exposing the user's entire inventory.
+ // For example, you could call GetItemsByID with the IDs of the user's
+ // currently equipped cosmetic items and serialize this to a buffer, and
+ // then transmit this buffer to other players upon joining a game.
+ METHOD_DESC(Captures the state of a subset of the current users Steam inventory identified by an array of item instance IDs.)
+ virtual bool GetItemsByID( SteamInventoryResult_t *pResultHandle, ARRAY_COUNT( unCountInstanceIDs ) const SteamItemInstanceID_t *pInstanceIDs, uint32 unCountInstanceIDs ) = 0;
+
+
+ // RESULT SERIALIZATION AND AUTHENTICATION
+ //
+ // Serialized result sets contain a short signature which can't be forged
+ // or replayed across different game sessions. A result set can be serialized
+ // on the local client, transmitted to other players via your game networking,
+ // and deserialized by the remote players. This is a secure way of preventing
+ // hackers from lying about posessing rare/high-value items.
+
+ // Serializes a result set with signature bytes to an output buffer. Pass
+ // NULL as an output buffer to get the required size via punOutBufferSize.
+ // The size of a serialized result depends on the number items which are being
+ // serialized. When securely transmitting items to other players, it is
+ // recommended to use "GetItemsByID" first to create a minimal result set.
+ // Results have a built-in timestamp which will be considered "expired" after
+ // an hour has elapsed. See DeserializeResult for expiration handling.
+ virtual bool SerializeResult( SteamInventoryResult_t resultHandle, OUT_BUFFER_COUNT(punOutBufferSize) void *pOutBuffer, uint32 *punOutBufferSize ) = 0;
+
+ // Deserializes a result set and verifies the signature bytes. Returns false
+ // if bRequireFullOnlineVerify is set but Steam is running in Offline mode.
+ // Otherwise returns true and then delivers error codes via GetResultStatus.
+ //
+ // The bRESERVED_MUST_BE_FALSE flag is reserved for future use and should not
+ // be set to true by your game at this time.
+ //
+ // DeserializeResult has a potential soft-failure mode where the handle status
+ // is set to k_EResultExpired. GetResultItems() still succeeds in this mode.
+ // The "expired" result could indicate that the data may be out of date - not
+ // just due to timed expiration (one hour), but also because one of the items
+ // in the result set may have been traded or consumed since the result set was
+ // generated. You could compare the timestamp from GetResultTimestamp() to
+ // ISteamUtils::GetServerRealTime() to determine how old the data is. You could
+ // simply ignore the "expired" result code and continue as normal, or you
+ // could challenge the player with expired data to send an updated result set.
+ virtual bool DeserializeResult( SteamInventoryResult_t *pOutResultHandle, BUFFER_COUNT(punOutBufferSize) const void *pBuffer, uint32 unBufferSize, bool bRESERVED_MUST_BE_FALSE = false ) = 0;
+
+
+ // INVENTORY ASYNC MODIFICATION
+ //
+
+ // GenerateItems() creates one or more items and then generates a SteamInventoryCallback_t
+ // notification with a matching nCallbackContext parameter. This API is only intended
+ // for prototyping - it is only usable by Steam accounts that belong to the publisher group
+ // for your game.
+ // If punArrayQuantity is not NULL, it should be the same length as pArrayItems and should
+ // describe the quantity of each item to generate.
+ virtual bool GenerateItems( SteamInventoryResult_t *pResultHandle, ARRAY_COUNT(unArrayLength) const SteamItemDef_t *pArrayItemDefs, ARRAY_COUNT(unArrayLength) const uint32 *punArrayQuantity, uint32 unArrayLength ) = 0;
+
+ // GrantPromoItems() checks the list of promotional items for which the user may be eligible
+ // and grants the items (one time only). On success, the result set will include items which
+ // were granted, if any. If no items were granted because the user isn't eligible for any
+ // promotions, this is still considered a success.
+ METHOD_DESC(GrantPromoItems() checks the list of promotional items for which the user may be eligible and grants the items (one time only).)
+ virtual bool GrantPromoItems( SteamInventoryResult_t *pResultHandle ) = 0;
+
+ // AddPromoItem() / AddPromoItems() are restricted versions of GrantPromoItems(). Instead of
+ // scanning for all eligible promotional items, the check is restricted to a single item
+ // definition or set of item definitions. This can be useful if your game has custom UI for
+ // showing a specific promo item to the user.
+ virtual bool AddPromoItem( SteamInventoryResult_t *pResultHandle, SteamItemDef_t itemDef ) = 0;
+ virtual bool AddPromoItems( SteamInventoryResult_t *pResultHandle, ARRAY_COUNT(unArrayLength) const SteamItemDef_t *pArrayItemDefs, uint32 unArrayLength ) = 0;
+
+ // ConsumeItem() removes items from the inventory, permanently. They cannot be recovered.
+ // Not for the faint of heart - if your game implements item removal at all, a high-friction
+ // UI confirmation process is highly recommended.
+ METHOD_DESC(ConsumeItem() removes items from the inventory permanently.)
+ virtual bool ConsumeItem( SteamInventoryResult_t *pResultHandle, SteamItemInstanceID_t itemConsume, uint32 unQuantity ) = 0;
+
+ // ExchangeItems() is an atomic combination of item generation and consumption.
+ // It can be used to implement crafting recipes or transmutations, or items which unpack
+ // themselves into other items (e.g., a chest).
+ // Exchange recipes are defined in the ItemDef, and explicitly list the required item
+ // types and resulting generated type.
+ // Exchange recipes are evaluated atomically by the Inventory Service; if the supplied
+ // components do not match the recipe, or do not contain sufficient quantity, the
+ // exchange will fail.
+ virtual bool ExchangeItems( SteamInventoryResult_t *pResultHandle,
+ ARRAY_COUNT(unArrayGenerateLength) const SteamItemDef_t *pArrayGenerate, ARRAY_COUNT(unArrayGenerateLength) const uint32 *punArrayGenerateQuantity, uint32 unArrayGenerateLength,
+ ARRAY_COUNT(unArrayDestroyLength) const SteamItemInstanceID_t *pArrayDestroy, ARRAY_COUNT(unArrayDestroyLength) const uint32 *punArrayDestroyQuantity, uint32 unArrayDestroyLength ) = 0;
+
+
+ // TransferItemQuantity() is intended for use with items which are "stackable" (can have
+ // quantity greater than one). It can be used to split a stack into two, or to transfer
+ // quantity from one stack into another stack of identical items. To split one stack into
+ // two, pass k_SteamItemInstanceIDInvalid for itemIdDest and a new item will be generated.
+ virtual bool TransferItemQuantity( SteamInventoryResult_t *pResultHandle, SteamItemInstanceID_t itemIdSource, uint32 unQuantity, SteamItemInstanceID_t itemIdDest ) = 0;
+
+
+ // TIMED DROPS AND PLAYTIME CREDIT
+ //
+
+ // Deprecated. Calling this method is not required for proper playtime accounting.
+ METHOD_DESC( Deprecated method. Playtime accounting is performed on the Steam servers. )
+ virtual void SendItemDropHeartbeat() = 0;
+
+ // Playtime credit must be consumed and turned into item drops by your game. Only item
+ // definitions which are marked as "playtime item generators" can be spawned. The call
+ // will return an empty result set if there is not enough playtime credit for a drop.
+ // Your game should call TriggerItemDrop at an appropriate time for the user to receive
+ // new items, such as between rounds or while the player is dead. Note that players who
+ // hack their clients could modify the value of "dropListDefinition", so do not use it
+ // to directly control rarity.
+ // See your Steamworks configuration to set playtime drop rates for individual itemdefs.
+ // The client library will suppress too-frequent calls to this method.
+ METHOD_DESC(Playtime credit must be consumed and turned into item drops by your game.)
+ virtual bool TriggerItemDrop( SteamInventoryResult_t *pResultHandle, SteamItemDef_t dropListDefinition ) = 0;
+
+
+ // IN-GAME TRADING
+ //
+ // TradeItems() implements limited in-game trading of items, if you prefer not to use
+ // the overlay or an in-game web browser to perform Steam Trading through the website.
+ // You should implement a UI where both players can see and agree to a trade, and then
+ // each client should call TradeItems simultaneously (+/- 5 seconds) with matching
+ // (but reversed) parameters. The result is the same as if both players performed a
+ // Steam Trading transaction through the web. Each player will get an inventory result
+ // confirming the removal or quantity changes of the items given away, and the new
+ // item instance id numbers and quantities of the received items.
+ // (Note: new item instance IDs are generated whenever an item changes ownership.)
+ virtual bool TradeItems( SteamInventoryResult_t *pResultHandle, CSteamID steamIDTradePartner,
+ ARRAY_COUNT(nArrayGiveLength) const SteamItemInstanceID_t *pArrayGive, ARRAY_COUNT(nArrayGiveLength) const uint32 *pArrayGiveQuantity, uint32 nArrayGiveLength,
+ ARRAY_COUNT(nArrayGetLength) const SteamItemInstanceID_t *pArrayGet, ARRAY_COUNT(nArrayGetLength) const uint32 *pArrayGetQuantity, uint32 nArrayGetLength ) = 0;
+
+
+ // ITEM DEFINITIONS
+ //
+ // Item definitions are a mapping of "definition IDs" (integers between 1 and 1000000)
+ // to a set of string properties. Some of these properties are required to display items
+ // on the Steam community web site. Other properties can be defined by applications.
+ // Use of these functions is optional; there is no reason to call LoadItemDefinitions
+ // if your game hardcodes the numeric definition IDs (eg, purple face mask = 20, blue
+ // weapon mod = 55) and does not allow for adding new item types without a client patch.
+ //
+
+ // LoadItemDefinitions triggers the automatic load and refresh of item definitions.
+ // Every time new item definitions are available (eg, from the dynamic addition of new
+ // item types while players are still in-game), a SteamInventoryDefinitionUpdate_t
+ // callback will be fired.
+ METHOD_DESC(LoadItemDefinitions triggers the automatic load and refresh of item definitions.)
+ virtual bool LoadItemDefinitions() = 0;
+
+ // GetItemDefinitionIDs returns the set of all defined item definition IDs (which are
+ // defined via Steamworks configuration, and not necessarily contiguous integers).
+ // If pItemDefIDs is null, the call will return true and *punItemDefIDsArraySize will
+ // contain the total size necessary for a subsequent call. Otherwise, the call will
+ // return false if and only if there is not enough space in the output array.
+ virtual bool GetItemDefinitionIDs(
+ OUT_ARRAY_COUNT(punItemDefIDsArraySize,List of item definition IDs) SteamItemDef_t *pItemDefIDs,
+ DESC(Size of array is passed in and actual size used is returned in this param) uint32 *punItemDefIDsArraySize ) = 0;
+
+ // GetItemDefinitionProperty returns a string property from a given item definition.
+ // Note that some properties (for example, "name") may be localized and will depend
+ // on the current Steam language settings (see ISteamApps::GetCurrentGameLanguage).
+ // Property names are always composed of ASCII letters, numbers, and/or underscores.
+ // Pass a NULL pointer for pchPropertyName to get a comma - separated list of available
+ // property names. If pchValueBuffer is NULL, *punValueBufferSize will contain the
+ // suggested buffer size. Otherwise it will be the number of bytes actually copied
+ // to pchValueBuffer. If the results do not fit in the given buffer, partial
+ // results may be copied.
+ virtual bool GetItemDefinitionProperty( SteamItemDef_t iDefinition, const char *pchPropertyName,
+ OUT_STRING_COUNT(punValueBufferSizeOut) char *pchValueBuffer, uint32 *punValueBufferSizeOut ) = 0;
+
+ // Request the list of "eligible" promo items that can be manually granted to the given
+ // user. These are promo items of type "manual" that won't be granted automatically.
+ // An example usage of this is an item that becomes available every week.
+ CALL_RESULT( SteamInventoryEligiblePromoItemDefIDs_t )
+ virtual SteamAPICall_t RequestEligiblePromoItemDefinitionsIDs( CSteamID steamID ) = 0;
+
+ // After handling a SteamInventoryEligiblePromoItemDefIDs_t call result, use this
+ // function to pull out the list of item definition ids that the user can be
+ // manually granted via the AddPromoItems() call.
+ virtual bool GetEligiblePromoItemDefinitionIDs(
+ CSteamID steamID,
+ OUT_ARRAY_COUNT(punItemDefIDsArraySize,List of item definition IDs) SteamItemDef_t *pItemDefIDs,
+ DESC(Size of array is passed in and actual size used is returned in this param) uint32 *punItemDefIDsArraySize ) = 0;
+};
+
+#define STEAMINVENTORY_INTERFACE_VERSION "STEAMINVENTORY_INTERFACE_V002"
+
+
+// SteamInventoryResultReady_t callbacks are fired whenever asynchronous
+// results transition from "Pending" to "OK" or an error state. There will
+// always be exactly one callback per handle.
+struct SteamInventoryResultReady_t
+{
+ enum { k_iCallback = k_iClientInventoryCallbacks + 0 };
+ SteamInventoryResult_t m_handle;
+ EResult m_result;
+};
+
+
+// SteamInventoryFullUpdate_t callbacks are triggered when GetAllItems
+// successfully returns a result which is newer / fresher than the last
+// known result. (It will not trigger if the inventory hasn't changed,
+// or if results from two overlapping calls are reversed in flight and
+// the earlier result is already known to be stale/out-of-date.)
+// The normal ResultReady callback will still be triggered immediately
+// afterwards; this is an additional notification for your convenience.
+struct SteamInventoryFullUpdate_t
+{
+ enum { k_iCallback = k_iClientInventoryCallbacks + 1 };
+ SteamInventoryResult_t m_handle;
+};
+
+
+// A SteamInventoryDefinitionUpdate_t callback is triggered whenever
+// item definitions have been updated, which could be in response to
+// LoadItemDefinitions() or any other async request which required
+// a definition update in order to process results from the server.
+struct SteamInventoryDefinitionUpdate_t
+{
+ enum { k_iCallback = k_iClientInventoryCallbacks + 2 };
+};
+
+// Returned
+struct SteamInventoryEligiblePromoItemDefIDs_t
+{
+ enum { k_iCallback = k_iClientInventoryCallbacks + 3 };
+ EResult m_result;
+ CSteamID m_steamID;
+ int m_numEligiblePromoItemDefs;
+ bool m_bCachedData; // indicates that the data was retrieved from the cache and not the server
+};
+
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMCONTROLLER_H
diff --git a/dep/steam_api/isteammasterserverupdater.h b/dep/steam_api/isteammasterserverupdater.h
new file mode 100644
index 0000000..4be0ca5
--- /dev/null
+++ b/dep/steam_api/isteammasterserverupdater.h
@@ -0,0 +1 @@
+#error "This file isn't used any more"
diff --git a/dep/steam_api/isteammatchmaking.h b/dep/steam_api/isteammatchmaking.h
new file mode 100644
index 0000000..837d98b
--- /dev/null
+++ b/dep/steam_api/isteammatchmaking.h
@@ -0,0 +1,751 @@
+//====== Copyright © 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to steam managing game server/client match making
+//
+//=============================================================================
+
+#ifndef ISTEAMMATCHMAKING
+#define ISTEAMMATCHMAKING
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "steamtypes.h"
+#include "steamclientpublic.h"
+#include "matchmakingtypes.h"
+#include "isteamclient.h"
+#include "isteamfriends.h"
+
+// lobby type description
+enum ELobbyType
+{
+ k_ELobbyTypePrivate = 0, // only way to join the lobby is to invite to someone else
+ k_ELobbyTypeFriendsOnly = 1, // shows for friends or invitees, but not in lobby list
+ k_ELobbyTypePublic = 2, // visible for friends and in lobby list
+ k_ELobbyTypeInvisible = 3, // returned by search, but not visible to other friends
+ // useful if you want a user in two lobbies, for example matching groups together
+ // a user can be in only one regular lobby, and up to two invisible lobbies
+};
+
+// lobby search filter tools
+enum ELobbyComparison
+{
+ k_ELobbyComparisonEqualToOrLessThan = -2,
+ k_ELobbyComparisonLessThan = -1,
+ k_ELobbyComparisonEqual = 0,
+ k_ELobbyComparisonGreaterThan = 1,
+ k_ELobbyComparisonEqualToOrGreaterThan = 2,
+ k_ELobbyComparisonNotEqual = 3,
+};
+
+// lobby search distance. Lobby results are sorted from closest to farthest.
+enum ELobbyDistanceFilter
+{
+ k_ELobbyDistanceFilterClose, // only lobbies in the same immediate region will be returned
+ k_ELobbyDistanceFilterDefault, // only lobbies in the same region or near by regions
+ k_ELobbyDistanceFilterFar, // for games that don't have many latency requirements, will return lobbies about half-way around the globe
+ k_ELobbyDistanceFilterWorldwide, // no filtering, will match lobbies as far as India to NY (not recommended, expect multiple seconds of latency between the clients)
+};
+
+// maximum number of characters a lobby metadata key can be
+#define k_nMaxLobbyKeyLength 255
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for match making services for clients to get to favorites
+// and to operate on game lobbies.
+//-----------------------------------------------------------------------------
+class ISteamMatchmaking
+{
+public:
+ // game server favorites storage
+ // saves basic details about a multiplayer game server locally
+
+ // returns the number of favorites servers the user has stored
+ virtual int GetFavoriteGameCount() = 0;
+
+ // returns the details of the game server
+ // iGame is of range [0,GetFavoriteGameCount())
+ // *pnIP, *pnConnPort are filled in the with IP:port of the game server
+ // *punFlags specify whether the game server was stored as an explicit favorite or in the history of connections
+ // *pRTime32LastPlayedOnServer is filled in the with the Unix time the favorite was added
+ virtual bool GetFavoriteGame( int iGame, AppId_t *pnAppID, uint32 *pnIP, uint16 *pnConnPort, uint16 *pnQueryPort, uint32 *punFlags, uint32 *pRTime32LastPlayedOnServer ) = 0;
+
+ // adds the game server to the local list; updates the time played of the server if it already exists in the list
+ virtual int AddFavoriteGame( AppId_t nAppID, uint32 nIP, uint16 nConnPort, uint16 nQueryPort, uint32 unFlags, uint32 rTime32LastPlayedOnServer ) = 0;
+
+ // removes the game server from the local storage; returns true if one was removed
+ virtual bool RemoveFavoriteGame( AppId_t nAppID, uint32 nIP, uint16 nConnPort, uint16 nQueryPort, uint32 unFlags ) = 0;
+
+ ///////
+ // Game lobby functions
+
+ // Get a list of relevant lobbies
+ // this is an asynchronous request
+ // results will be returned by LobbyMatchList_t callback & call result, with the number of lobbies found
+ // this will never return lobbies that are full
+ // to add more filter, the filter calls below need to be call before each and every RequestLobbyList() call
+ // use the CCallResult<> object in steam_api.h to match the SteamAPICall_t call result to a function in an object, e.g.
+ /*
+ class CMyLobbyListManager
+ {
+ CCallResult m_CallResultLobbyMatchList;
+ void FindLobbies()
+ {
+ // SteamMatchmaking()->AddRequestLobbyListFilter*() functions would be called here, before RequestLobbyList()
+ SteamAPICall_t hSteamAPICall = SteamMatchmaking()->RequestLobbyList();
+ m_CallResultLobbyMatchList.Set( hSteamAPICall, this, &CMyLobbyListManager::OnLobbyMatchList );
+ }
+
+ void OnLobbyMatchList( LobbyMatchList_t *pLobbyMatchList, bool bIOFailure )
+ {
+ // lobby list has be retrieved from Steam back-end, use results
+ }
+ }
+ */
+ //
+ CALL_RESULT( LobbyMatchList_t )
+ virtual SteamAPICall_t RequestLobbyList() = 0;
+ // filters for lobbies
+ // this needs to be called before RequestLobbyList() to take effect
+ // these are cleared on each call to RequestLobbyList()
+ virtual void AddRequestLobbyListStringFilter( const char *pchKeyToMatch, const char *pchValueToMatch, ELobbyComparison eComparisonType ) = 0;
+ // numerical comparison
+ virtual void AddRequestLobbyListNumericalFilter( const char *pchKeyToMatch, int nValueToMatch, ELobbyComparison eComparisonType ) = 0;
+ // returns results closest to the specified value. Multiple near filters can be added, with early filters taking precedence
+ virtual void AddRequestLobbyListNearValueFilter( const char *pchKeyToMatch, int nValueToBeCloseTo ) = 0;
+ // returns only lobbies with the specified number of slots available
+ virtual void AddRequestLobbyListFilterSlotsAvailable( int nSlotsAvailable ) = 0;
+ // sets the distance for which we should search for lobbies (based on users IP address to location map on the Steam backed)
+ virtual void AddRequestLobbyListDistanceFilter( ELobbyDistanceFilter eLobbyDistanceFilter ) = 0;
+ // sets how many results to return, the lower the count the faster it is to download the lobby results & details to the client
+ virtual void AddRequestLobbyListResultCountFilter( int cMaxResults ) = 0;
+
+ virtual void AddRequestLobbyListCompatibleMembersFilter( CSteamID steamIDLobby ) = 0;
+
+ // returns the CSteamID of a lobby, as retrieved by a RequestLobbyList call
+ // should only be called after a LobbyMatchList_t callback is received
+ // iLobby is of the range [0, LobbyMatchList_t::m_nLobbiesMatching)
+ // the returned CSteamID::IsValid() will be false if iLobby is out of range
+ virtual CSteamID GetLobbyByIndex( int iLobby ) = 0;
+
+ // Create a lobby on the Steam servers.
+ // If private, then the lobby will not be returned by any RequestLobbyList() call; the CSteamID
+ // of the lobby will need to be communicated via game channels or via InviteUserToLobby()
+ // this is an asynchronous request
+ // results will be returned by LobbyCreated_t callback and call result; lobby is joined & ready to use at this point
+ // a LobbyEnter_t callback will also be received (since the local user is joining their own lobby)
+ CALL_RESULT( LobbyCreated_t )
+ virtual SteamAPICall_t CreateLobby( ELobbyType eLobbyType, int cMaxMembers ) = 0;
+
+ // Joins an existing lobby
+ // this is an asynchronous request
+ // results will be returned by LobbyEnter_t callback & call result, check m_EChatRoomEnterResponse to see if was successful
+ // lobby metadata is available to use immediately on this call completing
+ CALL_RESULT( LobbyEnter_t )
+ virtual SteamAPICall_t JoinLobby( CSteamID steamIDLobby ) = 0;
+
+ // Leave a lobby; this will take effect immediately on the client side
+ // other users in the lobby will be notified by a LobbyChatUpdate_t callback
+ virtual void LeaveLobby( CSteamID steamIDLobby ) = 0;
+
+ // Invite another user to the lobby
+ // the target user will receive a LobbyInvite_t callback
+ // will return true if the invite is successfully sent, whether or not the target responds
+ // returns false if the local user is not connected to the Steam servers
+ // if the other user clicks the join link, a GameLobbyJoinRequested_t will be posted if the user is in-game,
+ // or if the game isn't running yet the game will be launched with the parameter +connect_lobby <64-bit lobby id>
+ virtual bool InviteUserToLobby( CSteamID steamIDLobby, CSteamID steamIDInvitee ) = 0;
+
+ // Lobby iteration, for viewing details of users in a lobby
+ // only accessible if the lobby user is a member of the specified lobby
+ // persona information for other lobby members (name, avatar, etc.) will be asynchronously received
+ // and accessible via ISteamFriends interface
+
+ // returns the number of users in the specified lobby
+ virtual int GetNumLobbyMembers( CSteamID steamIDLobby ) = 0;
+ // returns the CSteamID of a user in the lobby
+ // iMember is of range [0,GetNumLobbyMembers())
+ // note that the current user must be in a lobby to retrieve CSteamIDs of other users in that lobby
+ virtual CSteamID GetLobbyMemberByIndex( CSteamID steamIDLobby, int iMember ) = 0;
+
+ // Get data associated with this lobby
+ // takes a simple key, and returns the string associated with it
+ // "" will be returned if no value is set, or if steamIDLobby is invalid
+ virtual const char *GetLobbyData( CSteamID steamIDLobby, const char *pchKey ) = 0;
+ // Sets a key/value pair in the lobby metadata
+ // each user in the lobby will be broadcast this new value, and any new users joining will receive any existing data
+ // this can be used to set lobby names, map, etc.
+ // to reset a key, just set it to ""
+ // other users in the lobby will receive notification of the lobby data change via a LobbyDataUpdate_t callback
+ virtual bool SetLobbyData( CSteamID steamIDLobby, const char *pchKey, const char *pchValue ) = 0;
+
+ // returns the number of metadata keys set on the specified lobby
+ virtual int GetLobbyDataCount( CSteamID steamIDLobby ) = 0;
+
+ // returns a lobby metadata key/values pair by index, of range [0, GetLobbyDataCount())
+ virtual bool GetLobbyDataByIndex( CSteamID steamIDLobby, int iLobbyData, char *pchKey, int cchKeyBufferSize, char *pchValue, int cchValueBufferSize ) = 0;
+
+ // removes a metadata key from the lobby
+ virtual bool DeleteLobbyData( CSteamID steamIDLobby, const char *pchKey ) = 0;
+
+ // Gets per-user metadata for someone in this lobby
+ virtual const char *GetLobbyMemberData( CSteamID steamIDLobby, CSteamID steamIDUser, const char *pchKey ) = 0;
+ // Sets per-user metadata (for the local user implicitly)
+ virtual void SetLobbyMemberData( CSteamID steamIDLobby, const char *pchKey, const char *pchValue ) = 0;
+
+ // Broadcasts a chat message to the all the users in the lobby
+ // users in the lobby (including the local user) will receive a LobbyChatMsg_t callback
+ // returns true if the message is successfully sent
+ // pvMsgBody can be binary or text data, up to 4k
+ // if pvMsgBody is text, cubMsgBody should be strlen( text ) + 1, to include the null terminator
+ virtual bool SendLobbyChatMsg( CSteamID steamIDLobby, const void *pvMsgBody, int cubMsgBody ) = 0;
+ // Get a chat message as specified in a LobbyChatMsg_t callback
+ // iChatID is the LobbyChatMsg_t::m_iChatID value in the callback
+ // *pSteamIDUser is filled in with the CSteamID of the member
+ // *pvData is filled in with the message itself
+ // return value is the number of bytes written into the buffer
+ virtual int GetLobbyChatEntry( CSteamID steamIDLobby, int iChatID, OUT_STRUCT() CSteamID *pSteamIDUser, void *pvData, int cubData, EChatEntryType *peChatEntryType ) = 0;
+
+ // Refreshes metadata for a lobby you're not necessarily in right now
+ // you never do this for lobbies you're a member of, only if your
+ // this will send down all the metadata associated with a lobby
+ // this is an asynchronous call
+ // returns false if the local user is not connected to the Steam servers
+ // results will be returned by a LobbyDataUpdate_t callback
+ // if the specified lobby doesn't exist, LobbyDataUpdate_t::m_bSuccess will be set to false
+ virtual bool RequestLobbyData( CSteamID steamIDLobby ) = 0;
+
+ // sets the game server associated with the lobby
+ // usually at this point, the users will join the specified game server
+ // either the IP/Port or the steamID of the game server has to be valid, depending on how you want the clients to be able to connect
+ virtual void SetLobbyGameServer( CSteamID steamIDLobby, uint32 unGameServerIP, uint16 unGameServerPort, CSteamID steamIDGameServer ) = 0;
+ // returns the details of a game server set in a lobby - returns false if there is no game server set, or that lobby doesn't exist
+ virtual bool GetLobbyGameServer( CSteamID steamIDLobby, uint32 *punGameServerIP, uint16 *punGameServerPort, OUT_STRUCT() CSteamID *psteamIDGameServer ) = 0;
+
+ // set the limit on the # of users who can join the lobby
+ virtual bool SetLobbyMemberLimit( CSteamID steamIDLobby, int cMaxMembers ) = 0;
+ // returns the current limit on the # of users who can join the lobby; returns 0 if no limit is defined
+ virtual int GetLobbyMemberLimit( CSteamID steamIDLobby ) = 0;
+
+ // updates which type of lobby it is
+ // only lobbies that are k_ELobbyTypePublic or k_ELobbyTypeInvisible, and are set to joinable, will be returned by RequestLobbyList() calls
+ virtual bool SetLobbyType( CSteamID steamIDLobby, ELobbyType eLobbyType ) = 0;
+
+ // sets whether or not a lobby is joinable - defaults to true for a new lobby
+ // if set to false, no user can join, even if they are a friend or have been invited
+ virtual bool SetLobbyJoinable( CSteamID steamIDLobby, bool bLobbyJoinable ) = 0;
+
+ // returns the current lobby owner
+ // you must be a member of the lobby to access this
+ // there always one lobby owner - if the current owner leaves, another user will become the owner
+ // it is possible (bur rare) to join a lobby just as the owner is leaving, thus entering a lobby with self as the owner
+ virtual CSteamID GetLobbyOwner( CSteamID steamIDLobby ) = 0;
+
+ // changes who the lobby owner is
+ // you must be the lobby owner for this to succeed, and steamIDNewOwner must be in the lobby
+ // after completion, the local user will no longer be the owner
+ virtual bool SetLobbyOwner( CSteamID steamIDLobby, CSteamID steamIDNewOwner ) = 0;
+
+ // link two lobbies for the purposes of checking player compatibility
+ // you must be the lobby owner of both lobbies
+ virtual bool SetLinkedLobby( CSteamID steamIDLobby, CSteamID steamIDLobbyDependent ) = 0;
+
+#ifdef _PS3
+ // changes who the lobby owner is
+ // you must be the lobby owner for this to succeed, and steamIDNewOwner must be in the lobby
+ // after completion, the local user will no longer be the owner
+ virtual void CheckForPSNGameBootInvite( unsigned int iGameBootAttributes ) = 0;
+#endif
+ CALL_BACK( LobbyChatUpdate_t )
+};
+#define STEAMMATCHMAKING_INTERFACE_VERSION "SteamMatchMaking009"
+
+
+//-----------------------------------------------------------------------------
+// Callback interfaces for server list functions (see ISteamMatchmakingServers below)
+//
+// The idea here is that your game code implements objects that implement these
+// interfaces to receive callback notifications after calling asynchronous functions
+// inside the ISteamMatchmakingServers() interface below.
+//
+// This is different than normal Steam callback handling due to the potentially
+// large size of server lists.
+//-----------------------------------------------------------------------------
+
+//-----------------------------------------------------------------------------
+// Typedef for handle type you will receive when requesting server list.
+//-----------------------------------------------------------------------------
+typedef void* HServerListRequest;
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback interface for receiving responses after a server list refresh
+// or an individual server update.
+//
+// Since you get these callbacks after requesting full list refreshes you will
+// usually implement this interface inside an object like CServerBrowser. If that
+// object is getting destructed you should use ISteamMatchMakingServers()->CancelQuery()
+// to cancel any in-progress queries so you don't get a callback into the destructed
+// object and crash.
+//-----------------------------------------------------------------------------
+class ISteamMatchmakingServerListResponse
+{
+public:
+ // Server has responded ok with updated data
+ virtual void ServerResponded( HServerListRequest hRequest, int iServer ) = 0;
+
+ // Server has failed to respond
+ virtual void ServerFailedToRespond( HServerListRequest hRequest, int iServer ) = 0;
+
+ // A list refresh you had initiated is now 100% completed
+ virtual void RefreshComplete( HServerListRequest hRequest, EMatchMakingServerResponse response ) = 0;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback interface for receiving responses after pinging an individual server
+//
+// These callbacks all occur in response to querying an individual server
+// via the ISteamMatchmakingServers()->PingServer() call below. If you are
+// destructing an object that implements this interface then you should call
+// ISteamMatchmakingServers()->CancelServerQuery() passing in the handle to the query
+// which is in progress. Failure to cancel in progress queries when destructing
+// a callback handler may result in a crash when a callback later occurs.
+//-----------------------------------------------------------------------------
+class ISteamMatchmakingPingResponse
+{
+public:
+ // Server has responded successfully and has updated data
+ virtual void ServerResponded( gameserveritem_t &server ) = 0;
+
+ // Server failed to respond to the ping request
+ virtual void ServerFailedToRespond() = 0;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback interface for receiving responses after requesting details on
+// who is playing on a particular server.
+//
+// These callbacks all occur in response to querying an individual server
+// via the ISteamMatchmakingServers()->PlayerDetails() call below. If you are
+// destructing an object that implements this interface then you should call
+// ISteamMatchmakingServers()->CancelServerQuery() passing in the handle to the query
+// which is in progress. Failure to cancel in progress queries when destructing
+// a callback handler may result in a crash when a callback later occurs.
+//-----------------------------------------------------------------------------
+class ISteamMatchmakingPlayersResponse
+{
+public:
+ // Got data on a new player on the server -- you'll get this callback once per player
+ // on the server which you have requested player data on.
+ virtual void AddPlayerToList( const char *pchName, int nScore, float flTimePlayed ) = 0;
+
+ // The server failed to respond to the request for player details
+ virtual void PlayersFailedToRespond() = 0;
+
+ // The server has finished responding to the player details request
+ // (ie, you won't get anymore AddPlayerToList callbacks)
+ virtual void PlayersRefreshComplete() = 0;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback interface for receiving responses after requesting rules
+// details on a particular server.
+//
+// These callbacks all occur in response to querying an individual server
+// via the ISteamMatchmakingServers()->ServerRules() call below. If you are
+// destructing an object that implements this interface then you should call
+// ISteamMatchmakingServers()->CancelServerQuery() passing in the handle to the query
+// which is in progress. Failure to cancel in progress queries when destructing
+// a callback handler may result in a crash when a callback later occurs.
+//-----------------------------------------------------------------------------
+class ISteamMatchmakingRulesResponse
+{
+public:
+ // Got data on a rule on the server -- you'll get one of these per rule defined on
+ // the server you are querying
+ virtual void RulesResponded( const char *pchRule, const char *pchValue ) = 0;
+
+ // The server failed to respond to the request for rule details
+ virtual void RulesFailedToRespond() = 0;
+
+ // The server has finished responding to the rule details request
+ // (ie, you won't get anymore RulesResponded callbacks)
+ virtual void RulesRefreshComplete() = 0;
+};
+
+
+//-----------------------------------------------------------------------------
+// Typedef for handle type you will receive when querying details on an individual server.
+//-----------------------------------------------------------------------------
+typedef int HServerQuery;
+const int HSERVERQUERY_INVALID = 0xffffffff;
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for match making services for clients to get to game lists and details
+//-----------------------------------------------------------------------------
+class ISteamMatchmakingServers
+{
+public:
+ // Request a new list of servers of a particular type. These calls each correspond to one of the EMatchMakingType values.
+ // Each call allocates a new asynchronous request object.
+ // Request object must be released by calling ReleaseRequest( hServerListRequest )
+ virtual HServerListRequest RequestInternetServerList( AppId_t iApp, ARRAY_COUNT(nFilters) MatchMakingKeyValuePair_t **ppchFilters, uint32 nFilters, ISteamMatchmakingServerListResponse *pRequestServersResponse ) = 0;
+ virtual HServerListRequest RequestLANServerList( AppId_t iApp, ISteamMatchmakingServerListResponse *pRequestServersResponse ) = 0;
+ virtual HServerListRequest RequestFriendsServerList( AppId_t iApp, ARRAY_COUNT(nFilters) MatchMakingKeyValuePair_t **ppchFilters, uint32 nFilters, ISteamMatchmakingServerListResponse *pRequestServersResponse ) = 0;
+ virtual HServerListRequest RequestFavoritesServerList( AppId_t iApp, ARRAY_COUNT(nFilters) MatchMakingKeyValuePair_t **ppchFilters, uint32 nFilters, ISteamMatchmakingServerListResponse *pRequestServersResponse ) = 0;
+ virtual HServerListRequest RequestHistoryServerList( AppId_t iApp, ARRAY_COUNT(nFilters) MatchMakingKeyValuePair_t **ppchFilters, uint32 nFilters, ISteamMatchmakingServerListResponse *pRequestServersResponse ) = 0;
+ virtual HServerListRequest RequestSpectatorServerList( AppId_t iApp, ARRAY_COUNT(nFilters) MatchMakingKeyValuePair_t **ppchFilters, uint32 nFilters, ISteamMatchmakingServerListResponse *pRequestServersResponse ) = 0;
+
+ // Releases the asynchronous request object and cancels any pending query on it if there's a pending query in progress.
+ // RefreshComplete callback is not posted when request is released.
+ virtual void ReleaseRequest( HServerListRequest hServerListRequest ) = 0;
+
+ /* the filter operation codes that go in the key part of MatchMakingKeyValuePair_t should be one of these:
+
+ "map"
+ - Server passes the filter if the server is playing the specified map.
+ "gamedataand"
+ - Server passes the filter if the server's game data (ISteamGameServer::SetGameData) contains all of the
+ specified strings. The value field is a comma-delimited list of strings to match.
+ "gamedataor"
+ - Server passes the filter if the server's game data (ISteamGameServer::SetGameData) contains at least one of the
+ specified strings. The value field is a comma-delimited list of strings to match.
+ "gamedatanor"
+ - Server passes the filter if the server's game data (ISteamGameServer::SetGameData) does not contain any
+ of the specified strings. The value field is a comma-delimited list of strings to check.
+ "gametagsand"
+ - Server passes the filter if the server's game tags (ISteamGameServer::SetGameTags) contains all
+ of the specified strings. The value field is a comma-delimited list of strings to check.
+ "gametagsnor"
+ - Server passes the filter if the server's game tags (ISteamGameServer::SetGameTags) does not contain any
+ of the specified strings. The value field is a comma-delimited list of strings to check.
+ "and" (x1 && x2 && ... && xn)
+ "or" (x1 || x2 || ... || xn)
+ "nand" !(x1 && x2 && ... && xn)
+ "nor" !(x1 || x2 || ... || xn)
+ - Performs Boolean operation on the following filters. The operand to this filter specifies
+ the "size" of the Boolean inputs to the operation, in Key/value pairs. (The keyvalue
+ pairs must immediately follow, i.e. this is a prefix logical operator notation.)
+ In the simplest case where Boolean expressions are not nested, this is simply
+ the number of operands.
+
+ For example, to match servers on a particular map or with a particular tag, would would
+ use these filters.
+
+ ( server.map == "cp_dustbowl" || server.gametags.contains("payload") )
+ "or", "2"
+ "map", "cp_dustbowl"
+ "gametagsand", "payload"
+
+ If logical inputs are nested, then the operand specifies the size of the entire
+ "length" of its operands, not the number of immediate children.
+
+ ( server.map == "cp_dustbowl" || ( server.gametags.contains("payload") && !server.gametags.contains("payloadrace") ) )
+ "or", "4"
+ "map", "cp_dustbowl"
+ "and", "2"
+ "gametagsand", "payload"
+ "gametagsnor", "payloadrace"
+
+ Unary NOT can be achieved using either "nand" or "nor" with a single operand.
+
+ "addr"
+ - Server passes the filter if the server's query address matches the specified IP or IP:port.
+ "gameaddr"
+ - Server passes the filter if the server's game address matches the specified IP or IP:port.
+
+ The following filter operations ignore the "value" part of MatchMakingKeyValuePair_t
+
+ "dedicated"
+ - Server passes the filter if it passed true to SetDedicatedServer.
+ "secure"
+ - Server passes the filter if the server is VAC-enabled.
+ "notfull"
+ - Server passes the filter if the player count is less than the reported max player count.
+ "hasplayers"
+ - Server passes the filter if the player count is greater than zero.
+ "noplayers"
+ - Server passes the filter if it doesn't have any players.
+ "linux"
+ - Server passes the filter if it's a linux server
+ */
+
+ // Get details on a given server in the list, you can get the valid range of index
+ // values by calling GetServerCount(). You will also receive index values in
+ // ISteamMatchmakingServerListResponse::ServerResponded() callbacks
+ virtual gameserveritem_t *GetServerDetails( HServerListRequest hRequest, int iServer ) = 0;
+
+ // Cancel an request which is operation on the given list type. You should call this to cancel
+ // any in-progress requests before destructing a callback object that may have been passed
+ // to one of the above list request calls. Not doing so may result in a crash when a callback
+ // occurs on the destructed object.
+ // Canceling a query does not release the allocated request handle.
+ // The request handle must be released using ReleaseRequest( hRequest )
+ virtual void CancelQuery( HServerListRequest hRequest ) = 0;
+
+ // Ping every server in your list again but don't update the list of servers
+ // Query callback installed when the server list was requested will be used
+ // again to post notifications and RefreshComplete, so the callback must remain
+ // valid until another RefreshComplete is called on it or the request
+ // is released with ReleaseRequest( hRequest )
+ virtual void RefreshQuery( HServerListRequest hRequest ) = 0;
+
+ // Returns true if the list is currently refreshing its server list
+ virtual bool IsRefreshing( HServerListRequest hRequest ) = 0;
+
+ // How many servers in the given list, GetServerDetails above takes 0... GetServerCount() - 1
+ virtual int GetServerCount( HServerListRequest hRequest ) = 0;
+
+ // Refresh a single server inside of a query (rather than all the servers )
+ virtual void RefreshServer( HServerListRequest hRequest, int iServer ) = 0;
+
+
+ //-----------------------------------------------------------------------------
+ // Queries to individual servers directly via IP/Port
+ //-----------------------------------------------------------------------------
+
+ // Request updated ping time and other details from a single server
+ virtual HServerQuery PingServer( uint32 unIP, uint16 usPort, ISteamMatchmakingPingResponse *pRequestServersResponse ) = 0;
+
+ // Request the list of players currently playing on a server
+ virtual HServerQuery PlayerDetails( uint32 unIP, uint16 usPort, ISteamMatchmakingPlayersResponse *pRequestServersResponse ) = 0;
+
+ // Request the list of rules that the server is running (See ISteamGameServer::SetKeyValue() to set the rules server side)
+ virtual HServerQuery ServerRules( uint32 unIP, uint16 usPort, ISteamMatchmakingRulesResponse *pRequestServersResponse ) = 0;
+
+ // Cancel an outstanding Ping/Players/Rules query from above. You should call this to cancel
+ // any in-progress requests before destructing a callback object that may have been passed
+ // to one of the above calls to avoid crashing when callbacks occur.
+ virtual void CancelServerQuery( HServerQuery hServerQuery ) = 0;
+};
+#define STEAMMATCHMAKINGSERVERS_INTERFACE_VERSION "SteamMatchMakingServers002"
+
+// game server flags
+const uint32 k_unFavoriteFlagNone = 0x00;
+const uint32 k_unFavoriteFlagFavorite = 0x01; // this game favorite entry is for the favorites list
+const uint32 k_unFavoriteFlagHistory = 0x02; // this game favorite entry is for the history list
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Used in ChatInfo messages - fields specific to a chat member - must fit in a uint32
+//-----------------------------------------------------------------------------
+enum EChatMemberStateChange
+{
+ // Specific to joining / leaving the chatroom
+ k_EChatMemberStateChangeEntered = 0x0001, // This user has joined or is joining the chat room
+ k_EChatMemberStateChangeLeft = 0x0002, // This user has left or is leaving the chat room
+ k_EChatMemberStateChangeDisconnected = 0x0004, // User disconnected without leaving the chat first
+ k_EChatMemberStateChangeKicked = 0x0008, // User kicked
+ k_EChatMemberStateChangeBanned = 0x0010, // User kicked and banned
+};
+
+// returns true of the flags indicate that a user has been removed from the chat
+#define BChatMemberStateChangeRemoved( rgfChatMemberStateChangeFlags ) ( rgfChatMemberStateChangeFlags & ( k_EChatMemberStateChangeDisconnected | k_EChatMemberStateChangeLeft | k_EChatMemberStateChangeKicked | k_EChatMemberStateChangeBanned ) )
+
+
+//-----------------------------------------------------------------------------
+// Callbacks for ISteamMatchmaking (which go through the regular Steam callback registration system)
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: a server was added/removed from the favorites list, you should refresh now
+//-----------------------------------------------------------------------------
+struct FavoritesListChanged_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 2 };
+ uint32 m_nIP; // an IP of 0 means reload the whole list, any other value means just one server
+ uint32 m_nQueryPort;
+ uint32 m_nConnPort;
+ uint32 m_nAppID;
+ uint32 m_nFlags;
+ bool m_bAdd; // true if this is adding the entry, otherwise it is a remove
+ AccountID_t m_unAccountId;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Someone has invited you to join a Lobby
+// normally you don't need to do anything with this, since
+// the Steam UI will also display a ' has invited you to the lobby, join?' dialog
+//
+// if the user outside a game chooses to join, your game will be launched with the parameter "+connect_lobby <64-bit lobby id>",
+// or with the callback GameLobbyJoinRequested_t if they're already in-game
+//-----------------------------------------------------------------------------
+struct LobbyInvite_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 3 };
+
+ uint64 m_ulSteamIDUser; // Steam ID of the person making the invite
+ uint64 m_ulSteamIDLobby; // Steam ID of the Lobby
+ uint64 m_ulGameID; // GameID of the Lobby
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Sent on entering a lobby, or on failing to enter
+// m_EChatRoomEnterResponse will be set to k_EChatRoomEnterResponseSuccess on success,
+// or a higher value on failure (see enum EChatRoomEnterResponse)
+//-----------------------------------------------------------------------------
+struct LobbyEnter_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 4 };
+
+ uint64 m_ulSteamIDLobby; // SteamID of the Lobby you have entered
+ uint32 m_rgfChatPermissions; // Permissions of the current user
+ bool m_bLocked; // If true, then only invited users may join
+ uint32 m_EChatRoomEnterResponse; // EChatRoomEnterResponse
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The lobby metadata has changed
+// if m_ulSteamIDMember is the steamID of a lobby member, use GetLobbyMemberData() to access per-user details
+// if m_ulSteamIDMember == m_ulSteamIDLobby, use GetLobbyData() to access lobby metadata
+//-----------------------------------------------------------------------------
+struct LobbyDataUpdate_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 5 };
+
+ uint64 m_ulSteamIDLobby; // steamID of the Lobby
+ uint64 m_ulSteamIDMember; // steamID of the member whose data changed, or the room itself
+ uint8 m_bSuccess; // true if we lobby data was successfully changed;
+ // will only be false if RequestLobbyData() was called on a lobby that no longer exists
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The lobby chat room state has changed
+// this is usually sent when a user has joined or left the lobby
+//-----------------------------------------------------------------------------
+struct LobbyChatUpdate_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 6 };
+
+ uint64 m_ulSteamIDLobby; // Lobby ID
+ uint64 m_ulSteamIDUserChanged; // user who's status in the lobby just changed - can be recipient
+ uint64 m_ulSteamIDMakingChange; // Chat member who made the change (different from SteamIDUserChange if kicking, muting, etc.)
+ // for example, if one user kicks another from the lobby, this will be set to the id of the user who initiated the kick
+ uint32 m_rgfChatMemberStateChange; // bitfield of EChatMemberStateChange values
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: A chat message for this lobby has been sent
+// use GetLobbyChatEntry( m_iChatID ) to retrieve the contents of this message
+//-----------------------------------------------------------------------------
+struct LobbyChatMsg_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 7 };
+
+ uint64 m_ulSteamIDLobby; // the lobby id this is in
+ uint64 m_ulSteamIDUser; // steamID of the user who has sent this message
+ uint8 m_eChatEntryType; // type of message
+ uint32 m_iChatID; // index of the chat entry to lookup
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: A game created a game for all the members of the lobby to join,
+// as triggered by a SetLobbyGameServer()
+// it's up to the individual clients to take action on this; the usual
+// game behavior is to leave the lobby and connect to the specified game server
+//-----------------------------------------------------------------------------
+struct LobbyGameCreated_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 9 };
+
+ uint64 m_ulSteamIDLobby; // the lobby we were in
+ uint64 m_ulSteamIDGameServer; // the new game server that has been created or found for the lobby members
+ uint32 m_unIP; // IP & Port of the game server (if any)
+ uint16 m_usPort;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Number of matching lobbies found
+// iterate the returned lobbies with GetLobbyByIndex(), from values 0 to m_nLobbiesMatching-1
+//-----------------------------------------------------------------------------
+struct LobbyMatchList_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 10 };
+ uint32 m_nLobbiesMatching; // Number of lobbies that matched search criteria and we have SteamIDs for
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: posted if a user is forcefully removed from a lobby
+// can occur if a user loses connection to Steam
+//-----------------------------------------------------------------------------
+struct LobbyKicked_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 12 };
+ uint64 m_ulSteamIDLobby; // Lobby
+ uint64 m_ulSteamIDAdmin; // User who kicked you - possibly the ID of the lobby itself
+ uint8 m_bKickedDueToDisconnect; // true if you were kicked from the lobby due to the user losing connection to Steam (currently always true)
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Result of our request to create a Lobby
+// m_eResult == k_EResultOK on success
+// at this point, the lobby has been joined and is ready for use
+// a LobbyEnter_t callback will also be received (since the local user is joining their own lobby)
+//-----------------------------------------------------------------------------
+struct LobbyCreated_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 13 };
+
+ EResult m_eResult; // k_EResultOK - the lobby was successfully created
+ // k_EResultNoConnection - your Steam client doesn't have a connection to the back-end
+ // k_EResultTimeout - you the message to the Steam servers, but it didn't respond
+ // k_EResultFail - the server responded, but with an unknown internal error
+ // k_EResultAccessDenied - your game isn't set to allow lobbies, or your client does haven't rights to play the game
+ // k_EResultLimitExceeded - your game client has created too many lobbies
+
+ uint64 m_ulSteamIDLobby; // chat room, zero if failed
+};
+
+// used by now obsolete RequestFriendsLobbiesResponse_t
+// enum { k_iCallback = k_iSteamMatchmakingCallbacks + 14 };
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Result of CheckForPSNGameBootInvite
+// m_eResult == k_EResultOK on success
+// at this point, the local user may not have finishing joining this lobby;
+// game code should wait until the subsequent LobbyEnter_t callback is received
+//-----------------------------------------------------------------------------
+struct PSNGameBootInviteResult_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 15 };
+
+ bool m_bGameBootInviteExists;
+ CSteamID m_steamIDLobby; // Should be valid if m_bGameBootInviteExists == true
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Result of our request to create a Lobby
+// m_eResult == k_EResultOK on success
+// at this point, the lobby has been joined and is ready for use
+// a LobbyEnter_t callback will also be received (since the local user is joining their own lobby)
+//-----------------------------------------------------------------------------
+struct FavoritesListAccountsUpdated_t
+{
+ enum { k_iCallback = k_iSteamMatchmakingCallbacks + 16 };
+
+ EResult m_eResult;
+};
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMMATCHMAKING
diff --git a/dep/steam_api/isteammusic.h b/dep/steam_api/isteammusic.h
new file mode 100644
index 0000000..779a4c2
--- /dev/null
+++ b/dep/steam_api/isteammusic.h
@@ -0,0 +1,67 @@
+//============ Copyright (c) Valve Corporation, All rights reserved. ============
+
+#ifndef ISTEAMMUSIC_H
+#define ISTEAMMUSIC_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+enum AudioPlayback_Status
+{
+ AudioPlayback_Undefined = 0,
+ AudioPlayback_Playing = 1,
+ AudioPlayback_Paused = 2,
+ AudioPlayback_Idle = 3
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions to control music playback in the steam client
+//-----------------------------------------------------------------------------
+class ISteamMusic
+{
+public:
+ virtual bool BIsEnabled() = 0;
+ virtual bool BIsPlaying() = 0;
+
+ virtual AudioPlayback_Status GetPlaybackStatus() = 0;
+
+ virtual void Play() = 0;
+ virtual void Pause() = 0;
+ virtual void PlayPrevious() = 0;
+ virtual void PlayNext() = 0;
+
+ // volume is between 0.0 and 1.0
+ virtual void SetVolume( float flVolume ) = 0;
+ virtual float GetVolume() = 0;
+
+};
+
+#define STEAMMUSIC_INTERFACE_VERSION "STEAMMUSIC_INTERFACE_VERSION001"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+DEFINE_CALLBACK( PlaybackStatusHasChanged_t, k_iSteamMusicCallbacks + 1 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( VolumeHasChanged_t, k_iSteamMusicCallbacks + 2 )
+ CALLBACK_MEMBER( 0, float, m_flNewVolume )
+END_DEFINE_CALLBACK_1()
+
+#pragma pack( pop )
+
+
+#endif // #define ISTEAMMUSIC_H
diff --git a/dep/steam_api/isteammusicremote.h b/dep/steam_api/isteammusicremote.h
new file mode 100644
index 0000000..ea29a7d
--- /dev/null
+++ b/dep/steam_api/isteammusicremote.h
@@ -0,0 +1,129 @@
+//============ Copyright (c) Valve Corporation, All rights reserved. ============
+
+#ifndef ISTEAMMUSICREMOTE_H
+#define ISTEAMMUSICREMOTE_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+#include "isteammusic.h"
+
+#define k_SteamMusicNameMaxLength 255
+#define k_SteamMusicPNGMaxLength 65535
+
+
+class ISteamMusicRemote
+{
+public:
+ // Service Definition
+ virtual bool RegisterSteamMusicRemote( const char *pchName ) = 0;
+ virtual bool DeregisterSteamMusicRemote() = 0;
+ virtual bool BIsCurrentMusicRemote() = 0;
+ virtual bool BActivationSuccess( bool bValue ) = 0;
+
+ virtual bool SetDisplayName( const char *pchDisplayName ) = 0;
+ virtual bool SetPNGIcon_64x64( void *pvBuffer, uint32 cbBufferLength ) = 0;
+
+ // Abilities for the user interface
+ virtual bool EnablePlayPrevious(bool bValue) = 0;
+ virtual bool EnablePlayNext( bool bValue ) = 0;
+ virtual bool EnableShuffled( bool bValue ) = 0;
+ virtual bool EnableLooped( bool bValue ) = 0;
+ virtual bool EnableQueue( bool bValue ) = 0;
+ virtual bool EnablePlaylists( bool bValue ) = 0;
+
+ // Status
+ virtual bool UpdatePlaybackStatus( AudioPlayback_Status nStatus ) = 0;
+ virtual bool UpdateShuffled( bool bValue ) = 0;
+ virtual bool UpdateLooped( bool bValue ) = 0;
+ virtual bool UpdateVolume( float flValue ) = 0; // volume is between 0.0 and 1.0
+
+ // Current Entry
+ virtual bool CurrentEntryWillChange() = 0;
+ virtual bool CurrentEntryIsAvailable( bool bAvailable ) = 0;
+ virtual bool UpdateCurrentEntryText( const char *pchText ) = 0;
+ virtual bool UpdateCurrentEntryElapsedSeconds( int nValue ) = 0;
+ virtual bool UpdateCurrentEntryCoverArt( void *pvBuffer, uint32 cbBufferLength ) = 0;
+ virtual bool CurrentEntryDidChange() = 0;
+
+ // Queue
+ virtual bool QueueWillChange() = 0;
+ virtual bool ResetQueueEntries() = 0;
+ virtual bool SetQueueEntry( int nID, int nPosition, const char *pchEntryText ) = 0;
+ virtual bool SetCurrentQueueEntry( int nID ) = 0;
+ virtual bool QueueDidChange() = 0;
+
+ // Playlist
+ virtual bool PlaylistWillChange() = 0;
+ virtual bool ResetPlaylistEntries() = 0;
+ virtual bool SetPlaylistEntry( int nID, int nPosition, const char *pchEntryText ) = 0;
+ virtual bool SetCurrentPlaylistEntry( int nID ) = 0;
+ virtual bool PlaylistDidChange() = 0;
+};
+
+#define STEAMMUSICREMOTE_INTERFACE_VERSION "STEAMMUSICREMOTE_INTERFACE_VERSION001"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+DEFINE_CALLBACK( MusicPlayerRemoteWillActivate_t, k_iSteamMusicRemoteCallbacks + 1)
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerRemoteWillDeactivate_t, k_iSteamMusicRemoteCallbacks + 2 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerRemoteToFront_t, k_iSteamMusicRemoteCallbacks + 3 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerWillQuit_t, k_iSteamMusicRemoteCallbacks + 4 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerWantsPlay_t, k_iSteamMusicRemoteCallbacks + 5 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerWantsPause_t, k_iSteamMusicRemoteCallbacks + 6 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerWantsPlayPrevious_t, k_iSteamMusicRemoteCallbacks + 7 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerWantsPlayNext_t, k_iSteamMusicRemoteCallbacks + 8 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( MusicPlayerWantsShuffled_t, k_iSteamMusicRemoteCallbacks + 9 )
+ CALLBACK_MEMBER( 0, bool, m_bShuffled )
+END_DEFINE_CALLBACK_1()
+
+DEFINE_CALLBACK( MusicPlayerWantsLooped_t, k_iSteamMusicRemoteCallbacks + 10 )
+ CALLBACK_MEMBER(0, bool, m_bLooped )
+END_DEFINE_CALLBACK_1()
+
+DEFINE_CALLBACK( MusicPlayerWantsVolume_t, k_iSteamMusicCallbacks + 11 )
+ CALLBACK_MEMBER(0, float, m_flNewVolume)
+END_DEFINE_CALLBACK_1()
+
+DEFINE_CALLBACK( MusicPlayerSelectsQueueEntry_t, k_iSteamMusicCallbacks + 12 )
+ CALLBACK_MEMBER(0, int, nID )
+END_DEFINE_CALLBACK_1()
+
+DEFINE_CALLBACK( MusicPlayerSelectsPlaylistEntry_t, k_iSteamMusicCallbacks + 13 )
+ CALLBACK_MEMBER(0, int, nID )
+END_DEFINE_CALLBACK_1()
+
+DEFINE_CALLBACK( MusicPlayerWantsPlayingRepeatStatus_t, k_iSteamMusicRemoteCallbacks + 14 )
+ CALLBACK_MEMBER(0, int, m_nPlayingRepeatStatus )
+END_DEFINE_CALLBACK_1()
+
+#pragma pack( pop )
+
+
+
+#endif // #define ISTEAMMUSICREMOTE_H
diff --git a/dep/steam_api/isteamnetworking.h b/dep/steam_api/isteamnetworking.h
new file mode 100644
index 0000000..8f70819
--- /dev/null
+++ b/dep/steam_api/isteamnetworking.h
@@ -0,0 +1,306 @@
+//====== Copyright © 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to steam managing network connections between game clients & servers
+//
+//=============================================================================
+
+#ifndef ISTEAMNETWORKING
+#define ISTEAMNETWORKING
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "steamtypes.h"
+#include "steamclientpublic.h"
+
+
+// list of possible errors returned by SendP2PPacket() API
+// these will be posted in the P2PSessionConnectFail_t callback
+enum EP2PSessionError
+{
+ k_EP2PSessionErrorNone = 0,
+ k_EP2PSessionErrorNotRunningApp = 1, // target is not running the same game
+ k_EP2PSessionErrorNoRightsToApp = 2, // local user doesn't own the app that is running
+ k_EP2PSessionErrorDestinationNotLoggedIn = 3, // target user isn't connected to Steam
+ k_EP2PSessionErrorTimeout = 4, // target isn't responding, perhaps not calling AcceptP2PSessionWithUser()
+ // corporate firewalls can also block this (NAT traversal is not firewall traversal)
+ // make sure that UDP ports 3478, 4379, and 4380 are open in an outbound direction
+ k_EP2PSessionErrorMax = 5
+};
+
+// SendP2PPacket() send types
+// Typically k_EP2PSendUnreliable is what you want for UDP-like packets, k_EP2PSendReliable for TCP-like packets
+enum EP2PSend
+{
+ // Basic UDP send. Packets can't be bigger than 1200 bytes (your typical MTU size). Can be lost, or arrive out of order (rare).
+ // The sending API does have some knowledge of the underlying connection, so if there is no NAT-traversal accomplished or
+ // there is a recognized adjustment happening on the connection, the packet will be batched until the connection is open again.
+ k_EP2PSendUnreliable = 0,
+
+ // As above, but if the underlying p2p connection isn't yet established the packet will just be thrown away. Using this on the first
+ // packet sent to a remote host almost guarantees the packet will be dropped.
+ // This is only really useful for kinds of data that should never buffer up, i.e. voice payload packets
+ k_EP2PSendUnreliableNoDelay = 1,
+
+ // Reliable message send. Can send up to 1MB of data in a single message.
+ // Does fragmentation/re-assembly of messages under the hood, as well as a sliding window for efficient sends of large chunks of data.
+ k_EP2PSendReliable = 2,
+
+ // As above, but applies the Nagle algorithm to the send - sends will accumulate
+ // until the current MTU size (typically ~1200 bytes, but can change) or ~200ms has passed (Nagle algorithm).
+ // Useful if you want to send a set of smaller messages but have the coalesced into a single packet
+ // Since the reliable stream is all ordered, you can do several small message sends with k_EP2PSendReliableWithBuffering and then
+ // do a normal k_EP2PSendReliable to force all the buffered data to be sent.
+ k_EP2PSendReliableWithBuffering = 3,
+
+};
+
+
+// connection state to a specified user, returned by GetP2PSessionState()
+// this is under-the-hood info about what's going on with a SendP2PPacket(), shouldn't be needed except for debuggin
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+struct P2PSessionState_t
+{
+ uint8 m_bConnectionActive; // true if we've got an active open connection
+ uint8 m_bConnecting; // true if we're currently trying to establish a connection
+ uint8 m_eP2PSessionError; // last error recorded (see enum above)
+ uint8 m_bUsingRelay; // true if it's going through a relay server (TURN)
+ int32 m_nBytesQueuedForSend;
+ int32 m_nPacketsQueuedForSend;
+ uint32 m_nRemoteIP; // potential IP:Port of remote host. Could be TURN server.
+ uint16 m_nRemotePort; // Only exists for compatibility with older authentication api's
+};
+#pragma pack( pop )
+
+
+// handle to a socket
+typedef uint32 SNetSocket_t; // CreateP2PConnectionSocket()
+typedef uint32 SNetListenSocket_t; // CreateListenSocket()
+
+// connection progress indicators, used by CreateP2PConnectionSocket()
+enum ESNetSocketState
+{
+ k_ESNetSocketStateInvalid = 0,
+
+ // communication is valid
+ k_ESNetSocketStateConnected = 1,
+
+ // states while establishing a connection
+ k_ESNetSocketStateInitiated = 10, // the connection state machine has started
+
+ // p2p connections
+ k_ESNetSocketStateLocalCandidatesFound = 11, // we've found our local IP info
+ k_ESNetSocketStateReceivedRemoteCandidates = 12,// we've received information from the remote machine, via the Steam back-end, about their IP info
+
+ // direct connections
+ k_ESNetSocketStateChallengeHandshake = 15, // we've received a challenge packet from the server
+
+ // failure states
+ k_ESNetSocketStateDisconnecting = 21, // the API shut it down, and we're in the process of telling the other end
+ k_ESNetSocketStateLocalDisconnect = 22, // the API shut it down, and we've completed shutdown
+ k_ESNetSocketStateTimeoutDuringConnect = 23, // we timed out while trying to creating the connection
+ k_ESNetSocketStateRemoteEndDisconnected = 24, // the remote end has disconnected from us
+ k_ESNetSocketStateConnectionBroken = 25, // connection has been broken; either the other end has disappeared or our local network connection has broke
+
+};
+
+// describes how the socket is currently connected
+enum ESNetSocketConnectionType
+{
+ k_ESNetSocketConnectionTypeNotConnected = 0,
+ k_ESNetSocketConnectionTypeUDP = 1,
+ k_ESNetSocketConnectionTypeUDPRelay = 2,
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for making connections and sending data between clients,
+// traversing NAT's where possible
+//-----------------------------------------------------------------------------
+class ISteamNetworking
+{
+public:
+ ////////////////////////////////////////////////////////////////////////////////////////////
+ // Session-less connection functions
+ // automatically establishes NAT-traversing or Relay server connections
+
+ // Sends a P2P packet to the specified user
+ // UDP-like, unreliable and a max packet size of 1200 bytes
+ // the first packet send may be delayed as the NAT-traversal code runs
+ // if we can't get through to the user, an error will be posted via the callback P2PSessionConnectFail_t
+ // see EP2PSend enum above for the descriptions of the different ways of sending packets
+ //
+ // nChannel is a routing number you can use to help route message to different systems - you'll have to call ReadP2PPacket()
+ // with the same channel number in order to retrieve the data on the other end
+ // using different channels to talk to the same user will still use the same underlying p2p connection, saving on resources
+ virtual bool SendP2PPacket( CSteamID steamIDRemote, const void *pubData, uint32 cubData, EP2PSend eP2PSendType, int nChannel = 0 ) = 0;
+
+ // returns true if any data is available for read, and the amount of data that will need to be read
+ virtual bool IsP2PPacketAvailable( uint32 *pcubMsgSize, int nChannel = 0 ) = 0;
+
+ // reads in a packet that has been sent from another user via SendP2PPacket()
+ // returns the size of the message and the steamID of the user who sent it in the last two parameters
+ // if the buffer passed in is too small, the message will be truncated
+ // this call is not blocking, and will return false if no data is available
+ virtual bool ReadP2PPacket( void *pubDest, uint32 cubDest, uint32 *pcubMsgSize, CSteamID *psteamIDRemote, int nChannel = 0 ) = 0;
+
+ // AcceptP2PSessionWithUser() should only be called in response to a P2PSessionRequest_t callback
+ // P2PSessionRequest_t will be posted if another user tries to send you a packet that you haven't talked to yet
+ // if you don't want to talk to the user, just ignore the request
+ // if the user continues to send you packets, another P2PSessionRequest_t will be posted periodically
+ // this may be called multiple times for a single user
+ // (if you've called SendP2PPacket() on the other user, this implicitly accepts the session request)
+ virtual bool AcceptP2PSessionWithUser( CSteamID steamIDRemote ) = 0;
+
+ // call CloseP2PSessionWithUser() when you're done talking to a user, will free up resources under-the-hood
+ // if the remote user tries to send data to you again, another P2PSessionRequest_t callback will be posted
+ virtual bool CloseP2PSessionWithUser( CSteamID steamIDRemote ) = 0;
+
+ // call CloseP2PChannelWithUser() when you're done talking to a user on a specific channel. Once all channels
+ // open channels to a user have been closed, the open session to the user will be closed and new data from this
+ // user will trigger a P2PSessionRequest_t callback
+ virtual bool CloseP2PChannelWithUser( CSteamID steamIDRemote, int nChannel ) = 0;
+
+ // fills out P2PSessionState_t structure with details about the underlying connection to the user
+ // should only needed for debugging purposes
+ // returns false if no connection exists to the specified user
+ virtual bool GetP2PSessionState( CSteamID steamIDRemote, P2PSessionState_t *pConnectionState ) = 0;
+
+ // Allow P2P connections to fall back to being relayed through the Steam servers if a direct connection
+ // or NAT-traversal cannot be established. Only applies to connections created after setting this value,
+ // or to existing connections that need to automatically reconnect after this value is set.
+ //
+ // P2P packet relay is allowed by default
+ virtual bool AllowP2PPacketRelay( bool bAllow ) = 0;
+
+
+ ////////////////////////////////////////////////////////////////////////////////////////////
+ // LISTEN / CONNECT style interface functions
+ //
+ // This is an older set of functions designed around the Berkeley TCP sockets model
+ // it's preferential that you use the above P2P functions, they're more robust
+ // and these older functions will be removed eventually
+ //
+ ////////////////////////////////////////////////////////////////////////////////////////////
+
+
+ // creates a socket and listens others to connect
+ // will trigger a SocketStatusCallback_t callback on another client connecting
+ // nVirtualP2PPort is the unique ID that the client will connect to, in case you have multiple ports
+ // this can usually just be 0 unless you want multiple sets of connections
+ // unIP is the local IP address to bind to
+ // pass in 0 if you just want the default local IP
+ // unPort is the port to use
+ // pass in 0 if you don't want users to be able to connect via IP/Port, but expect to be always peer-to-peer connections only
+ virtual SNetListenSocket_t CreateListenSocket( int nVirtualP2PPort, uint32 nIP, uint16 nPort, bool bAllowUseOfPacketRelay ) = 0;
+
+ // creates a socket and begin connection to a remote destination
+ // can connect via a known steamID (client or game server), or directly to an IP
+ // on success will trigger a SocketStatusCallback_t callback
+ // on failure or timeout will trigger a SocketStatusCallback_t callback with a failure code in m_eSNetSocketState
+ virtual SNetSocket_t CreateP2PConnectionSocket( CSteamID steamIDTarget, int nVirtualPort, int nTimeoutSec, bool bAllowUseOfPacketRelay ) = 0;
+ virtual SNetSocket_t CreateConnectionSocket( uint32 nIP, uint16 nPort, int nTimeoutSec ) = 0;
+
+ // disconnects the connection to the socket, if any, and invalidates the handle
+ // any unread data on the socket will be thrown away
+ // if bNotifyRemoteEnd is set, socket will not be completely destroyed until the remote end acknowledges the disconnect
+ virtual bool DestroySocket( SNetSocket_t hSocket, bool bNotifyRemoteEnd ) = 0;
+ // destroying a listen socket will automatically kill all the regular sockets generated from it
+ virtual bool DestroyListenSocket( SNetListenSocket_t hSocket, bool bNotifyRemoteEnd ) = 0;
+
+ // sending data
+ // must be a handle to a connected socket
+ // data is all sent via UDP, and thus send sizes are limited to 1200 bytes; after this, many routers will start dropping packets
+ // use the reliable flag with caution; although the resend rate is pretty aggressive,
+ // it can still cause stalls in receiving data (like TCP)
+ virtual bool SendDataOnSocket( SNetSocket_t hSocket, void *pubData, uint32 cubData, bool bReliable ) = 0;
+
+ // receiving data
+ // returns false if there is no data remaining
+ // fills out *pcubMsgSize with the size of the next message, in bytes
+ virtual bool IsDataAvailableOnSocket( SNetSocket_t hSocket, uint32 *pcubMsgSize ) = 0;
+
+ // fills in pubDest with the contents of the message
+ // messages are always complete, of the same size as was sent (i.e. packetized, not streaming)
+ // if *pcubMsgSize < cubDest, only partial data is written
+ // returns false if no data is available
+ virtual bool RetrieveDataFromSocket( SNetSocket_t hSocket, void *pubDest, uint32 cubDest, uint32 *pcubMsgSize ) = 0;
+
+ // checks for data from any socket that has been connected off this listen socket
+ // returns false if there is no data remaining
+ // fills out *pcubMsgSize with the size of the next message, in bytes
+ // fills out *phSocket with the socket that data is available on
+ virtual bool IsDataAvailable( SNetListenSocket_t hListenSocket, uint32 *pcubMsgSize, SNetSocket_t *phSocket ) = 0;
+
+ // retrieves data from any socket that has been connected off this listen socket
+ // fills in pubDest with the contents of the message
+ // messages are always complete, of the same size as was sent (i.e. packetized, not streaming)
+ // if *pcubMsgSize < cubDest, only partial data is written
+ // returns false if no data is available
+ // fills out *phSocket with the socket that data is available on
+ virtual bool RetrieveData( SNetListenSocket_t hListenSocket, void *pubDest, uint32 cubDest, uint32 *pcubMsgSize, SNetSocket_t *phSocket ) = 0;
+
+ // returns information about the specified socket, filling out the contents of the pointers
+ virtual bool GetSocketInfo( SNetSocket_t hSocket, CSteamID *pSteamIDRemote, int *peSocketStatus, uint32 *punIPRemote, uint16 *punPortRemote ) = 0;
+
+ // returns which local port the listen socket is bound to
+ // *pnIP and *pnPort will be 0 if the socket is set to listen for P2P connections only
+ virtual bool GetListenSocketInfo( SNetListenSocket_t hListenSocket, uint32 *pnIP, uint16 *pnPort ) = 0;
+
+ // returns true to describe how the socket ended up connecting
+ virtual ESNetSocketConnectionType GetSocketConnectionType( SNetSocket_t hSocket ) = 0;
+
+ // max packet size, in bytes
+ virtual int GetMaxPacketSize( SNetSocket_t hSocket ) = 0;
+};
+#define STEAMNETWORKING_INTERFACE_VERSION "SteamNetworking005"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+// callback notification - a user wants to talk to us over the P2P channel via the SendP2PPacket() API
+// in response, a call to AcceptP2PPacketsFromUser() needs to be made, if you want to talk with them
+struct P2PSessionRequest_t
+{
+ enum { k_iCallback = k_iSteamNetworkingCallbacks + 2 };
+ CSteamID m_steamIDRemote; // user who wants to talk to us
+};
+
+
+// callback notification - packets can't get through to the specified user via the SendP2PPacket() API
+// all packets queued packets unsent at this point will be dropped
+// further attempts to send will retry making the connection (but will be dropped if we fail again)
+struct P2PSessionConnectFail_t
+{
+ enum { k_iCallback = k_iSteamNetworkingCallbacks + 3 };
+ CSteamID m_steamIDRemote; // user we were sending packets to
+ uint8 m_eP2PSessionError; // EP2PSessionError indicating why we're having trouble
+};
+
+
+// callback notification - status of a socket has changed
+// used as part of the CreateListenSocket() / CreateP2PConnectionSocket()
+struct SocketStatusCallback_t
+{
+ enum { k_iCallback = k_iSteamNetworkingCallbacks + 1 };
+ SNetSocket_t m_hSocket; // the socket used to send/receive data to the remote host
+ SNetListenSocket_t m_hListenSocket; // this is the server socket that we were listening on; NULL if this was an outgoing connection
+ CSteamID m_steamIDRemote; // remote steamID we have connected to, if it has one
+ int m_eSNetSocketState; // socket state, ESNetSocketState
+};
+
+#pragma pack( pop )
+
+#endif // ISTEAMNETWORKING
diff --git a/dep/steam_api/isteamps3overlayrenderer.h b/dep/steam_api/isteamps3overlayrenderer.h
new file mode 100644
index 0000000..4e07d4a
--- /dev/null
+++ b/dep/steam_api/isteamps3overlayrenderer.h
@@ -0,0 +1,91 @@
+//====== Copyright 1996-2010, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface the game must provide Steam with on PS3 in order for the
+// Steam overlay to render.
+//
+//=============================================================================
+
+#ifndef ISTEAMPS3OVERLAYRENDERER_H
+#define ISTEAMPS3OVERLAYRENDERER_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "cell/pad.h"
+
+//-----------------------------------------------------------------------------
+// Purpose: Enum for supported gradient directions
+//-----------------------------------------------------------------------------
+enum EOverlayGradientDirection
+{
+ k_EOverlayGradientHorizontal = 1,
+ k_EOverlayGradientVertical = 2,
+ k_EOverlayGradientNone = 3,
+};
+
+// Helpers for fetching individual color components from ARGB packed DWORD colors Steam PS3 overlay renderer uses.
+#define STEAM_COLOR_RED( color ) \
+ (int)(((color)>>16)&0xff)
+
+#define STEAM_COLOR_GREEN( color ) \
+ (int)(((color)>>8)&0xff)
+
+#define STEAM_COLOR_BLUE( color ) \
+ (int)((color)&0xff)
+
+#define STEAM_COLOR_ALPHA( color ) \
+ (int)(((color)>>24)&0xff)
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Interface the game must expose to Steam for rendering
+//-----------------------------------------------------------------------------
+class ISteamPS3OverlayRenderHost
+{
+public:
+
+ // Interface for game engine to implement which Steam requires to render.
+
+ // Draw a textured rect. This may use only part of the texture and will pass texture coords, it will also possibly request a gradient and will specify colors for vertexes.
+ virtual void DrawTexturedRect( int x0, int y0, int x1, int y1, float u0, float v0, float u1, float v1, int32 iTextureID, DWORD colorStart, DWORD colorEnd, EOverlayGradientDirection eDirection ) = 0;
+
+ // Load a RGBA texture for Steam, or update a previously loaded one. Updates may be partial. You must not evict or remove this texture once Steam has uploaded it.
+ virtual void LoadOrUpdateTexture( int32 iTextureID, bool bIsFullTexture, int x0, int y0, uint32 uWidth, uint32 uHeight, int32 iBytes, char *pData ) = 0;
+
+ // Delete a texture Steam previously uploaded
+ virtual void DeleteTexture( int32 iTextureID ) = 0;
+
+ // Delete all previously uploaded textures
+ virtual void DeleteAllTextures() = 0;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Interface Steam exposes for the game to tell it when to render, etc.
+//-----------------------------------------------------------------------------
+class ISteamPS3OverlayRender
+{
+public:
+
+ // Call once at startup to initialize the Steam overlay and pass it your host interface ptr
+ virtual bool BHostInitialize( uint32 unScreenWidth, uint32 unScreenHeight, uint32 unRefreshRate, ISteamPS3OverlayRenderHost *pRenderHost, void *CellFontLib ) = 0;
+
+ // Call this once a frame when you are ready for the Steam overlay to render (ie, right before flipping buffers, after all your rendering)
+ virtual void Render() = 0;
+
+ // Call this everytime you read input on PS3.
+ //
+ // If this returns true, then the overlay is active and has consumed the input, your game
+ // should then ignore all the input until BHandleCellPadData once again returns false, which
+ // will mean the overlay is deactivated.
+ virtual bool BHandleCellPadData( const CellPadData &padData ) = 0;
+
+ // Call this if you detect no controllers connected or that the XMB is intercepting input
+ //
+ // This is important to clear input state for the overlay, so keys left down during XMB activation
+ // are not continued to be processed.
+ virtual bool BResetInputState() = 0;
+};
+
+
+#endif // ISTEAMPS3OVERLAYRENDERER_H
\ No newline at end of file
diff --git a/dep/steam_api/isteamremotestorage.h b/dep/steam_api/isteamremotestorage.h
new file mode 100644
index 0000000..3ac2871
--- /dev/null
+++ b/dep/steam_api/isteamremotestorage.h
@@ -0,0 +1,681 @@
+//====== Copyright � 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: public interface to user remote file storage in Steam
+//
+//=============================================================================
+
+#ifndef ISTEAMREMOTESTORAGE_H
+#define ISTEAMREMOTESTORAGE_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Defines the largest allowed file size. Cloud files cannot be written
+// in a single chunk over 100MB (and cannot be over 200MB total.)
+//-----------------------------------------------------------------------------
+const uint32 k_unMaxCloudFileChunkSize = 100 * 1024 * 1024;
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Structure that contains an array of const char * strings and the number of those strings
+//-----------------------------------------------------------------------------
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+struct SteamParamStringArray_t
+{
+ const char ** m_ppStrings;
+ int32 m_nNumStrings;
+};
+#pragma pack( pop )
+
+// A handle to a piece of user generated content
+typedef uint64 UGCHandle_t;
+typedef uint64 PublishedFileUpdateHandle_t;
+typedef uint64 PublishedFileId_t;
+const PublishedFileId_t k_PublishedFileIdInvalid = 0;
+const UGCHandle_t k_UGCHandleInvalid = 0xffffffffffffffffull;
+const PublishedFileUpdateHandle_t k_PublishedFileUpdateHandleInvalid = 0xffffffffffffffffull;
+
+// Handle for writing to Steam Cloud
+typedef uint64 UGCFileWriteStreamHandle_t;
+const UGCFileWriteStreamHandle_t k_UGCFileStreamHandleInvalid = 0xffffffffffffffffull;
+
+const uint32 k_cchPublishedDocumentTitleMax = 128 + 1;
+const uint32 k_cchPublishedDocumentDescriptionMax = 8000;
+const uint32 k_cchPublishedDocumentChangeDescriptionMax = 8000;
+const uint32 k_unEnumeratePublishedFilesMaxResults = 50;
+const uint32 k_cchTagListMax = 1024 + 1;
+const uint32 k_cchFilenameMax = 260;
+const uint32 k_cchPublishedFileURLMax = 256;
+
+
+enum ERemoteStoragePlatform
+{
+ k_ERemoteStoragePlatformNone = 0,
+ k_ERemoteStoragePlatformWindows = (1 << 0),
+ k_ERemoteStoragePlatformOSX = (1 << 1),
+ k_ERemoteStoragePlatformPS3 = (1 << 2),
+ k_ERemoteStoragePlatformLinux = (1 << 3),
+ k_ERemoteStoragePlatformReserved2 = (1 << 4),
+
+ k_ERemoteStoragePlatformAll = 0xffffffff
+};
+
+enum ERemoteStoragePublishedFileVisibility
+{
+ k_ERemoteStoragePublishedFileVisibilityPublic = 0,
+ k_ERemoteStoragePublishedFileVisibilityFriendsOnly = 1,
+ k_ERemoteStoragePublishedFileVisibilityPrivate = 2,
+};
+
+
+enum EWorkshopFileType
+{
+ k_EWorkshopFileTypeFirst = 0,
+
+ k_EWorkshopFileTypeCommunity = 0, // normal Workshop item that can be subscribed to
+ k_EWorkshopFileTypeMicrotransaction = 1, // Workshop item that is meant to be voted on for the purpose of selling in-game
+ k_EWorkshopFileTypeCollection = 2, // a collection of Workshop or Greenlight items
+ k_EWorkshopFileTypeArt = 3, // artwork
+ k_EWorkshopFileTypeVideo = 4, // external video
+ k_EWorkshopFileTypeScreenshot = 5, // screenshot
+ k_EWorkshopFileTypeGame = 6, // Greenlight game entry
+ k_EWorkshopFileTypeSoftware = 7, // Greenlight software entry
+ k_EWorkshopFileTypeConcept = 8, // Greenlight concept
+ k_EWorkshopFileTypeWebGuide = 9, // Steam web guide
+ k_EWorkshopFileTypeIntegratedGuide = 10, // application integrated guide
+ k_EWorkshopFileTypeMerch = 11, // Workshop merchandise meant to be voted on for the purpose of being sold
+ k_EWorkshopFileTypeControllerBinding = 12, // Steam Controller bindings
+ k_EWorkshopFileTypeSteamworksAccessInvite = 13, // internal
+ k_EWorkshopFileTypeSteamVideo = 14, // Steam video
+ k_EWorkshopFileTypeGameManagedItem = 15, // managed completely by the game, not the user, and not shown on the web
+
+ // Update k_EWorkshopFileTypeMax if you add values.
+ k_EWorkshopFileTypeMax = 16
+
+};
+
+enum EWorkshopVote
+{
+ k_EWorkshopVoteUnvoted = 0,
+ k_EWorkshopVoteFor = 1,
+ k_EWorkshopVoteAgainst = 2,
+ k_EWorkshopVoteLater = 3,
+};
+
+enum EWorkshopFileAction
+{
+ k_EWorkshopFileActionPlayed = 0,
+ k_EWorkshopFileActionCompleted = 1,
+};
+
+enum EWorkshopEnumerationType
+{
+ k_EWorkshopEnumerationTypeRankedByVote = 0,
+ k_EWorkshopEnumerationTypeRecent = 1,
+ k_EWorkshopEnumerationTypeTrending = 2,
+ k_EWorkshopEnumerationTypeFavoritesOfFriends = 3,
+ k_EWorkshopEnumerationTypeVotedByFriends = 4,
+ k_EWorkshopEnumerationTypeContentByFriends = 5,
+ k_EWorkshopEnumerationTypeRecentFromFollowedUsers = 6,
+};
+
+enum EWorkshopVideoProvider
+{
+ k_EWorkshopVideoProviderNone = 0,
+ k_EWorkshopVideoProviderYoutube = 1
+};
+
+
+enum EUGCReadAction
+{
+ // Keeps the file handle open unless the last byte is read. You can use this when reading large files (over 100MB) in sequential chunks.
+ // If the last byte is read, this will behave the same as k_EUGCRead_Close. Otherwise, it behaves the same as k_EUGCRead_ContinueReading.
+ // This value maintains the same behavior as before the EUGCReadAction parameter was introduced.
+ k_EUGCRead_ContinueReadingUntilFinished = 0,
+
+ // Keeps the file handle open. Use this when using UGCRead to seek to different parts of the file.
+ // When you are done seeking around the file, make a final call with k_EUGCRead_Close to close it.
+ k_EUGCRead_ContinueReading = 1,
+
+ // Frees the file handle. Use this when you're done reading the content.
+ // To read the file from Steam again you will need to call UGCDownload again.
+ k_EUGCRead_Close = 2,
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for accessing, reading and writing files stored remotely
+// and cached locally
+//-----------------------------------------------------------------------------
+class ISteamRemoteStorage
+{
+ public:
+ // NOTE
+ //
+ // Filenames are case-insensitive, and will be converted to lowercase automatically.
+ // So "foo.bar" and "Foo.bar" are the same file, and if you write "Foo.bar" then
+ // iterate the files, the filename returned will be "foo.bar".
+ //
+
+ // file operations
+ virtual bool FileWrite( const char *pchFile, const void *pvData, int32 cubData ) = 0;
+ virtual int32 FileRead( const char *pchFile, void *pvData, int32 cubDataToRead ) = 0;
+
+ CALL_RESULT( RemoteStorageFileWriteAsyncComplete_t )
+ virtual SteamAPICall_t FileWriteAsync( const char *pchFile, const void *pvData, uint32 cubData ) = 0;
+
+ CALL_RESULT( RemoteStorageFileReadAsyncComplete_t )
+ virtual SteamAPICall_t FileReadAsync( const char *pchFile, uint32 nOffset, uint32 cubToRead ) = 0;
+ virtual bool FileReadAsyncComplete( SteamAPICall_t hReadCall, void *pvBuffer, uint32 cubToRead ) = 0;
+
+ virtual bool FileForget( const char *pchFile ) = 0;
+ virtual bool FileDelete( const char *pchFile ) = 0;
+ CALL_RESULT( RemoteStorageFileShareResult_t )
+ virtual SteamAPICall_t FileShare( const char *pchFile ) = 0;
+ virtual bool SetSyncPlatforms( const char *pchFile, ERemoteStoragePlatform eRemoteStoragePlatform ) = 0;
+
+ // file operations that cause network IO
+ virtual UGCFileWriteStreamHandle_t FileWriteStreamOpen( const char *pchFile ) = 0;
+ virtual bool FileWriteStreamWriteChunk( UGCFileWriteStreamHandle_t writeHandle, const void *pvData, int32 cubData ) = 0;
+ virtual bool FileWriteStreamClose( UGCFileWriteStreamHandle_t writeHandle ) = 0;
+ virtual bool FileWriteStreamCancel( UGCFileWriteStreamHandle_t writeHandle ) = 0;
+
+ // file information
+ virtual bool FileExists( const char *pchFile ) = 0;
+ virtual bool FilePersisted( const char *pchFile ) = 0;
+ virtual int32 GetFileSize( const char *pchFile ) = 0;
+ virtual int64 GetFileTimestamp( const char *pchFile ) = 0;
+ virtual ERemoteStoragePlatform GetSyncPlatforms( const char *pchFile ) = 0;
+
+ // iteration
+ virtual int32 GetFileCount() = 0;
+ virtual const char *GetFileNameAndSize( int iFile, int32 *pnFileSizeInBytes ) = 0;
+
+ // configuration management
+ virtual bool GetQuota( uint64 *pnTotalBytes, uint64 *puAvailableBytes ) = 0;
+ virtual bool IsCloudEnabledForAccount() = 0;
+ virtual bool IsCloudEnabledForApp() = 0;
+ virtual void SetCloudEnabledForApp( bool bEnabled ) = 0;
+
+ // user generated content
+
+ // Downloads a UGC file. A priority value of 0 will download the file immediately,
+ // otherwise it will wait to download the file until all downloads with a lower priority
+ // value are completed. Downloads with equal priority will occur simultaneously.
+ CALL_RESULT( RemoteStorageDownloadUGCResult_t )
+ virtual SteamAPICall_t UGCDownload( UGCHandle_t hContent, uint32 unPriority ) = 0;
+
+ // Gets the amount of data downloaded so far for a piece of content. pnBytesExpected can be 0 if function returns false
+ // or if the transfer hasn't started yet, so be careful to check for that before dividing to get a percentage
+ virtual bool GetUGCDownloadProgress( UGCHandle_t hContent, int32 *pnBytesDownloaded, int32 *pnBytesExpected ) = 0;
+
+ // Gets metadata for a file after it has been downloaded. This is the same metadata given in the RemoteStorageDownloadUGCResult_t call result
+ virtual bool GetUGCDetails( UGCHandle_t hContent, AppId_t *pnAppID, OUT_STRING() char **ppchName, int32 *pnFileSizeInBytes, OUT_STRUCT() CSteamID *pSteamIDOwner ) = 0;
+
+ // After download, gets the content of the file.
+ // Small files can be read all at once by calling this function with an offset of 0 and cubDataToRead equal to the size of the file.
+ // Larger files can be read in chunks to reduce memory usage (since both sides of the IPC client and the game itself must allocate
+ // enough memory for each chunk). Once the last byte is read, the file is implicitly closed and further calls to UGCRead will fail
+ // unless UGCDownload is called again.
+ // For especially large files (anything over 100MB) it is a requirement that the file is read in chunks.
+ virtual int32 UGCRead( UGCHandle_t hContent, void *pvData, int32 cubDataToRead, uint32 cOffset, EUGCReadAction eAction ) = 0;
+
+ // Functions to iterate through UGC that has finished downloading but has not yet been read via UGCRead()
+ virtual int32 GetCachedUGCCount() = 0;
+ virtual UGCHandle_t GetCachedUGCHandle( int32 iCachedContent ) = 0;
+
+ // The following functions are only necessary on the Playstation 3. On PC & Mac, the Steam client will handle these operations for you
+ // On Playstation 3, the game controls which files are stored in the cloud, via FilePersist, FileFetch, and FileForget.
+
+#if defined(_PS3) || defined(_SERVER)
+ // Connect to Steam and get a list of files in the Cloud - results in a RemoteStorageAppSyncStatusCheck_t callback
+ virtual void GetFileListFromServer() = 0;
+ // Indicate this file should be downloaded in the next sync
+ virtual bool FileFetch( const char *pchFile ) = 0;
+ // Indicate this file should be persisted in the next sync
+ virtual bool FilePersist( const char *pchFile ) = 0;
+ // Pull any requested files down from the Cloud - results in a RemoteStorageAppSyncedClient_t callback
+ virtual bool SynchronizeToClient() = 0;
+ // Upload any requested files to the Cloud - results in a RemoteStorageAppSyncedServer_t callback
+ virtual bool SynchronizeToServer() = 0;
+ // Reset any fetch/persist/etc requests
+ virtual bool ResetFileRequestState() = 0;
+#endif
+
+ // publishing UGC
+ CALL_RESULT( RemoteStoragePublishFileProgress_t )
+ virtual SteamAPICall_t PublishWorkshopFile( const char *pchFile, const char *pchPreviewFile, AppId_t nConsumerAppId, const char *pchTitle, const char *pchDescription, ERemoteStoragePublishedFileVisibility eVisibility, SteamParamStringArray_t *pTags, EWorkshopFileType eWorkshopFileType ) = 0;
+ virtual PublishedFileUpdateHandle_t CreatePublishedFileUpdateRequest( PublishedFileId_t unPublishedFileId ) = 0;
+ virtual bool UpdatePublishedFileFile( PublishedFileUpdateHandle_t updateHandle, const char *pchFile ) = 0;
+ virtual bool UpdatePublishedFilePreviewFile( PublishedFileUpdateHandle_t updateHandle, const char *pchPreviewFile ) = 0;
+ virtual bool UpdatePublishedFileTitle( PublishedFileUpdateHandle_t updateHandle, const char *pchTitle ) = 0;
+ virtual bool UpdatePublishedFileDescription( PublishedFileUpdateHandle_t updateHandle, const char *pchDescription ) = 0;
+ virtual bool UpdatePublishedFileVisibility( PublishedFileUpdateHandle_t updateHandle, ERemoteStoragePublishedFileVisibility eVisibility ) = 0;
+ virtual bool UpdatePublishedFileTags( PublishedFileUpdateHandle_t updateHandle, SteamParamStringArray_t *pTags ) = 0;
+ CALL_RESULT( RemoteStorageUpdatePublishedFileResult_t )
+ virtual SteamAPICall_t CommitPublishedFileUpdate( PublishedFileUpdateHandle_t updateHandle ) = 0;
+ // Gets published file details for the given publishedfileid. If unMaxSecondsOld is greater than 0,
+ // cached data may be returned, depending on how long ago it was cached. A value of 0 will force a refresh.
+ // A value of k_WorkshopForceLoadPublishedFileDetailsFromCache will use cached data if it exists, no matter how old it is.
+ CALL_RESULT( RemoteStorageGetPublishedFileDetailsResult_t )
+ virtual SteamAPICall_t GetPublishedFileDetails( PublishedFileId_t unPublishedFileId, uint32 unMaxSecondsOld ) = 0;
+ CALL_RESULT( RemoteStorageDeletePublishedFileResult_t )
+ virtual SteamAPICall_t DeletePublishedFile( PublishedFileId_t unPublishedFileId ) = 0;
+ // enumerate the files that the current user published with this app
+ CALL_RESULT( RemoteStorageEnumerateUserPublishedFilesResult_t )
+ virtual SteamAPICall_t EnumerateUserPublishedFiles( uint32 unStartIndex ) = 0;
+ CALL_RESULT( RemoteStorageSubscribePublishedFileResult_t )
+ virtual SteamAPICall_t SubscribePublishedFile( PublishedFileId_t unPublishedFileId ) = 0;
+ CALL_RESULT( RemoteStorageEnumerateUserSubscribedFilesResult_t )
+ virtual SteamAPICall_t EnumerateUserSubscribedFiles( uint32 unStartIndex ) = 0;
+ CALL_RESULT( RemoteStorageUnsubscribePublishedFileResult_t )
+ virtual SteamAPICall_t UnsubscribePublishedFile( PublishedFileId_t unPublishedFileId ) = 0;
+ virtual bool UpdatePublishedFileSetChangeDescription( PublishedFileUpdateHandle_t updateHandle, const char *pchChangeDescription ) = 0;
+ CALL_RESULT( RemoteStorageGetPublishedItemVoteDetailsResult_t )
+ virtual SteamAPICall_t GetPublishedItemVoteDetails( PublishedFileId_t unPublishedFileId ) = 0;
+ CALL_RESULT( RemoteStorageUpdateUserPublishedItemVoteResult_t )
+ virtual SteamAPICall_t UpdateUserPublishedItemVote( PublishedFileId_t unPublishedFileId, bool bVoteUp ) = 0;
+ CALL_RESULT( RemoteStorageGetPublishedItemVoteDetailsResult_t )
+ virtual SteamAPICall_t GetUserPublishedItemVoteDetails( PublishedFileId_t unPublishedFileId ) = 0;
+ CALL_RESULT( RemoteStorageEnumerateUserPublishedFilesResult_t )
+ virtual SteamAPICall_t EnumerateUserSharedWorkshopFiles( CSteamID steamId, uint32 unStartIndex, SteamParamStringArray_t *pRequiredTags, SteamParamStringArray_t *pExcludedTags ) = 0;
+ CALL_RESULT( RemoteStoragePublishFileProgress_t )
+ virtual SteamAPICall_t PublishVideo( EWorkshopVideoProvider eVideoProvider, const char *pchVideoAccount, const char *pchVideoIdentifier, const char *pchPreviewFile, AppId_t nConsumerAppId, const char *pchTitle, const char *pchDescription, ERemoteStoragePublishedFileVisibility eVisibility, SteamParamStringArray_t *pTags ) = 0;
+ CALL_RESULT( RemoteStorageSetUserPublishedFileActionResult_t )
+ virtual SteamAPICall_t SetUserPublishedFileAction( PublishedFileId_t unPublishedFileId, EWorkshopFileAction eAction ) = 0;
+ CALL_RESULT( RemoteStorageEnumeratePublishedFilesByUserActionResult_t )
+ virtual SteamAPICall_t EnumeratePublishedFilesByUserAction( EWorkshopFileAction eAction, uint32 unStartIndex ) = 0;
+ // this method enumerates the public view of workshop files
+ CALL_RESULT( RemoteStorageEnumerateWorkshopFilesResult_t )
+ virtual SteamAPICall_t EnumeratePublishedWorkshopFiles( EWorkshopEnumerationType eEnumerationType, uint32 unStartIndex, uint32 unCount, uint32 unDays, SteamParamStringArray_t *pTags, SteamParamStringArray_t *pUserTags ) = 0;
+
+ CALL_RESULT( RemoteStorageDownloadUGCResult_t )
+ virtual SteamAPICall_t UGCDownloadToLocation( UGCHandle_t hContent, const char *pchLocation, uint32 unPriority ) = 0;
+};
+
+#define STEAMREMOTESTORAGE_INTERFACE_VERSION "STEAMREMOTESTORAGE_INTERFACE_VERSION014"
+
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: sent when the local file cache is fully synced with the server for an app
+// That means that an application can be started and has all latest files
+//-----------------------------------------------------------------------------
+struct RemoteStorageAppSyncedClient_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 1 };
+ AppId_t m_nAppID;
+ EResult m_eResult;
+ int m_unNumDownloads;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: sent when the server is fully synced with the local file cache for an app
+// That means that we can shutdown Steam and our data is stored on the server
+//-----------------------------------------------------------------------------
+struct RemoteStorageAppSyncedServer_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 2 };
+ AppId_t m_nAppID;
+ EResult m_eResult;
+ int m_unNumUploads;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Status of up and downloads during a sync session
+//
+//-----------------------------------------------------------------------------
+struct RemoteStorageAppSyncProgress_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 3 };
+ char m_rgchCurrentFile[k_cchFilenameMax]; // Current file being transferred
+ AppId_t m_nAppID; // App this info relates to
+ uint32 m_uBytesTransferredThisChunk; // Bytes transferred this chunk
+ double m_dAppPercentComplete; // Percent complete that this app's transfers are
+ bool m_bUploading; // if false, downloading
+};
+
+//
+// IMPORTANT! k_iClientRemoteStorageCallbacks + 4 is used, see iclientremotestorage.h
+//
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Sent after we've determined the list of files that are out of sync
+// with the server.
+//-----------------------------------------------------------------------------
+struct RemoteStorageAppSyncStatusCheck_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 5 };
+ AppId_t m_nAppID;
+ EResult m_eResult;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to FileShare()
+//-----------------------------------------------------------------------------
+struct RemoteStorageFileShareResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 7 };
+ EResult m_eResult; // The result of the operation
+ UGCHandle_t m_hFile; // The handle that can be shared with users and features
+ char m_rgchFilename[k_cchFilenameMax]; // The name of the file that was shared
+};
+
+
+// k_iClientRemoteStorageCallbacks + 8 is deprecated! Do not reuse
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to PublishFile()
+//-----------------------------------------------------------------------------
+struct RemoteStoragePublishFileResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 9 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId;
+ bool m_bUserNeedsToAcceptWorkshopLegalAgreement;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to DeletePublishedFile()
+//-----------------------------------------------------------------------------
+struct RemoteStorageDeletePublishedFileResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 11 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to EnumerateUserPublishedFiles()
+//-----------------------------------------------------------------------------
+struct RemoteStorageEnumerateUserPublishedFilesResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 12 };
+ EResult m_eResult; // The result of the operation.
+ int32 m_nResultsReturned;
+ int32 m_nTotalResultCount;
+ PublishedFileId_t m_rgPublishedFileId[ k_unEnumeratePublishedFilesMaxResults ];
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to SubscribePublishedFile()
+//-----------------------------------------------------------------------------
+struct RemoteStorageSubscribePublishedFileResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 13 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to EnumerateSubscribePublishedFiles()
+//-----------------------------------------------------------------------------
+struct RemoteStorageEnumerateUserSubscribedFilesResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 14 };
+ EResult m_eResult; // The result of the operation.
+ int32 m_nResultsReturned;
+ int32 m_nTotalResultCount;
+ PublishedFileId_t m_rgPublishedFileId[ k_unEnumeratePublishedFilesMaxResults ];
+ uint32 m_rgRTimeSubscribed[ k_unEnumeratePublishedFilesMaxResults ];
+};
+
+#if defined(VALVE_CALLBACK_PACK_SMALL)
+ VALVE_COMPILE_TIME_ASSERT( sizeof( RemoteStorageEnumerateUserSubscribedFilesResult_t ) == (1 + 1 + 1 + 50 + 100) * 4 );
+#elif defined(VALVE_CALLBACK_PACK_LARGE)
+ VALVE_COMPILE_TIME_ASSERT( sizeof( RemoteStorageEnumerateUserSubscribedFilesResult_t ) == (1 + 1 + 1 + 50 + 100) * 4 + 4 );
+#else
+#warning You must first include isteamclient.h
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to UnsubscribePublishedFile()
+//-----------------------------------------------------------------------------
+struct RemoteStorageUnsubscribePublishedFileResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 15 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to CommitPublishedFileUpdate()
+//-----------------------------------------------------------------------------
+struct RemoteStorageUpdatePublishedFileResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 16 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId;
+ bool m_bUserNeedsToAcceptWorkshopLegalAgreement;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to UGCDownload()
+//-----------------------------------------------------------------------------
+struct RemoteStorageDownloadUGCResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 17 };
+ EResult m_eResult; // The result of the operation.
+ UGCHandle_t m_hFile; // The handle to the file that was attempted to be downloaded.
+ AppId_t m_nAppID; // ID of the app that created this file.
+ int32 m_nSizeInBytes; // The size of the file that was downloaded, in bytes.
+ char m_pchFileName[k_cchFilenameMax]; // The name of the file that was downloaded.
+ uint64 m_ulSteamIDOwner; // Steam ID of the user who created this content.
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to GetPublishedFileDetails()
+//-----------------------------------------------------------------------------
+struct RemoteStorageGetPublishedFileDetailsResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 18 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId;
+ AppId_t m_nCreatorAppID; // ID of the app that created this file.
+ AppId_t m_nConsumerAppID; // ID of the app that will consume this file.
+ char m_rgchTitle[k_cchPublishedDocumentTitleMax]; // title of document
+ char m_rgchDescription[k_cchPublishedDocumentDescriptionMax]; // description of document
+ UGCHandle_t m_hFile; // The handle of the primary file
+ UGCHandle_t m_hPreviewFile; // The handle of the preview file
+ uint64 m_ulSteamIDOwner; // Steam ID of the user who created this content.
+ uint32 m_rtimeCreated; // time when the published file was created
+ uint32 m_rtimeUpdated; // time when the published file was last updated
+ ERemoteStoragePublishedFileVisibility m_eVisibility;
+ bool m_bBanned;
+ char m_rgchTags[k_cchTagListMax]; // comma separated list of all tags associated with this file
+ bool m_bTagsTruncated; // whether the list of tags was too long to be returned in the provided buffer
+ char m_pchFileName[k_cchFilenameMax]; // The name of the primary file
+ int32 m_nFileSize; // Size of the primary file
+ int32 m_nPreviewFileSize; // Size of the preview file
+ char m_rgchURL[k_cchPublishedFileURLMax]; // URL (for a video or a website)
+ EWorkshopFileType m_eFileType; // Type of the file
+ bool m_bAcceptedForUse; // developer has specifically flagged this item as accepted in the Workshop
+};
+
+
+struct RemoteStorageEnumerateWorkshopFilesResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 19 };
+ EResult m_eResult;
+ int32 m_nResultsReturned;
+ int32 m_nTotalResultCount;
+ PublishedFileId_t m_rgPublishedFileId[ k_unEnumeratePublishedFilesMaxResults ];
+ float m_rgScore[ k_unEnumeratePublishedFilesMaxResults ];
+ AppId_t m_nAppId;
+ uint32 m_unStartIndex;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of GetPublishedItemVoteDetails
+//-----------------------------------------------------------------------------
+struct RemoteStorageGetPublishedItemVoteDetailsResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 20 };
+ EResult m_eResult;
+ PublishedFileId_t m_unPublishedFileId;
+ int32 m_nVotesFor;
+ int32 m_nVotesAgainst;
+ int32 m_nReports;
+ float m_fScore;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: User subscribed to a file for the app (from within the app or on the web)
+//-----------------------------------------------------------------------------
+struct RemoteStoragePublishedFileSubscribed_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 21 };
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+ AppId_t m_nAppID; // ID of the app that will consume this file.
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: User unsubscribed from a file for the app (from within the app or on the web)
+//-----------------------------------------------------------------------------
+struct RemoteStoragePublishedFileUnsubscribed_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 22 };
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+ AppId_t m_nAppID; // ID of the app that will consume this file.
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Published file that a user owns was deleted (from within the app or the web)
+//-----------------------------------------------------------------------------
+struct RemoteStoragePublishedFileDeleted_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 23 };
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+ AppId_t m_nAppID; // ID of the app that will consume this file.
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to UpdateUserPublishedItemVote()
+//-----------------------------------------------------------------------------
+struct RemoteStorageUpdateUserPublishedItemVoteResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 24 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to GetUserPublishedItemVoteDetails()
+//-----------------------------------------------------------------------------
+struct RemoteStorageUserVoteDetails_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 25 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+ EWorkshopVote m_eVote; // what the user voted
+};
+
+struct RemoteStorageEnumerateUserSharedWorkshopFilesResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 26 };
+ EResult m_eResult; // The result of the operation.
+ int32 m_nResultsReturned;
+ int32 m_nTotalResultCount;
+ PublishedFileId_t m_rgPublishedFileId[ k_unEnumeratePublishedFilesMaxResults ];
+};
+
+struct RemoteStorageSetUserPublishedFileActionResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 27 };
+ EResult m_eResult; // The result of the operation.
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+ EWorkshopFileAction m_eAction; // the action that was attempted
+};
+
+struct RemoteStorageEnumeratePublishedFilesByUserActionResult_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 28 };
+ EResult m_eResult; // The result of the operation.
+ EWorkshopFileAction m_eAction; // the action that was filtered on
+ int32 m_nResultsReturned;
+ int32 m_nTotalResultCount;
+ PublishedFileId_t m_rgPublishedFileId[ k_unEnumeratePublishedFilesMaxResults ];
+ uint32 m_rgRTimeUpdated[ k_unEnumeratePublishedFilesMaxResults ];
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Called periodically while a PublishWorkshopFile is in progress
+//-----------------------------------------------------------------------------
+struct RemoteStoragePublishFileProgress_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 29 };
+ double m_dPercentFile;
+ bool m_bPreview;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Called when the content for a published file is updated
+//-----------------------------------------------------------------------------
+struct RemoteStoragePublishedFileUpdated_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 30 };
+ PublishedFileId_t m_nPublishedFileId; // The published file id
+ AppId_t m_nAppID; // ID of the app that will consume this file.
+ uint64 m_ulUnused; // not used anymore
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Called when a FileWriteAsync completes
+//-----------------------------------------------------------------------------
+struct RemoteStorageFileWriteAsyncComplete_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 31 };
+ EResult m_eResult; // result
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Called when a FileReadAsync completes
+//-----------------------------------------------------------------------------
+struct RemoteStorageFileReadAsyncComplete_t
+{
+ enum { k_iCallback = k_iClientRemoteStorageCallbacks + 32 };
+ SteamAPICall_t m_hFileReadAsync; // call handle of the async read which was made
+ EResult m_eResult; // result
+ uint32 m_nOffset; // offset in the file this read was at
+ uint32 m_cubRead; // amount read - will the <= the amount requested
+};
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMREMOTESTORAGE_H
diff --git a/dep/steam_api/isteamscreenshots.h b/dep/steam_api/isteamscreenshots.h
new file mode 100644
index 0000000..6095705
--- /dev/null
+++ b/dep/steam_api/isteamscreenshots.h
@@ -0,0 +1,116 @@
+//====== Copyright � 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: public interface to user remote file storage in Steam
+//
+//=============================================================================
+
+#ifndef ISTEAMSCREENSHOTS_H
+#define ISTEAMSCREENSHOTS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+const uint32 k_nScreenshotMaxTaggedUsers = 32;
+const uint32 k_nScreenshotMaxTaggedPublishedFiles = 32;
+const int k_cubUFSTagTypeMax = 255;
+const int k_cubUFSTagValueMax = 255;
+
+// Required with of a thumbnail provided to AddScreenshotToLibrary. If you do not provide a thumbnail
+// one will be generated.
+const int k_ScreenshotThumbWidth = 200;
+
+// Handle is valid for the lifetime of your process and no longer
+typedef uint32 ScreenshotHandle;
+#define INVALID_SCREENSHOT_HANDLE 0
+
+enum EVRScreenshotType
+{
+ k_EVRScreenshotType_None = 0,
+ k_EVRScreenshotType_Mono = 1,
+ k_EVRScreenshotType_Stereo = 2,
+ k_EVRScreenshotType_MonoCubemap = 3,
+ k_EVRScreenshotType_MonoPanorama = 4,
+ k_EVRScreenshotType_StereoPanorama = 5
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for adding screenshots to the user's screenshot library
+//-----------------------------------------------------------------------------
+class ISteamScreenshots
+{
+public:
+ // Writes a screenshot to the user's screenshot library given the raw image data, which must be in RGB format.
+ // The return value is a handle that is valid for the duration of the game process and can be used to apply tags.
+ virtual ScreenshotHandle WriteScreenshot( void *pubRGB, uint32 cubRGB, int nWidth, int nHeight ) = 0;
+
+ // Adds a screenshot to the user's screenshot library from disk. If a thumbnail is provided, it must be 200 pixels wide and the same aspect ratio
+ // as the screenshot, otherwise a thumbnail will be generated if the user uploads the screenshot. The screenshots must be in either JPEG or TGA format.
+ // The return value is a handle that is valid for the duration of the game process and can be used to apply tags.
+ // JPEG, TGA, and PNG formats are supported.
+ virtual ScreenshotHandle AddScreenshotToLibrary( const char *pchFilename, const char *pchThumbnailFilename, int nWidth, int nHeight ) = 0;
+
+ // Causes the Steam overlay to take a screenshot. If screenshots are being hooked by the game then a ScreenshotRequested_t callback is sent back to the game instead.
+ virtual void TriggerScreenshot() = 0;
+
+ // Toggles whether the overlay handles screenshots when the user presses the screenshot hotkey, or the game handles them. If the game is hooking screenshots,
+ // then the ScreenshotRequested_t callback will be sent if the user presses the hotkey, and the game is expected to call WriteScreenshot or AddScreenshotToLibrary
+ // in response.
+ virtual void HookScreenshots( bool bHook ) = 0;
+
+ // Sets metadata about a screenshot's location (for example, the name of the map)
+ virtual bool SetLocation( ScreenshotHandle hScreenshot, const char *pchLocation ) = 0;
+
+ // Tags a user as being visible in the screenshot
+ virtual bool TagUser( ScreenshotHandle hScreenshot, CSteamID steamID ) = 0;
+
+ // Tags a published file as being visible in the screenshot
+ virtual bool TagPublishedFile( ScreenshotHandle hScreenshot, PublishedFileId_t unPublishedFileID ) = 0;
+
+ // Returns true if the app has hooked the screenshot
+ virtual bool IsScreenshotsHooked() = 0;
+
+ // Adds a VR screenshot to the user's screenshot library from disk in the supported type.
+ // pchFilename should be the normal 2D image used in the library view
+ // pchVRFilename should contain the image that matches the correct type
+ // The return value is a handle that is valid for the duration of the game process and can be used to apply tags.
+ // JPEG, TGA, and PNG formats are supported.
+ virtual ScreenshotHandle AddVRScreenshotToLibrary( EVRScreenshotType eType, const char *pchFilename, const char *pchVRFilename ) = 0;
+};
+
+#define STEAMSCREENSHOTS_INTERFACE_VERSION "STEAMSCREENSHOTS_INTERFACE_VERSION003"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+//-----------------------------------------------------------------------------
+// Purpose: Screenshot successfully written or otherwise added to the library
+// and can now be tagged
+//-----------------------------------------------------------------------------
+struct ScreenshotReady_t
+{
+ enum { k_iCallback = k_iSteamScreenshotsCallbacks + 1 };
+ ScreenshotHandle m_hLocal;
+ EResult m_eResult;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Screenshot has been requested by the user. Only sent if
+// HookScreenshots() has been called, in which case Steam will not take
+// the screenshot itself.
+//-----------------------------------------------------------------------------
+struct ScreenshotRequested_t
+{
+ enum { k_iCallback = k_iSteamScreenshotsCallbacks + 2 };
+};
+
+#pragma pack( pop )
+
+#endif // ISTEAMSCREENSHOTS_H
+
diff --git a/dep/steam_api/isteamugc.h b/dep/steam_api/isteamugc.h
new file mode 100644
index 0000000..3d973f4
--- /dev/null
+++ b/dep/steam_api/isteamugc.h
@@ -0,0 +1,484 @@
+//====== Copyright 1996-2013, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to steam ugc
+//
+//=============================================================================
+
+#ifndef ISTEAMUGC_H
+#define ISTEAMUGC_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+typedef uint64 UGCQueryHandle_t;
+typedef uint64 UGCUpdateHandle_t;
+
+
+const UGCQueryHandle_t k_UGCQueryHandleInvalid = 0xffffffffffffffffull;
+const UGCUpdateHandle_t k_UGCUpdateHandleInvalid = 0xffffffffffffffffull;
+
+
+// Matching UGC types for queries
+enum EUGCMatchingUGCType
+{
+ k_EUGCMatchingUGCType_Items = 0, // both mtx items and ready-to-use items
+ k_EUGCMatchingUGCType_Items_Mtx = 1,
+ k_EUGCMatchingUGCType_Items_ReadyToUse = 2,
+ k_EUGCMatchingUGCType_Collections = 3,
+ k_EUGCMatchingUGCType_Artwork = 4,
+ k_EUGCMatchingUGCType_Videos = 5,
+ k_EUGCMatchingUGCType_Screenshots = 6,
+ k_EUGCMatchingUGCType_AllGuides = 7, // both web guides and integrated guides
+ k_EUGCMatchingUGCType_WebGuides = 8,
+ k_EUGCMatchingUGCType_IntegratedGuides = 9,
+ k_EUGCMatchingUGCType_UsableInGame = 10, // ready-to-use items and integrated guides
+ k_EUGCMatchingUGCType_ControllerBindings = 11,
+ k_EUGCMatchingUGCType_GameManagedItems = 12, // game managed items (not managed by users)
+ k_EUGCMatchingUGCType_All = ~0, // return everything
+};
+
+// Different lists of published UGC for a user.
+// If the current logged in user is different than the specified user, then some options may not be allowed.
+enum EUserUGCList
+{
+ k_EUserUGCList_Published,
+ k_EUserUGCList_VotedOn,
+ k_EUserUGCList_VotedUp,
+ k_EUserUGCList_VotedDown,
+ k_EUserUGCList_WillVoteLater,
+ k_EUserUGCList_Favorited,
+ k_EUserUGCList_Subscribed,
+ k_EUserUGCList_UsedOrPlayed,
+ k_EUserUGCList_Followed,
+};
+
+// Sort order for user published UGC lists (defaults to creation order descending)
+enum EUserUGCListSortOrder
+{
+ k_EUserUGCListSortOrder_CreationOrderDesc,
+ k_EUserUGCListSortOrder_CreationOrderAsc,
+ k_EUserUGCListSortOrder_TitleAsc,
+ k_EUserUGCListSortOrder_LastUpdatedDesc,
+ k_EUserUGCListSortOrder_SubscriptionDateDesc,
+ k_EUserUGCListSortOrder_VoteScoreDesc,
+ k_EUserUGCListSortOrder_ForModeration,
+};
+
+// Combination of sorting and filtering for queries across all UGC
+enum EUGCQuery
+{
+ k_EUGCQuery_RankedByVote = 0,
+ k_EUGCQuery_RankedByPublicationDate = 1,
+ k_EUGCQuery_AcceptedForGameRankedByAcceptanceDate = 2,
+ k_EUGCQuery_RankedByTrend = 3,
+ k_EUGCQuery_FavoritedByFriendsRankedByPublicationDate = 4,
+ k_EUGCQuery_CreatedByFriendsRankedByPublicationDate = 5,
+ k_EUGCQuery_RankedByNumTimesReported = 6,
+ k_EUGCQuery_CreatedByFollowedUsersRankedByPublicationDate = 7,
+ k_EUGCQuery_NotYetRated = 8,
+ k_EUGCQuery_RankedByTotalVotesAsc = 9,
+ k_EUGCQuery_RankedByVotesUp = 10,
+ k_EUGCQuery_RankedByTextSearch = 11,
+ k_EUGCQuery_RankedByTotalUniqueSubscriptions = 12,
+ k_EUGCQuery_RankedByPlaytimeTrend = 13,
+ k_EUGCQuery_RankedByTotalPlaytime = 14,
+ k_EUGCQuery_RankedByAveragePlaytimeTrend = 15,
+ k_EUGCQuery_RankedByLifetimeAveragePlaytime = 16,
+ k_EUGCQuery_RankedByPlaytimeSessionsTrend = 17,
+ k_EUGCQuery_RankedByLifetimePlaytimeSessions = 18,
+};
+
+enum EItemUpdateStatus
+{
+ k_EItemUpdateStatusInvalid = 0, // The item update handle was invalid, job might be finished, listen too SubmitItemUpdateResult_t
+ k_EItemUpdateStatusPreparingConfig = 1, // The item update is processing configuration data
+ k_EItemUpdateStatusPreparingContent = 2, // The item update is reading and processing content files
+ k_EItemUpdateStatusUploadingContent = 3, // The item update is uploading content changes to Steam
+ k_EItemUpdateStatusUploadingPreviewFile = 4, // The item update is uploading new preview file image
+ k_EItemUpdateStatusCommittingChanges = 5 // The item update is committing all changes
+};
+
+enum EItemState
+{
+ k_EItemStateNone = 0, // item not tracked on client
+ k_EItemStateSubscribed = 1, // current user is subscribed to this item. Not just cached.
+ k_EItemStateLegacyItem = 2, // item was created with ISteamRemoteStorage
+ k_EItemStateInstalled = 4, // item is installed and usable (but maybe out of date)
+ k_EItemStateNeedsUpdate = 8, // items needs an update. Either because it's not installed yet or creator updated content
+ k_EItemStateDownloading = 16, // item update is currently downloading
+ k_EItemStateDownloadPending = 32, // DownloadItem() was called for this item, content isn't available until DownloadItemResult_t is fired
+};
+
+enum EItemStatistic
+{
+ k_EItemStatistic_NumSubscriptions = 0,
+ k_EItemStatistic_NumFavorites = 1,
+ k_EItemStatistic_NumFollowers = 2,
+ k_EItemStatistic_NumUniqueSubscriptions = 3,
+ k_EItemStatistic_NumUniqueFavorites = 4,
+ k_EItemStatistic_NumUniqueFollowers = 5,
+ k_EItemStatistic_NumUniqueWebsiteViews = 6,
+ k_EItemStatistic_ReportScore = 7,
+ k_EItemStatistic_NumSecondsPlayed = 8,
+ k_EItemStatistic_NumPlaytimeSessions = 9,
+ k_EItemStatistic_NumComments = 10,
+ k_EItemStatistic_NumSecondsPlayedDuringTimePeriod = 11,
+ k_EItemStatistic_NumPlaytimeSessionsDuringTimePeriod = 12,
+};
+
+enum EItemPreviewType
+{
+ k_EItemPreviewType_Image = 0, // standard image file expected (e.g. jpg, png, gif, etc.)
+ k_EItemPreviewType_YouTubeVideo = 1, // video id is stored
+ k_EItemPreviewType_Sketchfab = 2, // model id is stored
+ k_EItemPreviewType_EnvironmentMap_HorizontalCross = 3, // standard image file expected - cube map in the layout
+ // +---+---+-------+
+ // | |Up | |
+ // +---+---+---+---+
+ // | L | F | R | B |
+ // +---+---+---+---+
+ // | |Dn | |
+ // +---+---+---+---+
+ k_EItemPreviewType_EnvironmentMap_LatLong = 4, // standard image file expected
+ k_EItemPreviewType_ReservedMax = 255, // you can specify your own types above this value
+};
+
+const uint32 kNumUGCResultsPerPage = 50;
+const uint32 k_cchDeveloperMetadataMax = 5000;
+
+// Details for a single published file/UGC
+struct SteamUGCDetails_t
+{
+ PublishedFileId_t m_nPublishedFileId;
+ EResult m_eResult; // The result of the operation.
+ EWorkshopFileType m_eFileType; // Type of the file
+ AppId_t m_nCreatorAppID; // ID of the app that created this file.
+ AppId_t m_nConsumerAppID; // ID of the app that will consume this file.
+ char m_rgchTitle[k_cchPublishedDocumentTitleMax]; // title of document
+ char m_rgchDescription[k_cchPublishedDocumentDescriptionMax]; // description of document
+ uint64 m_ulSteamIDOwner; // Steam ID of the user who created this content.
+ uint32 m_rtimeCreated; // time when the published file was created
+ uint32 m_rtimeUpdated; // time when the published file was last updated
+ uint32 m_rtimeAddedToUserList; // time when the user added the published file to their list (not always applicable)
+ ERemoteStoragePublishedFileVisibility m_eVisibility; // visibility
+ bool m_bBanned; // whether the file was banned
+ bool m_bAcceptedForUse; // developer has specifically flagged this item as accepted in the Workshop
+ bool m_bTagsTruncated; // whether the list of tags was too long to be returned in the provided buffer
+ char m_rgchTags[k_cchTagListMax]; // comma separated list of all tags associated with this file
+ // file/url information
+ UGCHandle_t m_hFile; // The handle of the primary file
+ UGCHandle_t m_hPreviewFile; // The handle of the preview file
+ char m_pchFileName[k_cchFilenameMax]; // The cloud filename of the primary file
+ int32 m_nFileSize; // Size of the primary file
+ int32 m_nPreviewFileSize; // Size of the preview file
+ char m_rgchURL[k_cchPublishedFileURLMax]; // URL (for a video or a website)
+ // voting information
+ uint32 m_unVotesUp; // number of votes up
+ uint32 m_unVotesDown; // number of votes down
+ float m_flScore; // calculated score
+ // collection details
+ uint32 m_unNumChildren;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: Steam UGC support API
+//-----------------------------------------------------------------------------
+class ISteamUGC
+{
+public:
+
+ // Query UGC associated with a user. Creator app id or consumer app id must be valid and be set to the current running app. unPage should start at 1.
+ virtual UGCQueryHandle_t CreateQueryUserUGCRequest( AccountID_t unAccountID, EUserUGCList eListType, EUGCMatchingUGCType eMatchingUGCType, EUserUGCListSortOrder eSortOrder, AppId_t nCreatorAppID, AppId_t nConsumerAppID, uint32 unPage ) = 0;
+
+ // Query for all matching UGC. Creator app id or consumer app id must be valid and be set to the current running app. unPage should start at 1.
+ virtual UGCQueryHandle_t CreateQueryAllUGCRequest( EUGCQuery eQueryType, EUGCMatchingUGCType eMatchingeMatchingUGCTypeFileType, AppId_t nCreatorAppID, AppId_t nConsumerAppID, uint32 unPage ) = 0;
+
+ // Query for the details of the given published file ids (the RequestUGCDetails call is deprecated and replaced with this)
+ virtual UGCQueryHandle_t CreateQueryUGCDetailsRequest( PublishedFileId_t *pvecPublishedFileID, uint32 unNumPublishedFileIDs ) = 0;
+
+ // Send the query to Steam
+ CALL_RESULT( SteamUGCQueryCompleted_t )
+ virtual SteamAPICall_t SendQueryUGCRequest( UGCQueryHandle_t handle ) = 0;
+
+ // Retrieve an individual result after receiving the callback for querying UGC
+ virtual bool GetQueryUGCResult( UGCQueryHandle_t handle, uint32 index, SteamUGCDetails_t *pDetails ) = 0;
+ virtual bool GetQueryUGCPreviewURL( UGCQueryHandle_t handle, uint32 index, OUT_STRING_COUNT(cchURLSize) char *pchURL, uint32 cchURLSize ) = 0;
+ virtual bool GetQueryUGCMetadata( UGCQueryHandle_t handle, uint32 index, OUT_STRING_COUNT(cchMetadatasize) char *pchMetadata, uint32 cchMetadatasize ) = 0;
+ virtual bool GetQueryUGCChildren( UGCQueryHandle_t handle, uint32 index, PublishedFileId_t* pvecPublishedFileID, uint32 cMaxEntries ) = 0;
+ virtual bool GetQueryUGCStatistic( UGCQueryHandle_t handle, uint32 index, EItemStatistic eStatType, uint64 *pStatValue ) = 0;
+ virtual uint32 GetQueryUGCNumAdditionalPreviews( UGCQueryHandle_t handle, uint32 index ) = 0;
+ virtual bool GetQueryUGCAdditionalPreview( UGCQueryHandle_t handle, uint32 index, uint32 previewIndex, OUT_STRING_COUNT(cchURLSize) char *pchURLOrVideoID, uint32 cchURLSize, OUT_STRING_COUNT(cchURLSize) char *pchOriginalFileName, uint32 cchOriginalFileNameSize, EItemPreviewType *pPreviewType ) = 0;
+ virtual uint32 GetQueryUGCNumKeyValueTags( UGCQueryHandle_t handle, uint32 index ) = 0;
+ virtual bool GetQueryUGCKeyValueTag( UGCQueryHandle_t handle, uint32 index, uint32 keyValueTagIndex, OUT_STRING_COUNT(cchKeySize) char *pchKey, uint32 cchKeySize, OUT_STRING_COUNT(cchValueSize) char *pchValue, uint32 cchValueSize ) = 0;
+
+ // Release the request to free up memory, after retrieving results
+ virtual bool ReleaseQueryUGCRequest( UGCQueryHandle_t handle ) = 0;
+
+ // Options to set for querying UGC
+ virtual bool AddRequiredTag( UGCQueryHandle_t handle, const char *pTagName ) = 0;
+ virtual bool AddExcludedTag( UGCQueryHandle_t handle, const char *pTagName ) = 0;
+ virtual bool SetReturnOnlyIDs( UGCQueryHandle_t handle, bool bReturnOnlyIDs ) = 0;
+ virtual bool SetReturnKeyValueTags( UGCQueryHandle_t handle, bool bReturnKeyValueTags ) = 0;
+ virtual bool SetReturnLongDescription( UGCQueryHandle_t handle, bool bReturnLongDescription ) = 0;
+ virtual bool SetReturnMetadata( UGCQueryHandle_t handle, bool bReturnMetadata ) = 0;
+ virtual bool SetReturnChildren( UGCQueryHandle_t handle, bool bReturnChildren ) = 0;
+ virtual bool SetReturnAdditionalPreviews( UGCQueryHandle_t handle, bool bReturnAdditionalPreviews ) = 0;
+ virtual bool SetReturnTotalOnly( UGCQueryHandle_t handle, bool bReturnTotalOnly ) = 0;
+ virtual bool SetReturnPlaytimeStats( UGCQueryHandle_t handle, uint32 unDays ) = 0;
+ virtual bool SetLanguage( UGCQueryHandle_t handle, const char *pchLanguage ) = 0;
+ virtual bool SetAllowCachedResponse( UGCQueryHandle_t handle, uint32 unMaxAgeSeconds ) = 0;
+
+ // Options only for querying user UGC
+ virtual bool SetCloudFileNameFilter( UGCQueryHandle_t handle, const char *pMatchCloudFileName ) = 0;
+
+ // Options only for querying all UGC
+ virtual bool SetMatchAnyTag( UGCQueryHandle_t handle, bool bMatchAnyTag ) = 0;
+ virtual bool SetSearchText( UGCQueryHandle_t handle, const char *pSearchText ) = 0;
+ virtual bool SetRankedByTrendDays( UGCQueryHandle_t handle, uint32 unDays ) = 0;
+ virtual bool AddRequiredKeyValueTag( UGCQueryHandle_t handle, const char *pKey, const char *pValue ) = 0;
+
+ // DEPRECATED - Use CreateQueryUGCDetailsRequest call above instead!
+ virtual SteamAPICall_t RequestUGCDetails( PublishedFileId_t nPublishedFileID, uint32 unMaxAgeSeconds ) = 0;
+
+ // Steam Workshop Creator API
+ CALL_RESULT( CreateItemResult_t )
+ virtual SteamAPICall_t CreateItem( AppId_t nConsumerAppId, EWorkshopFileType eFileType ) = 0; // create new item for this app with no content attached yet
+
+ virtual UGCUpdateHandle_t StartItemUpdate( AppId_t nConsumerAppId, PublishedFileId_t nPublishedFileID ) = 0; // start an UGC item update. Set changed properties before commiting update with CommitItemUpdate()
+
+ virtual bool SetItemTitle( UGCUpdateHandle_t handle, const char *pchTitle ) = 0; // change the title of an UGC item
+ virtual bool SetItemDescription( UGCUpdateHandle_t handle, const char *pchDescription ) = 0; // change the description of an UGC item
+ virtual bool SetItemUpdateLanguage( UGCUpdateHandle_t handle, const char *pchLanguage ) = 0; // specify the language of the title or description that will be set
+ virtual bool SetItemMetadata( UGCUpdateHandle_t handle, const char *pchMetaData ) = 0; // change the metadata of an UGC item (max = k_cchDeveloperMetadataMax)
+ virtual bool SetItemVisibility( UGCUpdateHandle_t handle, ERemoteStoragePublishedFileVisibility eVisibility ) = 0; // change the visibility of an UGC item
+ virtual bool SetItemTags( UGCUpdateHandle_t updateHandle, const SteamParamStringArray_t *pTags ) = 0; // change the tags of an UGC item
+ virtual bool SetItemContent( UGCUpdateHandle_t handle, const char *pszContentFolder ) = 0; // update item content from this local folder
+ virtual bool SetItemPreview( UGCUpdateHandle_t handle, const char *pszPreviewFile ) = 0; // change preview image file for this item. pszPreviewFile points to local image file, which must be under 1MB in size
+ virtual bool RemoveItemKeyValueTags( UGCUpdateHandle_t handle, const char *pchKey ) = 0; // remove any existing key-value tags with the specified key
+ virtual bool AddItemKeyValueTag( UGCUpdateHandle_t handle, const char *pchKey, const char *pchValue ) = 0; // add new key-value tags for the item. Note that there can be multiple values for a tag.
+ virtual bool AddItemPreviewFile( UGCUpdateHandle_t handle, const char *pszPreviewFile, EItemPreviewType type ) = 0; // add preview file for this item. pszPreviewFile points to local file, which must be under 1MB in size
+ virtual bool AddItemPreviewVideo( UGCUpdateHandle_t handle, const char *pszVideoID ) = 0; // add preview video for this item
+ virtual bool UpdateItemPreviewFile( UGCUpdateHandle_t handle, uint32 index, const char *pszPreviewFile ) = 0; // updates an existing preview file for this item. pszPreviewFile points to local file, which must be under 1MB in size
+ virtual bool UpdateItemPreviewVideo( UGCUpdateHandle_t handle, uint32 index, const char *pszVideoID ) = 0; // updates an existing preview video for this item
+ virtual bool RemoveItemPreview( UGCUpdateHandle_t handle, uint32 index ) = 0; // remove a preview by index starting at 0 (previews are sorted)
+
+ CALL_RESULT( SubmitItemUpdateResult_t )
+ virtual SteamAPICall_t SubmitItemUpdate( UGCUpdateHandle_t handle, const char *pchChangeNote ) = 0; // commit update process started with StartItemUpdate()
+ virtual EItemUpdateStatus GetItemUpdateProgress( UGCUpdateHandle_t handle, uint64 *punBytesProcessed, uint64* punBytesTotal ) = 0;
+
+ // Steam Workshop Consumer API
+ CALL_RESULT( SetUserItemVoteResult_t )
+ virtual SteamAPICall_t SetUserItemVote( PublishedFileId_t nPublishedFileID, bool bVoteUp ) = 0;
+ CALL_RESULT( GetUserItemVoteResult_t )
+ virtual SteamAPICall_t GetUserItemVote( PublishedFileId_t nPublishedFileID ) = 0;
+ CALL_RESULT( UserFavoriteItemsListChanged_t )
+ virtual SteamAPICall_t AddItemToFavorites( AppId_t nAppId, PublishedFileId_t nPublishedFileID ) = 0;
+ CALL_RESULT( UserFavoriteItemsListChanged_t )
+ virtual SteamAPICall_t RemoveItemFromFavorites( AppId_t nAppId, PublishedFileId_t nPublishedFileID ) = 0;
+ CALL_RESULT( RemoteStorageSubscribePublishedFileResult_t )
+ virtual SteamAPICall_t SubscribeItem( PublishedFileId_t nPublishedFileID ) = 0; // subscribe to this item, will be installed ASAP
+ CALL_RESULT( RemoteStorageUnsubscribePublishedFileResult_t )
+ virtual SteamAPICall_t UnsubscribeItem( PublishedFileId_t nPublishedFileID ) = 0; // unsubscribe from this item, will be uninstalled after game quits
+ virtual uint32 GetNumSubscribedItems() = 0; // number of subscribed items
+ virtual uint32 GetSubscribedItems( PublishedFileId_t* pvecPublishedFileID, uint32 cMaxEntries ) = 0; // all subscribed item PublishFileIDs
+
+ // get EItemState flags about item on this client
+ virtual uint32 GetItemState( PublishedFileId_t nPublishedFileID ) = 0;
+
+ // get info about currently installed content on disc for items that have k_EItemStateInstalled set
+ // if k_EItemStateLegacyItem is set, pchFolder contains the path to the legacy file itself (not a folder)
+ virtual bool GetItemInstallInfo( PublishedFileId_t nPublishedFileID, uint64 *punSizeOnDisk, OUT_STRING_COUNT( cchFolderSize ) char *pchFolder, uint32 cchFolderSize, uint32 *punTimeStamp ) = 0;
+
+ // get info about pending update for items that have k_EItemStateNeedsUpdate set. punBytesTotal will be valid after download started once
+ virtual bool GetItemDownloadInfo( PublishedFileId_t nPublishedFileID, uint64 *punBytesDownloaded, uint64 *punBytesTotal ) = 0;
+
+ // download new or update already installed item. If function returns true, wait for DownloadItemResult_t. If the item is already installed,
+ // then files on disk should not be used until callback received. If item is not subscribed to, it will be cached for some time.
+ // If bHighPriority is set, any other item download will be suspended and this item downloaded ASAP.
+ virtual bool DownloadItem( PublishedFileId_t nPublishedFileID, bool bHighPriority ) = 0;
+
+ // game servers can set a specific workshop folder before issuing any UGC commands.
+ // This is helpful if you want to support multiple game servers running out of the same install folder
+ virtual bool BInitWorkshopForGameServer( DepotId_t unWorkshopDepotID, const char *pszFolder ) = 0;
+
+ // SuspendDownloads( true ) will suspend all workshop downloads until SuspendDownloads( false ) is called or the game ends
+ virtual void SuspendDownloads( bool bSuspend ) = 0;
+
+ // usage tracking
+ CALL_RESULT( StartPlaytimeTrackingResult_t )
+ virtual SteamAPICall_t StartPlaytimeTracking( PublishedFileId_t *pvecPublishedFileID, uint32 unNumPublishedFileIDs ) = 0;
+ CALL_RESULT( StopPlaytimeTrackingResult_t )
+ virtual SteamAPICall_t StopPlaytimeTracking( PublishedFileId_t *pvecPublishedFileID, uint32 unNumPublishedFileIDs ) = 0;
+ CALL_RESULT( StopPlaytimeTrackingResult_t )
+ virtual SteamAPICall_t StopPlaytimeTrackingForAllItems() = 0;
+
+ // parent-child relationship or dependency management
+ CALL_RESULT( AddUGCDependencyResult_t )
+ virtual SteamAPICall_t AddDependency( PublishedFileId_t nParentPublishedFileID, PublishedFileId_t nChildPublishedFileID ) = 0;
+ CALL_RESULT( RemoveUGCDependencyResult_t )
+ virtual SteamAPICall_t RemoveDependency( PublishedFileId_t nParentPublishedFileID, PublishedFileId_t nChildPublishedFileID ) = 0;
+};
+
+#define STEAMUGC_INTERFACE_VERSION "STEAMUGC_INTERFACE_VERSION010"
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback for querying UGC
+//-----------------------------------------------------------------------------
+struct SteamUGCQueryCompleted_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 1 };
+ UGCQueryHandle_t m_handle;
+ EResult m_eResult;
+ uint32 m_unNumResultsReturned;
+ uint32 m_unTotalMatchingResults;
+ bool m_bCachedData; // indicates whether this data was retrieved from the local on-disk cache
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback for requesting details on one piece of UGC
+//-----------------------------------------------------------------------------
+struct SteamUGCRequestUGCDetailsResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 2 };
+ SteamUGCDetails_t m_details;
+ bool m_bCachedData; // indicates whether this data was retrieved from the local on-disk cache
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: result for ISteamUGC::CreateItem()
+//-----------------------------------------------------------------------------
+struct CreateItemResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 3 };
+ EResult m_eResult;
+ PublishedFileId_t m_nPublishedFileId; // new item got this UGC PublishFileID
+ bool m_bUserNeedsToAcceptWorkshopLegalAgreement;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: result for ISteamUGC::SubmitItemUpdate()
+//-----------------------------------------------------------------------------
+struct SubmitItemUpdateResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 4 };
+ EResult m_eResult;
+ bool m_bUserNeedsToAcceptWorkshopLegalAgreement;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: a Workshop item has been installed or updated
+//-----------------------------------------------------------------------------
+struct ItemInstalled_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 5 };
+ AppId_t m_unAppID;
+ PublishedFileId_t m_nPublishedFileId;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: result of DownloadItem(), existing item files can be accessed again
+//-----------------------------------------------------------------------------
+struct DownloadItemResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 6 };
+ AppId_t m_unAppID;
+ PublishedFileId_t m_nPublishedFileId;
+ EResult m_eResult;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: result of AddItemToFavorites() or RemoveItemFromFavorites()
+//-----------------------------------------------------------------------------
+struct UserFavoriteItemsListChanged_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 7 };
+ PublishedFileId_t m_nPublishedFileId;
+ EResult m_eResult;
+ bool m_bWasAddRequest;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to SetUserItemVote()
+//-----------------------------------------------------------------------------
+struct SetUserItemVoteResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 8 };
+ PublishedFileId_t m_nPublishedFileId;
+ EResult m_eResult;
+ bool m_bVoteUp;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to GetUserItemVote()
+//-----------------------------------------------------------------------------
+struct GetUserItemVoteResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 9 };
+ PublishedFileId_t m_nPublishedFileId;
+ EResult m_eResult;
+ bool m_bVotedUp;
+ bool m_bVotedDown;
+ bool m_bVoteSkipped;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to StartPlaytimeTracking()
+//-----------------------------------------------------------------------------
+struct StartPlaytimeTrackingResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 10 };
+ EResult m_eResult;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to StopPlaytimeTracking()
+//-----------------------------------------------------------------------------
+struct StopPlaytimeTrackingResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 11 };
+ EResult m_eResult;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to AddDependency
+//-----------------------------------------------------------------------------
+struct AddUGCDependencyResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 12 };
+ EResult m_eResult;
+ PublishedFileId_t m_nPublishedFileId;
+ PublishedFileId_t m_nChildPublishedFileId;
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: The result of a call to RemoveDependency
+//-----------------------------------------------------------------------------
+struct RemoveUGCDependencyResult_t
+{
+ enum { k_iCallback = k_iClientUGCCallbacks + 13 };
+ EResult m_eResult;
+ PublishedFileId_t m_nPublishedFileId;
+ PublishedFileId_t m_nChildPublishedFileId;
+};
+
+
+#pragma pack( pop )
+
+#endif // ISTEAMUGC_H
diff --git a/dep/steam_api/isteamunifiedmessages.h b/dep/steam_api/isteamunifiedmessages.h
new file mode 100644
index 0000000..684f4e8
--- /dev/null
+++ b/dep/steam_api/isteamunifiedmessages.h
@@ -0,0 +1,63 @@
+//====== Copyright � 1996-2007, Valve Corporation, All rights reserved. =======
+//
+// Purpose: Interface to unified messages client
+//
+// You should not need to use this interface except if your product is using a language other than C++.
+// Contact your Steam Tech contact for more details.
+//
+//=============================================================================
+
+#ifndef ISTEAMUNIFIEDMESSAGES_H
+#define ISTEAMUNIFIEDMESSAGES_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+typedef uint64 ClientUnifiedMessageHandle;
+
+class ISteamUnifiedMessages
+{
+public:
+ static const ClientUnifiedMessageHandle k_InvalidUnifiedMessageHandle = 0;
+
+ // Sends a service method (in binary serialized form) using the Steam Client.
+ // Returns a unified message handle (k_InvalidUnifiedMessageHandle if could not send the message).
+ virtual ClientUnifiedMessageHandle SendMethod( const char *pchServiceMethod, const void *pRequestBuffer, uint32 unRequestBufferSize, uint64 unContext ) = 0;
+
+ // Gets the size of the response and the EResult. Returns false if the response is not ready yet.
+ virtual bool GetMethodResponseInfo( ClientUnifiedMessageHandle hHandle, uint32 *punResponseSize, EResult *peResult ) = 0;
+
+ // Gets a response in binary serialized form (and optionally release the corresponding allocated memory).
+ virtual bool GetMethodResponseData( ClientUnifiedMessageHandle hHandle, void *pResponseBuffer, uint32 unResponseBufferSize, bool bAutoRelease ) = 0;
+
+ // Releases the message and its corresponding allocated memory.
+ virtual bool ReleaseMethod( ClientUnifiedMessageHandle hHandle ) = 0;
+
+ // Sends a service notification (in binary serialized form) using the Steam Client.
+ // Returns true if the notification was sent successfully.
+ virtual bool SendNotification( const char *pchServiceNotification, const void *pNotificationBuffer, uint32 unNotificationBufferSize ) = 0;
+};
+
+#define STEAMUNIFIEDMESSAGES_INTERFACE_VERSION "STEAMUNIFIEDMESSAGES_INTERFACE_VERSION001"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+struct SteamUnifiedMessagesSendMethodResult_t
+{
+ enum { k_iCallback = k_iClientUnifiedMessagesCallbacks + 1 };
+ ClientUnifiedMessageHandle m_hHandle; // The handle returned by SendMethod().
+ uint64 m_unContext; // Context provided when calling SendMethod().
+ EResult m_eResult; // The result of the method call.
+ uint32 m_unResponseSize; // The size of the response.
+};
+
+#pragma pack( pop )
+
+#endif // ISTEAMUNIFIEDMESSAGES_H
diff --git a/dep/steam_api/isteamuser.h b/dep/steam_api/isteamuser.h
new file mode 100644
index 0000000..0ea2bb8
--- /dev/null
+++ b/dep/steam_api/isteamuser.h
@@ -0,0 +1,369 @@
+//====== Copyright (c) 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to user account information in Steam
+//
+//=============================================================================
+
+#ifndef ISTEAMUSER_H
+#define ISTEAMUSER_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+// structure that contains client callback data
+// see callbacks documentation for more details
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+struct CallbackMsg_t
+{
+ HSteamUser m_hSteamUser;
+ int m_iCallback;
+ uint8 *m_pubParam;
+ int m_cubParam;
+};
+#pragma pack( pop )
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for accessing and manipulating a steam account
+// associated with one client instance
+//-----------------------------------------------------------------------------
+class ISteamUser
+{
+public:
+ // returns the HSteamUser this interface represents
+ // this is only used internally by the API, and by a few select interfaces that support multi-user
+ virtual HSteamUser GetHSteamUser() = 0;
+
+ // returns true if the Steam client current has a live connection to the Steam servers.
+ // If false, it means there is no active connection due to either a networking issue on the local machine, or the Steam server is down/busy.
+ // The Steam client will automatically be trying to recreate the connection as often as possible.
+ virtual bool BLoggedOn() = 0;
+
+ // returns the CSteamID of the account currently logged into the Steam client
+ // a CSteamID is a unique identifier for an account, and used to differentiate users in all parts of the Steamworks API
+ virtual CSteamID GetSteamID() = 0;
+
+ // Multiplayer Authentication functions
+
+ // InitiateGameConnection() starts the state machine for authenticating the game client with the game server
+ // It is the client portion of a three-way handshake between the client, the game server, and the steam servers
+ //
+ // Parameters:
+ // void *pAuthBlob - a pointer to empty memory that will be filled in with the authentication token.
+ // int cbMaxAuthBlob - the number of bytes of allocated memory in pBlob. Should be at least 2048 bytes.
+ // CSteamID steamIDGameServer - the steamID of the game server, received from the game server by the client
+ // CGameID gameID - the ID of the current game. For games without mods, this is just CGameID( )
+ // uint32 unIPServer, uint16 usPortServer - the IP address of the game server
+ // bool bSecure - whether or not the client thinks that the game server is reporting itself as secure (i.e. VAC is running)
+ //
+ // return value - returns the number of bytes written to pBlob. If the return is 0, then the buffer passed in was too small, and the call has failed
+ // The contents of pBlob should then be sent to the game server, for it to use to complete the authentication process.
+ virtual int InitiateGameConnection( void *pAuthBlob, int cbMaxAuthBlob, CSteamID steamIDGameServer, uint32 unIPServer, uint16 usPortServer, bool bSecure ) = 0;
+
+ // notify of disconnect
+ // needs to occur when the game client leaves the specified game server, needs to match with the InitiateGameConnection() call
+ virtual void TerminateGameConnection( uint32 unIPServer, uint16 usPortServer ) = 0;
+
+ // Legacy functions
+
+ // used by only a few games to track usage events
+ virtual void TrackAppUsageEvent( CGameID gameID, int eAppUsageEvent, const char *pchExtraInfo = "" ) = 0;
+
+ // get the local storage folder for current Steam account to write application data, e.g. save games, configs etc.
+ // this will usually be something like "C:\Progam Files\Steam\userdata\\\local"
+ virtual bool GetUserDataFolder( char *pchBuffer, int cubBuffer ) = 0;
+
+ // Starts voice recording. Once started, use GetVoice() to get the data
+ virtual void StartVoiceRecording( ) = 0;
+
+ // Stops voice recording. Because people often release push-to-talk keys early, the system will keep recording for
+ // a little bit after this function is called. GetVoice() should continue to be called until it returns
+ // k_eVoiceResultNotRecording
+ virtual void StopVoiceRecording( ) = 0;
+
+ // Determine the size of captured audio data that is available from GetVoice.
+ // Most applications will only use compressed data and should ignore the other
+ // parameters, which exist primarily for backwards compatibility. See comments
+ // below for further explanation of "uncompressed" data.
+ virtual EVoiceResult GetAvailableVoice( uint32 *pcbCompressed, uint32 *pcbUncompressed_Deprecated = 0, uint32 nUncompressedVoiceDesiredSampleRate_Deprecated = 0 ) = 0;
+
+ // ---------------------------------------------------------------------------
+ // NOTE: "uncompressed" audio is a deprecated feature and should not be used
+ // by most applications. It is raw single-channel 16-bit PCM wave data which
+ // may have been run through preprocessing filters and/or had silence removed,
+ // so the uncompressed audio could have a shorter duration than you expect.
+ // There may be no data at all during long periods of silence. Also, fetching
+ // uncompressed audio will cause GetVoice to discard any leftover compressed
+ // audio, so you must fetch both types at once. Finally, GetAvailableVoice is
+ // not precisely accurate when the uncompressed size is requested. So if you
+ // really need to use uncompressed audio, you should call GetVoice frequently
+ // with two very large (20kb+) output buffers instead of trying to allocate
+ // perfectly-sized buffers. But most applications should ignore all of these
+ // details and simply leave the "uncompressed" parameters as NULL/zero.
+ // ---------------------------------------------------------------------------
+
+ // Read captured audio data from the microphone buffer. This should be called
+ // at least once per frame, and preferably every few milliseconds, to keep the
+ // microphone input delay as low as possible. Most applications will only use
+ // compressed data and should pass NULL/zero for the "uncompressed" parameters.
+ // Compressed data can be transmitted by your application and decoded into raw
+ // using the DecompressVoice function below.
+ virtual EVoiceResult GetVoice( bool bWantCompressed, void *pDestBuffer, uint32 cbDestBufferSize, uint32 *nBytesWritten, bool bWantUncompressed_Deprecated = false, void *pUncompressedDestBuffer_Deprecated = 0, uint32 cbUncompressedDestBufferSize_Deprecated = 0, uint32 *nUncompressBytesWritten_Deprecated = 0, uint32 nUncompressedVoiceDesiredSampleRate_Deprecated = 0 ) = 0;
+
+ // Decodes the compressed voice data returned by GetVoice. The output data is
+ // raw single-channel 16-bit PCM audio. The decoder supports any sample rate
+ // from 11025 to 48000; see GetVoiceOptimalSampleRate() below for details.
+ // If the output buffer is not large enough, then *nBytesWritten will be set
+ // to the required buffer size, and k_EVoiceResultBufferTooSmall is returned.
+ // It is suggested to start with a 20kb buffer and reallocate as necessary.
+ virtual EVoiceResult DecompressVoice( const void *pCompressed, uint32 cbCompressed, void *pDestBuffer, uint32 cbDestBufferSize, uint32 *nBytesWritten, uint32 nDesiredSampleRate ) = 0;
+
+ // This returns the native sample rate of the Steam voice decompressor; using
+ // this sample rate for DecompressVoice will perform the least CPU processing.
+ // However, the final audio quality will depend on how well the audio device
+ // (and/or your application's audio output SDK) deals with lower sample rates.
+ // You may find that you get the best audio output quality when you ignore
+ // this function and use the native sample rate of your audio output device,
+ // which is usually 48000 or 44100.
+ virtual uint32 GetVoiceOptimalSampleRate() = 0;
+
+ // Retrieve ticket to be sent to the entity who wishes to authenticate you.
+ // pcbTicket retrieves the length of the actual ticket.
+ virtual HAuthTicket GetAuthSessionTicket( void *pTicket, int cbMaxTicket, uint32 *pcbTicket ) = 0;
+
+ // Authenticate ticket from entity steamID to be sure it is valid and isnt reused
+ // Registers for callbacks if the entity goes offline or cancels the ticket ( see ValidateAuthTicketResponse_t callback and EAuthSessionResponse )
+ virtual EBeginAuthSessionResult BeginAuthSession( const void *pAuthTicket, int cbAuthTicket, CSteamID steamID ) = 0;
+
+ // Stop tracking started by BeginAuthSession - called when no longer playing game with this entity
+ virtual void EndAuthSession( CSteamID steamID ) = 0;
+
+ // Cancel auth ticket from GetAuthSessionTicket, called when no longer playing game with the entity you gave the ticket to
+ virtual void CancelAuthTicket( HAuthTicket hAuthTicket ) = 0;
+
+ // After receiving a user's authentication data, and passing it to BeginAuthSession, use this function
+ // to determine if the user owns downloadable content specified by the provided AppID.
+ virtual EUserHasLicenseForAppResult UserHasLicenseForApp( CSteamID steamID, AppId_t appID ) = 0;
+
+ // returns true if this users looks like they are behind a NAT device. Only valid once the user has connected to steam
+ // (i.e a SteamServersConnected_t has been issued) and may not catch all forms of NAT.
+ virtual bool BIsBehindNAT() = 0;
+
+ // set data to be replicated to friends so that they can join your game
+ // CSteamID steamIDGameServer - the steamID of the game server, received from the game server by the client
+ // uint32 unIPServer, uint16 usPortServer - the IP address of the game server
+ virtual void AdvertiseGame( CSteamID steamIDGameServer, uint32 unIPServer, uint16 usPortServer ) = 0;
+
+ // Requests a ticket encrypted with an app specific shared key
+ // pDataToInclude, cbDataToInclude will be encrypted into the ticket
+ // ( This is asynchronous, you must wait for the ticket to be completed by the server )
+ CALL_RESULT( EncryptedAppTicketResponse_t )
+ virtual SteamAPICall_t RequestEncryptedAppTicket( void *pDataToInclude, int cbDataToInclude ) = 0;
+
+ // retrieve a finished ticket
+ virtual bool GetEncryptedAppTicket( void *pTicket, int cbMaxTicket, uint32 *pcbTicket ) = 0;
+
+ // Trading Card badges data access
+ // if you only have one set of cards, the series will be 1
+ // the user has can have two different badges for a series; the regular (max level 5) and the foil (max level 1)
+ virtual int GetGameBadgeLevel( int nSeries, bool bFoil ) = 0;
+
+ // gets the Steam Level of the user, as shown on their profile
+ virtual int GetPlayerSteamLevel() = 0;
+
+ // Requests a URL which authenticates an in-game browser for store check-out,
+ // and then redirects to the specified URL. As long as the in-game browser
+ // accepts and handles session cookies, Steam microtransaction checkout pages
+ // will automatically recognize the user instead of presenting a login page.
+ // The result of this API call will be a StoreAuthURLResponse_t callback.
+ // NOTE: The URL has a very short lifetime to prevent history-snooping attacks,
+ // so you should only call this API when you are about to launch the browser,
+ // or else immediately navigate to the result URL using a hidden browser window.
+ // NOTE 2: The resulting authorization cookie has an expiration time of one day,
+ // so it would be a good idea to request and visit a new auth URL every 12 hours.
+ CALL_RESULT( StoreAuthURLResponse_t )
+ virtual SteamAPICall_t RequestStoreAuthURL( const char *pchRedirectURL ) = 0;
+
+ // gets whether the users phone number is verified
+ virtual bool BIsPhoneVerified() = 0;
+
+ // gets whether the user has two factor enabled on their account
+ virtual bool BIsTwoFactorEnabled() = 0;
+
+ // gets whether the users phone number is identifying
+ virtual bool BIsPhoneIdentifying() = 0;
+
+ // gets whether the users phone number is awaiting (re)verification
+ virtual bool BIsPhoneRequiringVerification() = 0;
+
+};
+
+#define STEAMUSER_INTERFACE_VERSION "SteamUser019"
+
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: called when a connections to the Steam back-end has been established
+// this means the Steam client now has a working connection to the Steam servers
+// usually this will have occurred before the game has launched, and should
+// only be seen if the user has dropped connection due to a networking issue
+// or a Steam server update
+//-----------------------------------------------------------------------------
+struct SteamServersConnected_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 1 };
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: called when a connection attempt has failed
+// this will occur periodically if the Steam client is not connected,
+// and has failed in it's retry to establish a connection
+//-----------------------------------------------------------------------------
+struct SteamServerConnectFailure_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 2 };
+ EResult m_eResult;
+ bool m_bStillRetrying;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called if the client has lost connection to the Steam servers
+// real-time services will be disabled until a matching SteamServersConnected_t has been posted
+//-----------------------------------------------------------------------------
+struct SteamServersDisconnected_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 3 };
+ EResult m_eResult;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Sent by the Steam server to the client telling it to disconnect from the specified game server,
+// which it may be in the process of or already connected to.
+// The game client should immediately disconnect upon receiving this message.
+// This can usually occur if the user doesn't have rights to play on the game server.
+//-----------------------------------------------------------------------------
+struct ClientGameServerDeny_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 13 };
+
+ uint32 m_uAppID;
+ uint32 m_unGameServerIP;
+ uint16 m_usGameServerPort;
+ uint16 m_bSecure;
+ uint32 m_uReason;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when the callback system for this client is in an error state (and has flushed pending callbacks)
+// When getting this message the client should disconnect from Steam, reset any stored Steam state and reconnect.
+// This usually occurs in the rare event the Steam client has some kind of fatal error.
+//-----------------------------------------------------------------------------
+struct IPCFailure_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 17 };
+ enum EFailureType
+ {
+ k_EFailureFlushedCallbackQueue,
+ k_EFailurePipeFail,
+ };
+ uint8 m_eFailureType;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Signaled whenever licenses change
+//-----------------------------------------------------------------------------
+struct LicensesUpdated_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 25 };
+};
+
+
+//-----------------------------------------------------------------------------
+// callback for BeginAuthSession
+//-----------------------------------------------------------------------------
+struct ValidateAuthTicketResponse_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 43 };
+ CSteamID m_SteamID;
+ EAuthSessionResponse m_eAuthSessionResponse;
+ CSteamID m_OwnerSteamID; // different from m_SteamID if borrowed
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when a user has responded to a microtransaction authorization request
+//-----------------------------------------------------------------------------
+struct MicroTxnAuthorizationResponse_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 52 };
+
+ uint32 m_unAppID; // AppID for this microtransaction
+ uint64 m_ulOrderID; // OrderID provided for the microtransaction
+ uint8 m_bAuthorized; // if user authorized transaction
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Result from RequestEncryptedAppTicket
+//-----------------------------------------------------------------------------
+struct EncryptedAppTicketResponse_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 54 };
+
+ EResult m_eResult;
+};
+
+//-----------------------------------------------------------------------------
+// callback for GetAuthSessionTicket
+//-----------------------------------------------------------------------------
+struct GetAuthSessionTicketResponse_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 63 };
+ HAuthTicket m_hAuthTicket;
+ EResult m_eResult;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: sent to your game in response to a steam://gamewebcallback/ command
+//-----------------------------------------------------------------------------
+struct GameWebCallback_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 64 };
+ char m_szURL[256];
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: sent to your game in response to ISteamUser::RequestStoreAuthURL
+//-----------------------------------------------------------------------------
+struct StoreAuthURLResponse_t
+{
+ enum { k_iCallback = k_iSteamUserCallbacks + 65 };
+ char m_szURL[512];
+};
+
+
+
+#pragma pack( pop )
+
+#endif // ISTEAMUSER_H
diff --git a/dep/steam_api/isteamuserstats.h b/dep/steam_api/isteamuserstats.h
new file mode 100644
index 0000000..29ae38b
--- /dev/null
+++ b/dep/steam_api/isteamuserstats.h
@@ -0,0 +1,476 @@
+//====== Copyright � 1996-2009, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to stats, achievements, and leaderboards
+//
+//=============================================================================
+
+#ifndef ISTEAMUSERSTATS_H
+#define ISTEAMUSERSTATS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+#include "isteamremotestorage.h"
+
+// size limit on stat or achievement name (UTF-8 encoded)
+enum { k_cchStatNameMax = 128 };
+
+// maximum number of bytes for a leaderboard name (UTF-8 encoded)
+enum { k_cchLeaderboardNameMax = 128 };
+
+// maximum number of details int32's storable for a single leaderboard entry
+enum { k_cLeaderboardDetailsMax = 64 };
+
+// handle to a single leaderboard
+typedef uint64 SteamLeaderboard_t;
+
+// handle to a set of downloaded entries in a leaderboard
+typedef uint64 SteamLeaderboardEntries_t;
+
+// type of data request, when downloading leaderboard entries
+enum ELeaderboardDataRequest
+{
+ k_ELeaderboardDataRequestGlobal = 0,
+ k_ELeaderboardDataRequestGlobalAroundUser = 1,
+ k_ELeaderboardDataRequestFriends = 2,
+ k_ELeaderboardDataRequestUsers = 3
+};
+
+// the sort order of a leaderboard
+enum ELeaderboardSortMethod
+{
+ k_ELeaderboardSortMethodNone = 0,
+ k_ELeaderboardSortMethodAscending = 1, // top-score is lowest number
+ k_ELeaderboardSortMethodDescending = 2, // top-score is highest number
+};
+
+// the display type (used by the Steam Community web site) for a leaderboard
+enum ELeaderboardDisplayType
+{
+ k_ELeaderboardDisplayTypeNone = 0,
+ k_ELeaderboardDisplayTypeNumeric = 1, // simple numerical score
+ k_ELeaderboardDisplayTypeTimeSeconds = 2, // the score represents a time, in seconds
+ k_ELeaderboardDisplayTypeTimeMilliSeconds = 3, // the score represents a time, in milliseconds
+};
+
+enum ELeaderboardUploadScoreMethod
+{
+ k_ELeaderboardUploadScoreMethodNone = 0,
+ k_ELeaderboardUploadScoreMethodKeepBest = 1, // Leaderboard will keep user's best score
+ k_ELeaderboardUploadScoreMethodForceUpdate = 2, // Leaderboard will always replace score with specified
+};
+
+// a single entry in a leaderboard, as returned by GetDownloadedLeaderboardEntry()
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+struct LeaderboardEntry_t
+{
+ CSteamID m_steamIDUser; // user with the entry - use SteamFriends()->GetFriendPersonaName() & SteamFriends()->GetFriendAvatar() to get more info
+ int32 m_nGlobalRank; // [1..N], where N is the number of users with an entry in the leaderboard
+ int32 m_nScore; // score as set in the leaderboard
+ int32 m_cDetails; // number of int32 details available for this entry
+ UGCHandle_t m_hUGC; // handle for UGC attached to the entry
+};
+
+#pragma pack( pop )
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Functions for accessing stats, achievements, and leaderboard information
+//-----------------------------------------------------------------------------
+class ISteamUserStats
+{
+public:
+ // Ask the server to send down this user's data and achievements for this game
+ CALL_BACK( UserStatsReceived_t )
+ virtual bool RequestCurrentStats() = 0;
+
+ // Data accessors
+ virtual bool GetStat( const char *pchName, int32 *pData ) = 0;
+ virtual bool GetStat( const char *pchName, float *pData ) = 0;
+
+ // Set / update data
+ virtual bool SetStat( const char *pchName, int32 nData ) = 0;
+ virtual bool SetStat( const char *pchName, float fData ) = 0;
+ virtual bool UpdateAvgRateStat( const char *pchName, float flCountThisSession, double dSessionLength ) = 0;
+
+ // Achievement flag accessors
+ virtual bool GetAchievement( const char *pchName, bool *pbAchieved ) = 0;
+ virtual bool SetAchievement( const char *pchName ) = 0;
+ virtual bool ClearAchievement( const char *pchName ) = 0;
+
+ // Get the achievement status, and the time it was unlocked if unlocked.
+ // If the return value is true, but the unlock time is zero, that means it was unlocked before Steam
+ // began tracking achievement unlock times (December 2009). Time is seconds since January 1, 1970.
+ virtual bool GetAchievementAndUnlockTime( const char *pchName, bool *pbAchieved, uint32 *punUnlockTime ) = 0;
+
+ // Store the current data on the server, will get a callback when set
+ // And one callback for every new achievement
+ //
+ // If the callback has a result of k_EResultInvalidParam, one or more stats
+ // uploaded has been rejected, either because they broke constraints
+ // or were out of date. In this case the server sends back updated values.
+ // The stats should be re-iterated to keep in sync.
+ virtual bool StoreStats() = 0;
+
+ // Achievement / GroupAchievement metadata
+
+ // Gets the icon of the achievement, which is a handle to be used in ISteamUtils::GetImageRGBA(), or 0 if none set.
+ // A return value of 0 may indicate we are still fetching data, and you can wait for the UserAchievementIconFetched_t callback
+ // which will notify you when the bits are ready. If the callback still returns zero, then there is no image set for the
+ // specified achievement.
+ virtual int GetAchievementIcon( const char *pchName ) = 0;
+
+ // Get general attributes for an achievement. Accepts the following keys:
+ // - "name" and "desc" for retrieving the localized achievement name and description (returned in UTF8)
+ // - "hidden" for retrieving if an achievement is hidden (returns "0" when not hidden, "1" when hidden)
+ virtual const char *GetAchievementDisplayAttribute( const char *pchName, const char *pchKey ) = 0;
+
+ // Achievement progress - triggers an AchievementProgress callback, that is all.
+ // Calling this w/ N out of N progress will NOT set the achievement, the game must still do that.
+ virtual bool IndicateAchievementProgress( const char *pchName, uint32 nCurProgress, uint32 nMaxProgress ) = 0;
+
+ // Used for iterating achievements. In general games should not need these functions because they should have a
+ // list of existing achievements compiled into them
+ virtual uint32 GetNumAchievements() = 0;
+ // Get achievement name iAchievement in [0,GetNumAchievements)
+ virtual const char *GetAchievementName( uint32 iAchievement ) = 0;
+
+ // Friends stats & achievements
+
+ // downloads stats for the user
+ // returns a UserStatsReceived_t received when completed
+ // if the other user has no stats, UserStatsReceived_t.m_eResult will be set to k_EResultFail
+ // these stats won't be auto-updated; you'll need to call RequestUserStats() again to refresh any data
+ CALL_RESULT( UserStatsReceived_t )
+ virtual SteamAPICall_t RequestUserStats( CSteamID steamIDUser ) = 0;
+
+ // requests stat information for a user, usable after a successful call to RequestUserStats()
+ virtual bool GetUserStat( CSteamID steamIDUser, const char *pchName, int32 *pData ) = 0;
+ virtual bool GetUserStat( CSteamID steamIDUser, const char *pchName, float *pData ) = 0;
+ virtual bool GetUserAchievement( CSteamID steamIDUser, const char *pchName, bool *pbAchieved ) = 0;
+ // See notes for GetAchievementAndUnlockTime above
+ virtual bool GetUserAchievementAndUnlockTime( CSteamID steamIDUser, const char *pchName, bool *pbAchieved, uint32 *punUnlockTime ) = 0;
+
+ // Reset stats
+ virtual bool ResetAllStats( bool bAchievementsToo ) = 0;
+
+ // Leaderboard functions
+
+ // asks the Steam back-end for a leaderboard by name, and will create it if it's not yet
+ // This call is asynchronous, with the result returned in LeaderboardFindResult_t
+ CALL_RESULT(LeaderboardFindResult_t)
+ virtual SteamAPICall_t FindOrCreateLeaderboard( const char *pchLeaderboardName, ELeaderboardSortMethod eLeaderboardSortMethod, ELeaderboardDisplayType eLeaderboardDisplayType ) = 0;
+
+ // as above, but won't create the leaderboard if it's not found
+ // This call is asynchronous, with the result returned in LeaderboardFindResult_t
+ CALL_RESULT( LeaderboardFindResult_t )
+ virtual SteamAPICall_t FindLeaderboard( const char *pchLeaderboardName ) = 0;
+
+ // returns the name of a leaderboard
+ virtual const char *GetLeaderboardName( SteamLeaderboard_t hSteamLeaderboard ) = 0;
+
+ // returns the total number of entries in a leaderboard, as of the last request
+ virtual int GetLeaderboardEntryCount( SteamLeaderboard_t hSteamLeaderboard ) = 0;
+
+ // returns the sort method of the leaderboard
+ virtual ELeaderboardSortMethod GetLeaderboardSortMethod( SteamLeaderboard_t hSteamLeaderboard ) = 0;
+
+ // returns the display type of the leaderboard
+ virtual ELeaderboardDisplayType GetLeaderboardDisplayType( SteamLeaderboard_t hSteamLeaderboard ) = 0;
+
+ // Asks the Steam back-end for a set of rows in the leaderboard.
+ // This call is asynchronous, with the result returned in LeaderboardScoresDownloaded_t
+ // LeaderboardScoresDownloaded_t will contain a handle to pull the results from GetDownloadedLeaderboardEntries() (below)
+ // You can ask for more entries than exist, and it will return as many as do exist.
+ // k_ELeaderboardDataRequestGlobal requests rows in the leaderboard from the full table, with nRangeStart & nRangeEnd in the range [1, TotalEntries]
+ // k_ELeaderboardDataRequestGlobalAroundUser requests rows around the current user, nRangeStart being negate
+ // e.g. DownloadLeaderboardEntries( hLeaderboard, k_ELeaderboardDataRequestGlobalAroundUser, -3, 3 ) will return 7 rows, 3 before the user, 3 after
+ // k_ELeaderboardDataRequestFriends requests all the rows for friends of the current user
+ CALL_RESULT( LeaderboardScoresDownloaded_t )
+ virtual SteamAPICall_t DownloadLeaderboardEntries( SteamLeaderboard_t hSteamLeaderboard, ELeaderboardDataRequest eLeaderboardDataRequest, int nRangeStart, int nRangeEnd ) = 0;
+ // as above, but downloads leaderboard entries for an arbitrary set of users - ELeaderboardDataRequest is k_ELeaderboardDataRequestUsers
+ // if a user doesn't have a leaderboard entry, they won't be included in the result
+ // a max of 100 users can be downloaded at a time, with only one outstanding call at a time
+ METHOD_DESC(Downloads leaderboard entries for an arbitrary set of users - ELeaderboardDataRequest is k_ELeaderboardDataRequestUsers)
+ CALL_RESULT( LeaderboardScoresDownloaded_t )
+ virtual SteamAPICall_t DownloadLeaderboardEntriesForUsers( SteamLeaderboard_t hSteamLeaderboard,
+ ARRAY_COUNT_D(cUsers, Array of users to retrieve) CSteamID *prgUsers, int cUsers ) = 0;
+
+ // Returns data about a single leaderboard entry
+ // use a for loop from 0 to LeaderboardScoresDownloaded_t::m_cEntryCount to get all the downloaded entries
+ // e.g.
+ // void OnLeaderboardScoresDownloaded( LeaderboardScoresDownloaded_t *pLeaderboardScoresDownloaded )
+ // {
+ // for ( int index = 0; index < pLeaderboardScoresDownloaded->m_cEntryCount; index++ )
+ // {
+ // LeaderboardEntry_t leaderboardEntry;
+ // int32 details[3]; // we know this is how many we've stored previously
+ // GetDownloadedLeaderboardEntry( pLeaderboardScoresDownloaded->m_hSteamLeaderboardEntries, index, &leaderboardEntry, details, 3 );
+ // assert( leaderboardEntry.m_cDetails == 3 );
+ // ...
+ // }
+ // once you've accessed all the entries, the data will be free'd, and the SteamLeaderboardEntries_t handle will become invalid
+ virtual bool GetDownloadedLeaderboardEntry( SteamLeaderboardEntries_t hSteamLeaderboardEntries, int index, LeaderboardEntry_t *pLeaderboardEntry, int32 *pDetails, int cDetailsMax ) = 0;
+
+ // Uploads a user score to the Steam back-end.
+ // This call is asynchronous, with the result returned in LeaderboardScoreUploaded_t
+ // Details are extra game-defined information regarding how the user got that score
+ // pScoreDetails points to an array of int32's, cScoreDetailsCount is the number of int32's in the list
+ CALL_RESULT( LeaderboardScoreUploaded_t )
+ virtual SteamAPICall_t UploadLeaderboardScore( SteamLeaderboard_t hSteamLeaderboard, ELeaderboardUploadScoreMethod eLeaderboardUploadScoreMethod, int32 nScore, const int32 *pScoreDetails, int cScoreDetailsCount ) = 0;
+
+ // Attaches a piece of user generated content the user's entry on a leaderboard.
+ // hContent is a handle to a piece of user generated content that was shared using ISteamUserRemoteStorage::FileShare().
+ // This call is asynchronous, with the result returned in LeaderboardUGCSet_t.
+ CALL_RESULT( LeaderboardUGCSet_t )
+ virtual SteamAPICall_t AttachLeaderboardUGC( SteamLeaderboard_t hSteamLeaderboard, UGCHandle_t hUGC ) = 0;
+
+ // Retrieves the number of players currently playing your game (online + offline)
+ // This call is asynchronous, with the result returned in NumberOfCurrentPlayers_t
+ CALL_RESULT( NumberOfCurrentPlayers_t )
+ virtual SteamAPICall_t GetNumberOfCurrentPlayers() = 0;
+
+ // Requests that Steam fetch data on the percentage of players who have received each achievement
+ // for the game globally.
+ // This call is asynchronous, with the result returned in GlobalAchievementPercentagesReady_t.
+ CALL_RESULT( GlobalAchievementPercentagesReady_t )
+ virtual SteamAPICall_t RequestGlobalAchievementPercentages() = 0;
+
+ // Get the info on the most achieved achievement for the game, returns an iterator index you can use to fetch
+ // the next most achieved afterwards. Will return -1 if there is no data on achievement
+ // percentages (ie, you haven't called RequestGlobalAchievementPercentages and waited on the callback).
+ virtual int GetMostAchievedAchievementInfo( char *pchName, uint32 unNameBufLen, float *pflPercent, bool *pbAchieved ) = 0;
+
+ // Get the info on the next most achieved achievement for the game. Call this after GetMostAchievedAchievementInfo or another
+ // GetNextMostAchievedAchievementInfo call passing the iterator from the previous call. Returns -1 after the last
+ // achievement has been iterated.
+ virtual int GetNextMostAchievedAchievementInfo( int iIteratorPrevious, char *pchName, uint32 unNameBufLen, float *pflPercent, bool *pbAchieved ) = 0;
+
+ // Returns the percentage of users who have achieved the specified achievement.
+ virtual bool GetAchievementAchievedPercent( const char *pchName, float *pflPercent ) = 0;
+
+ // Requests global stats data, which is available for stats marked as "aggregated".
+ // This call is asynchronous, with the results returned in GlobalStatsReceived_t.
+ // nHistoryDays specifies how many days of day-by-day history to retrieve in addition
+ // to the overall totals. The limit is 60.
+ CALL_RESULT( GlobalStatsReceived_t )
+ virtual SteamAPICall_t RequestGlobalStats( int nHistoryDays ) = 0;
+
+ // Gets the lifetime totals for an aggregated stat
+ virtual bool GetGlobalStat( const char *pchStatName, int64 *pData ) = 0;
+ virtual bool GetGlobalStat( const char *pchStatName, double *pData ) = 0;
+
+ // Gets history for an aggregated stat. pData will be filled with daily values, starting with today.
+ // So when called, pData[0] will be today, pData[1] will be yesterday, and pData[2] will be two days ago,
+ // etc. cubData is the size in bytes of the pubData buffer. Returns the number of
+ // elements actually set.
+ virtual int32 GetGlobalStatHistory( const char *pchStatName, ARRAY_COUNT(cubData) int64 *pData, uint32 cubData ) = 0;
+ virtual int32 GetGlobalStatHistory( const char *pchStatName, ARRAY_COUNT(cubData) double *pData, uint32 cubData ) = 0;
+
+#ifdef _PS3
+ // Call to kick off installation of the PS3 trophies. This call is asynchronous, and the results will be returned in a PS3TrophiesInstalled_t
+ // callback.
+ virtual bool InstallPS3Trophies() = 0;
+
+ // Returns the amount of space required at boot to install trophies. This value can be used when comparing the amount of space needed
+ // by the game to the available space value passed to the game at boot. The value is set during InstallPS3Trophies().
+ virtual uint64 GetTrophySpaceRequiredBeforeInstall() = 0;
+
+ // On PS3, user stats & achievement progress through Steam must be stored with the user's saved game data.
+ // At startup, before calling RequestCurrentStats(), you must pass the user's stats data to Steam via this method.
+ // If you do not have any user data, call this function with pvData = NULL and cubData = 0
+ virtual bool SetUserStatsData( const void *pvData, uint32 cubData ) = 0;
+
+ // Call to get the user's current stats data. You should retrieve this data after receiving successful UserStatsReceived_t & UserStatsStored_t
+ // callbacks, and store the data with the user's save game data. You can call this method with pvData = NULL and cubData = 0 to get the required
+ // buffer size.
+ virtual bool GetUserStatsData( void *pvData, uint32 cubData, uint32 *pcubWritten ) = 0;
+#endif
+};
+
+#define STEAMUSERSTATS_INTERFACE_VERSION "STEAMUSERSTATS_INTERFACE_VERSION011"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: called when the latests stats and achievements have been received
+// from the server
+//-----------------------------------------------------------------------------
+struct UserStatsReceived_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 1 };
+ uint64 m_nGameID; // Game these stats are for
+ EResult m_eResult; // Success / error fetching the stats
+ CSteamID m_steamIDUser; // The user for whom the stats are retrieved for
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: result of a request to store the user stats for a game
+//-----------------------------------------------------------------------------
+struct UserStatsStored_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 2 };
+ uint64 m_nGameID; // Game these stats are for
+ EResult m_eResult; // success / error
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: result of a request to store the achievements for a game, or an
+// "indicate progress" call. If both m_nCurProgress and m_nMaxProgress
+// are zero, that means the achievement has been fully unlocked.
+//-----------------------------------------------------------------------------
+struct UserAchievementStored_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 3 };
+
+ uint64 m_nGameID; // Game this is for
+ bool m_bGroupAchievement; // if this is a "group" achievement
+ char m_rgchAchievementName[k_cchStatNameMax]; // name of the achievement
+ uint32 m_nCurProgress; // current progress towards the achievement
+ uint32 m_nMaxProgress; // "out of" this many
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: call result for finding a leaderboard, returned as a result of FindOrCreateLeaderboard() or FindLeaderboard()
+// use CCallResult<> to map this async result to a member function
+//-----------------------------------------------------------------------------
+struct LeaderboardFindResult_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 4 };
+ SteamLeaderboard_t m_hSteamLeaderboard; // handle to the leaderboard serarched for, 0 if no leaderboard found
+ uint8 m_bLeaderboardFound; // 0 if no leaderboard found
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: call result indicating scores for a leaderboard have been downloaded and are ready to be retrieved, returned as a result of DownloadLeaderboardEntries()
+// use CCallResult<> to map this async result to a member function
+//-----------------------------------------------------------------------------
+struct LeaderboardScoresDownloaded_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 5 };
+ SteamLeaderboard_t m_hSteamLeaderboard;
+ SteamLeaderboardEntries_t m_hSteamLeaderboardEntries; // the handle to pass into GetDownloadedLeaderboardEntries()
+ int m_cEntryCount; // the number of entries downloaded
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: call result indicating scores has been uploaded, returned as a result of UploadLeaderboardScore()
+// use CCallResult<> to map this async result to a member function
+//-----------------------------------------------------------------------------
+struct LeaderboardScoreUploaded_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 6 };
+ uint8 m_bSuccess; // 1 if the call was successful
+ SteamLeaderboard_t m_hSteamLeaderboard; // the leaderboard handle that was
+ int32 m_nScore; // the score that was attempted to set
+ uint8 m_bScoreChanged; // true if the score in the leaderboard change, false if the existing score was better
+ int m_nGlobalRankNew; // the new global rank of the user in this leaderboard
+ int m_nGlobalRankPrevious; // the previous global rank of the user in this leaderboard; 0 if the user had no existing entry in the leaderboard
+};
+
+struct NumberOfCurrentPlayers_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 7 };
+ uint8 m_bSuccess; // 1 if the call was successful
+ int32 m_cPlayers; // Number of players currently playing
+};
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback indicating that a user's stats have been unloaded.
+// Call RequestUserStats again to access stats for this user
+//-----------------------------------------------------------------------------
+struct UserStatsUnloaded_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 8 };
+ CSteamID m_steamIDUser; // User whose stats have been unloaded
+};
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback indicating that an achievement icon has been fetched
+//-----------------------------------------------------------------------------
+struct UserAchievementIconFetched_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 9 };
+
+ CGameID m_nGameID; // Game this is for
+ char m_rgchAchievementName[k_cchStatNameMax]; // name of the achievement
+ bool m_bAchieved; // Is the icon for the achieved or not achieved version?
+ int m_nIconHandle; // Handle to the image, which can be used in SteamUtils()->GetImageRGBA(), 0 means no image is set for the achievement
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Callback indicating that global achievement percentages are fetched
+//-----------------------------------------------------------------------------
+struct GlobalAchievementPercentagesReady_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 10 };
+
+ uint64 m_nGameID; // Game this is for
+ EResult m_eResult; // Result of the operation
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: call result indicating UGC has been uploaded, returned as a result of SetLeaderboardUGC()
+//-----------------------------------------------------------------------------
+struct LeaderboardUGCSet_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 11 };
+ EResult m_eResult; // The result of the operation
+ SteamLeaderboard_t m_hSteamLeaderboard; // the leaderboard handle that was
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: callback indicating that PS3 trophies have been installed
+//-----------------------------------------------------------------------------
+struct PS3TrophiesInstalled_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 12 };
+ uint64 m_nGameID; // Game these stats are for
+ EResult m_eResult; // The result of the operation
+ uint64 m_ulRequiredDiskSpace; // If m_eResult is k_EResultDiskFull, will contain the amount of space needed to install trophies
+
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: callback indicating global stats have been received.
+// Returned as a result of RequestGlobalStats()
+//-----------------------------------------------------------------------------
+struct GlobalStatsReceived_t
+{
+ enum { k_iCallback = k_iSteamUserStatsCallbacks + 12 };
+ uint64 m_nGameID; // Game global stats were requested for
+ EResult m_eResult; // The result of the request
+};
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMUSER_H
diff --git a/dep/steam_api/isteamutils.h b/dep/steam_api/isteamutils.h
new file mode 100644
index 0000000..e331fa6
--- /dev/null
+++ b/dep/steam_api/isteamutils.h
@@ -0,0 +1,264 @@
+//====== Copyright � 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to utility functions in Steam
+//
+//=============================================================================
+
+#ifndef ISTEAMUTILS_H
+#define ISTEAMUTILS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+
+// Steam API call failure results
+enum ESteamAPICallFailure
+{
+ k_ESteamAPICallFailureNone = -1, // no failure
+ k_ESteamAPICallFailureSteamGone = 0, // the local Steam process has gone away
+ k_ESteamAPICallFailureNetworkFailure = 1, // the network connection to Steam has been broken, or was already broken
+ // SteamServersDisconnected_t callback will be sent around the same time
+ // SteamServersConnected_t will be sent when the client is able to talk to the Steam servers again
+ k_ESteamAPICallFailureInvalidHandle = 2, // the SteamAPICall_t handle passed in no longer exists
+ k_ESteamAPICallFailureMismatchedCallback = 3,// GetAPICallResult() was called with the wrong callback type for this API call
+};
+
+
+// Input modes for the Big Picture gamepad text entry
+enum EGamepadTextInputMode
+{
+ k_EGamepadTextInputModeNormal = 0,
+ k_EGamepadTextInputModePassword = 1
+};
+
+
+// Controls number of allowed lines for the Big Picture gamepad text entry
+enum EGamepadTextInputLineMode
+{
+ k_EGamepadTextInputLineModeSingleLine = 0,
+ k_EGamepadTextInputLineModeMultipleLines = 1
+};
+
+
+// function prototype for warning message hook
+#if defined( POSIX )
+#define __cdecl
+#endif
+extern "C" typedef void (__cdecl *SteamAPIWarningMessageHook_t)(int, const char *);
+
+//-----------------------------------------------------------------------------
+// Purpose: interface to user independent utility functions
+//-----------------------------------------------------------------------------
+class ISteamUtils
+{
+public:
+ // return the number of seconds since the user
+ virtual uint32 GetSecondsSinceAppActive() = 0;
+ virtual uint32 GetSecondsSinceComputerActive() = 0;
+
+ // the universe this client is connecting to
+ virtual EUniverse GetConnectedUniverse() = 0;
+
+ // Steam server time. Number of seconds since January 1, 1970, GMT (i.e unix time)
+ virtual uint32 GetServerRealTime() = 0;
+
+ // returns the 2 digit ISO 3166-1-alpha-2 format country code this client is running in (as looked up via an IP-to-location database)
+ // e.g "US" or "UK".
+ virtual const char *GetIPCountry() = 0;
+
+ // returns true if the image exists, and valid sizes were filled out
+ virtual bool GetImageSize( int iImage, uint32 *pnWidth, uint32 *pnHeight ) = 0;
+
+ // returns true if the image exists, and the buffer was successfully filled out
+ // results are returned in RGBA format
+ // the destination buffer size should be 4 * height * width * sizeof(char)
+ virtual bool GetImageRGBA( int iImage, uint8 *pubDest, int nDestBufferSize ) = 0;
+
+ // returns the IP of the reporting server for valve - currently only used in Source engine games
+ virtual bool GetCSERIPPort( uint32 *unIP, uint16 *usPort ) = 0;
+
+ // return the amount of battery power left in the current system in % [0..100], 255 for being on AC power
+ virtual uint8 GetCurrentBatteryPower() = 0;
+
+ // returns the appID of the current process
+ virtual uint32 GetAppID() = 0;
+
+ // Sets the position where the overlay instance for the currently calling game should show notifications.
+ // This position is per-game and if this function is called from outside of a game context it will do nothing.
+ virtual void SetOverlayNotificationPosition( ENotificationPosition eNotificationPosition ) = 0;
+
+ // API asynchronous call results
+ // can be used directly, but more commonly used via the callback dispatch API (see steam_api.h)
+ virtual bool IsAPICallCompleted( SteamAPICall_t hSteamAPICall, bool *pbFailed ) = 0;
+ virtual ESteamAPICallFailure GetAPICallFailureReason( SteamAPICall_t hSteamAPICall ) = 0;
+ virtual bool GetAPICallResult( SteamAPICall_t hSteamAPICall, void *pCallback, int cubCallback, int iCallbackExpected, bool *pbFailed ) = 0;
+
+ // Deprecated. Applications should use SteamAPI_RunCallbacks() instead. Game servers do not need to call this function.
+ STEAM_PRIVATE_API( virtual void RunFrame() = 0; )
+
+ // returns the number of IPC calls made since the last time this function was called
+ // Used for perf debugging so you can understand how many IPC calls your game makes per frame
+ // Every IPC call is at minimum a thread context switch if not a process one so you want to rate
+ // control how often you do them.
+ virtual uint32 GetIPCCallCount() = 0;
+
+ // API warning handling
+ // 'int' is the severity; 0 for msg, 1 for warning
+ // 'const char *' is the text of the message
+ // callbacks will occur directly after the API function is called that generated the warning or message
+ virtual void SetWarningMessageHook( SteamAPIWarningMessageHook_t pFunction ) = 0;
+
+ // Returns true if the overlay is running & the user can access it. The overlay process could take a few seconds to
+ // start & hook the game process, so this function will initially return false while the overlay is loading.
+ virtual bool IsOverlayEnabled() = 0;
+
+ // Normally this call is unneeded if your game has a constantly running frame loop that calls the
+ // D3D Present API, or OGL SwapBuffers API every frame.
+ //
+ // However, if you have a game that only refreshes the screen on an event driven basis then that can break
+ // the overlay, as it uses your Present/SwapBuffers calls to drive it's internal frame loop and it may also
+ // need to Present() to the screen any time an even needing a notification happens or when the overlay is
+ // brought up over the game by a user. You can use this API to ask the overlay if it currently need a present
+ // in that case, and then you can check for this periodically (roughly 33hz is desirable) and make sure you
+ // refresh the screen with Present or SwapBuffers to allow the overlay to do it's work.
+ virtual bool BOverlayNeedsPresent() = 0;
+
+ // Asynchronous call to check if an executable file has been signed using the public key set on the signing tab
+ // of the partner site, for example to refuse to load modified executable files.
+ // The result is returned in CheckFileSignature_t.
+ // k_ECheckFileSignatureNoSignaturesFoundForThisApp - This app has not been configured on the signing tab of the partner site to enable this function.
+ // k_ECheckFileSignatureNoSignaturesFoundForThisFile - This file is not listed on the signing tab for the partner site.
+ // k_ECheckFileSignatureFileNotFound - The file does not exist on disk.
+ // k_ECheckFileSignatureInvalidSignature - The file exists, and the signing tab has been set for this file, but the file is either not signed or the signature does not match.
+ // k_ECheckFileSignatureValidSignature - The file is signed and the signature is valid.
+ CALL_RESULT( CheckFileSignature_t )
+ virtual SteamAPICall_t CheckFileSignature( const char *szFileName ) = 0;
+
+ // Activates the Big Picture text input dialog which only supports gamepad input
+ virtual bool ShowGamepadTextInput( EGamepadTextInputMode eInputMode, EGamepadTextInputLineMode eLineInputMode, const char *pchDescription, uint32 unCharMax, const char *pchExistingText ) = 0;
+
+ // Returns previously entered text & length
+ virtual uint32 GetEnteredGamepadTextLength() = 0;
+ virtual bool GetEnteredGamepadTextInput( char *pchText, uint32 cchText ) = 0;
+
+ // returns the language the steam client is running in, you probably want ISteamApps::GetCurrentGameLanguage instead, this is for very special usage cases
+ virtual const char *GetSteamUILanguage() = 0;
+
+ // returns true if Steam itself is running in VR mode
+ virtual bool IsSteamRunningInVR() = 0;
+
+ // Sets the inset of the overlay notification from the corner specified by SetOverlayNotificationPosition.
+ virtual void SetOverlayNotificationInset( int nHorizontalInset, int nVerticalInset ) = 0;
+
+ // returns true if Steam & the Steam Overlay are running in Big Picture mode
+ // Games much be launched through the Steam client to enable the Big Picture overlay. During development,
+ // a game can be added as a non-steam game to the developers library to test this feature
+ virtual bool IsSteamInBigPictureMode() = 0;
+
+ // ask SteamUI to create and render its OpenVR dashboard
+ virtual void StartVRDashboard() = 0;
+
+ // Returns true if the HMD content will be streamed via Steam In-Home Streaming
+ virtual bool IsVRHeadsetStreamingEnabled() = 0;
+
+ // Set whether the HMD content will be streamed via Steam In-Home Streaming
+ // If this is set to true, then the scene in the HMD headset will be streamed, and remote input will not be allowed.
+ // If this is set to false, then the application window will be streamed instead, and remote input will be allowed.
+ // The default is true unless "VRHeadsetStreaming" "0" is in the extended appinfo for a game.
+ // (this is useful for games that have asymmetric multiplayer gameplay)
+ virtual void SetVRHeadsetStreamingEnabled( bool bEnabled ) = 0;
+};
+
+#define STEAMUTILS_INTERFACE_VERSION "SteamUtils009"
+
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+//-----------------------------------------------------------------------------
+// Purpose: The country of the user changed
+//-----------------------------------------------------------------------------
+struct IPCountry_t
+{
+ enum { k_iCallback = k_iSteamUtilsCallbacks + 1 };
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Fired when running on a laptop and less than 10 minutes of battery is left, fires then every minute
+//-----------------------------------------------------------------------------
+struct LowBatteryPower_t
+{
+ enum { k_iCallback = k_iSteamUtilsCallbacks + 2 };
+ uint8 m_nMinutesBatteryLeft;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: called when a SteamAsyncCall_t has completed (or failed)
+//-----------------------------------------------------------------------------
+struct SteamAPICallCompleted_t
+{
+ enum { k_iCallback = k_iSteamUtilsCallbacks + 3 };
+ SteamAPICall_t m_hAsyncCall;
+ int m_iCallback;
+ uint32 m_cubParam;
+};
+
+
+//-----------------------------------------------------------------------------
+// called when Steam wants to shutdown
+//-----------------------------------------------------------------------------
+struct SteamShutdown_t
+{
+ enum { k_iCallback = k_iSteamUtilsCallbacks + 4 };
+};
+
+//-----------------------------------------------------------------------------
+// results for CheckFileSignature
+//-----------------------------------------------------------------------------
+enum ECheckFileSignature
+{
+ k_ECheckFileSignatureInvalidSignature = 0,
+ k_ECheckFileSignatureValidSignature = 1,
+ k_ECheckFileSignatureFileNotFound = 2,
+ k_ECheckFileSignatureNoSignaturesFoundForThisApp = 3,
+ k_ECheckFileSignatureNoSignaturesFoundForThisFile = 4,
+};
+
+//-----------------------------------------------------------------------------
+// callback for CheckFileSignature
+//-----------------------------------------------------------------------------
+struct CheckFileSignature_t
+{
+ enum { k_iCallback = k_iSteamUtilsCallbacks + 5 };
+ ECheckFileSignature m_eCheckFileSignature;
+};
+
+
+// k_iSteamUtilsCallbacks + 13 is taken
+
+
+//-----------------------------------------------------------------------------
+// Big Picture gamepad text input has been closed
+//-----------------------------------------------------------------------------
+struct GamepadTextInputDismissed_t
+{
+ enum { k_iCallback = k_iSteamUtilsCallbacks + 14 };
+ bool m_bSubmitted; // true if user entered & accepted text (Call ISteamUtils::GetEnteredGamepadTextInput() for text), false if canceled input
+ uint32 m_unSubmittedText;
+};
+
+// k_iSteamUtilsCallbacks + 15 is taken
+
+#pragma pack( pop )
+
+#endif // ISTEAMUTILS_H
diff --git a/dep/steam_api/isteamvideo.h b/dep/steam_api/isteamvideo.h
new file mode 100644
index 0000000..32eeb59
--- /dev/null
+++ b/dep/steam_api/isteamvideo.h
@@ -0,0 +1,71 @@
+//====== Copyright 1996-2014 Valve Corporation, All rights reserved. =======
+//
+// Purpose: interface to Steam Video
+//
+//=============================================================================
+
+#ifndef ISTEAMVIDEO_H
+#define ISTEAMVIDEO_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+
+// callbacks
+#if defined( VALVE_CALLBACK_PACK_SMALL )
+#pragma pack( push, 4 )
+#elif defined( VALVE_CALLBACK_PACK_LARGE )
+#pragma pack( push, 8 )
+#else
+#error isteamclient.h must be included
+#endif
+
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Steam Video API
+//-----------------------------------------------------------------------------
+class ISteamVideo
+{
+public:
+
+ // Get a URL suitable for streaming the given Video app ID's video
+ virtual void GetVideoURL( AppId_t unVideoAppID ) = 0;
+
+ // returns true if user is uploading a live broadcast
+ virtual bool IsBroadcasting( int *pnNumViewers ) = 0;
+
+ // Get the OPF Details for 360 Video Playback
+ CALL_BACK( GetOPFSettingsResult_t )
+ virtual void GetOPFSettings( AppId_t unVideoAppID ) = 0;
+ virtual bool GetOPFStringForApp( AppId_t unVideoAppID, char *pchBuffer, int32 *pnBufferSize ) = 0;
+};
+
+#define STEAMVIDEO_INTERFACE_VERSION "STEAMVIDEO_INTERFACE_V002"
+
+DEFINE_CALLBACK( BroadcastUploadStart_t, k_iClientVideoCallbacks + 4 )
+END_DEFINE_CALLBACK_0()
+
+DEFINE_CALLBACK( BroadcastUploadStop_t, k_iClientVideoCallbacks + 5 )
+ CALLBACK_MEMBER( 0, EBroadcastUploadResult, m_eResult )
+END_DEFINE_CALLBACK_1()
+
+DEFINE_CALLBACK( GetVideoURLResult_t, k_iClientVideoCallbacks + 11 )
+ CALLBACK_MEMBER( 0, EResult, m_eResult )
+ CALLBACK_MEMBER( 1, AppId_t, m_unVideoAppID )
+ CALLBACK_MEMBER( 2, char, m_rgchURL[256] )
+END_DEFINE_CALLBACK_3()
+
+
+DEFINE_CALLBACK( GetOPFSettingsResult_t, k_iClientVideoCallbacks + 24 )
+ CALLBACK_MEMBER( 0, EResult, m_eResult )
+ CALLBACK_MEMBER( 1, AppId_t, m_unVideoAppID )
+END_DEFINE_CALLBACK_2()
+
+
+#pragma pack( pop )
+
+
+#endif // ISTEAMVIDEO_H
diff --git a/dep/steam_api/matchmakingtypes.h b/dep/steam_api/matchmakingtypes.h
new file mode 100644
index 0000000..e52cfc6
--- /dev/null
+++ b/dep/steam_api/matchmakingtypes.h
@@ -0,0 +1,251 @@
+//========= Copyright � 1996-2008, Valve LLC, All rights reserved. ============
+//
+// Purpose:
+//
+// $NoKeywords: $
+//=============================================================================
+
+#ifndef MATCHMAKINGTYPES_H
+#define MATCHMAKINGTYPES_H
+
+#ifdef _WIN32
+#pragma once
+#endif
+
+#ifdef POSIX
+#ifndef _snprintf
+#define _snprintf snprintf
+#endif
+#endif
+
+#include
+#include
+
+//
+// Max size (in bytes of UTF-8 data, not in characters) of server fields, including null terminator.
+// WARNING: These cannot be changed easily, without breaking clients using old interfaces.
+//
+const int k_cbMaxGameServerGameDir = 32;
+const int k_cbMaxGameServerMapName = 32;
+const int k_cbMaxGameServerGameDescription = 64;
+const int k_cbMaxGameServerName = 64;
+const int k_cbMaxGameServerTags = 128;
+const int k_cbMaxGameServerGameData = 2048;
+
+/// Store key/value pair used in matchmaking queries.
+///
+/// Actually, the name Key/Value is a bit misleading. The "key" is better
+/// understood as "filter operation code" and the "value" is the operand to this
+/// filter operation. The meaning of the operand depends upon the filter.
+struct MatchMakingKeyValuePair_t
+{
+ MatchMakingKeyValuePair_t() { m_szKey[0] = m_szValue[0] = 0; }
+ MatchMakingKeyValuePair_t( const char *pchKey, const char *pchValue )
+ {
+ strncpy( m_szKey, pchKey, sizeof(m_szKey) ); // this is a public header, use basic c library string funcs only!
+ m_szKey[ sizeof( m_szKey ) - 1 ] = '\0';
+ strncpy( m_szValue, pchValue, sizeof(m_szValue) );
+ m_szValue[ sizeof( m_szValue ) - 1 ] = '\0';
+ }
+ char m_szKey[ 256 ];
+ char m_szValue[ 256 ];
+};
+
+
+enum EMatchMakingServerResponse
+{
+ eServerResponded = 0,
+ eServerFailedToRespond,
+ eNoServersListedOnMasterServer // for the Internet query type, returned in response callback if no servers of this type match
+};
+
+// servernetadr_t is all the addressing info the serverbrowser needs to know about a game server,
+// namely: its IP, its connection port, and its query port.
+class servernetadr_t
+{
+public:
+
+ servernetadr_t() : m_usConnectionPort( 0 ), m_usQueryPort( 0 ), m_unIP( 0 ) {}
+
+ void Init( unsigned int ip, uint16 usQueryPort, uint16 usConnectionPort );
+#ifdef NETADR_H
+ netadr_t GetIPAndQueryPort();
+#endif
+
+ // Access the query port.
+ uint16 GetQueryPort() const;
+ void SetQueryPort( uint16 usPort );
+
+ // Access the connection port.
+ uint16 GetConnectionPort() const;
+ void SetConnectionPort( uint16 usPort );
+
+ // Access the IP
+ uint32 GetIP() const;
+ void SetIP( uint32 );
+
+ // This gets the 'a.b.c.d:port' string with the connection port (instead of the query port).
+ const char *GetConnectionAddressString() const;
+ const char *GetQueryAddressString() const;
+
+ // Comparison operators and functions.
+ bool operator<(const servernetadr_t &netadr) const;
+ void operator=( const servernetadr_t &that )
+ {
+ m_usConnectionPort = that.m_usConnectionPort;
+ m_usQueryPort = that.m_usQueryPort;
+ m_unIP = that.m_unIP;
+ }
+
+
+private:
+ const char *ToString( uint32 unIP, uint16 usPort ) const;
+ uint16 m_usConnectionPort; // (in HOST byte order)
+ uint16 m_usQueryPort;
+ uint32 m_unIP;
+};
+
+
+inline void servernetadr_t::Init( unsigned int ip, uint16 usQueryPort, uint16 usConnectionPort )
+{
+ m_unIP = ip;
+ m_usQueryPort = usQueryPort;
+ m_usConnectionPort = usConnectionPort;
+}
+
+#ifdef NETADR_H
+inline netadr_t servernetadr_t::GetIPAndQueryPort()
+{
+ return netadr_t( m_unIP, m_usQueryPort );
+}
+#endif
+
+inline uint16 servernetadr_t::GetQueryPort() const
+{
+ return m_usQueryPort;
+}
+
+inline void servernetadr_t::SetQueryPort( uint16 usPort )
+{
+ m_usQueryPort = usPort;
+}
+
+inline uint16 servernetadr_t::GetConnectionPort() const
+{
+ return m_usConnectionPort;
+}
+
+inline void servernetadr_t::SetConnectionPort( uint16 usPort )
+{
+ m_usConnectionPort = usPort;
+}
+
+inline uint32 servernetadr_t::GetIP() const
+{
+ return m_unIP;
+}
+
+inline void servernetadr_t::SetIP( uint32 unIP )
+{
+ m_unIP = unIP;
+}
+
+inline const char *servernetadr_t::ToString( uint32 unIP, uint16 usPort ) const
+{
+ static char s[4][64];
+ static int nBuf = 0;
+ unsigned char *ipByte = (unsigned char *)&unIP;
+#ifdef VALVE_BIG_ENDIAN
+ _snprintf (s[nBuf], sizeof( s[nBuf] ), "%u.%u.%u.%u:%i", (int)(ipByte[0]), (int)(ipByte[1]), (int)(ipByte[2]), (int)(ipByte[3]), usPort );
+#else
+ _snprintf (s[nBuf], sizeof( s[nBuf] ), "%u.%u.%u.%u:%i", (int)(ipByte[3]), (int)(ipByte[2]), (int)(ipByte[1]), (int)(ipByte[0]), usPort );
+#endif
+ const char *pchRet = s[nBuf];
+ ++nBuf;
+ nBuf %= ( (sizeof(s)/sizeof(s[0])) );
+ return pchRet;
+}
+
+inline const char* servernetadr_t::GetConnectionAddressString() const
+{
+ return ToString( m_unIP, m_usConnectionPort );
+}
+
+inline const char* servernetadr_t::GetQueryAddressString() const
+{
+ return ToString( m_unIP, m_usQueryPort );
+}
+
+inline bool servernetadr_t::operator<(const servernetadr_t &netadr) const
+{
+ return ( m_unIP < netadr.m_unIP ) || ( m_unIP == netadr.m_unIP && m_usQueryPort < netadr.m_usQueryPort );
+}
+
+//-----------------------------------------------------------------------------
+// Purpose: Data describing a single server
+//-----------------------------------------------------------------------------
+class gameserveritem_t
+{
+public:
+ gameserveritem_t();
+
+ const char* GetName() const;
+ void SetName( const char *pName );
+
+public:
+ servernetadr_t m_NetAdr; ///< IP/Query Port/Connection Port for this server
+ int m_nPing; ///< current ping time in milliseconds
+ bool m_bHadSuccessfulResponse; ///< server has responded successfully in the past
+ bool m_bDoNotRefresh; ///< server is marked as not responding and should no longer be refreshed
+ char m_szGameDir[k_cbMaxGameServerGameDir]; ///< current game directory
+ char m_szMap[k_cbMaxGameServerMapName]; ///< current map
+ char m_szGameDescription[k_cbMaxGameServerGameDescription]; ///< game description
+ uint32 m_nAppID; ///< Steam App ID of this server
+ int m_nPlayers; ///< total number of players currently on the server. INCLUDES BOTS!!
+ int m_nMaxPlayers; ///< Maximum players that can join this server
+ int m_nBotPlayers; ///< Number of bots (i.e simulated players) on this server
+ bool m_bPassword; ///< true if this server needs a password to join
+ bool m_bSecure; ///< Is this server protected by VAC
+ uint32 m_ulTimeLastPlayed; ///< time (in unix time) when this server was last played on (for favorite/history servers)
+ int m_nServerVersion; ///< server version as reported to Steam
+
+private:
+
+ /// Game server name
+ char m_szServerName[k_cbMaxGameServerName];
+
+ // For data added after SteamMatchMaking001 add it here
+public:
+ /// the tags this server exposes
+ char m_szGameTags[k_cbMaxGameServerTags];
+
+ /// steamID of the game server - invalid if it's doesn't have one (old server, or not connected to Steam)
+ CSteamID m_steamID;
+};
+
+
+inline gameserveritem_t::gameserveritem_t()
+{
+ m_szGameDir[0] = m_szMap[0] = m_szGameDescription[0] = m_szServerName[0] = 0;
+ m_bHadSuccessfulResponse = m_bDoNotRefresh = m_bPassword = m_bSecure = false;
+ m_nPing = m_nAppID = m_nPlayers = m_nMaxPlayers = m_nBotPlayers = m_ulTimeLastPlayed = m_nServerVersion = 0;
+ m_szGameTags[0] = 0;
+}
+
+inline const char* gameserveritem_t::GetName() const
+{
+ // Use the IP address as the name if nothing is set yet.
+ if ( m_szServerName[0] == 0 )
+ return m_NetAdr.GetConnectionAddressString();
+ else
+ return m_szServerName;
+}
+
+inline void gameserveritem_t::SetName( const char *pName )
+{
+ strncpy( m_szServerName, pName, sizeof( m_szServerName ) );
+ m_szServerName[ sizeof( m_szServerName ) - 1 ] = '\0';
+}
+
+
+#endif // MATCHMAKINGTYPES_H
diff --git a/dep/steam_api/steam_api.h b/dep/steam_api/steam_api.h
new file mode 100644
index 0000000..e3a31ae
--- /dev/null
+++ b/dep/steam_api/steam_api.h
@@ -0,0 +1,394 @@
+//====== Copyright 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose:
+//
+//=============================================================================
+
+#ifndef STEAM_API_H
+#define STEAM_API_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "isteamclient.h"
+#include "isteamuser.h"
+#include "isteamfriends.h"
+#include "isteamutils.h"
+#include "isteammatchmaking.h"
+#include "isteamuserstats.h"
+#include "isteamapps.h"
+#include "isteamnetworking.h"
+#include "isteamremotestorage.h"
+#include "isteamscreenshots.h"
+#include "isteammusic.h"
+#include "isteammusicremote.h"
+#include "isteamhttp.h"
+#include "isteamunifiedmessages.h"
+#include "isteamcontroller.h"
+#include "isteamugc.h"
+#include "isteamapplist.h"
+#include "isteamhtmlsurface.h"
+#include "isteaminventory.h"
+#include "isteamvideo.h"
+
+
+// Steam API export macro
+#if defined( _WIN32 ) && !defined( _X360 )
+ #if defined( STEAM_API_EXPORTS )
+ #define S_API extern "C" __declspec( dllexport )
+ #elif defined( STEAM_API_NODLL )
+ #define S_API extern "C"
+ #else
+ #define S_API extern "C" __declspec( dllimport )
+ #endif // STEAM_API_EXPORTS
+#elif defined( GNUC )
+ #if defined( STEAM_API_EXPORTS )
+ #define S_API extern "C" __attribute__ ((visibility("default")))
+ #else
+ #define S_API extern "C"
+ #endif // STEAM_API_EXPORTS
+#else // !WIN32
+ #if defined( STEAM_API_EXPORTS )
+ #define S_API extern "C"
+ #else
+ #define S_API extern "C"
+ #endif // STEAM_API_EXPORTS
+#endif
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// Steam API setup & shutdown
+//
+// These functions manage loading, initializing and shutdown of the steamclient.dll
+//
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+
+
+// SteamAPI_Init must be called before using any other API functions. If it fails, an
+// error message will be output to the debugger (or stderr) with further information.
+S_API bool S_CALLTYPE SteamAPI_Init();
+
+// SteamAPI_Shutdown should be called during process shutdown if possible.
+S_API void S_CALLTYPE SteamAPI_Shutdown();
+
+// SteamAPI_RestartAppIfNecessary ensures that your executable was launched through Steam.
+//
+// Returns true if the current process should terminate. Steam is now re-launching your application.
+//
+// Returns false if no action needs to be taken. This means that your executable was started through
+// the Steam client, or a steam_appid.txt file is present in your game's directory (for development).
+// Your current process should continue if false is returned.
+//
+// NOTE: If you use the Steam DRM wrapper on your primary executable file, this check is unnecessary
+// since the DRM wrapper will ensure that your application was launched properly through Steam.
+S_API bool S_CALLTYPE SteamAPI_RestartAppIfNecessary( uint32 unOwnAppID );
+
+// Many Steam API functions allocate a small amount of thread-local memory for parameter storage.
+// SteamAPI_ReleaseCurrentThreadMemory() will free API memory associated with the calling thread.
+// This function is also called automatically by SteamAPI_RunCallbacks(), so a single-threaded
+// program never needs to explicitly call this function.
+S_API void S_CALLTYPE SteamAPI_ReleaseCurrentThreadMemory();
+
+
+// crash dump recording functions
+S_API void S_CALLTYPE SteamAPI_WriteMiniDump( uint32 uStructuredExceptionCode, void* pvExceptionInfo, uint32 uBuildID );
+S_API void S_CALLTYPE SteamAPI_SetMiniDumpComment( const char *pchMsg );
+
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// Global accessors for Steamworks C++ APIs. See individual isteam*.h files for details.
+// You should not cache the results of these accessors or pass the result pointers across
+// modules! Different modules may be compiled against different SDK header versions, and
+// the interface pointers could therefore be different across modules. Every line of code
+// which calls into a Steamworks API should retrieve the interface from a global accessor.
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+#if !defined( STEAM_API_EXPORTS )
+inline ISteamClient *SteamClient();
+inline ISteamUser *SteamUser();
+inline ISteamFriends *SteamFriends();
+inline ISteamUtils *SteamUtils();
+inline ISteamMatchmaking *SteamMatchmaking();
+inline ISteamUserStats *SteamUserStats();
+inline ISteamApps *SteamApps();
+inline ISteamNetworking *SteamNetworking();
+inline ISteamMatchmakingServers *SteamMatchmakingServers();
+inline ISteamRemoteStorage *SteamRemoteStorage();
+inline ISteamScreenshots *SteamScreenshots();
+inline ISteamHTTP *SteamHTTP();
+inline ISteamUnifiedMessages *SteamUnifiedMessages();
+inline ISteamController *SteamController();
+inline ISteamUGC *SteamUGC();
+inline ISteamAppList *SteamAppList();
+inline ISteamMusic *SteamMusic();
+inline ISteamMusicRemote *SteamMusicRemote();
+inline ISteamHTMLSurface *SteamHTMLSurface();
+inline ISteamInventory *SteamInventory();
+inline ISteamVideo *SteamVideo();
+#endif // VERSION_SAFE_STEAM_API_INTERFACES
+
+
+// CSteamAPIContext encapsulates the Steamworks API global accessors into
+// a single object. This is DEPRECATED and only remains for compatibility.
+class CSteamAPIContext
+{
+public:
+ // DEPRECATED - there is no benefit to using this over the global accessors
+ CSteamAPIContext() { Clear(); }
+ void Clear();
+ bool Init();
+ ISteamClient* SteamClient() const { return m_pSteamClient; }
+ ISteamUser* SteamUser() const { return m_pSteamUser; }
+ ISteamFriends* SteamFriends() const { return m_pSteamFriends; }
+ ISteamUtils* SteamUtils() const { return m_pSteamUtils; }
+ ISteamMatchmaking* SteamMatchmaking() const { return m_pSteamMatchmaking; }
+ ISteamUserStats* SteamUserStats() const { return m_pSteamUserStats; }
+ ISteamApps* SteamApps() const { return m_pSteamApps; }
+ ISteamMatchmakingServers* SteamMatchmakingServers() const { return m_pSteamMatchmakingServers; }
+ ISteamNetworking* SteamNetworking() const { return m_pSteamNetworking; }
+ ISteamRemoteStorage* SteamRemoteStorage() const { return m_pSteamRemoteStorage; }
+ ISteamScreenshots* SteamScreenshots() const { return m_pSteamScreenshots; }
+ ISteamHTTP* SteamHTTP() const { return m_pSteamHTTP; }
+ ISteamUnifiedMessages* SteamUnifiedMessages() const { return m_pSteamUnifiedMessages; }
+ ISteamController* SteamController() const { return m_pController; }
+ ISteamUGC* SteamUGC() const { return m_pSteamUGC; }
+ ISteamAppList* SteamAppList() const { return m_pSteamAppList; }
+ ISteamMusic* SteamMusic() const { return m_pSteamMusic; }
+ ISteamMusicRemote* SteamMusicRemote() const { return m_pSteamMusicRemote; }
+ ISteamHTMLSurface* SteamHTMLSurface() const { return m_pSteamHTMLSurface; }
+ ISteamInventory* SteamInventory() const { return m_pSteamInventory; }
+ ISteamVideo* SteamVideo() const { return m_pSteamVideo; }
+ // DEPRECATED - there is no benefit to using this over the global accessors
+private:
+ ISteamClient *m_pSteamClient;
+ ISteamUser *m_pSteamUser;
+ ISteamFriends *m_pSteamFriends;
+ ISteamUtils *m_pSteamUtils;
+ ISteamMatchmaking *m_pSteamMatchmaking;
+ ISteamUserStats *m_pSteamUserStats;
+ ISteamApps *m_pSteamApps;
+ ISteamMatchmakingServers *m_pSteamMatchmakingServers;
+ ISteamNetworking *m_pSteamNetworking;
+ ISteamRemoteStorage *m_pSteamRemoteStorage;
+ ISteamScreenshots *m_pSteamScreenshots;
+ ISteamHTTP *m_pSteamHTTP;
+ ISteamUnifiedMessages *m_pSteamUnifiedMessages;
+ ISteamController *m_pController;
+ ISteamUGC *m_pSteamUGC;
+ ISteamAppList *m_pSteamAppList;
+ ISteamMusic *m_pSteamMusic;
+ ISteamMusicRemote *m_pSteamMusicRemote;
+ ISteamHTMLSurface *m_pSteamHTMLSurface;
+ ISteamInventory *m_pSteamInventory;
+ ISteamVideo *m_pSteamVideo;
+};
+
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// steam callback and call-result helpers
+//
+// The following macros and classes are used to register your application for
+// callbacks and call-results, which are delivered in a predictable manner.
+//
+// STEAM_CALLBACK macros are meant for use inside of a C++ class definition.
+// They map a Steam notification callback directly to a class member function
+// which is automatically prototyped as "void func( callback_type *pParam )".
+//
+// CCallResult is used with specific Steam APIs that return "result handles".
+// The handle can be passed to a CCallResult object's Set function, along with
+// an object pointer and member-function pointer. The member function will
+// be executed once the results of the Steam API call are available.
+//
+// CCallback and CCallbackManual classes can be used instead of STEAM_CALLBACK
+// macros if you require finer control over registration and unregistration.
+//
+// Callbacks and call-results are queued automatically and are only
+// delivered/executed when your application calls SteamAPI_RunCallbacks().
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+
+// SteamAPI_RunCallbacks is safe to call from multiple threads simultaneously,
+// but if you choose to do this, callback code could be executed on any thread.
+// One alternative is to call SteamAPI_RunCallbacks from the main thread only,
+// and call SteamAPI_ReleaseCurrentThreadMemory regularly on other threads.
+S_API void S_CALLTYPE SteamAPI_RunCallbacks();
+
+
+// Declares a callback member function plus a helper member variable which
+// registers the callback on object creation and unregisters on destruction.
+// The optional fourth 'var' param exists only for backwards-compatibility
+// and can be ignored.
+#define STEAM_CALLBACK( thisclass, func, .../*callback_type, [deprecated] var*/ ) \
+ _STEAM_CALLBACK_SELECT( ( __VA_ARGS__, 4, 3 ), ( /**/, thisclass, func, __VA_ARGS__ ) )
+
+// Declares a callback function and a named CCallbackManual variable which
+// has Register and Unregister functions instead of automatic registration.
+#define STEAM_CALLBACK_MANUAL( thisclass, func, callback_type, var ) \
+ CCallbackManual< thisclass, callback_type > var; void func( callback_type *pParam )
+
+
+// Internal functions used by the utility CCallback objects to receive callbacks
+S_API void S_CALLTYPE SteamAPI_RegisterCallback( class CCallbackBase *pCallback, int iCallback );
+S_API void S_CALLTYPE SteamAPI_UnregisterCallback( class CCallbackBase *pCallback );
+// Internal functions used by the utility CCallResult objects to receive async call results
+S_API void S_CALLTYPE SteamAPI_RegisterCallResult( class CCallbackBase *pCallback, SteamAPICall_t hAPICall );
+S_API void S_CALLTYPE SteamAPI_UnregisterCallResult( class CCallbackBase *pCallback, SteamAPICall_t hAPICall );
+
+
+//-----------------------------------------------------------------------------
+// Purpose: base for callbacks and call results - internal implementation detail
+//-----------------------------------------------------------------------------
+class CCallbackBase
+{
+public:
+ CCallbackBase() { m_nCallbackFlags = 0; m_iCallback = 0; }
+ // don't add a virtual destructor because we export this binary interface across dll's
+ virtual void Run( void *pvParam ) = 0;
+ virtual void Run( void *pvParam, bool bIOFailure, SteamAPICall_t hSteamAPICall ) = 0;
+ int GetICallback() { return m_iCallback; }
+ virtual int GetCallbackSizeBytes() = 0;
+
+protected:
+ enum { k_ECallbackFlagsRegistered = 0x01, k_ECallbackFlagsGameServer = 0x02 };
+ uint8 m_nCallbackFlags;
+ int m_iCallback;
+ friend class CCallbackMgr;
+
+private:
+ CCallbackBase( const CCallbackBase& );
+ CCallbackBase& operator=( const CCallbackBase& );
+};
+
+//-----------------------------------------------------------------------------
+// Purpose: templated base for callbacks - internal implementation detail
+//-----------------------------------------------------------------------------
+template< int sizeof_P >
+class CCallbackImpl : protected CCallbackBase
+{
+public:
+ ~CCallbackImpl() { if ( m_nCallbackFlags & k_ECallbackFlagsRegistered ) SteamAPI_UnregisterCallback( this ); }
+ void SetGameserverFlag() { m_nCallbackFlags |= k_ECallbackFlagsGameServer; }
+
+protected:
+ virtual void Run( void *pvParam ) = 0;
+ virtual void Run( void *pvParam, bool /*bIOFailure*/, SteamAPICall_t /*hSteamAPICall*/ ) { Run( pvParam ); }
+ virtual int GetCallbackSizeBytes() { return sizeof_P; }
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: maps a steam async call result to a class member function
+// template params: T = local class, P = parameter struct
+//-----------------------------------------------------------------------------
+template< class T, class P >
+class CCallResult : private CCallbackBase
+{
+public:
+ typedef void (T::*func_t)( P*, bool );
+
+ CCallResult();
+ ~CCallResult();
+
+ void Set( SteamAPICall_t hAPICall, T *p, func_t func );
+ bool IsActive() const;
+ void Cancel();
+
+ void SetGameserverFlag() { m_nCallbackFlags |= k_ECallbackFlagsGameServer; }
+private:
+ virtual void Run( void *pvParam );
+ virtual void Run( void *pvParam, bool bIOFailure, SteamAPICall_t hSteamAPICall );
+ virtual int GetCallbackSizeBytes() { return sizeof( P ); }
+
+ SteamAPICall_t m_hAPICall;
+ T *m_pObj;
+ func_t m_Func;
+};
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: maps a steam callback to a class member function
+// template params: T = local class, P = parameter struct,
+// bGameserver = listen for gameserver callbacks instead of client callbacks
+//-----------------------------------------------------------------------------
+template< class T, class P, bool bGameserver = false >
+class CCallback : public CCallbackImpl< sizeof( P ) >
+{
+public:
+ typedef void (T::*func_t)(P*);
+
+ // NOTE: If you can't provide the correct parameters at construction time, you should
+ // use the CCallbackManual callback object (STEAM_CALLBACK_MANUAL macro) instead.
+ CCallback( T *pObj, func_t func );
+
+ void Register( T *pObj, func_t func );
+ void Unregister();
+
+protected:
+ virtual void Run( void *pvParam );
+
+ T *m_pObj;
+ func_t m_Func;
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: subclass of CCallback which allows default-construction in
+// an unregistered state; you must call Register manually
+//-----------------------------------------------------------------------------
+template< class T, class P, bool bGameServer = false >
+class CCallbackManual : public CCallback< T, P, bGameServer >
+{
+public:
+ CCallbackManual() : CCallback< T, P, bGameServer >( NULL, NULL ) {}
+
+ // Inherits public Register and Unregister functions from base class
+};
+
+
+
+#ifdef _WIN32
+// disable this warning; this pattern need for steam callback registration
+#pragma warning( disable: 4355 ) // 'this' : used in base member initializer list
+#endif
+
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// steamclient.dll private wrapper functions
+//
+// The following functions are part of abstracting API access to the steamclient.dll, but should only be used in very specific cases
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+
+// SteamAPI_IsSteamRunning() returns true if Steam is currently running
+S_API bool S_CALLTYPE SteamAPI_IsSteamRunning();
+
+// Pumps out all the steam messages, calling registered callbacks.
+// NOT THREADSAFE - do not call from multiple threads simultaneously.
+S_API void Steam_RunCallbacks( HSteamPipe hSteamPipe, bool bGameServerCallbacks );
+
+// register the callback funcs to use to interact with the steam dll
+S_API void Steam_RegisterInterfaceFuncs( void *hModule );
+
+// returns the HSteamUser of the last user to dispatch a callback
+S_API HSteamUser Steam_GetHSteamUserCurrent();
+
+// returns the filename path of the current running Steam process, used if you need to load an explicit steam dll by name.
+// DEPRECATED - implementation is Windows only, and the path returned is a UTF-8 string which must be converted to UTF-16 for use with Win32 APIs
+S_API const char *SteamAPI_GetSteamInstallPath();
+
+// returns the pipe we are communicating to Steam with
+S_API HSteamPipe SteamAPI_GetHSteamPipe();
+
+// sets whether or not Steam_RunCallbacks() should do a try {} catch (...) {} around calls to issuing callbacks
+S_API void SteamAPI_SetTryCatchCallbacks( bool bTryCatchCallbacks );
+
+// backwards compat export, passes through to SteamAPI_ variants
+S_API HSteamPipe GetHSteamPipe();
+S_API HSteamUser GetHSteamUser();
+
+
+#if defined( VERSION_SAFE_STEAM_API_INTERFACES )
+// exists only for backwards compat with code written against older SDKs
+S_API bool S_CALLTYPE SteamAPI_InitSafe();
+#endif
+
+#include "steam_api_internal.h"
+
+#endif // STEAM_API_H
diff --git a/dep/steam_api/steam_api_flat.h b/dep/steam_api/steam_api_flat.h
new file mode 100644
index 0000000..7d35cfe
--- /dev/null
+++ b/dep/steam_api/steam_api_flat.h
@@ -0,0 +1,816 @@
+//====== Copyright (c) 1996-2014, Valve Corporation, All rights reserved. =======
+//
+// Purpose: Header for flatted SteamAPI. Use this for binding to other languages.
+// This file is auto-generated, do not edit it.
+//
+//=============================================================================
+
+#ifndef STEAMAPIFLAT_H
+#define STEAMAPIFLAT_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include
+
+
+typedef unsigned char uint8;
+typedef unsigned char uint8;
+typedef signed char int8;
+typedef short int16;
+typedef unsigned short uint16;
+typedef int int32;
+typedef unsigned int uint32;
+typedef long long int64;
+typedef unsigned long long uint64;
+typedef int64 lint64;
+typedef uint64 ulint64;
+typedef uint8 Salt_t[8];
+typedef uint64 GID_t;
+typedef uint64 JobID_t;
+typedef GID_t TxnID_t;
+typedef uint32 PackageId_t;
+typedef uint32 BundleId_t;
+typedef uint32 AppId_t;
+typedef uint64 AssetClassId_t;
+typedef uint32 PhysicalItemId_t;
+typedef uint32 DepotId_t;
+typedef uint32 RTime32;
+typedef uint32 CellID_t;
+typedef uint64 SteamAPICall_t;
+typedef uint32 AccountID_t;
+typedef uint32 PartnerId_t;
+typedef uint64 ManifestId_t;
+typedef uint32 HAuthTicket;
+typedef void * BREAKPAD_HANDLE;
+typedef char compile_time_assert_type[1];
+typedef int32 HSteamPipe;
+typedef int32 HSteamUser;
+typedef int16 FriendsGroupID_t;
+typedef void * HServerListRequest;
+typedef int HServerQuery;
+typedef uint64 UGCHandle_t;
+typedef uint64 PublishedFileUpdateHandle_t;
+typedef uint64 PublishedFileId_t;
+typedef uint64 UGCFileWriteStreamHandle_t;
+typedef char compile_time_assert_type[1];
+typedef uint64 SteamLeaderboard_t;
+typedef uint64 SteamLeaderboardEntries_t;
+typedef uint32 SNetSocket_t;
+typedef uint32 SNetListenSocket_t;
+typedef uint32 ScreenshotHandle;
+typedef uint32 HTTPRequestHandle;
+typedef uint32 HTTPCookieContainerHandle;
+typedef uint64 ClientUnifiedMessageHandle;
+typedef uint64 ControllerHandle_t;
+typedef uint64 ControllerActionSetHandle_t;
+typedef uint64 ControllerDigitalActionHandle_t;
+typedef uint64 ControllerAnalogActionHandle_t;
+typedef uint64 UGCQueryHandle_t;
+typedef uint64 UGCUpdateHandle_t;
+typedef uint32 HHTMLBrowser;
+typedef uint64 SteamItemInstanceID_t;
+typedef int32 SteamItemDef_t;
+typedef int32 SteamInventoryResult_t;
+// OpenVR Constants
+int const_k_iSteamUserCallbacks = 100;
+int const_k_iSteamGameServerCallbacks = 200;
+int const_k_iSteamFriendsCallbacks = 300;
+int const_k_iSteamBillingCallbacks = 400;
+int const_k_iSteamMatchmakingCallbacks = 500;
+int const_k_iSteamContentServerCallbacks = 600;
+int const_k_iSteamUtilsCallbacks = 700;
+int const_k_iClientFriendsCallbacks = 800;
+int const_k_iClientUserCallbacks = 900;
+int const_k_iSteamAppsCallbacks = 1000;
+int const_k_iSteamUserStatsCallbacks = 1100;
+int const_k_iSteamNetworkingCallbacks = 1200;
+int const_k_iClientRemoteStorageCallbacks = 1300;
+int const_k_iClientDepotBuilderCallbacks = 1400;
+int const_k_iSteamGameServerItemsCallbacks = 1500;
+int const_k_iClientUtilsCallbacks = 1600;
+int const_k_iSteamGameCoordinatorCallbacks = 1700;
+int const_k_iSteamGameServerStatsCallbacks = 1800;
+int const_k_iSteam2AsyncCallbacks = 1900;
+int const_k_iSteamGameStatsCallbacks = 2000;
+int const_k_iClientHTTPCallbacks = 2100;
+int const_k_iClientScreenshotsCallbacks = 2200;
+int const_k_iSteamScreenshotsCallbacks = 2300;
+int const_k_iClientAudioCallbacks = 2400;
+int const_k_iClientUnifiedMessagesCallbacks = 2500;
+int const_k_iSteamStreamLauncherCallbacks = 2600;
+int const_k_iClientControllerCallbacks = 2700;
+int const_k_iSteamControllerCallbacks = 2800;
+int const_k_iClientParentalSettingsCallbacks = 2900;
+int const_k_iClientDeviceAuthCallbacks = 3000;
+int const_k_iClientNetworkDeviceManagerCallbacks = 3100;
+int const_k_iClientMusicCallbacks = 3200;
+int const_k_iClientRemoteClientManagerCallbacks = 3300;
+int const_k_iClientUGCCallbacks = 3400;
+int const_k_iSteamStreamClientCallbacks = 3500;
+int const_k_IClientProductBuilderCallbacks = 3600;
+int const_k_iClientShortcutsCallbacks = 3700;
+int const_k_iClientRemoteControlManagerCallbacks = 3800;
+int const_k_iSteamAppListCallbacks = 3900;
+int const_k_iSteamMusicCallbacks = 4000;
+int const_k_iSteamMusicRemoteCallbacks = 4100;
+int const_k_iClientVRCallbacks = 4200;
+int const_k_iClientGameNotificationCallbacks = 4300;
+int const_k_iSteamGameNotificationCallbacks = 4400;
+int const_k_iSteamHTMLSurfaceCallbacks = 4500;
+int const_k_iClientVideoCallbacks = 4600;
+int const_k_iClientInventoryCallbacks = 4700;
+int const_k_iClientBluetoothManagerCallbacks = 4800;
+int const_k_cchPersonaNameMax = 128;
+int const_k_cwchPersonaNameMax = 32;
+int const_k_cchMaxRichPresenceKeys = 20;
+int const_k_cchMaxRichPresenceKeyLength = 64;
+int const_k_cchMaxRichPresenceValueLength = 256;
+int const_k_cchStatNameMax = 128;
+int const_k_cchLeaderboardNameMax = 128;
+int const_k_cLeaderboardDetailsMax = 64;
+unsigned long const_k_InvalidUnifiedMessageHandle = 0;
+unsigned long const_k_SteamItemInstanceIDInvalid = 0xffffffff;
+int const_k_SteamInventoryResultInvalid = -1;
+
+
+
+// OpenVR Enums
+// OpenVR Structs
+
+
+
+S_API HSteamPipe SteamAPI_ISteamClient_CreateSteamPipe(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamClient_BReleaseSteamPipe(intptr_t instancePtr, HSteamPipe hSteamPipe);
+S_API HSteamUser SteamAPI_ISteamClient_ConnectToGlobalUser(intptr_t instancePtr, HSteamPipe hSteamPipe);
+S_API HSteamUser SteamAPI_ISteamClient_CreateLocalUser(intptr_t instancePtr, HSteamPipe * phSteamPipe, EAccountType eAccountType);
+S_API void SteamAPI_ISteamClient_ReleaseUser(intptr_t instancePtr, HSteamPipe hSteamPipe, HSteamUser hUser);
+S_API class ISteamUser * SteamAPI_ISteamClient_GetISteamUser(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamGameServer * SteamAPI_ISteamClient_GetISteamGameServer(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API void SteamAPI_ISteamClient_SetLocalIPBinding(intptr_t instancePtr, uint32 unIP, uint16 usPort);
+S_API class ISteamFriends * SteamAPI_ISteamClient_GetISteamFriends(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamUtils * SteamAPI_ISteamClient_GetISteamUtils(intptr_t instancePtr, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamMatchmaking * SteamAPI_ISteamClient_GetISteamMatchmaking(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamMatchmakingServers * SteamAPI_ISteamClient_GetISteamMatchmakingServers(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API void * SteamAPI_ISteamClient_GetISteamGenericInterface(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamUserStats * SteamAPI_ISteamClient_GetISteamUserStats(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamGameServerStats * SteamAPI_ISteamClient_GetISteamGameServerStats(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamApps * SteamAPI_ISteamClient_GetISteamApps(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamNetworking * SteamAPI_ISteamClient_GetISteamNetworking(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamRemoteStorage * SteamAPI_ISteamClient_GetISteamRemoteStorage(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamScreenshots * SteamAPI_ISteamClient_GetISteamScreenshots(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API uint32 SteamAPI_ISteamClient_GetIPCCallCount(intptr_t instancePtr);
+S_API void SteamAPI_ISteamClient_SetWarningMessageHook(intptr_t instancePtr, SteamAPIWarningMessageHook_t pFunction);
+S_API bool SteamAPI_ISteamClient_BShutdownIfAllPipesClosed(intptr_t instancePtr);
+S_API class ISteamHTTP * SteamAPI_ISteamClient_GetISteamHTTP(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamUnifiedMessages * SteamAPI_ISteamClient_GetISteamUnifiedMessages(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamController * SteamAPI_ISteamClient_GetISteamController(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamUGC * SteamAPI_ISteamClient_GetISteamUGC(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamAppList * SteamAPI_ISteamClient_GetISteamAppList(intptr_t instancePtr, HSteamUser hSteamUser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamMusic * SteamAPI_ISteamClient_GetISteamMusic(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamMusicRemote * SteamAPI_ISteamClient_GetISteamMusicRemote(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamHTMLSurface * SteamAPI_ISteamClient_GetISteamHTMLSurface(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamInventory * SteamAPI_ISteamClient_GetISteamInventory(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API class ISteamVideo * SteamAPI_ISteamClient_GetISteamVideo(intptr_t instancePtr, HSteamUser hSteamuser, HSteamPipe hSteamPipe, const char * pchVersion);
+S_API HSteamUser SteamAPI_ISteamUser_GetHSteamUser(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUser_BLoggedOn(intptr_t instancePtr);
+S_API uint64 SteamAPI_ISteamUser_GetSteamID(intptr_t instancePtr);
+S_API int SteamAPI_ISteamUser_InitiateGameConnection(intptr_t instancePtr, void * pAuthBlob, int cbMaxAuthBlob, class CSteamID steamIDGameServer, uint32 unIPServer, uint16 usPortServer, bool bSecure);
+S_API void SteamAPI_ISteamUser_TerminateGameConnection(intptr_t instancePtr, uint32 unIPServer, uint16 usPortServer);
+S_API void SteamAPI_ISteamUser_TrackAppUsageEvent(intptr_t instancePtr, class CGameID gameID, int eAppUsageEvent, const char * pchExtraInfo);
+S_API bool SteamAPI_ISteamUser_GetUserDataFolder(intptr_t instancePtr, char * pchBuffer, int cubBuffer);
+S_API void SteamAPI_ISteamUser_StartVoiceRecording(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUser_StopVoiceRecording(intptr_t instancePtr);
+S_API EVoiceResult SteamAPI_ISteamUser_GetAvailableVoice(intptr_t instancePtr, uint32 * pcbCompressed, uint32 * pcbUncompressed_Deprecated, uint32 nUncompressedVoiceDesiredSampleRate_Deprecated);
+S_API EVoiceResult SteamAPI_ISteamUser_GetVoice(intptr_t instancePtr, bool bWantCompressed, void * pDestBuffer, uint32 cbDestBufferSize, uint32 * nBytesWritten, bool bWantUncompressed_Deprecated, void * pUncompressedDestBuffer_Deprecated, uint32 cbUncompressedDestBufferSize_Deprecated, uint32 * nUncompressBytesWritten_Deprecated, uint32 nUncompressedVoiceDesiredSampleRate_Deprecated);
+S_API EVoiceResult SteamAPI_ISteamUser_DecompressVoice(intptr_t instancePtr, const void * pCompressed, uint32 cbCompressed, void * pDestBuffer, uint32 cbDestBufferSize, uint32 * nBytesWritten, uint32 nDesiredSampleRate);
+S_API uint32 SteamAPI_ISteamUser_GetVoiceOptimalSampleRate(intptr_t instancePtr);
+S_API HAuthTicket SteamAPI_ISteamUser_GetAuthSessionTicket(intptr_t instancePtr, void * pTicket, int cbMaxTicket, uint32 * pcbTicket);
+S_API EBeginAuthSessionResult SteamAPI_ISteamUser_BeginAuthSession(intptr_t instancePtr, const void * pAuthTicket, int cbAuthTicket, class CSteamID steamID);
+S_API void SteamAPI_ISteamUser_EndAuthSession(intptr_t instancePtr, class CSteamID steamID);
+S_API void SteamAPI_ISteamUser_CancelAuthTicket(intptr_t instancePtr, HAuthTicket hAuthTicket);
+S_API EUserHasLicenseForAppResult SteamAPI_ISteamUser_UserHasLicenseForApp(intptr_t instancePtr, class CSteamID steamID, AppId_t appID);
+S_API bool SteamAPI_ISteamUser_BIsBehindNAT(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUser_AdvertiseGame(intptr_t instancePtr, class CSteamID steamIDGameServer, uint32 unIPServer, uint16 usPortServer);
+S_API SteamAPICall_t SteamAPI_ISteamUser_RequestEncryptedAppTicket(intptr_t instancePtr, void * pDataToInclude, int cbDataToInclude);
+S_API bool SteamAPI_ISteamUser_GetEncryptedAppTicket(intptr_t instancePtr, void * pTicket, int cbMaxTicket, uint32 * pcbTicket);
+S_API int SteamAPI_ISteamUser_GetGameBadgeLevel(intptr_t instancePtr, int nSeries, bool bFoil);
+S_API int SteamAPI_ISteamUser_GetPlayerSteamLevel(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamUser_RequestStoreAuthURL(intptr_t instancePtr, const char * pchRedirectURL);
+S_API bool SteamAPI_ISteamUser_BIsPhoneVerified(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUser_BIsTwoFactorEnabled(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUser_BIsPhoneIdentifying(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUser_BIsPhoneRequiringVerification(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamFriends_GetPersonaName(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_SetPersonaName(intptr_t instancePtr, const char * pchPersonaName);
+S_API EPersonaState SteamAPI_ISteamFriends_GetPersonaState(intptr_t instancePtr);
+S_API int SteamAPI_ISteamFriends_GetFriendCount(intptr_t instancePtr, int iFriendFlags);
+S_API uint64 SteamAPI_ISteamFriends_GetFriendByIndex(intptr_t instancePtr, int iFriend, int iFriendFlags);
+S_API EFriendRelationship SteamAPI_ISteamFriends_GetFriendRelationship(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API EPersonaState SteamAPI_ISteamFriends_GetFriendPersonaState(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API const char * SteamAPI_ISteamFriends_GetFriendPersonaName(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API bool SteamAPI_ISteamFriends_GetFriendGamePlayed(intptr_t instancePtr, class CSteamID steamIDFriend, struct FriendGameInfo_t * pFriendGameInfo);
+S_API const char * SteamAPI_ISteamFriends_GetFriendPersonaNameHistory(intptr_t instancePtr, class CSteamID steamIDFriend, int iPersonaName);
+S_API int SteamAPI_ISteamFriends_GetFriendSteamLevel(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API const char * SteamAPI_ISteamFriends_GetPlayerNickname(intptr_t instancePtr, class CSteamID steamIDPlayer);
+S_API int SteamAPI_ISteamFriends_GetFriendsGroupCount(intptr_t instancePtr);
+S_API FriendsGroupID_t SteamAPI_ISteamFriends_GetFriendsGroupIDByIndex(intptr_t instancePtr, int iFG);
+S_API const char * SteamAPI_ISteamFriends_GetFriendsGroupName(intptr_t instancePtr, FriendsGroupID_t friendsGroupID);
+S_API int SteamAPI_ISteamFriends_GetFriendsGroupMembersCount(intptr_t instancePtr, FriendsGroupID_t friendsGroupID);
+S_API void SteamAPI_ISteamFriends_GetFriendsGroupMembersList(intptr_t instancePtr, FriendsGroupID_t friendsGroupID, class CSteamID * pOutSteamIDMembers, int nMembersCount);
+S_API bool SteamAPI_ISteamFriends_HasFriend(intptr_t instancePtr, class CSteamID steamIDFriend, int iFriendFlags);
+S_API int SteamAPI_ISteamFriends_GetClanCount(intptr_t instancePtr);
+S_API uint64 SteamAPI_ISteamFriends_GetClanByIndex(intptr_t instancePtr, int iClan);
+S_API const char * SteamAPI_ISteamFriends_GetClanName(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API const char * SteamAPI_ISteamFriends_GetClanTag(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API bool SteamAPI_ISteamFriends_GetClanActivityCounts(intptr_t instancePtr, class CSteamID steamIDClan, int * pnOnline, int * pnInGame, int * pnChatting);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_DownloadClanActivityCounts(intptr_t instancePtr, class CSteamID * psteamIDClans, int cClansToRequest);
+S_API int SteamAPI_ISteamFriends_GetFriendCountFromSource(intptr_t instancePtr, class CSteamID steamIDSource);
+S_API uint64 SteamAPI_ISteamFriends_GetFriendFromSourceByIndex(intptr_t instancePtr, class CSteamID steamIDSource, int iFriend);
+S_API bool SteamAPI_ISteamFriends_IsUserInSource(intptr_t instancePtr, class CSteamID steamIDUser, class CSteamID steamIDSource);
+S_API void SteamAPI_ISteamFriends_SetInGameVoiceSpeaking(intptr_t instancePtr, class CSteamID steamIDUser, bool bSpeaking);
+S_API void SteamAPI_ISteamFriends_ActivateGameOverlay(intptr_t instancePtr, const char * pchDialog);
+S_API void SteamAPI_ISteamFriends_ActivateGameOverlayToUser(intptr_t instancePtr, const char * pchDialog, class CSteamID steamID);
+S_API void SteamAPI_ISteamFriends_ActivateGameOverlayToWebPage(intptr_t instancePtr, const char * pchURL);
+S_API void SteamAPI_ISteamFriends_ActivateGameOverlayToStore(intptr_t instancePtr, AppId_t nAppID, EOverlayToStoreFlag eFlag);
+S_API void SteamAPI_ISteamFriends_SetPlayedWith(intptr_t instancePtr, class CSteamID steamIDUserPlayedWith);
+S_API void SteamAPI_ISteamFriends_ActivateGameOverlayInviteDialog(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API int SteamAPI_ISteamFriends_GetSmallFriendAvatar(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API int SteamAPI_ISteamFriends_GetMediumFriendAvatar(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API int SteamAPI_ISteamFriends_GetLargeFriendAvatar(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API bool SteamAPI_ISteamFriends_RequestUserInformation(intptr_t instancePtr, class CSteamID steamIDUser, bool bRequireNameOnly);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_RequestClanOfficerList(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API uint64 SteamAPI_ISteamFriends_GetClanOwner(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API int SteamAPI_ISteamFriends_GetClanOfficerCount(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API uint64 SteamAPI_ISteamFriends_GetClanOfficerByIndex(intptr_t instancePtr, class CSteamID steamIDClan, int iOfficer);
+S_API uint32 SteamAPI_ISteamFriends_GetUserRestrictions(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamFriends_SetRichPresence(intptr_t instancePtr, const char * pchKey, const char * pchValue);
+S_API void SteamAPI_ISteamFriends_ClearRichPresence(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamFriends_GetFriendRichPresence(intptr_t instancePtr, class CSteamID steamIDFriend, const char * pchKey);
+S_API int SteamAPI_ISteamFriends_GetFriendRichPresenceKeyCount(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API const char * SteamAPI_ISteamFriends_GetFriendRichPresenceKeyByIndex(intptr_t instancePtr, class CSteamID steamIDFriend, int iKey);
+S_API void SteamAPI_ISteamFriends_RequestFriendRichPresence(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API bool SteamAPI_ISteamFriends_InviteUserToGame(intptr_t instancePtr, class CSteamID steamIDFriend, const char * pchConnectString);
+S_API int SteamAPI_ISteamFriends_GetCoplayFriendCount(intptr_t instancePtr);
+S_API uint64 SteamAPI_ISteamFriends_GetCoplayFriend(intptr_t instancePtr, int iCoplayFriend);
+S_API int SteamAPI_ISteamFriends_GetFriendCoplayTime(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API AppId_t SteamAPI_ISteamFriends_GetFriendCoplayGame(intptr_t instancePtr, class CSteamID steamIDFriend);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_JoinClanChatRoom(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API bool SteamAPI_ISteamFriends_LeaveClanChatRoom(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API int SteamAPI_ISteamFriends_GetClanChatMemberCount(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API uint64 SteamAPI_ISteamFriends_GetChatMemberByIndex(intptr_t instancePtr, class CSteamID steamIDClan, int iUser);
+S_API bool SteamAPI_ISteamFriends_SendClanChatMessage(intptr_t instancePtr, class CSteamID steamIDClanChat, const char * pchText);
+S_API int SteamAPI_ISteamFriends_GetClanChatMessage(intptr_t instancePtr, class CSteamID steamIDClanChat, int iMessage, void * prgchText, int cchTextMax, EChatEntryType * peChatEntryType, class CSteamID * psteamidChatter);
+S_API bool SteamAPI_ISteamFriends_IsClanChatAdmin(intptr_t instancePtr, class CSteamID steamIDClanChat, class CSteamID steamIDUser);
+S_API bool SteamAPI_ISteamFriends_IsClanChatWindowOpenInSteam(intptr_t instancePtr, class CSteamID steamIDClanChat);
+S_API bool SteamAPI_ISteamFriends_OpenClanChatWindowInSteam(intptr_t instancePtr, class CSteamID steamIDClanChat);
+S_API bool SteamAPI_ISteamFriends_CloseClanChatWindowInSteam(intptr_t instancePtr, class CSteamID steamIDClanChat);
+S_API bool SteamAPI_ISteamFriends_SetListenForFriendsMessages(intptr_t instancePtr, bool bInterceptEnabled);
+S_API bool SteamAPI_ISteamFriends_ReplyToFriendMessage(intptr_t instancePtr, class CSteamID steamIDFriend, const char * pchMsgToSend);
+S_API int SteamAPI_ISteamFriends_GetFriendMessage(intptr_t instancePtr, class CSteamID steamIDFriend, int iMessageID, void * pvData, int cubData, EChatEntryType * peChatEntryType);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_GetFollowerCount(intptr_t instancePtr, class CSteamID steamID);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_IsFollowing(intptr_t instancePtr, class CSteamID steamID);
+S_API SteamAPICall_t SteamAPI_ISteamFriends_EnumerateFollowingList(intptr_t instancePtr, uint32 unStartIndex);
+S_API uint32 SteamAPI_ISteamUtils_GetSecondsSinceAppActive(intptr_t instancePtr);
+S_API uint32 SteamAPI_ISteamUtils_GetSecondsSinceComputerActive(intptr_t instancePtr);
+S_API EUniverse SteamAPI_ISteamUtils_GetConnectedUniverse(intptr_t instancePtr);
+S_API uint32 SteamAPI_ISteamUtils_GetServerRealTime(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamUtils_GetIPCountry(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUtils_GetImageSize(intptr_t instancePtr, int iImage, uint32 * pnWidth, uint32 * pnHeight);
+S_API bool SteamAPI_ISteamUtils_GetImageRGBA(intptr_t instancePtr, int iImage, uint8 * pubDest, int nDestBufferSize);
+S_API bool SteamAPI_ISteamUtils_GetCSERIPPort(intptr_t instancePtr, uint32 * unIP, uint16 * usPort);
+S_API uint8 SteamAPI_ISteamUtils_GetCurrentBatteryPower(intptr_t instancePtr);
+S_API uint32 SteamAPI_ISteamUtils_GetAppID(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUtils_SetOverlayNotificationPosition(intptr_t instancePtr, ENotificationPosition eNotificationPosition);
+S_API bool SteamAPI_ISteamUtils_IsAPICallCompleted(intptr_t instancePtr, SteamAPICall_t hSteamAPICall, bool * pbFailed);
+S_API ESteamAPICallFailure SteamAPI_ISteamUtils_GetAPICallFailureReason(intptr_t instancePtr, SteamAPICall_t hSteamAPICall);
+S_API bool SteamAPI_ISteamUtils_GetAPICallResult(intptr_t instancePtr, SteamAPICall_t hSteamAPICall, void * pCallback, int cubCallback, int iCallbackExpected, bool * pbFailed);
+S_API uint32 SteamAPI_ISteamUtils_GetIPCCallCount(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUtils_SetWarningMessageHook(intptr_t instancePtr, SteamAPIWarningMessageHook_t pFunction);
+S_API bool SteamAPI_ISteamUtils_IsOverlayEnabled(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUtils_BOverlayNeedsPresent(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamUtils_CheckFileSignature(intptr_t instancePtr, const char * szFileName);
+S_API bool SteamAPI_ISteamUtils_ShowGamepadTextInput(intptr_t instancePtr, EGamepadTextInputMode eInputMode, EGamepadTextInputLineMode eLineInputMode, const char * pchDescription, uint32 unCharMax, const char * pchExistingText);
+S_API uint32 SteamAPI_ISteamUtils_GetEnteredGamepadTextLength(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUtils_GetEnteredGamepadTextInput(intptr_t instancePtr, char * pchText, uint32 cchText);
+S_API const char * SteamAPI_ISteamUtils_GetSteamUILanguage(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUtils_IsSteamRunningInVR(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUtils_SetOverlayNotificationInset(intptr_t instancePtr, int nHorizontalInset, int nVerticalInset);
+S_API bool SteamAPI_ISteamUtils_IsSteamInBigPictureMode(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUtils_StartVRDashboard(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUtils_IsVRHeadsetStreamingEnabled(intptr_t instancePtr);
+S_API void SteamAPI_ISteamUtils_SetVRHeadsetStreamingEnabled(intptr_t instancePtr, bool bEnabled);
+S_API int SteamAPI_ISteamMatchmaking_GetFavoriteGameCount(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMatchmaking_GetFavoriteGame(intptr_t instancePtr, int iGame, AppId_t * pnAppID, uint32 * pnIP, uint16 * pnConnPort, uint16 * pnQueryPort, uint32 * punFlags, uint32 * pRTime32LastPlayedOnServer);
+S_API int SteamAPI_ISteamMatchmaking_AddFavoriteGame(intptr_t instancePtr, AppId_t nAppID, uint32 nIP, uint16 nConnPort, uint16 nQueryPort, uint32 unFlags, uint32 rTime32LastPlayedOnServer);
+S_API bool SteamAPI_ISteamMatchmaking_RemoveFavoriteGame(intptr_t instancePtr, AppId_t nAppID, uint32 nIP, uint16 nConnPort, uint16 nQueryPort, uint32 unFlags);
+S_API SteamAPICall_t SteamAPI_ISteamMatchmaking_RequestLobbyList(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListStringFilter(intptr_t instancePtr, const char * pchKeyToMatch, const char * pchValueToMatch, ELobbyComparison eComparisonType);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListNumericalFilter(intptr_t instancePtr, const char * pchKeyToMatch, int nValueToMatch, ELobbyComparison eComparisonType);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListNearValueFilter(intptr_t instancePtr, const char * pchKeyToMatch, int nValueToBeCloseTo);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListFilterSlotsAvailable(intptr_t instancePtr, int nSlotsAvailable);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListDistanceFilter(intptr_t instancePtr, ELobbyDistanceFilter eLobbyDistanceFilter);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListResultCountFilter(intptr_t instancePtr, int cMaxResults);
+S_API void SteamAPI_ISteamMatchmaking_AddRequestLobbyListCompatibleMembersFilter(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API uint64 SteamAPI_ISteamMatchmaking_GetLobbyByIndex(intptr_t instancePtr, int iLobby);
+S_API SteamAPICall_t SteamAPI_ISteamMatchmaking_CreateLobby(intptr_t instancePtr, ELobbyType eLobbyType, int cMaxMembers);
+S_API SteamAPICall_t SteamAPI_ISteamMatchmaking_JoinLobby(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API void SteamAPI_ISteamMatchmaking_LeaveLobby(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API bool SteamAPI_ISteamMatchmaking_InviteUserToLobby(intptr_t instancePtr, class CSteamID steamIDLobby, class CSteamID steamIDInvitee);
+S_API int SteamAPI_ISteamMatchmaking_GetNumLobbyMembers(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API uint64 SteamAPI_ISteamMatchmaking_GetLobbyMemberByIndex(intptr_t instancePtr, class CSteamID steamIDLobby, int iMember);
+S_API const char * SteamAPI_ISteamMatchmaking_GetLobbyData(intptr_t instancePtr, class CSteamID steamIDLobby, const char * pchKey);
+S_API bool SteamAPI_ISteamMatchmaking_SetLobbyData(intptr_t instancePtr, class CSteamID steamIDLobby, const char * pchKey, const char * pchValue);
+S_API int SteamAPI_ISteamMatchmaking_GetLobbyDataCount(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API bool SteamAPI_ISteamMatchmaking_GetLobbyDataByIndex(intptr_t instancePtr, class CSteamID steamIDLobby, int iLobbyData, char * pchKey, int cchKeyBufferSize, char * pchValue, int cchValueBufferSize);
+S_API bool SteamAPI_ISteamMatchmaking_DeleteLobbyData(intptr_t instancePtr, class CSteamID steamIDLobby, const char * pchKey);
+S_API const char * SteamAPI_ISteamMatchmaking_GetLobbyMemberData(intptr_t instancePtr, class CSteamID steamIDLobby, class CSteamID steamIDUser, const char * pchKey);
+S_API void SteamAPI_ISteamMatchmaking_SetLobbyMemberData(intptr_t instancePtr, class CSteamID steamIDLobby, const char * pchKey, const char * pchValue);
+S_API bool SteamAPI_ISteamMatchmaking_SendLobbyChatMsg(intptr_t instancePtr, class CSteamID steamIDLobby, const void * pvMsgBody, int cubMsgBody);
+S_API int SteamAPI_ISteamMatchmaking_GetLobbyChatEntry(intptr_t instancePtr, class CSteamID steamIDLobby, int iChatID, class CSteamID * pSteamIDUser, void * pvData, int cubData, EChatEntryType * peChatEntryType);
+S_API bool SteamAPI_ISteamMatchmaking_RequestLobbyData(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API void SteamAPI_ISteamMatchmaking_SetLobbyGameServer(intptr_t instancePtr, class CSteamID steamIDLobby, uint32 unGameServerIP, uint16 unGameServerPort, class CSteamID steamIDGameServer);
+S_API bool SteamAPI_ISteamMatchmaking_GetLobbyGameServer(intptr_t instancePtr, class CSteamID steamIDLobby, uint32 * punGameServerIP, uint16 * punGameServerPort, class CSteamID * psteamIDGameServer);
+S_API bool SteamAPI_ISteamMatchmaking_SetLobbyMemberLimit(intptr_t instancePtr, class CSteamID steamIDLobby, int cMaxMembers);
+S_API int SteamAPI_ISteamMatchmaking_GetLobbyMemberLimit(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API bool SteamAPI_ISteamMatchmaking_SetLobbyType(intptr_t instancePtr, class CSteamID steamIDLobby, ELobbyType eLobbyType);
+S_API bool SteamAPI_ISteamMatchmaking_SetLobbyJoinable(intptr_t instancePtr, class CSteamID steamIDLobby, bool bLobbyJoinable);
+S_API uint64 SteamAPI_ISteamMatchmaking_GetLobbyOwner(intptr_t instancePtr, class CSteamID steamIDLobby);
+S_API bool SteamAPI_ISteamMatchmaking_SetLobbyOwner(intptr_t instancePtr, class CSteamID steamIDLobby, class CSteamID steamIDNewOwner);
+S_API bool SteamAPI_ISteamMatchmaking_SetLinkedLobby(intptr_t instancePtr, class CSteamID steamIDLobby, class CSteamID steamIDLobbyDependent);
+S_API void SteamAPI_ISteamMatchmakingServerListResponse_ServerResponded(intptr_t instancePtr, HServerListRequest hRequest, int iServer);
+S_API void SteamAPI_ISteamMatchmakingServerListResponse_ServerFailedToRespond(intptr_t instancePtr, HServerListRequest hRequest, int iServer);
+S_API void SteamAPI_ISteamMatchmakingServerListResponse_RefreshComplete(intptr_t instancePtr, HServerListRequest hRequest, EMatchMakingServerResponse response);
+S_API void SteamAPI_ISteamMatchmakingPingResponse_ServerResponded(intptr_t instancePtr, class gameserveritem_t & server);
+S_API void SteamAPI_ISteamMatchmakingPingResponse_ServerFailedToRespond(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMatchmakingPlayersResponse_AddPlayerToList(intptr_t instancePtr, const char * pchName, int nScore, float flTimePlayed);
+S_API void SteamAPI_ISteamMatchmakingPlayersResponse_PlayersFailedToRespond(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMatchmakingPlayersResponse_PlayersRefreshComplete(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMatchmakingRulesResponse_RulesResponded(intptr_t instancePtr, const char * pchRule, const char * pchValue);
+S_API void SteamAPI_ISteamMatchmakingRulesResponse_RulesFailedToRespond(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMatchmakingRulesResponse_RulesRefreshComplete(intptr_t instancePtr);
+S_API HServerListRequest SteamAPI_ISteamMatchmakingServers_RequestInternetServerList(intptr_t instancePtr, AppId_t iApp, struct MatchMakingKeyValuePair_t ** ppchFilters, uint32 nFilters, class ISteamMatchmakingServerListResponse * pRequestServersResponse);
+S_API HServerListRequest SteamAPI_ISteamMatchmakingServers_RequestLANServerList(intptr_t instancePtr, AppId_t iApp, class ISteamMatchmakingServerListResponse * pRequestServersResponse);
+S_API HServerListRequest SteamAPI_ISteamMatchmakingServers_RequestFriendsServerList(intptr_t instancePtr, AppId_t iApp, struct MatchMakingKeyValuePair_t ** ppchFilters, uint32 nFilters, class ISteamMatchmakingServerListResponse * pRequestServersResponse);
+S_API HServerListRequest SteamAPI_ISteamMatchmakingServers_RequestFavoritesServerList(intptr_t instancePtr, AppId_t iApp, struct MatchMakingKeyValuePair_t ** ppchFilters, uint32 nFilters, class ISteamMatchmakingServerListResponse * pRequestServersResponse);
+S_API HServerListRequest SteamAPI_ISteamMatchmakingServers_RequestHistoryServerList(intptr_t instancePtr, AppId_t iApp, struct MatchMakingKeyValuePair_t ** ppchFilters, uint32 nFilters, class ISteamMatchmakingServerListResponse * pRequestServersResponse);
+S_API HServerListRequest SteamAPI_ISteamMatchmakingServers_RequestSpectatorServerList(intptr_t instancePtr, AppId_t iApp, struct MatchMakingKeyValuePair_t ** ppchFilters, uint32 nFilters, class ISteamMatchmakingServerListResponse * pRequestServersResponse);
+S_API void SteamAPI_ISteamMatchmakingServers_ReleaseRequest(intptr_t instancePtr, HServerListRequest hServerListRequest);
+S_API class gameserveritem_t * SteamAPI_ISteamMatchmakingServers_GetServerDetails(intptr_t instancePtr, HServerListRequest hRequest, int iServer);
+S_API void SteamAPI_ISteamMatchmakingServers_CancelQuery(intptr_t instancePtr, HServerListRequest hRequest);
+S_API void SteamAPI_ISteamMatchmakingServers_RefreshQuery(intptr_t instancePtr, HServerListRequest hRequest);
+S_API bool SteamAPI_ISteamMatchmakingServers_IsRefreshing(intptr_t instancePtr, HServerListRequest hRequest);
+S_API int SteamAPI_ISteamMatchmakingServers_GetServerCount(intptr_t instancePtr, HServerListRequest hRequest);
+S_API void SteamAPI_ISteamMatchmakingServers_RefreshServer(intptr_t instancePtr, HServerListRequest hRequest, int iServer);
+S_API HServerQuery SteamAPI_ISteamMatchmakingServers_PingServer(intptr_t instancePtr, uint32 unIP, uint16 usPort, class ISteamMatchmakingPingResponse * pRequestServersResponse);
+S_API HServerQuery SteamAPI_ISteamMatchmakingServers_PlayerDetails(intptr_t instancePtr, uint32 unIP, uint16 usPort, class ISteamMatchmakingPlayersResponse * pRequestServersResponse);
+S_API HServerQuery SteamAPI_ISteamMatchmakingServers_ServerRules(intptr_t instancePtr, uint32 unIP, uint16 usPort, class ISteamMatchmakingRulesResponse * pRequestServersResponse);
+S_API void SteamAPI_ISteamMatchmakingServers_CancelServerQuery(intptr_t instancePtr, HServerQuery hServerQuery);
+S_API bool SteamAPI_ISteamRemoteStorage_FileWrite(intptr_t instancePtr, const char * pchFile, const void * pvData, int32 cubData);
+S_API int32 SteamAPI_ISteamRemoteStorage_FileRead(intptr_t instancePtr, const char * pchFile, void * pvData, int32 cubDataToRead);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_FileWriteAsync(intptr_t instancePtr, const char * pchFile, const void * pvData, uint32 cubData);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_FileReadAsync(intptr_t instancePtr, const char * pchFile, uint32 nOffset, uint32 cubToRead);
+S_API bool SteamAPI_ISteamRemoteStorage_FileReadAsyncComplete(intptr_t instancePtr, SteamAPICall_t hReadCall, void * pvBuffer, uint32 cubToRead);
+S_API bool SteamAPI_ISteamRemoteStorage_FileForget(intptr_t instancePtr, const char * pchFile);
+S_API bool SteamAPI_ISteamRemoteStorage_FileDelete(intptr_t instancePtr, const char * pchFile);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_FileShare(intptr_t instancePtr, const char * pchFile);
+S_API bool SteamAPI_ISteamRemoteStorage_SetSyncPlatforms(intptr_t instancePtr, const char * pchFile, ERemoteStoragePlatform eRemoteStoragePlatform);
+S_API UGCFileWriteStreamHandle_t SteamAPI_ISteamRemoteStorage_FileWriteStreamOpen(intptr_t instancePtr, const char * pchFile);
+S_API bool SteamAPI_ISteamRemoteStorage_FileWriteStreamWriteChunk(intptr_t instancePtr, UGCFileWriteStreamHandle_t writeHandle, const void * pvData, int32 cubData);
+S_API bool SteamAPI_ISteamRemoteStorage_FileWriteStreamClose(intptr_t instancePtr, UGCFileWriteStreamHandle_t writeHandle);
+S_API bool SteamAPI_ISteamRemoteStorage_FileWriteStreamCancel(intptr_t instancePtr, UGCFileWriteStreamHandle_t writeHandle);
+S_API bool SteamAPI_ISteamRemoteStorage_FileExists(intptr_t instancePtr, const char * pchFile);
+S_API bool SteamAPI_ISteamRemoteStorage_FilePersisted(intptr_t instancePtr, const char * pchFile);
+S_API int32 SteamAPI_ISteamRemoteStorage_GetFileSize(intptr_t instancePtr, const char * pchFile);
+S_API int64 SteamAPI_ISteamRemoteStorage_GetFileTimestamp(intptr_t instancePtr, const char * pchFile);
+S_API ERemoteStoragePlatform SteamAPI_ISteamRemoteStorage_GetSyncPlatforms(intptr_t instancePtr, const char * pchFile);
+S_API int32 SteamAPI_ISteamRemoteStorage_GetFileCount(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamRemoteStorage_GetFileNameAndSize(intptr_t instancePtr, int iFile, int32 * pnFileSizeInBytes);
+S_API bool SteamAPI_ISteamRemoteStorage_GetQuota(intptr_t instancePtr, uint64 * pnTotalBytes, uint64 * puAvailableBytes);
+S_API bool SteamAPI_ISteamRemoteStorage_IsCloudEnabledForAccount(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamRemoteStorage_IsCloudEnabledForApp(intptr_t instancePtr);
+S_API void SteamAPI_ISteamRemoteStorage_SetCloudEnabledForApp(intptr_t instancePtr, bool bEnabled);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_UGCDownload(intptr_t instancePtr, UGCHandle_t hContent, uint32 unPriority);
+S_API bool SteamAPI_ISteamRemoteStorage_GetUGCDownloadProgress(intptr_t instancePtr, UGCHandle_t hContent, int32 * pnBytesDownloaded, int32 * pnBytesExpected);
+S_API bool SteamAPI_ISteamRemoteStorage_GetUGCDetails(intptr_t instancePtr, UGCHandle_t hContent, AppId_t * pnAppID, char ** ppchName, int32 * pnFileSizeInBytes, class CSteamID * pSteamIDOwner);
+S_API int32 SteamAPI_ISteamRemoteStorage_UGCRead(intptr_t instancePtr, UGCHandle_t hContent, void * pvData, int32 cubDataToRead, uint32 cOffset, EUGCReadAction eAction);
+S_API int32 SteamAPI_ISteamRemoteStorage_GetCachedUGCCount(intptr_t instancePtr);
+S_API UGCHandle_t SteamAPI_ISteamRemoteStorage_GetCachedUGCHandle(intptr_t instancePtr, int32 iCachedContent);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_PublishWorkshopFile(intptr_t instancePtr, const char * pchFile, const char * pchPreviewFile, AppId_t nConsumerAppId, const char * pchTitle, const char * pchDescription, ERemoteStoragePublishedFileVisibility eVisibility, struct SteamParamStringArray_t * pTags, EWorkshopFileType eWorkshopFileType);
+S_API PublishedFileUpdateHandle_t SteamAPI_ISteamRemoteStorage_CreatePublishedFileUpdateRequest(intptr_t instancePtr, PublishedFileId_t unPublishedFileId);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFileFile(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, const char * pchFile);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFilePreviewFile(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, const char * pchPreviewFile);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFileTitle(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, const char * pchTitle);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFileDescription(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, const char * pchDescription);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFileVisibility(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, ERemoteStoragePublishedFileVisibility eVisibility);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFileTags(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, struct SteamParamStringArray_t * pTags);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_CommitPublishedFileUpdate(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_GetPublishedFileDetails(intptr_t instancePtr, PublishedFileId_t unPublishedFileId, uint32 unMaxSecondsOld);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_DeletePublishedFile(intptr_t instancePtr, PublishedFileId_t unPublishedFileId);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_EnumerateUserPublishedFiles(intptr_t instancePtr, uint32 unStartIndex);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_SubscribePublishedFile(intptr_t instancePtr, PublishedFileId_t unPublishedFileId);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_EnumerateUserSubscribedFiles(intptr_t instancePtr, uint32 unStartIndex);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_UnsubscribePublishedFile(intptr_t instancePtr, PublishedFileId_t unPublishedFileId);
+S_API bool SteamAPI_ISteamRemoteStorage_UpdatePublishedFileSetChangeDescription(intptr_t instancePtr, PublishedFileUpdateHandle_t updateHandle, const char * pchChangeDescription);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_GetPublishedItemVoteDetails(intptr_t instancePtr, PublishedFileId_t unPublishedFileId);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_UpdateUserPublishedItemVote(intptr_t instancePtr, PublishedFileId_t unPublishedFileId, bool bVoteUp);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_GetUserPublishedItemVoteDetails(intptr_t instancePtr, PublishedFileId_t unPublishedFileId);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_EnumerateUserSharedWorkshopFiles(intptr_t instancePtr, class CSteamID steamId, uint32 unStartIndex, struct SteamParamStringArray_t * pRequiredTags, struct SteamParamStringArray_t * pExcludedTags);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_PublishVideo(intptr_t instancePtr, EWorkshopVideoProvider eVideoProvider, const char * pchVideoAccount, const char * pchVideoIdentifier, const char * pchPreviewFile, AppId_t nConsumerAppId, const char * pchTitle, const char * pchDescription, ERemoteStoragePublishedFileVisibility eVisibility, struct SteamParamStringArray_t * pTags);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_SetUserPublishedFileAction(intptr_t instancePtr, PublishedFileId_t unPublishedFileId, EWorkshopFileAction eAction);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_EnumeratePublishedFilesByUserAction(intptr_t instancePtr, EWorkshopFileAction eAction, uint32 unStartIndex);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_EnumeratePublishedWorkshopFiles(intptr_t instancePtr, EWorkshopEnumerationType eEnumerationType, uint32 unStartIndex, uint32 unCount, uint32 unDays, struct SteamParamStringArray_t * pTags, struct SteamParamStringArray_t * pUserTags);
+S_API SteamAPICall_t SteamAPI_ISteamRemoteStorage_UGCDownloadToLocation(intptr_t instancePtr, UGCHandle_t hContent, const char * pchLocation, uint32 unPriority);
+S_API bool SteamAPI_ISteamUserStats_RequestCurrentStats(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamUserStats_GetStat(intptr_t instancePtr, const char * pchName, int32 * pData);
+S_API bool SteamAPI_ISteamUserStats_GetStat0(intptr_t instancePtr, const char * pchName, float * pData);
+S_API bool SteamAPI_ISteamUserStats_SetStat(intptr_t instancePtr, const char * pchName, int32 nData);
+S_API bool SteamAPI_ISteamUserStats_SetStat0(intptr_t instancePtr, const char * pchName, float fData);
+S_API bool SteamAPI_ISteamUserStats_UpdateAvgRateStat(intptr_t instancePtr, const char * pchName, float flCountThisSession, double dSessionLength);
+S_API bool SteamAPI_ISteamUserStats_GetAchievement(intptr_t instancePtr, const char * pchName, bool * pbAchieved);
+S_API bool SteamAPI_ISteamUserStats_SetAchievement(intptr_t instancePtr, const char * pchName);
+S_API bool SteamAPI_ISteamUserStats_ClearAchievement(intptr_t instancePtr, const char * pchName);
+S_API bool SteamAPI_ISteamUserStats_GetAchievementAndUnlockTime(intptr_t instancePtr, const char * pchName, bool * pbAchieved, uint32 * punUnlockTime);
+S_API bool SteamAPI_ISteamUserStats_StoreStats(intptr_t instancePtr);
+S_API int SteamAPI_ISteamUserStats_GetAchievementIcon(intptr_t instancePtr, const char * pchName);
+S_API const char * SteamAPI_ISteamUserStats_GetAchievementDisplayAttribute(intptr_t instancePtr, const char * pchName, const char * pchKey);
+S_API bool SteamAPI_ISteamUserStats_IndicateAchievementProgress(intptr_t instancePtr, const char * pchName, uint32 nCurProgress, uint32 nMaxProgress);
+S_API uint32 SteamAPI_ISteamUserStats_GetNumAchievements(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamUserStats_GetAchievementName(intptr_t instancePtr, uint32 iAchievement);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_RequestUserStats(intptr_t instancePtr, class CSteamID steamIDUser);
+S_API bool SteamAPI_ISteamUserStats_GetUserStat(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, int32 * pData);
+S_API bool SteamAPI_ISteamUserStats_GetUserStat0(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, float * pData);
+S_API bool SteamAPI_ISteamUserStats_GetUserAchievement(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, bool * pbAchieved);
+S_API bool SteamAPI_ISteamUserStats_GetUserAchievementAndUnlockTime(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, bool * pbAchieved, uint32 * punUnlockTime);
+S_API bool SteamAPI_ISteamUserStats_ResetAllStats(intptr_t instancePtr, bool bAchievementsToo);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_FindOrCreateLeaderboard(intptr_t instancePtr, const char * pchLeaderboardName, ELeaderboardSortMethod eLeaderboardSortMethod, ELeaderboardDisplayType eLeaderboardDisplayType);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_FindLeaderboard(intptr_t instancePtr, const char * pchLeaderboardName);
+S_API const char * SteamAPI_ISteamUserStats_GetLeaderboardName(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard);
+S_API int SteamAPI_ISteamUserStats_GetLeaderboardEntryCount(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard);
+S_API ELeaderboardSortMethod SteamAPI_ISteamUserStats_GetLeaderboardSortMethod(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard);
+S_API ELeaderboardDisplayType SteamAPI_ISteamUserStats_GetLeaderboardDisplayType(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_DownloadLeaderboardEntries(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard, ELeaderboardDataRequest eLeaderboardDataRequest, int nRangeStart, int nRangeEnd);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_DownloadLeaderboardEntriesForUsers(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard, class CSteamID * prgUsers, int cUsers);
+S_API bool SteamAPI_ISteamUserStats_GetDownloadedLeaderboardEntry(intptr_t instancePtr, SteamLeaderboardEntries_t hSteamLeaderboardEntries, int index, struct LeaderboardEntry_t * pLeaderboardEntry, int32 * pDetails, int cDetailsMax);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_UploadLeaderboardScore(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard, ELeaderboardUploadScoreMethod eLeaderboardUploadScoreMethod, int32 nScore, const int32 * pScoreDetails, int cScoreDetailsCount);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_AttachLeaderboardUGC(intptr_t instancePtr, SteamLeaderboard_t hSteamLeaderboard, UGCHandle_t hUGC);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_GetNumberOfCurrentPlayers(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_RequestGlobalAchievementPercentages(intptr_t instancePtr);
+S_API int SteamAPI_ISteamUserStats_GetMostAchievedAchievementInfo(intptr_t instancePtr, char * pchName, uint32 unNameBufLen, float * pflPercent, bool * pbAchieved);
+S_API int SteamAPI_ISteamUserStats_GetNextMostAchievedAchievementInfo(intptr_t instancePtr, int iIteratorPrevious, char * pchName, uint32 unNameBufLen, float * pflPercent, bool * pbAchieved);
+S_API bool SteamAPI_ISteamUserStats_GetAchievementAchievedPercent(intptr_t instancePtr, const char * pchName, float * pflPercent);
+S_API SteamAPICall_t SteamAPI_ISteamUserStats_RequestGlobalStats(intptr_t instancePtr, int nHistoryDays);
+S_API bool SteamAPI_ISteamUserStats_GetGlobalStat(intptr_t instancePtr, const char * pchStatName, int64 * pData);
+S_API bool SteamAPI_ISteamUserStats_GetGlobalStat0(intptr_t instancePtr, const char * pchStatName, double * pData);
+S_API int32 SteamAPI_ISteamUserStats_GetGlobalStatHistory(intptr_t instancePtr, const char * pchStatName, int64 * pData, uint32 cubData);
+S_API int32 SteamAPI_ISteamUserStats_GetGlobalStatHistory0(intptr_t instancePtr, const char * pchStatName, double * pData, uint32 cubData);
+S_API bool SteamAPI_ISteamApps_BIsSubscribed(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamApps_BIsLowViolence(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamApps_BIsCybercafe(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamApps_BIsVACBanned(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamApps_GetCurrentGameLanguage(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamApps_GetAvailableGameLanguages(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamApps_BIsSubscribedApp(intptr_t instancePtr, AppId_t appID);
+S_API bool SteamAPI_ISteamApps_BIsDlcInstalled(intptr_t instancePtr, AppId_t appID);
+S_API uint32 SteamAPI_ISteamApps_GetEarliestPurchaseUnixTime(intptr_t instancePtr, AppId_t nAppID);
+S_API bool SteamAPI_ISteamApps_BIsSubscribedFromFreeWeekend(intptr_t instancePtr);
+S_API int SteamAPI_ISteamApps_GetDLCCount(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamApps_BGetDLCDataByIndex(intptr_t instancePtr, int iDLC, AppId_t * pAppID, bool * pbAvailable, char * pchName, int cchNameBufferSize);
+S_API void SteamAPI_ISteamApps_InstallDLC(intptr_t instancePtr, AppId_t nAppID);
+S_API void SteamAPI_ISteamApps_UninstallDLC(intptr_t instancePtr, AppId_t nAppID);
+S_API void SteamAPI_ISteamApps_RequestAppProofOfPurchaseKey(intptr_t instancePtr, AppId_t nAppID);
+S_API bool SteamAPI_ISteamApps_GetCurrentBetaName(intptr_t instancePtr, char * pchName, int cchNameBufferSize);
+S_API bool SteamAPI_ISteamApps_MarkContentCorrupt(intptr_t instancePtr, bool bMissingFilesOnly);
+S_API uint32 SteamAPI_ISteamApps_GetInstalledDepots(intptr_t instancePtr, AppId_t appID, DepotId_t * pvecDepots, uint32 cMaxDepots);
+S_API uint32 SteamAPI_ISteamApps_GetAppInstallDir(intptr_t instancePtr, AppId_t appID, char * pchFolder, uint32 cchFolderBufferSize);
+S_API bool SteamAPI_ISteamApps_BIsAppInstalled(intptr_t instancePtr, AppId_t appID);
+S_API uint64 SteamAPI_ISteamApps_GetAppOwner(intptr_t instancePtr);
+S_API const char * SteamAPI_ISteamApps_GetLaunchQueryParam(intptr_t instancePtr, const char * pchKey);
+S_API bool SteamAPI_ISteamApps_GetDlcDownloadProgress(intptr_t instancePtr, AppId_t nAppID, uint64 * punBytesDownloaded, uint64 * punBytesTotal);
+S_API int SteamAPI_ISteamApps_GetAppBuildId(intptr_t instancePtr);
+S_API void SteamAPI_ISteamApps_RequestAllProofOfPurchaseKeys(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamApps_GetFileDetails(intptr_t instancePtr, const char * pszFileName);
+S_API bool SteamAPI_ISteamNetworking_SendP2PPacket(intptr_t instancePtr, class CSteamID steamIDRemote, const void * pubData, uint32 cubData, EP2PSend eP2PSendType, int nChannel);
+S_API bool SteamAPI_ISteamNetworking_IsP2PPacketAvailable(intptr_t instancePtr, uint32 * pcubMsgSize, int nChannel);
+S_API bool SteamAPI_ISteamNetworking_ReadP2PPacket(intptr_t instancePtr, void * pubDest, uint32 cubDest, uint32 * pcubMsgSize, class CSteamID * psteamIDRemote, int nChannel);
+S_API bool SteamAPI_ISteamNetworking_AcceptP2PSessionWithUser(intptr_t instancePtr, class CSteamID steamIDRemote);
+S_API bool SteamAPI_ISteamNetworking_CloseP2PSessionWithUser(intptr_t instancePtr, class CSteamID steamIDRemote);
+S_API bool SteamAPI_ISteamNetworking_CloseP2PChannelWithUser(intptr_t instancePtr, class CSteamID steamIDRemote, int nChannel);
+S_API bool SteamAPI_ISteamNetworking_GetP2PSessionState(intptr_t instancePtr, class CSteamID steamIDRemote, struct P2PSessionState_t * pConnectionState);
+S_API bool SteamAPI_ISteamNetworking_AllowP2PPacketRelay(intptr_t instancePtr, bool bAllow);
+S_API SNetListenSocket_t SteamAPI_ISteamNetworking_CreateListenSocket(intptr_t instancePtr, int nVirtualP2PPort, uint32 nIP, uint16 nPort, bool bAllowUseOfPacketRelay);
+S_API SNetSocket_t SteamAPI_ISteamNetworking_CreateP2PConnectionSocket(intptr_t instancePtr, class CSteamID steamIDTarget, int nVirtualPort, int nTimeoutSec, bool bAllowUseOfPacketRelay);
+S_API SNetSocket_t SteamAPI_ISteamNetworking_CreateConnectionSocket(intptr_t instancePtr, uint32 nIP, uint16 nPort, int nTimeoutSec);
+S_API bool SteamAPI_ISteamNetworking_DestroySocket(intptr_t instancePtr, SNetSocket_t hSocket, bool bNotifyRemoteEnd);
+S_API bool SteamAPI_ISteamNetworking_DestroyListenSocket(intptr_t instancePtr, SNetListenSocket_t hSocket, bool bNotifyRemoteEnd);
+S_API bool SteamAPI_ISteamNetworking_SendDataOnSocket(intptr_t instancePtr, SNetSocket_t hSocket, void * pubData, uint32 cubData, bool bReliable);
+S_API bool SteamAPI_ISteamNetworking_IsDataAvailableOnSocket(intptr_t instancePtr, SNetSocket_t hSocket, uint32 * pcubMsgSize);
+S_API bool SteamAPI_ISteamNetworking_RetrieveDataFromSocket(intptr_t instancePtr, SNetSocket_t hSocket, void * pubDest, uint32 cubDest, uint32 * pcubMsgSize);
+S_API bool SteamAPI_ISteamNetworking_IsDataAvailable(intptr_t instancePtr, SNetListenSocket_t hListenSocket, uint32 * pcubMsgSize, SNetSocket_t * phSocket);
+S_API bool SteamAPI_ISteamNetworking_RetrieveData(intptr_t instancePtr, SNetListenSocket_t hListenSocket, void * pubDest, uint32 cubDest, uint32 * pcubMsgSize, SNetSocket_t * phSocket);
+S_API bool SteamAPI_ISteamNetworking_GetSocketInfo(intptr_t instancePtr, SNetSocket_t hSocket, class CSteamID * pSteamIDRemote, int * peSocketStatus, uint32 * punIPRemote, uint16 * punPortRemote);
+S_API bool SteamAPI_ISteamNetworking_GetListenSocketInfo(intptr_t instancePtr, SNetListenSocket_t hListenSocket, uint32 * pnIP, uint16 * pnPort);
+S_API ESNetSocketConnectionType SteamAPI_ISteamNetworking_GetSocketConnectionType(intptr_t instancePtr, SNetSocket_t hSocket);
+S_API int SteamAPI_ISteamNetworking_GetMaxPacketSize(intptr_t instancePtr, SNetSocket_t hSocket);
+S_API ScreenshotHandle SteamAPI_ISteamScreenshots_WriteScreenshot(intptr_t instancePtr, void * pubRGB, uint32 cubRGB, int nWidth, int nHeight);
+S_API ScreenshotHandle SteamAPI_ISteamScreenshots_AddScreenshotToLibrary(intptr_t instancePtr, const char * pchFilename, const char * pchThumbnailFilename, int nWidth, int nHeight);
+S_API void SteamAPI_ISteamScreenshots_TriggerScreenshot(intptr_t instancePtr);
+S_API void SteamAPI_ISteamScreenshots_HookScreenshots(intptr_t instancePtr, bool bHook);
+S_API bool SteamAPI_ISteamScreenshots_SetLocation(intptr_t instancePtr, ScreenshotHandle hScreenshot, const char * pchLocation);
+S_API bool SteamAPI_ISteamScreenshots_TagUser(intptr_t instancePtr, ScreenshotHandle hScreenshot, class CSteamID steamID);
+S_API bool SteamAPI_ISteamScreenshots_TagPublishedFile(intptr_t instancePtr, ScreenshotHandle hScreenshot, PublishedFileId_t unPublishedFileID);
+S_API bool SteamAPI_ISteamScreenshots_IsScreenshotsHooked(intptr_t instancePtr);
+S_API ScreenshotHandle SteamAPI_ISteamScreenshots_AddVRScreenshotToLibrary(intptr_t instancePtr, EVRScreenshotType eType, const char * pchFilename, const char * pchVRFilename);
+S_API bool SteamAPI_ISteamMusic_BIsEnabled(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusic_BIsPlaying(intptr_t instancePtr);
+S_API AudioPlayback_Status SteamAPI_ISteamMusic_GetPlaybackStatus(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMusic_Play(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMusic_Pause(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMusic_PlayPrevious(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMusic_PlayNext(intptr_t instancePtr);
+S_API void SteamAPI_ISteamMusic_SetVolume(intptr_t instancePtr, float flVolume);
+S_API float SteamAPI_ISteamMusic_GetVolume(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_RegisterSteamMusicRemote(intptr_t instancePtr, const char * pchName);
+S_API bool SteamAPI_ISteamMusicRemote_DeregisterSteamMusicRemote(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_BIsCurrentMusicRemote(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_BActivationSuccess(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_SetDisplayName(intptr_t instancePtr, const char * pchDisplayName);
+S_API bool SteamAPI_ISteamMusicRemote_SetPNGIcon_64x64(intptr_t instancePtr, void * pvBuffer, uint32 cbBufferLength);
+S_API bool SteamAPI_ISteamMusicRemote_EnablePlayPrevious(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_EnablePlayNext(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_EnableShuffled(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_EnableLooped(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_EnableQueue(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_EnablePlaylists(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_UpdatePlaybackStatus(intptr_t instancePtr, AudioPlayback_Status nStatus);
+S_API bool SteamAPI_ISteamMusicRemote_UpdateShuffled(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_UpdateLooped(intptr_t instancePtr, bool bValue);
+S_API bool SteamAPI_ISteamMusicRemote_UpdateVolume(intptr_t instancePtr, float flValue);
+S_API bool SteamAPI_ISteamMusicRemote_CurrentEntryWillChange(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_CurrentEntryIsAvailable(intptr_t instancePtr, bool bAvailable);
+S_API bool SteamAPI_ISteamMusicRemote_UpdateCurrentEntryText(intptr_t instancePtr, const char * pchText);
+S_API bool SteamAPI_ISteamMusicRemote_UpdateCurrentEntryElapsedSeconds(intptr_t instancePtr, int nValue);
+S_API bool SteamAPI_ISteamMusicRemote_UpdateCurrentEntryCoverArt(intptr_t instancePtr, void * pvBuffer, uint32 cbBufferLength);
+S_API bool SteamAPI_ISteamMusicRemote_CurrentEntryDidChange(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_QueueWillChange(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_ResetQueueEntries(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_SetQueueEntry(intptr_t instancePtr, int nID, int nPosition, const char * pchEntryText);
+S_API bool SteamAPI_ISteamMusicRemote_SetCurrentQueueEntry(intptr_t instancePtr, int nID);
+S_API bool SteamAPI_ISteamMusicRemote_QueueDidChange(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_PlaylistWillChange(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_ResetPlaylistEntries(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamMusicRemote_SetPlaylistEntry(intptr_t instancePtr, int nID, int nPosition, const char * pchEntryText);
+S_API bool SteamAPI_ISteamMusicRemote_SetCurrentPlaylistEntry(intptr_t instancePtr, int nID);
+S_API bool SteamAPI_ISteamMusicRemote_PlaylistDidChange(intptr_t instancePtr);
+S_API HTTPRequestHandle SteamAPI_ISteamHTTP_CreateHTTPRequest(intptr_t instancePtr, EHTTPMethod eHTTPRequestMethod, const char * pchAbsoluteURL);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestContextValue(intptr_t instancePtr, HTTPRequestHandle hRequest, uint64 ulContextValue);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestNetworkActivityTimeout(intptr_t instancePtr, HTTPRequestHandle hRequest, uint32 unTimeoutSeconds);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestHeaderValue(intptr_t instancePtr, HTTPRequestHandle hRequest, const char * pchHeaderName, const char * pchHeaderValue);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestGetOrPostParameter(intptr_t instancePtr, HTTPRequestHandle hRequest, const char * pchParamName, const char * pchParamValue);
+S_API bool SteamAPI_ISteamHTTP_SendHTTPRequest(intptr_t instancePtr, HTTPRequestHandle hRequest, SteamAPICall_t * pCallHandle);
+S_API bool SteamAPI_ISteamHTTP_SendHTTPRequestAndStreamResponse(intptr_t instancePtr, HTTPRequestHandle hRequest, SteamAPICall_t * pCallHandle);
+S_API bool SteamAPI_ISteamHTTP_DeferHTTPRequest(intptr_t instancePtr, HTTPRequestHandle hRequest);
+S_API bool SteamAPI_ISteamHTTP_PrioritizeHTTPRequest(intptr_t instancePtr, HTTPRequestHandle hRequest);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPResponseHeaderSize(intptr_t instancePtr, HTTPRequestHandle hRequest, const char * pchHeaderName, uint32 * unResponseHeaderSize);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPResponseHeaderValue(intptr_t instancePtr, HTTPRequestHandle hRequest, const char * pchHeaderName, uint8 * pHeaderValueBuffer, uint32 unBufferSize);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPResponseBodySize(intptr_t instancePtr, HTTPRequestHandle hRequest, uint32 * unBodySize);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPResponseBodyData(intptr_t instancePtr, HTTPRequestHandle hRequest, uint8 * pBodyDataBuffer, uint32 unBufferSize);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPStreamingResponseBodyData(intptr_t instancePtr, HTTPRequestHandle hRequest, uint32 cOffset, uint8 * pBodyDataBuffer, uint32 unBufferSize);
+S_API bool SteamAPI_ISteamHTTP_ReleaseHTTPRequest(intptr_t instancePtr, HTTPRequestHandle hRequest);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPDownloadProgressPct(intptr_t instancePtr, HTTPRequestHandle hRequest, float * pflPercentOut);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestRawPostBody(intptr_t instancePtr, HTTPRequestHandle hRequest, const char * pchContentType, uint8 * pubBody, uint32 unBodyLen);
+S_API HTTPCookieContainerHandle SteamAPI_ISteamHTTP_CreateCookieContainer(intptr_t instancePtr, bool bAllowResponsesToModify);
+S_API bool SteamAPI_ISteamHTTP_ReleaseCookieContainer(intptr_t instancePtr, HTTPCookieContainerHandle hCookieContainer);
+S_API bool SteamAPI_ISteamHTTP_SetCookie(intptr_t instancePtr, HTTPCookieContainerHandle hCookieContainer, const char * pchHost, const char * pchUrl, const char * pchCookie);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestCookieContainer(intptr_t instancePtr, HTTPRequestHandle hRequest, HTTPCookieContainerHandle hCookieContainer);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestUserAgentInfo(intptr_t instancePtr, HTTPRequestHandle hRequest, const char * pchUserAgentInfo);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestRequiresVerifiedCertificate(intptr_t instancePtr, HTTPRequestHandle hRequest, bool bRequireVerifiedCertificate);
+S_API bool SteamAPI_ISteamHTTP_SetHTTPRequestAbsoluteTimeoutMS(intptr_t instancePtr, HTTPRequestHandle hRequest, uint32 unMilliseconds);
+S_API bool SteamAPI_ISteamHTTP_GetHTTPRequestWasTimedOut(intptr_t instancePtr, HTTPRequestHandle hRequest, bool * pbWasTimedOut);
+S_API ClientUnifiedMessageHandle SteamAPI_ISteamUnifiedMessages_SendMethod(intptr_t instancePtr, const char * pchServiceMethod, const void * pRequestBuffer, uint32 unRequestBufferSize, uint64 unContext);
+S_API bool SteamAPI_ISteamUnifiedMessages_GetMethodResponseInfo(intptr_t instancePtr, ClientUnifiedMessageHandle hHandle, uint32 * punResponseSize, EResult * peResult);
+S_API bool SteamAPI_ISteamUnifiedMessages_GetMethodResponseData(intptr_t instancePtr, ClientUnifiedMessageHandle hHandle, void * pResponseBuffer, uint32 unResponseBufferSize, bool bAutoRelease);
+S_API bool SteamAPI_ISteamUnifiedMessages_ReleaseMethod(intptr_t instancePtr, ClientUnifiedMessageHandle hHandle);
+S_API bool SteamAPI_ISteamUnifiedMessages_SendNotification(intptr_t instancePtr, const char * pchServiceNotification, const void * pNotificationBuffer, uint32 unNotificationBufferSize);
+S_API bool SteamAPI_ISteamController_Init(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamController_Shutdown(intptr_t instancePtr);
+S_API void SteamAPI_ISteamController_RunFrame(intptr_t instancePtr);
+S_API int SteamAPI_ISteamController_GetConnectedControllers(intptr_t instancePtr, ControllerHandle_t * handlesOut);
+S_API bool SteamAPI_ISteamController_ShowBindingPanel(intptr_t instancePtr, ControllerHandle_t controllerHandle);
+S_API ControllerActionSetHandle_t SteamAPI_ISteamController_GetActionSetHandle(intptr_t instancePtr, const char * pszActionSetName);
+S_API void SteamAPI_ISteamController_ActivateActionSet(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerActionSetHandle_t actionSetHandle);
+S_API ControllerActionSetHandle_t SteamAPI_ISteamController_GetCurrentActionSet(intptr_t instancePtr, ControllerHandle_t controllerHandle);
+S_API ControllerDigitalActionHandle_t SteamAPI_ISteamController_GetDigitalActionHandle(intptr_t instancePtr, const char * pszActionName);
+S_API struct ControllerDigitalActionData_t SteamAPI_ISteamController_GetDigitalActionData(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerDigitalActionHandle_t digitalActionHandle);
+S_API int SteamAPI_ISteamController_GetDigitalActionOrigins(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerActionSetHandle_t actionSetHandle, ControllerDigitalActionHandle_t digitalActionHandle, EControllerActionOrigin * originsOut);
+S_API ControllerAnalogActionHandle_t SteamAPI_ISteamController_GetAnalogActionHandle(intptr_t instancePtr, const char * pszActionName);
+S_API struct ControllerAnalogActionData_t SteamAPI_ISteamController_GetAnalogActionData(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerAnalogActionHandle_t analogActionHandle);
+S_API int SteamAPI_ISteamController_GetAnalogActionOrigins(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerActionSetHandle_t actionSetHandle, ControllerAnalogActionHandle_t analogActionHandle, EControllerActionOrigin * originsOut);
+S_API void SteamAPI_ISteamController_StopAnalogActionMomentum(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerAnalogActionHandle_t eAction);
+S_API void SteamAPI_ISteamController_TriggerHapticPulse(intptr_t instancePtr, ControllerHandle_t controllerHandle, ESteamControllerPad eTargetPad, unsigned short usDurationMicroSec);
+S_API void SteamAPI_ISteamController_TriggerRepeatedHapticPulse(intptr_t instancePtr, ControllerHandle_t controllerHandle, ESteamControllerPad eTargetPad, unsigned short usDurationMicroSec, unsigned short usOffMicroSec, unsigned short unRepeat, unsigned int nFlags);
+S_API void SteamAPI_ISteamController_TriggerVibration(intptr_t instancePtr, ControllerHandle_t controllerHandle, unsigned short usLeftSpeed, unsigned short usRightSpeed);
+S_API void SteamAPI_ISteamController_SetLEDColor(intptr_t instancePtr, ControllerHandle_t controllerHandle, uint8 nColorR, uint8 nColorG, uint8 nColorB, unsigned int nFlags);
+S_API int SteamAPI_ISteamController_GetGamepadIndexForController(intptr_t instancePtr, ControllerHandle_t ulControllerHandle);
+S_API ControllerHandle_t SteamAPI_ISteamController_GetControllerForGamepadIndex(intptr_t instancePtr, int nIndex);
+S_API struct ControllerMotionData_t SteamAPI_ISteamController_GetMotionData(intptr_t instancePtr, ControllerHandle_t controllerHandle);
+S_API bool SteamAPI_ISteamController_ShowDigitalActionOrigins(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerDigitalActionHandle_t digitalActionHandle, float flScale, float flXPosition, float flYPosition);
+S_API bool SteamAPI_ISteamController_ShowAnalogActionOrigins(intptr_t instancePtr, ControllerHandle_t controllerHandle, ControllerAnalogActionHandle_t analogActionHandle, float flScale, float flXPosition, float flYPosition);
+S_API const char * SteamAPI_ISteamController_GetStringForActionOrigin(intptr_t instancePtr, EControllerActionOrigin eOrigin);
+S_API const char * SteamAPI_ISteamController_GetGlyphForActionOrigin(intptr_t instancePtr, EControllerActionOrigin eOrigin);
+S_API UGCQueryHandle_t SteamAPI_ISteamUGC_CreateQueryUserUGCRequest(intptr_t instancePtr, AccountID_t unAccountID, EUserUGCList eListType, EUGCMatchingUGCType eMatchingUGCType, EUserUGCListSortOrder eSortOrder, AppId_t nCreatorAppID, AppId_t nConsumerAppID, uint32 unPage);
+S_API UGCQueryHandle_t SteamAPI_ISteamUGC_CreateQueryAllUGCRequest(intptr_t instancePtr, EUGCQuery eQueryType, EUGCMatchingUGCType eMatchingeMatchingUGCTypeFileType, AppId_t nCreatorAppID, AppId_t nConsumerAppID, uint32 unPage);
+S_API UGCQueryHandle_t SteamAPI_ISteamUGC_CreateQueryUGCDetailsRequest(intptr_t instancePtr, PublishedFileId_t * pvecPublishedFileID, uint32 unNumPublishedFileIDs);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_SendQueryUGCRequest(intptr_t instancePtr, UGCQueryHandle_t handle);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCResult(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, struct SteamUGCDetails_t * pDetails);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCPreviewURL(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, char * pchURL, uint32 cchURLSize);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCMetadata(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, char * pchMetadata, uint32 cchMetadatasize);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCChildren(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, PublishedFileId_t * pvecPublishedFileID, uint32 cMaxEntries);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCStatistic(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, EItemStatistic eStatType, uint64 * pStatValue);
+S_API uint32 SteamAPI_ISteamUGC_GetQueryUGCNumAdditionalPreviews(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCAdditionalPreview(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, uint32 previewIndex, char * pchURLOrVideoID, uint32 cchURLSize, char * pchOriginalFileName, uint32 cchOriginalFileNameSize, EItemPreviewType * pPreviewType);
+S_API uint32 SteamAPI_ISteamUGC_GetQueryUGCNumKeyValueTags(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index);
+S_API bool SteamAPI_ISteamUGC_GetQueryUGCKeyValueTag(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 index, uint32 keyValueTagIndex, char * pchKey, uint32 cchKeySize, char * pchValue, uint32 cchValueSize);
+S_API bool SteamAPI_ISteamUGC_ReleaseQueryUGCRequest(intptr_t instancePtr, UGCQueryHandle_t handle);
+S_API bool SteamAPI_ISteamUGC_AddRequiredTag(intptr_t instancePtr, UGCQueryHandle_t handle, const char * pTagName);
+S_API bool SteamAPI_ISteamUGC_AddExcludedTag(intptr_t instancePtr, UGCQueryHandle_t handle, const char * pTagName);
+S_API bool SteamAPI_ISteamUGC_SetReturnOnlyIDs(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnOnlyIDs);
+S_API bool SteamAPI_ISteamUGC_SetReturnKeyValueTags(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnKeyValueTags);
+S_API bool SteamAPI_ISteamUGC_SetReturnLongDescription(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnLongDescription);
+S_API bool SteamAPI_ISteamUGC_SetReturnMetadata(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnMetadata);
+S_API bool SteamAPI_ISteamUGC_SetReturnChildren(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnChildren);
+S_API bool SteamAPI_ISteamUGC_SetReturnAdditionalPreviews(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnAdditionalPreviews);
+S_API bool SteamAPI_ISteamUGC_SetReturnTotalOnly(intptr_t instancePtr, UGCQueryHandle_t handle, bool bReturnTotalOnly);
+S_API bool SteamAPI_ISteamUGC_SetReturnPlaytimeStats(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 unDays);
+S_API bool SteamAPI_ISteamUGC_SetLanguage(intptr_t instancePtr, UGCQueryHandle_t handle, const char * pchLanguage);
+S_API bool SteamAPI_ISteamUGC_SetAllowCachedResponse(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 unMaxAgeSeconds);
+S_API bool SteamAPI_ISteamUGC_SetCloudFileNameFilter(intptr_t instancePtr, UGCQueryHandle_t handle, const char * pMatchCloudFileName);
+S_API bool SteamAPI_ISteamUGC_SetMatchAnyTag(intptr_t instancePtr, UGCQueryHandle_t handle, bool bMatchAnyTag);
+S_API bool SteamAPI_ISteamUGC_SetSearchText(intptr_t instancePtr, UGCQueryHandle_t handle, const char * pSearchText);
+S_API bool SteamAPI_ISteamUGC_SetRankedByTrendDays(intptr_t instancePtr, UGCQueryHandle_t handle, uint32 unDays);
+S_API bool SteamAPI_ISteamUGC_AddRequiredKeyValueTag(intptr_t instancePtr, UGCQueryHandle_t handle, const char * pKey, const char * pValue);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_RequestUGCDetails(intptr_t instancePtr, PublishedFileId_t nPublishedFileID, uint32 unMaxAgeSeconds);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_CreateItem(intptr_t instancePtr, AppId_t nConsumerAppId, EWorkshopFileType eFileType);
+S_API UGCUpdateHandle_t SteamAPI_ISteamUGC_StartItemUpdate(intptr_t instancePtr, AppId_t nConsumerAppId, PublishedFileId_t nPublishedFileID);
+S_API bool SteamAPI_ISteamUGC_SetItemTitle(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchTitle);
+S_API bool SteamAPI_ISteamUGC_SetItemDescription(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchDescription);
+S_API bool SteamAPI_ISteamUGC_SetItemUpdateLanguage(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchLanguage);
+S_API bool SteamAPI_ISteamUGC_SetItemMetadata(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchMetaData);
+S_API bool SteamAPI_ISteamUGC_SetItemVisibility(intptr_t instancePtr, UGCUpdateHandle_t handle, ERemoteStoragePublishedFileVisibility eVisibility);
+S_API bool SteamAPI_ISteamUGC_SetItemTags(intptr_t instancePtr, UGCUpdateHandle_t updateHandle, const struct SteamParamStringArray_t * pTags);
+S_API bool SteamAPI_ISteamUGC_SetItemContent(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pszContentFolder);
+S_API bool SteamAPI_ISteamUGC_SetItemPreview(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pszPreviewFile);
+S_API bool SteamAPI_ISteamUGC_RemoveItemKeyValueTags(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchKey);
+S_API bool SteamAPI_ISteamUGC_AddItemKeyValueTag(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchKey, const char * pchValue);
+S_API bool SteamAPI_ISteamUGC_AddItemPreviewFile(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pszPreviewFile, EItemPreviewType type);
+S_API bool SteamAPI_ISteamUGC_AddItemPreviewVideo(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pszVideoID);
+S_API bool SteamAPI_ISteamUGC_UpdateItemPreviewFile(intptr_t instancePtr, UGCUpdateHandle_t handle, uint32 index, const char * pszPreviewFile);
+S_API bool SteamAPI_ISteamUGC_UpdateItemPreviewVideo(intptr_t instancePtr, UGCUpdateHandle_t handle, uint32 index, const char * pszVideoID);
+S_API bool SteamAPI_ISteamUGC_RemoveItemPreview(intptr_t instancePtr, UGCUpdateHandle_t handle, uint32 index);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_SubmitItemUpdate(intptr_t instancePtr, UGCUpdateHandle_t handle, const char * pchChangeNote);
+S_API EItemUpdateStatus SteamAPI_ISteamUGC_GetItemUpdateProgress(intptr_t instancePtr, UGCUpdateHandle_t handle, uint64 * punBytesProcessed, uint64 * punBytesTotal);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_SetUserItemVote(intptr_t instancePtr, PublishedFileId_t nPublishedFileID, bool bVoteUp);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_GetUserItemVote(intptr_t instancePtr, PublishedFileId_t nPublishedFileID);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_AddItemToFavorites(intptr_t instancePtr, AppId_t nAppId, PublishedFileId_t nPublishedFileID);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_RemoveItemFromFavorites(intptr_t instancePtr, AppId_t nAppId, PublishedFileId_t nPublishedFileID);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_SubscribeItem(intptr_t instancePtr, PublishedFileId_t nPublishedFileID);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_UnsubscribeItem(intptr_t instancePtr, PublishedFileId_t nPublishedFileID);
+S_API uint32 SteamAPI_ISteamUGC_GetNumSubscribedItems(intptr_t instancePtr);
+S_API uint32 SteamAPI_ISteamUGC_GetSubscribedItems(intptr_t instancePtr, PublishedFileId_t * pvecPublishedFileID, uint32 cMaxEntries);
+S_API uint32 SteamAPI_ISteamUGC_GetItemState(intptr_t instancePtr, PublishedFileId_t nPublishedFileID);
+S_API bool SteamAPI_ISteamUGC_GetItemInstallInfo(intptr_t instancePtr, PublishedFileId_t nPublishedFileID, uint64 * punSizeOnDisk, char * pchFolder, uint32 cchFolderSize, uint32 * punTimeStamp);
+S_API bool SteamAPI_ISteamUGC_GetItemDownloadInfo(intptr_t instancePtr, PublishedFileId_t nPublishedFileID, uint64 * punBytesDownloaded, uint64 * punBytesTotal);
+S_API bool SteamAPI_ISteamUGC_DownloadItem(intptr_t instancePtr, PublishedFileId_t nPublishedFileID, bool bHighPriority);
+S_API bool SteamAPI_ISteamUGC_BInitWorkshopForGameServer(intptr_t instancePtr, DepotId_t unWorkshopDepotID, const char * pszFolder);
+S_API void SteamAPI_ISteamUGC_SuspendDownloads(intptr_t instancePtr, bool bSuspend);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_StartPlaytimeTracking(intptr_t instancePtr, PublishedFileId_t * pvecPublishedFileID, uint32 unNumPublishedFileIDs);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_StopPlaytimeTracking(intptr_t instancePtr, PublishedFileId_t * pvecPublishedFileID, uint32 unNumPublishedFileIDs);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_StopPlaytimeTrackingForAllItems(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_AddDependency(intptr_t instancePtr, PublishedFileId_t nParentPublishedFileID, PublishedFileId_t nChildPublishedFileID);
+S_API SteamAPICall_t SteamAPI_ISteamUGC_RemoveDependency(intptr_t instancePtr, PublishedFileId_t nParentPublishedFileID, PublishedFileId_t nChildPublishedFileID);
+S_API uint32 SteamAPI_ISteamAppList_GetNumInstalledApps(intptr_t instancePtr);
+S_API uint32 SteamAPI_ISteamAppList_GetInstalledApps(intptr_t instancePtr, AppId_t * pvecAppID, uint32 unMaxAppIDs);
+S_API int SteamAPI_ISteamAppList_GetAppName(intptr_t instancePtr, AppId_t nAppID, char * pchName, int cchNameMax);
+S_API int SteamAPI_ISteamAppList_GetAppInstallDir(intptr_t instancePtr, AppId_t nAppID, char * pchDirectory, int cchNameMax);
+S_API int SteamAPI_ISteamAppList_GetAppBuildId(intptr_t instancePtr, AppId_t nAppID);
+S_API void SteamAPI_ISteamHTMLSurface_DestructISteamHTMLSurface(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamHTMLSurface_Init(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamHTMLSurface_Shutdown(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamHTMLSurface_CreateBrowser(intptr_t instancePtr, const char * pchUserAgent, const char * pchUserCSS);
+S_API void SteamAPI_ISteamHTMLSurface_RemoveBrowser(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_LoadURL(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, const char * pchURL, const char * pchPostData);
+S_API void SteamAPI_ISteamHTMLSurface_SetSize(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, uint32 unWidth, uint32 unHeight);
+S_API void SteamAPI_ISteamHTMLSurface_StopLoad(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_Reload(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_GoBack(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_GoForward(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_AddHeader(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, const char * pchKey, const char * pchValue);
+S_API void SteamAPI_ISteamHTMLSurface_ExecuteJavascript(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, const char * pchScript);
+S_API void SteamAPI_ISteamHTMLSurface_MouseUp(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, ISteamHTMLSurface::EHTMLMouseButton eMouseButton);
+S_API void SteamAPI_ISteamHTMLSurface_MouseDown(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, ISteamHTMLSurface::EHTMLMouseButton eMouseButton);
+S_API void SteamAPI_ISteamHTMLSurface_MouseDoubleClick(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, ISteamHTMLSurface::EHTMLMouseButton eMouseButton);
+S_API void SteamAPI_ISteamHTMLSurface_MouseMove(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, int x, int y);
+S_API void SteamAPI_ISteamHTMLSurface_MouseWheel(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, int32 nDelta);
+S_API void SteamAPI_ISteamHTMLSurface_KeyDown(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, uint32 nNativeKeyCode, ISteamHTMLSurface::EHTMLKeyModifiers eHTMLKeyModifiers);
+S_API void SteamAPI_ISteamHTMLSurface_KeyUp(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, uint32 nNativeKeyCode, ISteamHTMLSurface::EHTMLKeyModifiers eHTMLKeyModifiers);
+S_API void SteamAPI_ISteamHTMLSurface_KeyChar(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, uint32 cUnicodeChar, ISteamHTMLSurface::EHTMLKeyModifiers eHTMLKeyModifiers);
+S_API void SteamAPI_ISteamHTMLSurface_SetHorizontalScroll(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, uint32 nAbsolutePixelScroll);
+S_API void SteamAPI_ISteamHTMLSurface_SetVerticalScroll(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, uint32 nAbsolutePixelScroll);
+S_API void SteamAPI_ISteamHTMLSurface_SetKeyFocus(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, bool bHasKeyFocus);
+S_API void SteamAPI_ISteamHTMLSurface_ViewSource(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_CopyToClipboard(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_PasteFromClipboard(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_Find(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, const char * pchSearchStr, bool bCurrentlyInFind, bool bReverse);
+S_API void SteamAPI_ISteamHTMLSurface_StopFind(intptr_t instancePtr, HHTMLBrowser unBrowserHandle);
+S_API void SteamAPI_ISteamHTMLSurface_GetLinkAtPosition(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, int x, int y);
+S_API void SteamAPI_ISteamHTMLSurface_SetCookie(intptr_t instancePtr, const char * pchHostname, const char * pchKey, const char * pchValue, const char * pchPath, RTime32 nExpires, bool bSecure, bool bHTTPOnly);
+S_API void SteamAPI_ISteamHTMLSurface_SetPageScaleFactor(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, float flZoom, int nPointX, int nPointY);
+S_API void SteamAPI_ISteamHTMLSurface_SetBackgroundMode(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, bool bBackgroundMode);
+S_API void SteamAPI_ISteamHTMLSurface_AllowStartRequest(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, bool bAllowed);
+S_API void SteamAPI_ISteamHTMLSurface_JSDialogResponse(intptr_t instancePtr, HHTMLBrowser unBrowserHandle, bool bResult);
+S_API EResult SteamAPI_ISteamInventory_GetResultStatus(intptr_t instancePtr, SteamInventoryResult_t resultHandle);
+S_API bool SteamAPI_ISteamInventory_GetResultItems(intptr_t instancePtr, SteamInventoryResult_t resultHandle, struct SteamItemDetails_t * pOutItemsArray, uint32 * punOutItemsArraySize);
+S_API bool SteamAPI_ISteamInventory_GetResultItemProperty(intptr_t instancePtr, SteamInventoryResult_t resultHandle, uint32 unItemIndex, const char * pchPropertyName, char * pchValueBuffer, uint32 * punValueBufferSizeOut);
+S_API uint32 SteamAPI_ISteamInventory_GetResultTimestamp(intptr_t instancePtr, SteamInventoryResult_t resultHandle);
+S_API bool SteamAPI_ISteamInventory_CheckResultSteamID(intptr_t instancePtr, SteamInventoryResult_t resultHandle, class CSteamID steamIDExpected);
+S_API void SteamAPI_ISteamInventory_DestroyResult(intptr_t instancePtr, SteamInventoryResult_t resultHandle);
+S_API bool SteamAPI_ISteamInventory_GetAllItems(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle);
+S_API bool SteamAPI_ISteamInventory_GetItemsByID(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, const SteamItemInstanceID_t * pInstanceIDs, uint32 unCountInstanceIDs);
+S_API bool SteamAPI_ISteamInventory_SerializeResult(intptr_t instancePtr, SteamInventoryResult_t resultHandle, void * pOutBuffer, uint32 * punOutBufferSize);
+S_API bool SteamAPI_ISteamInventory_DeserializeResult(intptr_t instancePtr, SteamInventoryResult_t * pOutResultHandle, const void * pBuffer, uint32 unBufferSize, bool bRESERVED_MUST_BE_FALSE);
+S_API bool SteamAPI_ISteamInventory_GenerateItems(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, const SteamItemDef_t * pArrayItemDefs, const uint32 * punArrayQuantity, uint32 unArrayLength);
+S_API bool SteamAPI_ISteamInventory_GrantPromoItems(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle);
+S_API bool SteamAPI_ISteamInventory_AddPromoItem(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, SteamItemDef_t itemDef);
+S_API bool SteamAPI_ISteamInventory_AddPromoItems(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, const SteamItemDef_t * pArrayItemDefs, uint32 unArrayLength);
+S_API bool SteamAPI_ISteamInventory_ConsumeItem(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, SteamItemInstanceID_t itemConsume, uint32 unQuantity);
+S_API bool SteamAPI_ISteamInventory_ExchangeItems(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, const SteamItemDef_t * pArrayGenerate, const uint32 * punArrayGenerateQuantity, uint32 unArrayGenerateLength, const SteamItemInstanceID_t * pArrayDestroy, const uint32 * punArrayDestroyQuantity, uint32 unArrayDestroyLength);
+S_API bool SteamAPI_ISteamInventory_TransferItemQuantity(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, SteamItemInstanceID_t itemIdSource, uint32 unQuantity, SteamItemInstanceID_t itemIdDest);
+S_API void SteamAPI_ISteamInventory_SendItemDropHeartbeat(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamInventory_TriggerItemDrop(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, SteamItemDef_t dropListDefinition);
+S_API bool SteamAPI_ISteamInventory_TradeItems(intptr_t instancePtr, SteamInventoryResult_t * pResultHandle, class CSteamID steamIDTradePartner, const SteamItemInstanceID_t * pArrayGive, const uint32 * pArrayGiveQuantity, uint32 nArrayGiveLength, const SteamItemInstanceID_t * pArrayGet, const uint32 * pArrayGetQuantity, uint32 nArrayGetLength);
+S_API bool SteamAPI_ISteamInventory_LoadItemDefinitions(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamInventory_GetItemDefinitionIDs(intptr_t instancePtr, SteamItemDef_t * pItemDefIDs, uint32 * punItemDefIDsArraySize);
+S_API bool SteamAPI_ISteamInventory_GetItemDefinitionProperty(intptr_t instancePtr, SteamItemDef_t iDefinition, const char * pchPropertyName, char * pchValueBuffer, uint32 * punValueBufferSizeOut);
+S_API SteamAPICall_t SteamAPI_ISteamInventory_RequestEligiblePromoItemDefinitionsIDs(intptr_t instancePtr, class CSteamID steamID);
+S_API bool SteamAPI_ISteamInventory_GetEligiblePromoItemDefinitionIDs(intptr_t instancePtr, class CSteamID steamID, SteamItemDef_t * pItemDefIDs, uint32 * punItemDefIDsArraySize);
+S_API void SteamAPI_ISteamVideo_GetVideoURL(intptr_t instancePtr, AppId_t unVideoAppID);
+S_API bool SteamAPI_ISteamVideo_IsBroadcasting(intptr_t instancePtr, int * pnNumViewers);
+S_API void SteamAPI_ISteamVideo_GetOPFSettings(intptr_t instancePtr, AppId_t unVideoAppID);
+S_API bool SteamAPI_ISteamVideo_GetOPFStringForApp(intptr_t instancePtr, AppId_t unVideoAppID, char * pchBuffer, int32 * pnBufferSize);
+S_API bool SteamAPI_ISteamGameServer_InitGameServer(intptr_t instancePtr, uint32 unIP, uint16 usGamePort, uint16 usQueryPort, uint32 unFlags, AppId_t nGameAppId, const char * pchVersionString);
+S_API void SteamAPI_ISteamGameServer_SetProduct(intptr_t instancePtr, const char * pszProduct);
+S_API void SteamAPI_ISteamGameServer_SetGameDescription(intptr_t instancePtr, const char * pszGameDescription);
+S_API void SteamAPI_ISteamGameServer_SetModDir(intptr_t instancePtr, const char * pszModDir);
+S_API void SteamAPI_ISteamGameServer_SetDedicatedServer(intptr_t instancePtr, bool bDedicated);
+S_API void SteamAPI_ISteamGameServer_LogOn(intptr_t instancePtr, const char * pszToken);
+S_API void SteamAPI_ISteamGameServer_LogOnAnonymous(intptr_t instancePtr);
+S_API void SteamAPI_ISteamGameServer_LogOff(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamGameServer_BLoggedOn(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamGameServer_BSecure(intptr_t instancePtr);
+S_API uint64 SteamAPI_ISteamGameServer_GetSteamID(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamGameServer_WasRestartRequested(intptr_t instancePtr);
+S_API void SteamAPI_ISteamGameServer_SetMaxPlayerCount(intptr_t instancePtr, int cPlayersMax);
+S_API void SteamAPI_ISteamGameServer_SetBotPlayerCount(intptr_t instancePtr, int cBotplayers);
+S_API void SteamAPI_ISteamGameServer_SetServerName(intptr_t instancePtr, const char * pszServerName);
+S_API void SteamAPI_ISteamGameServer_SetMapName(intptr_t instancePtr, const char * pszMapName);
+S_API void SteamAPI_ISteamGameServer_SetPasswordProtected(intptr_t instancePtr, bool bPasswordProtected);
+S_API void SteamAPI_ISteamGameServer_SetSpectatorPort(intptr_t instancePtr, uint16 unSpectatorPort);
+S_API void SteamAPI_ISteamGameServer_SetSpectatorServerName(intptr_t instancePtr, const char * pszSpectatorServerName);
+S_API void SteamAPI_ISteamGameServer_ClearAllKeyValues(intptr_t instancePtr);
+S_API void SteamAPI_ISteamGameServer_SetKeyValue(intptr_t instancePtr, const char * pKey, const char * pValue);
+S_API void SteamAPI_ISteamGameServer_SetGameTags(intptr_t instancePtr, const char * pchGameTags);
+S_API void SteamAPI_ISteamGameServer_SetGameData(intptr_t instancePtr, const char * pchGameData);
+S_API void SteamAPI_ISteamGameServer_SetRegion(intptr_t instancePtr, const char * pszRegion);
+S_API bool SteamAPI_ISteamGameServer_SendUserConnectAndAuthenticate(intptr_t instancePtr, uint32 unIPClient, const void * pvAuthBlob, uint32 cubAuthBlobSize, class CSteamID * pSteamIDUser);
+S_API uint64 SteamAPI_ISteamGameServer_CreateUnauthenticatedUserConnection(intptr_t instancePtr);
+S_API void SteamAPI_ISteamGameServer_SendUserDisconnect(intptr_t instancePtr, class CSteamID steamIDUser);
+S_API bool SteamAPI_ISteamGameServer_BUpdateUserData(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchPlayerName, uint32 uScore);
+S_API HAuthTicket SteamAPI_ISteamGameServer_GetAuthSessionTicket(intptr_t instancePtr, void * pTicket, int cbMaxTicket, uint32 * pcbTicket);
+S_API EBeginAuthSessionResult SteamAPI_ISteamGameServer_BeginAuthSession(intptr_t instancePtr, const void * pAuthTicket, int cbAuthTicket, class CSteamID steamID);
+S_API void SteamAPI_ISteamGameServer_EndAuthSession(intptr_t instancePtr, class CSteamID steamID);
+S_API void SteamAPI_ISteamGameServer_CancelAuthTicket(intptr_t instancePtr, HAuthTicket hAuthTicket);
+S_API EUserHasLicenseForAppResult SteamAPI_ISteamGameServer_UserHasLicenseForApp(intptr_t instancePtr, class CSteamID steamID, AppId_t appID);
+S_API bool SteamAPI_ISteamGameServer_RequestUserGroupStatus(intptr_t instancePtr, class CSteamID steamIDUser, class CSteamID steamIDGroup);
+S_API void SteamAPI_ISteamGameServer_GetGameplayStats(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamGameServer_GetServerReputation(intptr_t instancePtr);
+S_API uint32 SteamAPI_ISteamGameServer_GetPublicIP(intptr_t instancePtr);
+S_API bool SteamAPI_ISteamGameServer_HandleIncomingPacket(intptr_t instancePtr, const void * pData, int cbData, uint32 srcIP, uint16 srcPort);
+S_API int SteamAPI_ISteamGameServer_GetNextOutgoingPacket(intptr_t instancePtr, void * pOut, int cbMaxOut, uint32 * pNetAdr, uint16 * pPort);
+S_API void SteamAPI_ISteamGameServer_EnableHeartbeats(intptr_t instancePtr, bool bActive);
+S_API void SteamAPI_ISteamGameServer_SetHeartbeatInterval(intptr_t instancePtr, int iHeartbeatInterval);
+S_API void SteamAPI_ISteamGameServer_ForceHeartbeat(intptr_t instancePtr);
+S_API SteamAPICall_t SteamAPI_ISteamGameServer_AssociateWithClan(intptr_t instancePtr, class CSteamID steamIDClan);
+S_API SteamAPICall_t SteamAPI_ISteamGameServer_ComputeNewPlayerCompatibility(intptr_t instancePtr, class CSteamID steamIDNewPlayer);
+S_API SteamAPICall_t SteamAPI_ISteamGameServerStats_RequestUserStats(intptr_t instancePtr, class CSteamID steamIDUser);
+S_API bool SteamAPI_ISteamGameServerStats_GetUserStat(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, int32 * pData);
+S_API bool SteamAPI_ISteamGameServerStats_GetUserStat0(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, float * pData);
+S_API bool SteamAPI_ISteamGameServerStats_GetUserAchievement(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, bool * pbAchieved);
+S_API bool SteamAPI_ISteamGameServerStats_SetUserStat(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, int32 nData);
+S_API bool SteamAPI_ISteamGameServerStats_SetUserStat0(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, float fData);
+S_API bool SteamAPI_ISteamGameServerStats_UpdateUserAvgRateStat(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName, float flCountThisSession, double dSessionLength);
+S_API bool SteamAPI_ISteamGameServerStats_SetUserAchievement(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName);
+S_API bool SteamAPI_ISteamGameServerStats_ClearUserAchievement(intptr_t instancePtr, class CSteamID steamIDUser, const char * pchName);
+S_API SteamAPICall_t SteamAPI_ISteamGameServerStats_StoreUserStats(intptr_t instancePtr, class CSteamID steamIDUser);
+#endif // STEAMAPIFLAT_H
+
+
diff --git a/dep/steam_api/steam_api_internal.h b/dep/steam_api/steam_api_internal.h
new file mode 100644
index 0000000..ed0423b
--- /dev/null
+++ b/dep/steam_api/steam_api_internal.h
@@ -0,0 +1,327 @@
+//====== Copyright 1996-2015, Valve Corporation, All rights reserved. =======
+//
+// Purpose: Internal private Steamworks API declarations and definitions
+//
+//=============================================================================
+
+#ifndef STEAM_API_INTERNAL_H
+#define STEAM_API_INTERNAL_H
+
+S_API HSteamUser SteamAPI_GetHSteamUser();
+S_API void * S_CALLTYPE SteamInternal_ContextInit( void *pContextInitData );
+S_API void * S_CALLTYPE SteamInternal_CreateInterface( const char *ver );
+
+#if !defined( STEAM_API_EXPORTS )
+
+inline void S_CALLTYPE SteamInternal_OnContextInit( void* p )
+{
+ ((CSteamAPIContext*)p)->Clear();
+ if ( SteamAPI_GetHSteamPipe() )
+ ((CSteamAPIContext*)p)->Init();
+}
+inline CSteamAPIContext& SteamInternal_ModuleContext()
+{
+ // SteamInternal_ContextInit takes a base pointer for the equivalent of
+ // struct { void (*pFn)(void* pCtx); uintp counter; CSteamAPIContext ctx; }
+ // Do not change layout of 2 + sizeof... or add non-pointer aligned data!
+ // NOTE: declaring "static CSteamAPIConext" creates a large function
+ // which queries the initialization status of the object. We know that
+ // it is pointer-aligned and fully memset with zeros, so just alias a
+ // static buffer of the appropriate size and call it a CSteamAPIContext.
+ static void* s_CallbackCounterAndContext[ 2 + sizeof(CSteamAPIContext)/sizeof(void*) ] = { (void*)&SteamInternal_OnContextInit, 0 };
+ return *(CSteamAPIContext*)SteamInternal_ContextInit( s_CallbackCounterAndContext );
+}
+
+inline ISteamClient *SteamClient() { return SteamInternal_ModuleContext().SteamClient(); }
+inline ISteamUser *SteamUser() { return SteamInternal_ModuleContext().SteamUser(); }
+inline ISteamFriends *SteamFriends() { return SteamInternal_ModuleContext().SteamFriends(); }
+inline ISteamUtils *SteamUtils() { return SteamInternal_ModuleContext().SteamUtils(); }
+inline ISteamMatchmaking *SteamMatchmaking() { return SteamInternal_ModuleContext().SteamMatchmaking(); }
+inline ISteamUserStats *SteamUserStats() { return SteamInternal_ModuleContext().SteamUserStats(); }
+inline ISteamApps *SteamApps() { return SteamInternal_ModuleContext().SteamApps(); }
+inline ISteamMatchmakingServers *SteamMatchmakingServers() { return SteamInternal_ModuleContext().SteamMatchmakingServers(); }
+inline ISteamNetworking *SteamNetworking() { return SteamInternal_ModuleContext().SteamNetworking(); }
+inline ISteamRemoteStorage *SteamRemoteStorage() { return SteamInternal_ModuleContext().SteamRemoteStorage(); }
+inline ISteamScreenshots *SteamScreenshots() { return SteamInternal_ModuleContext().SteamScreenshots(); }
+inline ISteamHTTP *SteamHTTP() { return SteamInternal_ModuleContext().SteamHTTP(); }
+inline ISteamUnifiedMessages *SteamUnifiedMessages() { return SteamInternal_ModuleContext().SteamUnifiedMessages(); }
+inline ISteamController *SteamController() { return SteamInternal_ModuleContext().SteamController(); }
+inline ISteamUGC *SteamUGC() { return SteamInternal_ModuleContext().SteamUGC(); }
+inline ISteamAppList *SteamAppList() { return SteamInternal_ModuleContext().SteamAppList(); }
+inline ISteamMusic *SteamMusic() { return SteamInternal_ModuleContext().SteamMusic(); }
+inline ISteamMusicRemote *SteamMusicRemote() { return SteamInternal_ModuleContext().SteamMusicRemote(); }
+inline ISteamHTMLSurface *SteamHTMLSurface() { return SteamInternal_ModuleContext().SteamHTMLSurface(); }
+inline ISteamInventory *SteamInventory() { return SteamInternal_ModuleContext().SteamInventory(); }
+inline ISteamVideo *SteamVideo() { return SteamInternal_ModuleContext().SteamVideo(); }
+
+#endif // !defined( STEAM_API_EXPORTS )
+
+
+inline void CSteamAPIContext::Clear()
+{
+ m_pSteamClient = NULL;
+ m_pSteamUser = NULL;
+ m_pSteamFriends = NULL;
+ m_pSteamUtils = NULL;
+ m_pSteamMatchmaking = NULL;
+ m_pSteamUserStats = NULL;
+ m_pSteamApps = NULL;
+ m_pSteamMatchmakingServers = NULL;
+ m_pSteamNetworking = NULL;
+ m_pSteamRemoteStorage = NULL;
+ m_pSteamHTTP = NULL;
+ m_pSteamScreenshots = NULL;
+ m_pSteamMusic = NULL;
+ m_pSteamUnifiedMessages = NULL;
+ m_pController = NULL;
+ m_pSteamUGC = NULL;
+ m_pSteamAppList = NULL;
+ m_pSteamMusic = NULL;
+ m_pSteamMusicRemote = NULL;
+ m_pSteamHTMLSurface = NULL;
+ m_pSteamInventory = NULL;
+}
+
+
+// This function must be declared inline in the header so the module using steam_api.dll gets the version names they want.
+inline bool CSteamAPIContext::Init()
+{
+ HSteamUser hSteamUser = SteamAPI_GetHSteamUser();
+ HSteamPipe hSteamPipe = SteamAPI_GetHSteamPipe();
+ if ( !hSteamPipe )
+ return false;
+
+ m_pSteamClient = (ISteamClient*) SteamInternal_CreateInterface( STEAMCLIENT_INTERFACE_VERSION );
+ if ( !m_pSteamClient )
+ return false;
+
+ m_pSteamUser = m_pSteamClient->GetISteamUser( hSteamUser, hSteamPipe, STEAMUSER_INTERFACE_VERSION );
+ if ( !m_pSteamUser )
+ return false;
+
+ m_pSteamFriends = m_pSteamClient->GetISteamFriends( hSteamUser, hSteamPipe, STEAMFRIENDS_INTERFACE_VERSION );
+ if ( !m_pSteamFriends )
+ return false;
+
+ m_pSteamUtils = m_pSteamClient->GetISteamUtils( hSteamPipe, STEAMUTILS_INTERFACE_VERSION );
+ if ( !m_pSteamUtils )
+ return false;
+
+ m_pSteamMatchmaking = m_pSteamClient->GetISteamMatchmaking( hSteamUser, hSteamPipe, STEAMMATCHMAKING_INTERFACE_VERSION );
+ if ( !m_pSteamMatchmaking )
+ return false;
+
+ m_pSteamMatchmakingServers = m_pSteamClient->GetISteamMatchmakingServers( hSteamUser, hSteamPipe, STEAMMATCHMAKINGSERVERS_INTERFACE_VERSION );
+ if ( !m_pSteamMatchmakingServers )
+ return false;
+
+ m_pSteamUserStats = m_pSteamClient->GetISteamUserStats( hSteamUser, hSteamPipe, STEAMUSERSTATS_INTERFACE_VERSION );
+ if ( !m_pSteamUserStats )
+ return false;
+
+ m_pSteamApps = m_pSteamClient->GetISteamApps( hSteamUser, hSteamPipe, STEAMAPPS_INTERFACE_VERSION );
+ if ( !m_pSteamApps )
+ return false;
+
+ m_pSteamNetworking = m_pSteamClient->GetISteamNetworking( hSteamUser, hSteamPipe, STEAMNETWORKING_INTERFACE_VERSION );
+ if ( !m_pSteamNetworking )
+ return false;
+
+ m_pSteamRemoteStorage = m_pSteamClient->GetISteamRemoteStorage( hSteamUser, hSteamPipe, STEAMREMOTESTORAGE_INTERFACE_VERSION );
+ if ( !m_pSteamRemoteStorage )
+ return false;
+
+ m_pSteamScreenshots = m_pSteamClient->GetISteamScreenshots( hSteamUser, hSteamPipe, STEAMSCREENSHOTS_INTERFACE_VERSION );
+ if ( !m_pSteamScreenshots )
+ return false;
+
+ m_pSteamHTTP = m_pSteamClient->GetISteamHTTP( hSteamUser, hSteamPipe, STEAMHTTP_INTERFACE_VERSION );
+ if ( !m_pSteamHTTP )
+ return false;
+
+ m_pSteamUnifiedMessages = m_pSteamClient->GetISteamUnifiedMessages( hSteamUser, hSteamPipe, STEAMUNIFIEDMESSAGES_INTERFACE_VERSION );
+ if ( !m_pSteamUnifiedMessages )
+ return false;
+
+ m_pController = m_pSteamClient->GetISteamController( hSteamUser, hSteamPipe, STEAMCONTROLLER_INTERFACE_VERSION );
+ if ( !m_pController )
+ return false;
+
+ m_pSteamUGC = m_pSteamClient->GetISteamUGC( hSteamUser, hSteamPipe, STEAMUGC_INTERFACE_VERSION );
+ if ( !m_pSteamUGC )
+ return false;
+
+ m_pSteamAppList = m_pSteamClient->GetISteamAppList( hSteamUser, hSteamPipe, STEAMAPPLIST_INTERFACE_VERSION );
+ if ( !m_pSteamAppList )
+ return false;
+
+ m_pSteamMusic = m_pSteamClient->GetISteamMusic( hSteamUser, hSteamPipe, STEAMMUSIC_INTERFACE_VERSION );
+ if ( !m_pSteamMusic )
+ return false;
+
+ m_pSteamMusicRemote = m_pSteamClient->GetISteamMusicRemote( hSteamUser, hSteamPipe, STEAMMUSICREMOTE_INTERFACE_VERSION );
+ if ( !m_pSteamMusicRemote )
+ return false;
+
+ m_pSteamHTMLSurface = m_pSteamClient->GetISteamHTMLSurface( hSteamUser, hSteamPipe, STEAMHTMLSURFACE_INTERFACE_VERSION );
+ if ( !m_pSteamHTMLSurface )
+ return false;
+
+ m_pSteamInventory = m_pSteamClient->GetISteamInventory( hSteamUser, hSteamPipe, STEAMINVENTORY_INTERFACE_VERSION );
+ if ( !m_pSteamInventory )
+ return false;
+
+ m_pSteamVideo = m_pSteamClient->GetISteamVideo( hSteamUser, hSteamPipe, STEAMVIDEO_INTERFACE_VERSION );
+ if ( !m_pSteamVideo )
+ return false;
+
+ return true;
+}
+
+
+//-----------------------------------------------------------------------------
+// The following macros are implementation details, not intended for public use
+//-----------------------------------------------------------------------------
+#define _STEAM_CALLBACK_AUTO_HOOK( thisclass, func, param )
+#define _STEAM_CALLBACK_HELPER( _1, _2, SELECTED, ... ) _STEAM_CALLBACK_##SELECTED
+#define _STEAM_CALLBACK_SELECT( X, Y ) _STEAM_CALLBACK_HELPER X Y
+#define _STEAM_CALLBACK_3( extra_code, thisclass, func, param ) \
+ struct CCallbackInternal_ ## func : private CCallbackImpl< sizeof( param ) > { \
+ CCallbackInternal_ ## func () { extra_code SteamAPI_RegisterCallback( this, param::k_iCallback ); } \
+ CCallbackInternal_ ## func ( const CCallbackInternal_ ## func & ) { extra_code SteamAPI_RegisterCallback( this, param::k_iCallback ); } \
+ CCallbackInternal_ ## func & operator=( const CCallbackInternal_ ## func & ) { return *this; } \
+ private: virtual void Run( void *pvParam ) { _STEAM_CALLBACK_AUTO_HOOK( thisclass, func, param ) \
+ thisclass *pOuter = reinterpret_cast( reinterpret_cast(this) - offsetof( thisclass, m_steamcallback_ ## func ) ); \
+ pOuter->func( reinterpret_cast( pvParam ) ); \
+ } \
+ } m_steamcallback_ ## func ; void func( param *pParam )
+#define _STEAM_CALLBACK_4( _, thisclass, func, param, var ) \
+ CCallback< thisclass, param > var; void func( param *pParam )
+
+
+//-----------------------------------------------------------------------------
+// Purpose: maps a steam async call result to a class member function
+// template params: T = local class, P = parameter struct
+//-----------------------------------------------------------------------------
+template< class T, class P >
+inline CCallResult::CCallResult()
+{
+ m_hAPICall = k_uAPICallInvalid;
+ m_pObj = NULL;
+ m_Func = NULL;
+ m_iCallback = P::k_iCallback;
+}
+
+template< class T, class P >
+inline void CCallResult::Set( SteamAPICall_t hAPICall, T *p, func_t func )
+{
+ if ( m_hAPICall )
+ SteamAPI_UnregisterCallResult( this, m_hAPICall );
+
+ m_hAPICall = hAPICall;
+ m_pObj = p;
+ m_Func = func;
+
+ if ( hAPICall )
+ SteamAPI_RegisterCallResult( this, hAPICall );
+}
+
+template< class T, class P >
+inline bool CCallResult::IsActive() const
+{
+ return (m_hAPICall != k_uAPICallInvalid);
+}
+
+template< class T, class P >
+inline void CCallResult::Cancel()
+{
+ if ( m_hAPICall != k_uAPICallInvalid )
+ {
+ SteamAPI_UnregisterCallResult( this, m_hAPICall );
+ m_hAPICall = k_uAPICallInvalid;
+ }
+
+}
+
+template< class T, class P >
+inline CCallResult::~CCallResult()
+{
+ Cancel();
+}
+
+template< class T, class P >
+inline void CCallResult::Run( void *pvParam )
+{
+ m_hAPICall = k_uAPICallInvalid; // caller unregisters for us
+ (m_pObj->*m_Func)((P *)pvParam, false);
+}
+
+template< class T, class P >
+inline void CCallResult::Run( void *pvParam, bool bIOFailure, SteamAPICall_t hSteamAPICall )
+{
+ if ( hSteamAPICall == m_hAPICall )
+ {
+ m_hAPICall = k_uAPICallInvalid; // caller unregisters for us
+ (m_pObj->*m_Func)((P *)pvParam, bIOFailure);
+ }
+}
+
+
+//-----------------------------------------------------------------------------
+// Purpose: maps a steam callback to a class member function
+// template params: T = local class, P = parameter struct,
+// bGameserver = listen for gameserver callbacks instead of client callbacks
+//-----------------------------------------------------------------------------
+template< class T, class P, bool bGameserver >
+inline CCallback< T, P, bGameserver >::CCallback( T *pObj, func_t func )
+ : m_pObj( NULL ), m_Func( NULL )
+{
+ if ( bGameserver )
+ {
+ this->SetGameserverFlag();
+ }
+ Register( pObj, func );
+}
+
+template< class T, class P, bool bGameserver >
+inline void CCallback< T, P, bGameserver >::Register( T *pObj, func_t func )
+{
+ if ( !pObj || !func )
+ return;
+
+ if ( this->m_nCallbackFlags & CCallbackBase::k_ECallbackFlagsRegistered )
+ Unregister();
+
+ m_pObj = pObj;
+ m_Func = func;
+ // SteamAPI_RegisterCallback sets k_ECallbackFlagsRegistered
+ SteamAPI_RegisterCallback( this, P::k_iCallback );
+}
+
+template< class T, class P, bool bGameserver >
+inline void CCallback< T, P, bGameserver >::Unregister()
+{
+ // SteamAPI_UnregisterCallback removes k_ECallbackFlagsRegistered
+ SteamAPI_UnregisterCallback( this );
+}
+
+template< class T, class P, bool bGameserver >
+inline void CCallback< T, P, bGameserver >::Run( void *pvParam )
+{
+ (m_pObj->*m_Func)((P *)pvParam);
+}
+
+
+#if defined(USE_BREAKPAD_HANDLER) || defined(STEAM_API_EXPORTS)
+// this should be called before the game initialized the steam APIs
+// pchDate should be of the format "Mmm dd yyyy" (such as from the __ DATE __ macro )
+// pchTime should be of the format "hh:mm:ss" (such as from the __ TIME __ macro )
+// bFullMemoryDumps (Win32 only) -- writes out a uuid-full.dmp in the client/dumps folder
+// pvContext-- can be NULL, will be the void * context passed into m_pfnPreMinidumpCallback
+// PFNPreMinidumpCallback m_pfnPreMinidumpCallback -- optional callback which occurs just before a .dmp file is written during a crash. Applications can hook this to allow adding additional information into the .dmp comment stream.
+S_API void S_CALLTYPE SteamAPI_UseBreakpadCrashHandler( char const *pchVersion, char const *pchDate, char const *pchTime, bool bFullMemoryDumps, void *pvContext, PFNPreMinidumpCallback m_pfnPreMinidumpCallback );
+S_API void S_CALLTYPE SteamAPI_SetBreakpadAppID( uint32 unAppID );
+#endif
+
+
+#endif // STEAM_API_INTERNAL_H
diff --git a/dep/steam_api/steam_gameserver.h b/dep/steam_api/steam_gameserver.h
new file mode 100644
index 0000000..c6bdd52
--- /dev/null
+++ b/dep/steam_api/steam_gameserver.h
@@ -0,0 +1,243 @@
+//====== Copyright 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose:
+//
+//=============================================================================
+
+#ifndef STEAM_GAMESERVER_H
+#define STEAM_GAMESERVER_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#include "steam_api.h"
+#include "isteamgameserver.h"
+#include "isteamgameserverstats.h"
+
+enum EServerMode
+{
+ eServerModeInvalid = 0, // DO NOT USE
+ eServerModeNoAuthentication = 1, // Don't authenticate user logins and don't list on the server list
+ eServerModeAuthentication = 2, // Authenticate users, list on the server list, don't run VAC on clients that connect
+ eServerModeAuthenticationAndSecure = 3, // Authenticate users, list on the server list and VAC protect clients
+};
+
+// Initialize ISteamGameServer interface object, and set server properties which may not be changed.
+//
+// After calling this function, you should set any additional server parameters, and then
+// call ISteamGameServer::LogOnAnonymous() or ISteamGameServer::LogOn()
+//
+// - usSteamPort is the local port used to communicate with the steam servers.
+// - usGamePort is the port that clients will connect to for gameplay.
+// - usQueryPort is the port that will manage server browser related duties and info
+// pings from clients. If you pass MASTERSERVERUPDATERPORT_USEGAMESOCKETSHARE for usQueryPort, then it
+// will use "GameSocketShare" mode, which means that the game is responsible for sending and receiving
+// UDP packets for the master server updater. See references to GameSocketShare in isteamgameserver.h.
+// - The version string is usually in the form x.x.x.x, and is used by the master server to detect when the
+// server is out of date. (Only servers with the latest version will be listed.)
+
+inline bool SteamGameServer_Init( uint32 unIP, uint16 usSteamPort, uint16 usGamePort, uint16 usQueryPort, EServerMode eServerMode, const char *pchVersionString );
+
+S_API void SteamGameServer_Shutdown();
+S_API void SteamGameServer_RunCallbacks();
+
+// Most Steam API functions allocate some amount of thread-local memory for
+// parameter storage. Calling SteamGameServer_ReleaseCurrentThreadMemory()
+// will free all API-related memory associated with the calling thread.
+// This memory is released automatically by SteamGameServer_RunCallbacks(),
+// so single-threaded servers do not need to explicitly call this function.
+inline void SteamGameServer_ReleaseCurrentThreadMemory();
+
+S_API bool SteamGameServer_BSecure();
+S_API uint64 SteamGameServer_GetSteamID();
+
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// Global accessors for game server C++ APIs. See individual isteam*.h files for details.
+// You should not cache the results of these accessors or pass the result pointers across
+// modules! Different modules may be compiled against different SDK header versions, and
+// the interface pointers could therefore be different across modules. Every line of code
+// which calls into a Steamworks API should retrieve the interface from a global accessor.
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+#if !defined( STEAM_API_EXPORTS )
+inline ISteamClient *SteamGameServerClient();
+inline ISteamGameServer *SteamGameServer();
+inline ISteamUtils *SteamGameServerUtils();
+inline ISteamNetworking *SteamGameServerNetworking();
+inline ISteamGameServerStats *SteamGameServerStats();
+inline ISteamHTTP *SteamGameServerHTTP();
+inline ISteamInventory *SteamGameServerInventory();
+inline ISteamUGC *SteamGameServerUGC();
+inline ISteamApps *SteamGameServerApps();
+#endif
+
+class CSteamGameServerAPIContext
+{
+public:
+ CSteamGameServerAPIContext() { Clear(); }
+ inline void Clear();
+ inline bool Init();
+
+ ISteamClient *SteamClient() const { return m_pSteamClient; }
+ ISteamGameServer *SteamGameServer() const { return m_pSteamGameServer; }
+ ISteamUtils *SteamGameServerUtils() const { return m_pSteamGameServerUtils; }
+ ISteamNetworking *SteamGameServerNetworking() const { return m_pSteamGameServerNetworking; }
+ ISteamGameServerStats *SteamGameServerStats() const { return m_pSteamGameServerStats; }
+ ISteamHTTP *SteamHTTP() const { return m_pSteamHTTP; }
+ ISteamInventory *SteamInventory() const { return m_pSteamInventory; }
+ ISteamUGC *SteamUGC() const { return m_pSteamUGC; }
+ ISteamApps *SteamApps() const { return m_pSteamApps; }
+
+private:
+ ISteamClient *m_pSteamClient;
+ ISteamGameServer *m_pSteamGameServer;
+ ISteamUtils *m_pSteamGameServerUtils;
+ ISteamNetworking *m_pSteamGameServerNetworking;
+ ISteamGameServerStats *m_pSteamGameServerStats;
+ ISteamHTTP *m_pSteamHTTP;
+ ISteamInventory *m_pSteamInventory;
+ ISteamUGC *m_pSteamUGC;
+ ISteamApps *m_pSteamApps;
+};
+
+
+// Older SDKs exported this global pointer, but it is no longer supported.
+// You should use SteamGameServerClient() or CSteamGameServerAPIContext to
+// safely access the ISteamClient APIs from your game server application.
+//S_API ISteamClient *g_pSteamClientGameServer;
+
+// SteamGameServer_InitSafe has been replaced with SteamGameServer_Init and
+// is no longer supported. Use SteamGameServer_Init instead.
+//S_API void S_CALLTYPE SteamGameServer_InitSafe();
+
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// These macros are similar to the STEAM_CALLBACK_* macros in steam_api.h, but only trigger for gameserver callbacks
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+#define STEAM_GAMESERVER_CALLBACK( thisclass, func, /*callback_type, [deprecated] var*/... ) \
+ _STEAM_CALLBACK_SELECT( ( __VA_ARGS__, GS, 3 ), ( this->SetGameserverFlag();, thisclass, func, __VA_ARGS__ ) )
+
+#define STEAM_GAMESERVER_CALLBACK_MANUAL( thisclass, func, callback_type, var ) \
+ CCallbackManual< thisclass, callback_type, true > var; void func( callback_type *pParam )
+
+
+#define _STEAM_CALLBACK_GS( _, thisclass, func, param, var ) \
+ CCallback< thisclass, param, true > var; void func( param *pParam )
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// steamclient.dll private wrapper functions
+//
+// The following functions are part of abstracting API access to the steamclient.dll, but should only be used in very specific cases
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+S_API HSteamPipe S_CALLTYPE SteamGameServer_GetHSteamPipe();
+S_API HSteamUser S_CALLTYPE SteamGameServer_GetHSteamUser();
+S_API bool S_CALLTYPE SteamInternal_GameServer_Init( uint32 unIP, uint16 usPort, uint16 usGamePort, uint16 usQueryPort, EServerMode eServerMode, const char *pchVersionString );
+
+
+#if !defined( STEAM_API_EXPORTS )
+inline void S_CALLTYPE SteamGameServerInternal_OnContextInit( void* p )
+{
+ ((CSteamGameServerAPIContext*)p)->Clear();
+ if ( SteamGameServer_GetHSteamPipe() )
+ ((CSteamGameServerAPIContext*)p)->Init();
+}
+inline CSteamGameServerAPIContext& SteamGameServerInternal_ModuleContext()
+{
+ // SteamInternal_ContextInit takes a base pointer for the equivalent of
+ // struct { void (*pFn)(void* pCtx); uintp counter; CSteamAPIContext ctx; }
+ // Do not change layout of 2 + sizeof... or add non-pointer aligned data!
+ // NOTE: declaring "static CSteamAPIConext" creates a large function
+ // which queries the initialization status of the object. We know that
+ // it is pointer-aligned and fully memset with zeros, so just alias a
+ // static buffer of the appropriate size and call it a CSteamAPIContext.
+ static void* s_CallbackCounterAndContext[2 + sizeof( CSteamGameServerAPIContext ) / sizeof( void* )] = { (void*)&SteamGameServerInternal_OnContextInit, 0 };
+ return *(CSteamGameServerAPIContext*)SteamInternal_ContextInit( s_CallbackCounterAndContext );
+}
+inline ISteamClient *SteamGameServerClient() { return SteamGameServerInternal_ModuleContext().SteamClient(); }
+inline ISteamGameServer *SteamGameServer() { return SteamGameServerInternal_ModuleContext().SteamGameServer(); }
+inline ISteamUtils *SteamGameServerUtils() { return SteamGameServerInternal_ModuleContext().SteamGameServerUtils(); }
+inline ISteamNetworking *SteamGameServerNetworking() { return SteamGameServerInternal_ModuleContext().SteamGameServerNetworking(); }
+inline ISteamGameServerStats *SteamGameServerStats() { return SteamGameServerInternal_ModuleContext().SteamGameServerStats(); }
+inline ISteamHTTP *SteamGameServerHTTP() { return SteamGameServerInternal_ModuleContext().SteamHTTP(); }
+inline ISteamInventory *SteamGameServerInventory() { return SteamGameServerInternal_ModuleContext().SteamInventory(); }
+inline ISteamUGC *SteamGameServerUGC() { return SteamGameServerInternal_ModuleContext().SteamUGC(); }
+inline ISteamApps *SteamGameServerApps() { return SteamGameServerInternal_ModuleContext().SteamApps(); }
+#endif // !defined( STEAM_API_EXPORTS )
+
+
+inline void CSteamGameServerAPIContext::Clear()
+{
+ m_pSteamClient = NULL;
+ m_pSteamGameServer = NULL;
+ m_pSteamGameServerUtils = NULL;
+ m_pSteamGameServerNetworking = NULL;
+ m_pSteamGameServerStats = NULL;
+ m_pSteamHTTP = NULL;
+ m_pSteamInventory = NULL;
+ m_pSteamUGC = NULL;
+ m_pSteamApps = NULL;
+}
+
+// This function must be declared inline in the header so the module using steam_api.dll gets the version names they want.
+inline bool CSteamGameServerAPIContext::Init()
+{
+ HSteamUser hSteamUser = SteamGameServer_GetHSteamUser();
+ HSteamPipe hSteamPipe = SteamGameServer_GetHSteamPipe();
+ if ( !hSteamPipe )
+ return false;
+
+ m_pSteamClient = (ISteamClient*) SteamInternal_CreateInterface( STEAMCLIENT_INTERFACE_VERSION );
+ if ( !m_pSteamClient )
+ return false;
+
+ m_pSteamGameServer = m_pSteamClient->GetISteamGameServer( hSteamUser, hSteamPipe, STEAMGAMESERVER_INTERFACE_VERSION );
+ if ( !m_pSteamGameServer )
+ return false;
+
+ m_pSteamGameServerUtils = m_pSteamClient->GetISteamUtils( hSteamPipe, STEAMUTILS_INTERFACE_VERSION );
+ if ( !m_pSteamGameServerUtils )
+ return false;
+
+ m_pSteamGameServerNetworking = m_pSteamClient->GetISteamNetworking( hSteamUser, hSteamPipe, STEAMNETWORKING_INTERFACE_VERSION );
+ if ( !m_pSteamGameServerNetworking )
+ return false;
+
+ m_pSteamGameServerStats = m_pSteamClient->GetISteamGameServerStats( hSteamUser, hSteamPipe, STEAMGAMESERVERSTATS_INTERFACE_VERSION );
+ if ( !m_pSteamGameServerStats )
+ return false;
+
+ m_pSteamHTTP = m_pSteamClient->GetISteamHTTP( hSteamUser, hSteamPipe, STEAMHTTP_INTERFACE_VERSION );
+ if ( !m_pSteamHTTP )
+ return false;
+
+ m_pSteamInventory = m_pSteamClient->GetISteamInventory( hSteamUser, hSteamPipe, STEAMINVENTORY_INTERFACE_VERSION );
+ if ( !m_pSteamInventory )
+ return false;
+
+ m_pSteamUGC = m_pSteamClient->GetISteamUGC( hSteamUser, hSteamPipe, STEAMUGC_INTERFACE_VERSION );
+ if ( !m_pSteamUGC )
+ return false;
+
+ m_pSteamApps = m_pSteamClient->GetISteamApps( hSteamUser, hSteamPipe, STEAMAPPS_INTERFACE_VERSION );
+ if ( !m_pSteamApps )
+ return false;
+
+ return true;
+}
+
+
+inline bool SteamGameServer_Init( uint32 unIP, uint16 usSteamPort, uint16 usGamePort, uint16 usQueryPort, EServerMode eServerMode, const char *pchVersionString )
+{
+ if ( !SteamInternal_GameServer_Init( unIP, usSteamPort, usGamePort, usQueryPort, eServerMode, pchVersionString ) )
+ return false;
+
+ return true;
+}
+
+
+inline void SteamGameServer_ReleaseCurrentThreadMemory()
+{
+ SteamAPI_ReleaseCurrentThreadMemory();
+}
+
+#endif // STEAM_GAMESERVER_H
diff --git a/dep/steam_api/steamclientpublic.h b/dep/steam_api/steamclientpublic.h
new file mode 100644
index 0000000..23b7581
--- /dev/null
+++ b/dep/steam_api/steamclientpublic.h
@@ -0,0 +1,1235 @@
+//========= Copyright � 1996-2008, Valve LLC, All rights reserved. ============
+//
+// Purpose:
+//
+//=============================================================================
+
+#ifndef STEAMCLIENTPUBLIC_H
+#define STEAMCLIENTPUBLIC_H
+#ifdef _WIN32
+#pragma once
+#endif
+//lint -save -e1931 -e1927 -e1924 -e613 -e726
+
+// This header file defines the interface between the calling application and the code that
+// knows how to communicate with the connection manager (CM) from the Steam service
+
+// This header file is intended to be portable; ideally this 1 header file plus a lib or dll
+// is all you need to integrate the client library into some other tree. So please avoid
+// including or requiring other header files if possible. This header should only describe the
+// interface layer, no need to include anything about the implementation.
+
+#include "steamtypes.h"
+#include "steamuniverse.h"
+
+// General result codes
+enum EResult
+{
+ k_EResultOK = 1, // success
+ k_EResultFail = 2, // generic failure
+ k_EResultNoConnection = 3, // no/failed network connection
+// k_EResultNoConnectionRetry = 4, // OBSOLETE - removed
+ k_EResultInvalidPassword = 5, // password/ticket is invalid
+ k_EResultLoggedInElsewhere = 6, // same user logged in elsewhere
+ k_EResultInvalidProtocolVer = 7, // protocol version is incorrect
+ k_EResultInvalidParam = 8, // a parameter is incorrect
+ k_EResultFileNotFound = 9, // file was not found
+ k_EResultBusy = 10, // called method busy - action not taken
+ k_EResultInvalidState = 11, // called object was in an invalid state
+ k_EResultInvalidName = 12, // name is invalid
+ k_EResultInvalidEmail = 13, // email is invalid
+ k_EResultDuplicateName = 14, // name is not unique
+ k_EResultAccessDenied = 15, // access is denied
+ k_EResultTimeout = 16, // operation timed out
+ k_EResultBanned = 17, // VAC2 banned
+ k_EResultAccountNotFound = 18, // account not found
+ k_EResultInvalidSteamID = 19, // steamID is invalid
+ k_EResultServiceUnavailable = 20, // The requested service is currently unavailable
+ k_EResultNotLoggedOn = 21, // The user is not logged on
+ k_EResultPending = 22, // Request is pending (may be in process, or waiting on third party)
+ k_EResultEncryptionFailure = 23, // Encryption or Decryption failed
+ k_EResultInsufficientPrivilege = 24, // Insufficient privilege
+ k_EResultLimitExceeded = 25, // Too much of a good thing
+ k_EResultRevoked = 26, // Access has been revoked (used for revoked guest passes)
+ k_EResultExpired = 27, // License/Guest pass the user is trying to access is expired
+ k_EResultAlreadyRedeemed = 28, // Guest pass has already been redeemed by account, cannot be acked again
+ k_EResultDuplicateRequest = 29, // The request is a duplicate and the action has already occurred in the past, ignored this time
+ k_EResultAlreadyOwned = 30, // All the games in this guest pass redemption request are already owned by the user
+ k_EResultIPNotFound = 31, // IP address not found
+ k_EResultPersistFailed = 32, // failed to write change to the data store
+ k_EResultLockingFailed = 33, // failed to acquire access lock for this operation
+ k_EResultLogonSessionReplaced = 34,
+ k_EResultConnectFailed = 35,
+ k_EResultHandshakeFailed = 36,
+ k_EResultIOFailure = 37,
+ k_EResultRemoteDisconnect = 38,
+ k_EResultShoppingCartNotFound = 39, // failed to find the shopping cart requested
+ k_EResultBlocked = 40, // a user didn't allow it
+ k_EResultIgnored = 41, // target is ignoring sender
+ k_EResultNoMatch = 42, // nothing matching the request found
+ k_EResultAccountDisabled = 43,
+ k_EResultServiceReadOnly = 44, // this service is not accepting content changes right now
+ k_EResultAccountNotFeatured = 45, // account doesn't have value, so this feature isn't available
+ k_EResultAdministratorOK = 46, // allowed to take this action, but only because requester is admin
+ k_EResultContentVersion = 47, // A Version mismatch in content transmitted within the Steam protocol.
+ k_EResultTryAnotherCM = 48, // The current CM can't service the user making a request, user should try another.
+ k_EResultPasswordRequiredToKickSession = 49,// You are already logged in elsewhere, this cached credential login has failed.
+ k_EResultAlreadyLoggedInElsewhere = 50, // You are already logged in elsewhere, you must wait
+ k_EResultSuspended = 51, // Long running operation (content download) suspended/paused
+ k_EResultCancelled = 52, // Operation canceled (typically by user: content download)
+ k_EResultDataCorruption = 53, // Operation canceled because data is ill formed or unrecoverable
+ k_EResultDiskFull = 54, // Operation canceled - not enough disk space.
+ k_EResultRemoteCallFailed = 55, // an remote call or IPC call failed
+ k_EResultPasswordUnset = 56, // Password could not be verified as it's unset server side
+ k_EResultExternalAccountUnlinked = 57, // External account (PSN, Facebook...) is not linked to a Steam account
+ k_EResultPSNTicketInvalid = 58, // PSN ticket was invalid
+ k_EResultExternalAccountAlreadyLinked = 59, // External account (PSN, Facebook...) is already linked to some other account, must explicitly request to replace/delete the link first
+ k_EResultRemoteFileConflict = 60, // The sync cannot resume due to a conflict between the local and remote files
+ k_EResultIllegalPassword = 61, // The requested new password is not legal
+ k_EResultSameAsPreviousValue = 62, // new value is the same as the old one ( secret question and answer )
+ k_EResultAccountLogonDenied = 63, // account login denied due to 2nd factor authentication failure
+ k_EResultCannotUseOldPassword = 64, // The requested new password is not legal
+ k_EResultInvalidLoginAuthCode = 65, // account login denied due to auth code invalid
+ k_EResultAccountLogonDeniedNoMail = 66, // account login denied due to 2nd factor auth failure - and no mail has been sent
+ k_EResultHardwareNotCapableOfIPT = 67, //
+ k_EResultIPTInitError = 68, //
+ k_EResultParentalControlRestricted = 69, // operation failed due to parental control restrictions for current user
+ k_EResultFacebookQueryError = 70, // Facebook query returned an error
+ k_EResultExpiredLoginAuthCode = 71, // account login denied due to auth code expired
+ k_EResultIPLoginRestrictionFailed = 72,
+ k_EResultAccountLockedDown = 73,
+ k_EResultAccountLogonDeniedVerifiedEmailRequired = 74,
+ k_EResultNoMatchingURL = 75,
+ k_EResultBadResponse = 76, // parse failure, missing field, etc.
+ k_EResultRequirePasswordReEntry = 77, // The user cannot complete the action until they re-enter their password
+ k_EResultValueOutOfRange = 78, // the value entered is outside the acceptable range
+ k_EResultUnexpectedError = 79, // something happened that we didn't expect to ever happen
+ k_EResultDisabled = 80, // The requested service has been configured to be unavailable
+ k_EResultInvalidCEGSubmission = 81, // The set of files submitted to the CEG server are not valid !
+ k_EResultRestrictedDevice = 82, // The device being used is not allowed to perform this action
+ k_EResultRegionLocked = 83, // The action could not be complete because it is region restricted
+ k_EResultRateLimitExceeded = 84, // Temporary rate limit exceeded, try again later, different from k_EResultLimitExceeded which may be permanent
+ k_EResultAccountLoginDeniedNeedTwoFactor = 85, // Need two-factor code to login
+ k_EResultItemDeleted = 86, // The thing we're trying to access has been deleted
+ k_EResultAccountLoginDeniedThrottle = 87, // login attempt failed, try to throttle response to possible attacker
+ k_EResultTwoFactorCodeMismatch = 88, // two factor code mismatch
+ k_EResultTwoFactorActivationCodeMismatch = 89, // activation code for two-factor didn't match
+ k_EResultAccountAssociatedToMultiplePartners = 90, // account has been associated with multiple partners
+ k_EResultNotModified = 91, // data not modified
+ k_EResultNoMobileDevice = 92, // the account does not have a mobile device associated with it
+ k_EResultTimeNotSynced = 93, // the time presented is out of range or tolerance
+ k_EResultSmsCodeFailed = 94, // SMS code failure (no match, none pending, etc.)
+ k_EResultAccountLimitExceeded = 95, // Too many accounts access this resource
+ k_EResultAccountActivityLimitExceeded = 96, // Too many changes to this account
+ k_EResultPhoneActivityLimitExceeded = 97, // Too many changes to this phone
+ k_EResultRefundToWallet = 98, // Cannot refund to payment method, must use wallet
+ k_EResultEmailSendFailure = 99, // Cannot send an email
+ k_EResultNotSettled = 100, // Can't perform operation till payment has settled
+ k_EResultNeedCaptcha = 101, // Needs to provide a valid captcha
+ k_EResultGSLTDenied = 102, // a game server login token owned by this token's owner has been banned
+ k_EResultGSOwnerDenied = 103, // game server owner is denied for other reason (account lock, community ban, vac ban, missing phone)
+ k_EResultInvalidItemType = 104, // the type of thing we were requested to act on is invalid
+ k_EResultIPBanned = 105, // the ip address has been banned from taking this action
+ k_EResultGSLTExpired = 106, // this token has expired from disuse; can be reset for use
+ k_EResultInsufficientFunds = 107, // user doesn't have enough wallet funds to complete the action
+ k_EResultTooManyPending = 108, // There are too many of this thing pending already
+};
+
+// Error codes for use with the voice functions
+enum EVoiceResult
+{
+ k_EVoiceResultOK = 0,
+ k_EVoiceResultNotInitialized = 1,
+ k_EVoiceResultNotRecording = 2,
+ k_EVoiceResultNoData = 3,
+ k_EVoiceResultBufferTooSmall = 4,
+ k_EVoiceResultDataCorrupted = 5,
+ k_EVoiceResultRestricted = 6,
+ k_EVoiceResultUnsupportedCodec = 7,
+ k_EVoiceResultReceiverOutOfDate = 8,
+ k_EVoiceResultReceiverDidNotAnswer = 9,
+
+};
+
+// Result codes to GSHandleClientDeny/Kick
+enum EDenyReason
+{
+ k_EDenyInvalid = 0,
+ k_EDenyInvalidVersion = 1,
+ k_EDenyGeneric = 2,
+ k_EDenyNotLoggedOn = 3,
+ k_EDenyNoLicense = 4,
+ k_EDenyCheater = 5,
+ k_EDenyLoggedInElseWhere = 6,
+ k_EDenyUnknownText = 7,
+ k_EDenyIncompatibleAnticheat = 8,
+ k_EDenyMemoryCorruption = 9,
+ k_EDenyIncompatibleSoftware = 10,
+ k_EDenySteamConnectionLost = 11,
+ k_EDenySteamConnectionError = 12,
+ k_EDenySteamResponseTimedOut = 13,
+ k_EDenySteamValidationStalled = 14,
+ k_EDenySteamOwnerLeftGuestUser = 15,
+};
+
+// return type of GetAuthSessionTicket
+typedef uint32 HAuthTicket;
+const HAuthTicket k_HAuthTicketInvalid = 0;
+
+// results from BeginAuthSession
+enum EBeginAuthSessionResult
+{
+ k_EBeginAuthSessionResultOK = 0, // Ticket is valid for this game and this steamID.
+ k_EBeginAuthSessionResultInvalidTicket = 1, // Ticket is not valid.
+ k_EBeginAuthSessionResultDuplicateRequest = 2, // A ticket has already been submitted for this steamID
+ k_EBeginAuthSessionResultInvalidVersion = 3, // Ticket is from an incompatible interface version
+ k_EBeginAuthSessionResultGameMismatch = 4, // Ticket is not for this game
+ k_EBeginAuthSessionResultExpiredTicket = 5, // Ticket has expired
+};
+
+// Callback values for callback ValidateAuthTicketResponse_t which is a response to BeginAuthSession
+enum EAuthSessionResponse
+{
+ k_EAuthSessionResponseOK = 0, // Steam has verified the user is online, the ticket is valid and ticket has not been reused.
+ k_EAuthSessionResponseUserNotConnectedToSteam = 1, // The user in question is not connected to steam
+ k_EAuthSessionResponseNoLicenseOrExpired = 2, // The license has expired.
+ k_EAuthSessionResponseVACBanned = 3, // The user is VAC banned for this game.
+ k_EAuthSessionResponseLoggedInElseWhere = 4, // The user account has logged in elsewhere and the session containing the game instance has been disconnected.
+ k_EAuthSessionResponseVACCheckTimedOut = 5, // VAC has been unable to perform anti-cheat checks on this user
+ k_EAuthSessionResponseAuthTicketCanceled = 6, // The ticket has been canceled by the issuer
+ k_EAuthSessionResponseAuthTicketInvalidAlreadyUsed = 7, // This ticket has already been used, it is not valid.
+ k_EAuthSessionResponseAuthTicketInvalid = 8, // This ticket is not from a user instance currently connected to steam.
+ k_EAuthSessionResponsePublisherIssuedBan = 9, // The user is banned for this game. The ban came via the web api and not VAC
+};
+
+// results from UserHasLicenseForApp
+enum EUserHasLicenseForAppResult
+{
+ k_EUserHasLicenseResultHasLicense = 0, // User has a license for specified app
+ k_EUserHasLicenseResultDoesNotHaveLicense = 1, // User does not have a license for the specified app
+ k_EUserHasLicenseResultNoAuth = 2, // User has not been authenticated
+};
+
+
+// Steam account types
+enum EAccountType
+{
+ k_EAccountTypeInvalid = 0,
+ k_EAccountTypeIndividual = 1, // single user account
+ k_EAccountTypeMultiseat = 2, // multiseat (e.g. cybercafe) account
+ k_EAccountTypeGameServer = 3, // game server account
+ k_EAccountTypeAnonGameServer = 4, // anonymous game server account
+ k_EAccountTypePending = 5, // pending
+ k_EAccountTypeContentServer = 6, // content server
+ k_EAccountTypeClan = 7,
+ k_EAccountTypeChat = 8,
+ k_EAccountTypeConsoleUser = 9, // Fake SteamID for local PSN account on PS3 or Live account on 360, etc.
+ k_EAccountTypeAnonUser = 10,
+
+ // Max of 16 items in this field
+ k_EAccountTypeMax
+};
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+enum EAppReleaseState
+{
+ k_EAppReleaseState_Unknown = 0, // unknown, required appinfo or license info is missing
+ k_EAppReleaseState_Unavailable = 1, // even if user 'just' owns it, can see game at all
+ k_EAppReleaseState_Prerelease = 2, // can be purchased and is visible in games list, nothing else. Common appInfo section released
+ k_EAppReleaseState_PreloadOnly = 3, // owners can preload app, not play it. AppInfo fully released.
+ k_EAppReleaseState_Released = 4, // owners can download and play app.
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose:
+//-----------------------------------------------------------------------------
+enum EAppOwnershipFlags
+{
+ k_EAppOwnershipFlags_None = 0x0000, // unknown
+ k_EAppOwnershipFlags_OwnsLicense = 0x0001, // owns license for this game
+ k_EAppOwnershipFlags_FreeLicense = 0x0002, // not paid for game
+ k_EAppOwnershipFlags_RegionRestricted = 0x0004, // owns app, but not allowed to play in current region
+ k_EAppOwnershipFlags_LowViolence = 0x0008, // only low violence version
+ k_EAppOwnershipFlags_InvalidPlatform = 0x0010, // app not supported on current platform
+ k_EAppOwnershipFlags_SharedLicense = 0x0020, // license was granted by authorized local device
+ k_EAppOwnershipFlags_FreeWeekend = 0x0040, // owned by a free weekend licenses
+ k_EAppOwnershipFlags_RetailLicense = 0x0080, // has a retail license for game, (CD-Key etc)
+ k_EAppOwnershipFlags_LicenseLocked = 0x0100, // shared license is locked (in use) by other user
+ k_EAppOwnershipFlags_LicensePending = 0x0200, // owns app, but transaction is still pending. Can't install or play
+ k_EAppOwnershipFlags_LicenseExpired = 0x0400, // doesn't own app anymore since license expired
+ k_EAppOwnershipFlags_LicensePermanent = 0x0800, // permanent license, not borrowed, or guest or freeweekend etc
+ k_EAppOwnershipFlags_LicenseRecurring = 0x1000, // Recurring license, user is charged periodically
+ k_EAppOwnershipFlags_LicenseCanceled = 0x2000, // Mark as canceled, but might be still active if recurring
+ k_EAppOwnershipFlags_AutoGrant = 0x4000, // Ownership is based on any kind of autogrant license
+ k_EAppOwnershipFlags_PendingGift = 0x8000, // user has pending gift to redeem
+ k_EAppOwnershipFlags_RentalNotActivated = 0x10000, // Rental hasn't been activated yet
+ k_EAppOwnershipFlags_Rental = 0x20000, // Is a rental
+ k_EAppOwnershipFlags_SiteLicense = 0x40000, // Is from a site license
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: designed as flags to allow filters masks
+//-----------------------------------------------------------------------------
+enum EAppType
+{
+ k_EAppType_Invalid = 0x000, // unknown / invalid
+ k_EAppType_Game = 0x001, // playable game, default type
+ k_EAppType_Application = 0x002, // software application
+ k_EAppType_Tool = 0x004, // SDKs, editors & dedicated servers
+ k_EAppType_Demo = 0x008, // game demo
+ k_EAppType_Media_DEPRECATED = 0x010, // legacy - was used for game trailers, which are now just videos on the web
+ k_EAppType_DLC = 0x020, // down loadable content
+ k_EAppType_Guide = 0x040, // game guide, PDF etc
+ k_EAppType_Driver = 0x080, // hardware driver updater (ATI, Razor etc)
+ k_EAppType_Config = 0x100, // hidden app used to config Steam features (backpack, sales, etc)
+ k_EAppType_Hardware = 0x200, // a hardware device (Steam Machine, Steam Controller, Steam Link, etc.)
+ k_EAppType_Franchise = 0x400, // A hub for collections of multiple apps, eg films, series, games
+ k_EAppType_Video = 0x800, // A video component of either a Film or TVSeries (may be the feature, an episode, preview, making-of, etc)
+ k_EAppType_Plugin = 0x1000, // Plug-in types for other Apps
+ k_EAppType_Music = 0x2000, // Music files
+ k_EAppType_Series = 0x4000, // Container app for video series
+
+ k_EAppType_Shortcut = 0x40000000, // just a shortcut, client side only
+ k_EAppType_DepotOnly = 0x80000000, // placeholder since depots and apps share the same namespace
+};
+
+
+
+//-----------------------------------------------------------------------------
+// types of user game stats fields
+// WARNING: DO NOT RENUMBER EXISTING VALUES - STORED IN DATABASE
+//-----------------------------------------------------------------------------
+enum ESteamUserStatType
+{
+ k_ESteamUserStatTypeINVALID = 0,
+ k_ESteamUserStatTypeINT = 1,
+ k_ESteamUserStatTypeFLOAT = 2,
+ // Read as FLOAT, set with count / session length
+ k_ESteamUserStatTypeAVGRATE = 3,
+ k_ESteamUserStatTypeACHIEVEMENTS = 4,
+ k_ESteamUserStatTypeGROUPACHIEVEMENTS = 5,
+
+ // max, for sanity checks
+ k_ESteamUserStatTypeMAX
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Chat Entry Types (previously was only friend-to-friend message types)
+//-----------------------------------------------------------------------------
+enum EChatEntryType
+{
+ k_EChatEntryTypeInvalid = 0,
+ k_EChatEntryTypeChatMsg = 1, // Normal text message from another user
+ k_EChatEntryTypeTyping = 2, // Another user is typing (not used in multi-user chat)
+ k_EChatEntryTypeInviteGame = 3, // Invite from other user into that users current game
+ k_EChatEntryTypeEmote = 4, // text emote message (deprecated, should be treated as ChatMsg)
+ //k_EChatEntryTypeLobbyGameStart = 5, // lobby game is starting (dead - listen for LobbyGameCreated_t callback instead)
+ k_EChatEntryTypeLeftConversation = 6, // user has left the conversation ( closed chat window )
+ // Above are previous FriendMsgType entries, now merged into more generic chat entry types
+ k_EChatEntryTypeEntered = 7, // user has entered the conversation (used in multi-user chat and group chat)
+ k_EChatEntryTypeWasKicked = 8, // user was kicked (data: 64-bit steamid of actor performing the kick)
+ k_EChatEntryTypeWasBanned = 9, // user was banned (data: 64-bit steamid of actor performing the ban)
+ k_EChatEntryTypeDisconnected = 10, // user disconnected
+ k_EChatEntryTypeHistoricalChat = 11, // a chat message from user's chat history or offilne message
+ //k_EChatEntryTypeReserved1 = 12, // No longer used
+ //k_EChatEntryTypeReserved2 = 13, // No longer used
+ k_EChatEntryTypeLinkBlocked = 14, // a link was removed by the chat filter.
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Chat Room Enter Responses
+//-----------------------------------------------------------------------------
+enum EChatRoomEnterResponse
+{
+ k_EChatRoomEnterResponseSuccess = 1, // Success
+ k_EChatRoomEnterResponseDoesntExist = 2, // Chat doesn't exist (probably closed)
+ k_EChatRoomEnterResponseNotAllowed = 3, // General Denied - You don't have the permissions needed to join the chat
+ k_EChatRoomEnterResponseFull = 4, // Chat room has reached its maximum size
+ k_EChatRoomEnterResponseError = 5, // Unexpected Error
+ k_EChatRoomEnterResponseBanned = 6, // You are banned from this chat room and may not join
+ k_EChatRoomEnterResponseLimited = 7, // Joining this chat is not allowed because you are a limited user (no value on account)
+ k_EChatRoomEnterResponseClanDisabled = 8, // Attempt to join a clan chat when the clan is locked or disabled
+ k_EChatRoomEnterResponseCommunityBan = 9, // Attempt to join a chat when the user has a community lock on their account
+ k_EChatRoomEnterResponseMemberBlockedYou = 10, // Join failed - some member in the chat has blocked you from joining
+ k_EChatRoomEnterResponseYouBlockedMember = 11, // Join failed - you have blocked some member already in the chat
+ // k_EChatRoomEnterResponseNoRankingDataLobby = 12, // No longer used
+ // k_EChatRoomEnterResponseNoRankingDataUser = 13, // No longer used
+ // k_EChatRoomEnterResponseRankOutOfRange = 14, // No longer used
+};
+
+
+typedef void (*PFNLegacyKeyRegistration)( const char *pchCDKey, const char *pchInstallPath );
+typedef bool (*PFNLegacyKeyInstalled)();
+
+const unsigned int k_unSteamAccountIDMask = 0xFFFFFFFF;
+const unsigned int k_unSteamAccountInstanceMask = 0x000FFFFF;
+// we allow 3 simultaneous user account instances right now, 1= desktop, 2 = console, 4 = web, 0 = all
+const unsigned int k_unSteamUserDesktopInstance = 1;
+const unsigned int k_unSteamUserConsoleInstance = 2;
+const unsigned int k_unSteamUserWebInstance = 4;
+
+// Special flags for Chat accounts - they go in the top 8 bits
+// of the steam ID's "instance", leaving 12 for the actual instances
+enum EChatSteamIDInstanceFlags
+{
+ k_EChatAccountInstanceMask = 0x00000FFF, // top 8 bits are flags
+
+ k_EChatInstanceFlagClan = ( k_unSteamAccountInstanceMask + 1 ) >> 1, // top bit
+ k_EChatInstanceFlagLobby = ( k_unSteamAccountInstanceMask + 1 ) >> 2, // next one down, etc
+ k_EChatInstanceFlagMMSLobby = ( k_unSteamAccountInstanceMask + 1 ) >> 3, // next one down, etc
+
+ // Max of 8 flags
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Marketing message flags that change how a client should handle them
+//-----------------------------------------------------------------------------
+enum EMarketingMessageFlags
+{
+ k_EMarketingMessageFlagsNone = 0,
+ k_EMarketingMessageFlagsHighPriority = 1 << 0,
+ k_EMarketingMessageFlagsPlatformWindows = 1 << 1,
+ k_EMarketingMessageFlagsPlatformMac = 1 << 2,
+ k_EMarketingMessageFlagsPlatformLinux = 1 << 3,
+
+ //aggregate flags
+ k_EMarketingMessageFlagsPlatformRestrictions =
+ k_EMarketingMessageFlagsPlatformWindows |
+ k_EMarketingMessageFlagsPlatformMac |
+ k_EMarketingMessageFlagsPlatformLinux,
+};
+
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Possible positions to tell the overlay to show notifications in
+//-----------------------------------------------------------------------------
+enum ENotificationPosition
+{
+ k_EPositionTopLeft = 0,
+ k_EPositionTopRight = 1,
+ k_EPositionBottomLeft = 2,
+ k_EPositionBottomRight = 3,
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Broadcast upload result details
+//-----------------------------------------------------------------------------
+enum EBroadcastUploadResult
+{
+ k_EBroadcastUploadResultNone = 0, // broadcast state unknown
+ k_EBroadcastUploadResultOK = 1, // broadcast was good, no problems
+ k_EBroadcastUploadResultInitFailed = 2, // broadcast init failed
+ k_EBroadcastUploadResultFrameFailed = 3, // broadcast frame upload failed
+ k_EBroadcastUploadResultTimeout = 4, // broadcast upload timed out
+ k_EBroadcastUploadResultBandwidthExceeded = 5, // broadcast send too much data
+ k_EBroadcastUploadResultLowFPS = 6, // broadcast FPS too low
+ k_EBroadcastUploadResultMissingKeyFrames = 7, // broadcast sending not enough key frames
+ k_EBroadcastUploadResultNoConnection = 8, // broadcast client failed to connect to relay
+ k_EBroadcastUploadResultRelayFailed = 9, // relay dropped the upload
+ k_EBroadcastUploadResultSettingsChanged = 10, // the client changed broadcast settings
+ k_EBroadcastUploadResultMissingAudio = 11, // client failed to send audio data
+ k_EBroadcastUploadResultTooFarBehind = 12, // clients was too slow uploading
+ k_EBroadcastUploadResultTranscodeBehind = 13, // server failed to keep up with transcode
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: codes for well defined launch options
+//-----------------------------------------------------------------------------
+enum ELaunchOptionType
+{
+ k_ELaunchOptionType_None = 0, // unknown what launch option does
+ k_ELaunchOptionType_Default = 1, // runs the game, app, whatever in default mode
+ k_ELaunchOptionType_SafeMode = 2, // runs the game in safe mode
+ k_ELaunchOptionType_Multiplayer = 3, // runs the game in multiplayer mode
+ k_ELaunchOptionType_Config = 4, // runs config tool for this game
+ k_ELaunchOptionType_OpenVR = 5, // runs game in VR mode using OpenVR
+ k_ELaunchOptionType_Server = 6, // runs dedicated server for this game
+ k_ELaunchOptionType_Editor = 7, // runs game editor
+ k_ELaunchOptionType_Manual = 8, // shows game manual
+ k_ELaunchOptionType_Benchmark = 9, // runs game benchmark
+ k_ELaunchOptionType_Option1 = 10, // generic run option, uses description field for game name
+ k_ELaunchOptionType_Option2 = 11, // generic run option, uses description field for game name
+ k_ELaunchOptionType_Option3 = 12, // generic run option, uses description field for game name
+ k_ELaunchOptionType_OculusVR = 13, // runs game in VR mode using the Oculus SDK
+ k_ELaunchOptionType_OpenVROverlay = 14, // runs an OpenVR dashboard overlay
+ k_ELaunchOptionType_OSVR = 15, // runs game in VR mode using the OSVR SDK
+
+
+ k_ELaunchOptionType_Dialog = 1000, // show launch options dialog
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: true if this launch option is any of the vr launching types
+//-----------------------------------------------------------------------------
+static inline bool BIsVRLaunchOptionType( const ELaunchOptionType eType )
+{
+ return eType == k_ELaunchOptionType_OpenVR
+ || eType == k_ELaunchOptionType_OpenVROverlay
+ || eType == k_ELaunchOptionType_OculusVR
+ || eType == k_ELaunchOptionType_OSVR;
+}
+
+
+//-----------------------------------------------------------------------------
+// Purpose: code points for VR HMD vendors and models
+// WARNING: DO NOT RENUMBER EXISTING VALUES - STORED IN A DATABASE
+//-----------------------------------------------------------------------------
+enum EVRHMDType
+{
+ k_eEVRHMDType_None = -1, // unknown vendor and model
+
+ k_eEVRHMDType_Unknown = 0, // unknown vendor and model
+
+ k_eEVRHMDType_HTC_Dev = 1, // original HTC dev kits
+ k_eEVRHMDType_HTC_VivePre = 2, // htc vive pre
+ k_eEVRHMDType_HTC_Vive = 3, // htc vive consumer release
+
+ k_eEVRHMDType_HTC_Unknown = 20, // unknown htc hmd
+
+ k_eEVRHMDType_Oculus_DK1 = 21, // Oculus DK1
+ k_eEVRHMDType_Oculus_DK2 = 22, // Oculus DK2
+ k_eEVRHMDType_Oculus_Rift = 23, // Oculus rift
+
+ k_eEVRHMDType_Oculus_Unknown = 40, // // Oculus unknown HMD
+};
+
+
+//-----------------------------------------------------------------------------
+// Purpose: true if this is from an Oculus HMD
+//-----------------------------------------------------------------------------
+static inline bool BIsOculusHMD( EVRHMDType eType )
+{
+ return eType == k_eEVRHMDType_Oculus_DK1 || eType == k_eEVRHMDType_Oculus_DK2 || eType == k_eEVRHMDType_Oculus_Rift || eType == k_eEVRHMDType_Oculus_Unknown;
+}
+
+
+//-----------------------------------------------------------------------------
+// Purpose: true if this is from an Vive HMD
+//-----------------------------------------------------------------------------
+static inline bool BIsViveHMD( EVRHMDType eType )
+{
+ return eType == k_eEVRHMDType_HTC_Dev || eType == k_eEVRHMDType_HTC_VivePre || eType == k_eEVRHMDType_HTC_Vive || eType == k_eEVRHMDType_HTC_Unknown;
+}
+
+
+#pragma pack( push, 1 )
+
+#define CSTEAMID_DEFINED
+
+// Steam ID structure (64 bits total)
+class CSteamID
+{
+public:
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Constructor
+ //-----------------------------------------------------------------------------
+ CSteamID()
+ {
+ m_steamid.m_comp.m_unAccountID = 0;
+ m_steamid.m_comp.m_EAccountType = k_EAccountTypeInvalid;
+ m_steamid.m_comp.m_EUniverse = k_EUniverseInvalid;
+ m_steamid.m_comp.m_unAccountInstance = 0;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Constructor
+ // Input : unAccountID - 32-bit account ID
+ // eUniverse - Universe this account belongs to
+ // eAccountType - Type of account
+ //-----------------------------------------------------------------------------
+ CSteamID( uint32 unAccountID, EUniverse eUniverse, EAccountType eAccountType )
+ {
+ Set( unAccountID, eUniverse, eAccountType );
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Constructor
+ // Input : unAccountID - 32-bit account ID
+ // unAccountInstance - instance
+ // eUniverse - Universe this account belongs to
+ // eAccountType - Type of account
+ //-----------------------------------------------------------------------------
+ CSteamID( uint32 unAccountID, unsigned int unAccountInstance, EUniverse eUniverse, EAccountType eAccountType )
+ {
+#if defined(_SERVER) && defined(Assert)
+ Assert( ! ( ( k_EAccountTypeIndividual == eAccountType ) && ( unAccountInstance > k_unSteamUserWebInstance ) ) ); // enforce that for individual accounts, instance is always 1
+#endif // _SERVER
+ InstancedSet( unAccountID, unAccountInstance, eUniverse, eAccountType );
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Constructor
+ // Input : ulSteamID - 64-bit representation of a Steam ID
+ // Note: Will not accept a uint32 or int32 as input, as that is a probable mistake.
+ // See the stubbed out overloads in the private: section for more info.
+ //-----------------------------------------------------------------------------
+ CSteamID( uint64 ulSteamID )
+ {
+ SetFromUint64( ulSteamID );
+ }
+#ifdef INT64_DIFFERENT_FROM_INT64_T
+ CSteamID( uint64_t ulSteamID )
+ {
+ SetFromUint64( (uint64)ulSteamID );
+ }
+#endif
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Sets parameters for steam ID
+ // Input : unAccountID - 32-bit account ID
+ // eUniverse - Universe this account belongs to
+ // eAccountType - Type of account
+ //-----------------------------------------------------------------------------
+ void Set( uint32 unAccountID, EUniverse eUniverse, EAccountType eAccountType )
+ {
+ m_steamid.m_comp.m_unAccountID = unAccountID;
+ m_steamid.m_comp.m_EUniverse = eUniverse;
+ m_steamid.m_comp.m_EAccountType = eAccountType;
+
+ if ( eAccountType == k_EAccountTypeClan || eAccountType == k_EAccountTypeGameServer )
+ {
+ m_steamid.m_comp.m_unAccountInstance = 0;
+ }
+ else
+ {
+ // by default we pick the desktop instance
+ m_steamid.m_comp.m_unAccountInstance = k_unSteamUserDesktopInstance;
+ }
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Sets parameters for steam ID
+ // Input : unAccountID - 32-bit account ID
+ // eUniverse - Universe this account belongs to
+ // eAccountType - Type of account
+ //-----------------------------------------------------------------------------
+ void InstancedSet( uint32 unAccountID, uint32 unInstance, EUniverse eUniverse, EAccountType eAccountType )
+ {
+ m_steamid.m_comp.m_unAccountID = unAccountID;
+ m_steamid.m_comp.m_EUniverse = eUniverse;
+ m_steamid.m_comp.m_EAccountType = eAccountType;
+ m_steamid.m_comp.m_unAccountInstance = unInstance;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Initializes a steam ID from its 52 bit parts and universe/type
+ // Input : ulIdentifier - 52 bits of goodness
+ //-----------------------------------------------------------------------------
+ void FullSet( uint64 ulIdentifier, EUniverse eUniverse, EAccountType eAccountType )
+ {
+ m_steamid.m_comp.m_unAccountID = ( ulIdentifier & k_unSteamAccountIDMask ); // account ID is low 32 bits
+ m_steamid.m_comp.m_unAccountInstance = ( ( ulIdentifier >> 32 ) & k_unSteamAccountInstanceMask ); // account instance is next 20 bits
+ m_steamid.m_comp.m_EUniverse = eUniverse;
+ m_steamid.m_comp.m_EAccountType = eAccountType;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Initializes a steam ID from its 64-bit representation
+ // Input : ulSteamID - 64-bit representation of a Steam ID
+ //-----------------------------------------------------------------------------
+ void SetFromUint64( uint64 ulSteamID )
+ {
+ m_steamid.m_unAll64Bits = ulSteamID;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Clear all fields, leaving an invalid ID.
+ //-----------------------------------------------------------------------------
+ void Clear()
+ {
+ m_steamid.m_comp.m_unAccountID = 0;
+ m_steamid.m_comp.m_EAccountType = k_EAccountTypeInvalid;
+ m_steamid.m_comp.m_EUniverse = k_EUniverseInvalid;
+ m_steamid.m_comp.m_unAccountInstance = 0;
+ }
+
+
+#if defined( INCLUDED_STEAM2_USERID_STRUCTS )
+ //-----------------------------------------------------------------------------
+ // Purpose: Initializes a steam ID from a Steam2 ID structure
+ // Input: pTSteamGlobalUserID - Steam2 ID to convert
+ // eUniverse - universe this ID belongs to
+ //-----------------------------------------------------------------------------
+ void SetFromSteam2( TSteamGlobalUserID *pTSteamGlobalUserID, EUniverse eUniverse )
+ {
+ m_steamid.m_comp.m_unAccountID = pTSteamGlobalUserID->m_SteamLocalUserID.Split.Low32bits * 2 +
+ pTSteamGlobalUserID->m_SteamLocalUserID.Split.High32bits;
+ m_steamid.m_comp.m_EUniverse = eUniverse; // set the universe
+ m_steamid.m_comp.m_EAccountType = k_EAccountTypeIndividual; // Steam 2 accounts always map to account type of individual
+ m_steamid.m_comp.m_unAccountInstance = k_unSteamUserDesktopInstance; // Steam2 only knew desktop instances
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Fills out a Steam2 ID structure
+ // Input: pTSteamGlobalUserID - Steam2 ID to write to
+ //-----------------------------------------------------------------------------
+ void ConvertToSteam2( TSteamGlobalUserID *pTSteamGlobalUserID ) const
+ {
+ // only individual accounts have any meaning in Steam 2, only they can be mapped
+ // Assert( m_steamid.m_comp.m_EAccountType == k_EAccountTypeIndividual );
+
+ pTSteamGlobalUserID->m_SteamInstanceID = 0;
+ pTSteamGlobalUserID->m_SteamLocalUserID.Split.High32bits = m_steamid.m_comp.m_unAccountID % 2;
+ pTSteamGlobalUserID->m_SteamLocalUserID.Split.Low32bits = m_steamid.m_comp.m_unAccountID / 2;
+ }
+#endif // defined( INCLUDED_STEAM_COMMON_STEAMCOMMON_H )
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Converts steam ID to its 64-bit representation
+ // Output : 64-bit representation of a Steam ID
+ //-----------------------------------------------------------------------------
+ uint64 ConvertToUint64() const
+ {
+ return m_steamid.m_unAll64Bits;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Converts the static parts of a steam ID to a 64-bit representation.
+ // For multiseat accounts, all instances of that account will have the
+ // same static account key, so they can be grouped together by the static
+ // account key.
+ // Output : 64-bit static account key
+ //-----------------------------------------------------------------------------
+ uint64 GetStaticAccountKey() const
+ {
+ // note we do NOT include the account instance (which is a dynamic property) in the static account key
+ return (uint64) ( ( ( (uint64) m_steamid.m_comp.m_EUniverse ) << 56 ) + ((uint64) m_steamid.m_comp.m_EAccountType << 52 ) + m_steamid.m_comp.m_unAccountID );
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: create an anonymous game server login to be filled in by the AM
+ //-----------------------------------------------------------------------------
+ void CreateBlankAnonLogon( EUniverse eUniverse )
+ {
+ m_steamid.m_comp.m_unAccountID = 0;
+ m_steamid.m_comp.m_EAccountType = k_EAccountTypeAnonGameServer;
+ m_steamid.m_comp.m_EUniverse = eUniverse;
+ m_steamid.m_comp.m_unAccountInstance = 0;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: create an anonymous game server login to be filled in by the AM
+ //-----------------------------------------------------------------------------
+ void CreateBlankAnonUserLogon( EUniverse eUniverse )
+ {
+ m_steamid.m_comp.m_unAccountID = 0;
+ m_steamid.m_comp.m_EAccountType = k_EAccountTypeAnonUser;
+ m_steamid.m_comp.m_EUniverse = eUniverse;
+ m_steamid.m_comp.m_unAccountInstance = 0;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this an anonymous game server login that will be filled in?
+ //-----------------------------------------------------------------------------
+ bool BBlankAnonAccount() const
+ {
+ return m_steamid.m_comp.m_unAccountID == 0 && BAnonAccount() && m_steamid.m_comp.m_unAccountInstance == 0;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a game server account id? (Either persistent or anonymous)
+ //-----------------------------------------------------------------------------
+ bool BGameServerAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeGameServer || m_steamid.m_comp.m_EAccountType == k_EAccountTypeAnonGameServer;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a persistent (not anonymous) game server account id?
+ //-----------------------------------------------------------------------------
+ bool BPersistentGameServerAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeGameServer;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this an anonymous game server account id?
+ //-----------------------------------------------------------------------------
+ bool BAnonGameServerAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeAnonGameServer;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a content server account id?
+ //-----------------------------------------------------------------------------
+ bool BContentServerAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeContentServer;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a clan account id?
+ //-----------------------------------------------------------------------------
+ bool BClanAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeClan;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a chat account id?
+ //-----------------------------------------------------------------------------
+ bool BChatAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeChat;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a chat account id?
+ //-----------------------------------------------------------------------------
+ bool IsLobby() const
+ {
+ return ( m_steamid.m_comp.m_EAccountType == k_EAccountTypeChat )
+ && ( m_steamid.m_comp.m_unAccountInstance & k_EChatInstanceFlagLobby );
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this an individual user account id?
+ //-----------------------------------------------------------------------------
+ bool BIndividualAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeIndividual || m_steamid.m_comp.m_EAccountType == k_EAccountTypeConsoleUser;
+ }
+
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this an anonymous account?
+ //-----------------------------------------------------------------------------
+ bool BAnonAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeAnonUser || m_steamid.m_comp.m_EAccountType == k_EAccountTypeAnonGameServer;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this an anonymous user account? ( used to create an account or reset a password )
+ //-----------------------------------------------------------------------------
+ bool BAnonUserAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeAnonUser;
+ }
+
+ //-----------------------------------------------------------------------------
+ // Purpose: Is this a faked up Steam ID for a PSN friend account?
+ //-----------------------------------------------------------------------------
+ bool BConsoleUserAccount() const
+ {
+ return m_steamid.m_comp.m_EAccountType == k_EAccountTypeConsoleUser;
+ }
+
+ // simple accessors
+ void SetAccountID( uint32 unAccountID ) { m_steamid.m_comp.m_unAccountID = unAccountID; }
+ void SetAccountInstance( uint32 unInstance ){ m_steamid.m_comp.m_unAccountInstance = unInstance; }
+ void ClearIndividualInstance() { if ( BIndividualAccount() ) m_steamid.m_comp.m_unAccountInstance = 0; }
+ bool HasNoIndividualInstance() const { return BIndividualAccount() && (m_steamid.m_comp.m_unAccountInstance==0); }
+ AccountID_t GetAccountID() const { return m_steamid.m_comp.m_unAccountID; }
+ uint32 GetUnAccountInstance() const { return m_steamid.m_comp.m_unAccountInstance; }
+ EAccountType GetEAccountType() const { return ( EAccountType ) m_steamid.m_comp.m_EAccountType; }
+ EUniverse GetEUniverse() const { return m_steamid.m_comp.m_EUniverse; }
+ void SetEUniverse( EUniverse eUniverse ) { m_steamid.m_comp.m_EUniverse = eUniverse; }
+ bool IsValid() const;
+
+ // this set of functions is hidden, will be moved out of class
+ explicit CSteamID( const char *pchSteamID, EUniverse eDefaultUniverse = k_EUniverseInvalid );
+ const char * Render() const; // renders this steam ID to string
+ static const char * Render( uint64 ulSteamID ); // static method to render a uint64 representation of a steam ID to a string
+
+ void SetFromString( const char *pchSteamID, EUniverse eDefaultUniverse );
+ // SetFromString allows many partially-correct strings, constraining how
+ // we might be able to change things in the future.
+ // SetFromStringStrict requires the exact string forms that we support
+ // and is preferred when the caller knows it's safe to be strict.
+ // Returns whether the string parsed correctly.
+ bool SetFromStringStrict( const char *pchSteamID, EUniverse eDefaultUniverse );
+ bool SetFromSteam2String( const char *pchSteam2ID, EUniverse eUniverse );
+
+ inline bool operator==( const CSteamID &val ) const { return m_steamid.m_unAll64Bits == val.m_steamid.m_unAll64Bits; }
+ inline bool operator!=( const CSteamID &val ) const { return !operator==( val ); }
+ inline bool operator<( const CSteamID &val ) const { return m_steamid.m_unAll64Bits < val.m_steamid.m_unAll64Bits; }
+ inline bool operator>( const CSteamID &val ) const { return m_steamid.m_unAll64Bits > val.m_steamid.m_unAll64Bits; }
+
+ // DEBUG function
+ bool BValidExternalSteamID() const;
+
+private:
+ // These are defined here to prevent accidental implicit conversion of a u32AccountID to a CSteamID.
+ // If you get a compiler error about an ambiguous constructor/function then it may be because you're
+ // passing a 32-bit int to a function that takes a CSteamID. You should explicitly create the SteamID
+ // using the correct Universe and account Type/Instance values.
+ CSteamID( uint32 );
+ CSteamID( int32 );
+
+ // 64 bits total
+ union SteamID_t
+ {
+ struct SteamIDComponent_t
+ {
+#ifdef VALVE_BIG_ENDIAN
+ EUniverse m_EUniverse : 8; // universe this account belongs to
+ unsigned int m_EAccountType : 4; // type of account - can't show as EAccountType, due to signed / unsigned difference
+ unsigned int m_unAccountInstance : 20; // dynamic instance ID
+ uint32 m_unAccountID : 32; // unique account identifier
+#else
+ uint32 m_unAccountID : 32; // unique account identifier
+ unsigned int m_unAccountInstance : 20; // dynamic instance ID
+ unsigned int m_EAccountType : 4; // type of account - can't show as EAccountType, due to signed / unsigned difference
+ EUniverse m_EUniverse : 8; // universe this account belongs to
+#endif
+ } m_comp;
+
+ uint64 m_unAll64Bits;
+ } m_steamid;
+};
+
+inline bool CSteamID::IsValid() const
+{
+ if ( m_steamid.m_comp.m_EAccountType <= k_EAccountTypeInvalid || m_steamid.m_comp.m_EAccountType >= k_EAccountTypeMax )
+ return false;
+
+ if ( m_steamid.m_comp.m_EUniverse <= k_EUniverseInvalid || m_steamid.m_comp.m_EUniverse >= k_EUniverseMax )
+ return false;
+
+ if ( m_steamid.m_comp.m_EAccountType == k_EAccountTypeIndividual )
+ {
+ if ( m_steamid.m_comp.m_unAccountID == 0 || m_steamid.m_comp.m_unAccountInstance > k_unSteamUserWebInstance )
+ return false;
+ }
+
+ if ( m_steamid.m_comp.m_EAccountType == k_EAccountTypeClan )
+ {
+ if ( m_steamid.m_comp.m_unAccountID == 0 || m_steamid.m_comp.m_unAccountInstance != 0 )
+ return false;
+ }
+
+ if ( m_steamid.m_comp.m_EAccountType == k_EAccountTypeGameServer )
+ {
+ if ( m_steamid.m_comp.m_unAccountID == 0 )
+ return false;
+ // Any limit on instances? We use them for local users and bots
+ }
+ return true;
+}
+
+// generic invalid CSteamID
+#define k_steamIDNil CSteamID()
+
+// This steamID comes from a user game connection to an out of date GS that hasnt implemented the protocol
+// to provide its steamID
+#define k_steamIDOutofDateGS CSteamID( 0, 0, k_EUniverseInvalid, k_EAccountTypeInvalid )
+// This steamID comes from a user game connection to an sv_lan GS
+#define k_steamIDLanModeGS CSteamID( 0, 0, k_EUniversePublic, k_EAccountTypeInvalid )
+// This steamID can come from a user game connection to a GS that has just booted but hasnt yet even initialized
+// its steam3 component and started logging on.
+#define k_steamIDNotInitYetGS CSteamID( 1, 0, k_EUniverseInvalid, k_EAccountTypeInvalid )
+// This steamID can come from a user game connection to a GS that isn't using the steam authentication system but still
+// wants to support the "Join Game" option in the friends list
+#define k_steamIDNonSteamGS CSteamID( 2, 0, k_EUniverseInvalid, k_EAccountTypeInvalid )
+
+
+#ifdef STEAM
+// Returns the matching chat steamID, with the default instance of 0
+// If the steamID passed in is already of type k_EAccountTypeChat it will be returned with the same instance
+CSteamID ChatIDFromSteamID( const CSteamID &steamID );
+// Returns the matching clan steamID, with the default instance of 0
+// If the steamID passed in is already of type k_EAccountTypeClan it will be returned with the same instance
+CSteamID ClanIDFromSteamID( const CSteamID &steamID );
+// Asserts steamID type before conversion
+CSteamID ChatIDFromClanID( const CSteamID &steamIDClan );
+// Asserts steamID type before conversion
+CSteamID ClanIDFromChatID( const CSteamID &steamIDChat );
+
+#endif // _STEAM
+
+
+//-----------------------------------------------------------------------------
+// Purpose: encapsulates an appID/modID pair
+//-----------------------------------------------------------------------------
+class CGameID
+{
+public:
+
+ CGameID()
+ {
+ m_gameID.m_nType = k_EGameIDTypeApp;
+ m_gameID.m_nAppID = k_uAppIdInvalid;
+ m_gameID.m_nModID = 0;
+ }
+
+ explicit CGameID( uint64 ulGameID )
+ {
+ m_ulGameID = ulGameID;
+ }
+#ifdef INT64_DIFFERENT_FROM_INT64_T
+ CGameID( uint64_t ulGameID )
+ {
+ m_ulGameID = (uint64)ulGameID;
+ }
+#endif
+
+ explicit CGameID( int32 nAppID )
+ {
+ m_ulGameID = 0;
+ m_gameID.m_nAppID = nAppID;
+ }
+
+ explicit CGameID( uint32 nAppID )
+ {
+ m_ulGameID = 0;
+ m_gameID.m_nAppID = nAppID;
+ }
+
+ CGameID( uint32 nAppID, uint32 nModID )
+ {
+ m_ulGameID = 0;
+ m_gameID.m_nAppID = nAppID;
+ m_gameID.m_nModID = nModID;
+ m_gameID.m_nType = k_EGameIDTypeGameMod;
+ }
+
+ // Hidden functions used only by Steam
+ explicit CGameID( const char *pchGameID );
+ const char *Render() const; // render this Game ID to string
+ static const char *Render( uint64 ulGameID ); // static method to render a uint64 representation of a Game ID to a string
+
+ // must include checksum_crc.h first to get this functionality
+#if defined( CHECKSUM_CRC_H )
+ CGameID( uint32 nAppID, const char *pchModPath )
+ {
+ m_ulGameID = 0;
+ m_gameID.m_nAppID = nAppID;
+ m_gameID.m_nType = k_EGameIDTypeGameMod;
+
+ char rgchModDir[MAX_PATH];
+ V_FileBase( pchModPath, rgchModDir, sizeof( rgchModDir ) );
+ CRC32_t crc32;
+ CRC32_Init( &crc32 );
+ CRC32_ProcessBuffer( &crc32, rgchModDir, V_strlen( rgchModDir ) );
+ CRC32_Final( &crc32 );
+
+ // set the high-bit on the mod-id
+ // reduces crc32 to 31bits, but lets us use the modID as a guaranteed unique
+ // replacement for appID's
+ m_gameID.m_nModID = crc32 | (0x80000000);
+ }
+
+ CGameID( const char *pchExePath, const char *pchAppName )
+ {
+ m_ulGameID = 0;
+ m_gameID.m_nAppID = k_uAppIdInvalid;
+ m_gameID.m_nType = k_EGameIDTypeShortcut;
+
+ CRC32_t crc32;
+ CRC32_Init( &crc32 );
+ if ( pchExePath )
+ CRC32_ProcessBuffer( &crc32, pchExePath, V_strlen( pchExePath ) );
+ if ( pchAppName )
+ CRC32_ProcessBuffer( &crc32, pchAppName, V_strlen( pchAppName ) );
+ CRC32_Final( &crc32 );
+
+ // set the high-bit on the mod-id
+ // reduces crc32 to 31bits, but lets us use the modID as a guaranteed unique
+ // replacement for appID's
+ m_gameID.m_nModID = crc32 | (0x80000000);
+ }
+
+#if defined( VSTFILEID_H )
+
+ CGameID( VstFileID vstFileID )
+ {
+ m_ulGameID = 0;
+ m_gameID.m_nAppID = k_uAppIdInvalid;
+ m_gameID.m_nType = k_EGameIDTypeP2P;
+
+ CRC32_t crc32;
+ CRC32_Init( &crc32 );
+ const char *pchFileId = vstFileID.Render();
+ CRC32_ProcessBuffer( &crc32, pchFileId, V_strlen( pchFileId ) );
+ CRC32_Final( &crc32 );
+
+ // set the high-bit on the mod-id
+ // reduces crc32 to 31bits, but lets us use the modID as a guaranteed unique
+ // replacement for appID's
+ m_gameID.m_nModID = crc32 | (0x80000000);
+ }
+
+#endif /* VSTFILEID_H */
+
+#endif /* CHECKSUM_CRC_H */
+
+
+ uint64 ToUint64() const
+ {
+ return m_ulGameID;
+ }
+
+ uint64 *GetUint64Ptr()
+ {
+ return &m_ulGameID;
+ }
+
+ void Set( uint64 ulGameID )
+ {
+ m_ulGameID = ulGameID;
+ }
+
+ bool IsMod() const
+ {
+ return ( m_gameID.m_nType == k_EGameIDTypeGameMod );
+ }
+
+ bool IsShortcut() const
+ {
+ return ( m_gameID.m_nType == k_EGameIDTypeShortcut );
+ }
+
+ bool IsP2PFile() const
+ {
+ return ( m_gameID.m_nType == k_EGameIDTypeP2P );
+ }
+
+ bool IsSteamApp() const
+ {
+ return ( m_gameID.m_nType == k_EGameIDTypeApp );
+ }
+
+ uint32 ModID() const
+ {
+ return m_gameID.m_nModID;
+ }
+
+ uint32 AppID() const
+ {
+ return m_gameID.m_nAppID;
+ }
+
+ bool operator == ( const CGameID &rhs ) const
+ {
+ return m_ulGameID == rhs.m_ulGameID;
+ }
+
+ bool operator != ( const CGameID &rhs ) const
+ {
+ return !(*this == rhs);
+ }
+
+ bool operator < ( const CGameID &rhs ) const
+ {
+ return ( m_ulGameID < rhs.m_ulGameID );
+ }
+
+ bool IsValid() const
+ {
+ // each type has it's own invalid fixed point:
+ switch( m_gameID.m_nType )
+ {
+ case k_EGameIDTypeApp:
+ return m_gameID.m_nAppID != k_uAppIdInvalid;
+
+ case k_EGameIDTypeGameMod:
+ return m_gameID.m_nAppID != k_uAppIdInvalid && m_gameID.m_nModID & 0x80000000;
+
+ case k_EGameIDTypeShortcut:
+ return (m_gameID.m_nModID & 0x80000000) != 0;
+
+ case k_EGameIDTypeP2P:
+ return m_gameID.m_nAppID == k_uAppIdInvalid && m_gameID.m_nModID & 0x80000000;
+
+ default:
+#if defined(Assert)
+ Assert(false);
+#endif
+ return false;
+ }
+
+ }
+
+ void Reset()
+ {
+ m_ulGameID = 0;
+ }
+
+
+
+private:
+
+ enum EGameIDType
+ {
+ k_EGameIDTypeApp = 0,
+ k_EGameIDTypeGameMod = 1,
+ k_EGameIDTypeShortcut = 2,
+ k_EGameIDTypeP2P = 3,
+ };
+
+ struct GameID_t
+ {
+#ifdef VALVE_BIG_ENDIAN
+ unsigned int m_nModID : 32;
+ unsigned int m_nType : 8;
+ unsigned int m_nAppID : 24;
+#else
+ unsigned int m_nAppID : 24;
+ unsigned int m_nType : 8;
+ unsigned int m_nModID : 32;
+#endif
+ };
+
+ union
+ {
+ uint64 m_ulGameID;
+ GameID_t m_gameID;
+ };
+};
+
+#pragma pack( pop )
+
+const int k_cchGameExtraInfoMax = 64;
+
+
+//-----------------------------------------------------------------------------
+// Constants used for query ports.
+//-----------------------------------------------------------------------------
+
+#define QUERY_PORT_NOT_INITIALIZED 0xFFFF // We haven't asked the GS for this query port's actual value yet.
+#define QUERY_PORT_ERROR 0xFFFE // We were unable to get the query port for this server.
+
+
+//-----------------------------------------------------------------------------
+// Purpose: Passed as argument to SteamAPI_UseBreakpadCrashHandler to enable optional callback
+// just before minidump file is captured after a crash has occurred. (Allows app to append additional comment data to the dump, etc.)
+//-----------------------------------------------------------------------------
+typedef void (*PFNPreMinidumpCallback)(void *context);
+
+//-----------------------------------------------------------------------------
+// Purpose: Used by ICrashHandler interfaces to reference particular installed crash handlers
+//-----------------------------------------------------------------------------
+typedef void *BREAKPAD_HANDLE;
+#define BREAKPAD_INVALID_HANDLE (BREAKPAD_HANDLE)0
+
+#endif // STEAMCLIENTPUBLIC_H
diff --git a/dep/steam_api/steamencryptedappticket.h b/dep/steam_api/steamencryptedappticket.h
new file mode 100644
index 0000000..48c63b4
--- /dev/null
+++ b/dep/steam_api/steamencryptedappticket.h
@@ -0,0 +1,32 @@
+//========= Copyright 1996-2010, Valve LLC, All rights reserved. ============
+//
+// Purpose: utilities to decode/decrypt a ticket from the
+// ISteamUser::RequestEncryptedAppTicket, ISteamUser::GetEncryptedAppTicket API
+//
+// To use: declare CSteamEncryptedAppTicket, then call BDecryptTicket
+// if BDecryptTicket returns true, other accessors are valid
+//
+//=============================================================================
+
+#include "steam_api.h"
+
+static const int k_nSteamEncryptedAppTicketSymmetricKeyLen = 32;
+
+
+S_API bool SteamEncryptedAppTicket_BDecryptTicket( const uint8 *rgubTicketEncrypted, uint32 cubTicketEncrypted,
+ uint8 *rgubTicketDecrypted, uint32 *pcubTicketDecrypted,
+ const uint8 rgubKey[k_nSteamEncryptedAppTicketSymmetricKeyLen], int cubKey );
+
+S_API bool SteamEncryptedAppTicket_BIsTicketForApp( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted, AppId_t nAppID );
+
+S_API RTime32 SteamEncryptedAppTicket_GetTicketIssueTime( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted );
+
+S_API void SteamEncryptedAppTicket_GetTicketSteamID( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted, CSteamID *psteamID );
+
+S_API AppId_t SteamEncryptedAppTicket_GetTicketAppID( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted );
+
+S_API bool SteamEncryptedAppTicket_BUserOwnsAppInTicket( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted, AppId_t nAppID );
+
+S_API bool SteamEncryptedAppTicket_BUserIsVacBanned( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted );
+
+S_API const uint8 *SteamEncryptedAppTicket_GetUserVariableData( uint8 *rgubTicketDecrypted, uint32 cubTicketDecrypted, uint32 *pcubUserData );
\ No newline at end of file
diff --git a/dep/steam_api/steamhttpenums.h b/dep/steam_api/steamhttpenums.h
new file mode 100644
index 0000000..d95f195
--- /dev/null
+++ b/dep/steam_api/steamhttpenums.h
@@ -0,0 +1,98 @@
+//====== Copyright 1996-2010, Valve Corporation, All rights reserved. =======
+//
+// Purpose: HTTP related enums, stuff that is shared by both clients and servers, and our
+// UI projects goes here.
+//
+//=============================================================================
+
+#ifndef STEAMHTTPENUMS_H
+#define STEAMHTTPENUMS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+// HTTP related types
+
+// This enum is used in client API methods, do not re-number existing values.
+enum EHTTPMethod
+{
+ k_EHTTPMethodInvalid = 0,
+ k_EHTTPMethodGET,
+ k_EHTTPMethodHEAD,
+ k_EHTTPMethodPOST,
+ k_EHTTPMethodPUT,
+ k_EHTTPMethodDELETE,
+ k_EHTTPMethodOPTIONS,
+ k_EHTTPMethodPATCH,
+
+ // The remaining HTTP methods are not yet supported, per rfc2616 section 5.1.1 only GET and HEAD are required for
+ // a compliant general purpose server. We'll likely add more as we find uses for them.
+
+ // k_EHTTPMethodTRACE,
+ // k_EHTTPMethodCONNECT
+};
+
+
+// HTTP Status codes that the server can send in response to a request, see rfc2616 section 10.3 for descriptions
+// of each of these.
+enum EHTTPStatusCode
+{
+ // Invalid status code (this isn't defined in HTTP, used to indicate unset in our code)
+ k_EHTTPStatusCodeInvalid = 0,
+
+ // Informational codes
+ k_EHTTPStatusCode100Continue = 100,
+ k_EHTTPStatusCode101SwitchingProtocols = 101,
+
+ // Success codes
+ k_EHTTPStatusCode200OK = 200,
+ k_EHTTPStatusCode201Created = 201,
+ k_EHTTPStatusCode202Accepted = 202,
+ k_EHTTPStatusCode203NonAuthoritative = 203,
+ k_EHTTPStatusCode204NoContent = 204,
+ k_EHTTPStatusCode205ResetContent = 205,
+ k_EHTTPStatusCode206PartialContent = 206,
+
+ // Redirection codes
+ k_EHTTPStatusCode300MultipleChoices = 300,
+ k_EHTTPStatusCode301MovedPermanently = 301,
+ k_EHTTPStatusCode302Found = 302,
+ k_EHTTPStatusCode303SeeOther = 303,
+ k_EHTTPStatusCode304NotModified = 304,
+ k_EHTTPStatusCode305UseProxy = 305,
+ //k_EHTTPStatusCode306Unused = 306, (used in old HTTP spec, now unused in 1.1)
+ k_EHTTPStatusCode307TemporaryRedirect = 307,
+
+ // Error codes
+ k_EHTTPStatusCode400BadRequest = 400,
+ k_EHTTPStatusCode401Unauthorized = 401, // You probably want 403 or something else. 401 implies you're sending a WWW-Authenticate header and the client can sent an Authorization header in response.
+ k_EHTTPStatusCode402PaymentRequired = 402, // This is reserved for future HTTP specs, not really supported by clients
+ k_EHTTPStatusCode403Forbidden = 403,
+ k_EHTTPStatusCode404NotFound = 404,
+ k_EHTTPStatusCode405MethodNotAllowed = 405,
+ k_EHTTPStatusCode406NotAcceptable = 406,
+ k_EHTTPStatusCode407ProxyAuthRequired = 407,
+ k_EHTTPStatusCode408RequestTimeout = 408,
+ k_EHTTPStatusCode409Conflict = 409,
+ k_EHTTPStatusCode410Gone = 410,
+ k_EHTTPStatusCode411LengthRequired = 411,
+ k_EHTTPStatusCode412PreconditionFailed = 412,
+ k_EHTTPStatusCode413RequestEntityTooLarge = 413,
+ k_EHTTPStatusCode414RequestURITooLong = 414,
+ k_EHTTPStatusCode415UnsupportedMediaType = 415,
+ k_EHTTPStatusCode416RequestedRangeNotSatisfiable = 416,
+ k_EHTTPStatusCode417ExpectationFailed = 417,
+ k_EHTTPStatusCode4xxUnknown = 418, // 418 is reserved, so we'll use it to mean unknown
+ k_EHTTPStatusCode429TooManyRequests = 429,
+
+ // Server error codes
+ k_EHTTPStatusCode500InternalServerError = 500,
+ k_EHTTPStatusCode501NotImplemented = 501,
+ k_EHTTPStatusCode502BadGateway = 502,
+ k_EHTTPStatusCode503ServiceUnavailable = 503,
+ k_EHTTPStatusCode504GatewayTimeout = 504,
+ k_EHTTPStatusCode505HTTPVersionNotSupported = 505,
+ k_EHTTPStatusCode5xxUnknown = 599,
+};
+
+#endif // STEAMHTTPENUMS_H
\ No newline at end of file
diff --git a/dep/steam_api/steamps3params.h b/dep/steam_api/steamps3params.h
new file mode 100644
index 0000000..c0741b4
--- /dev/null
+++ b/dep/steam_api/steamps3params.h
@@ -0,0 +1,112 @@
+//====== Copyright 1996-2008, Valve Corporation, All rights reserved. =======
+//
+// Purpose:
+//
+//=============================================================================
+
+#ifndef STEAMPS3PARAMS_H
+#define STEAMPS3PARAMS_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// PlayStation 3 initialization parameters
+//
+// The following structure must be passed to when loading steam_api_ps3.prx
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+#define STEAM_PS3_PATH_MAX 1055
+#define STEAM_PS3_SERVICE_ID_MAX 32
+#define STEAM_PS3_COMMUNICATION_ID_MAX 10
+#define STEAM_PS3_COMMUNICATION_SIG_MAX 160
+#define STEAM_PS3_LANGUAGE_MAX 64
+#define STEAM_PS3_REGION_CODE_MAX 16
+#define STEAM_PS3_CURRENT_PARAMS_VER 2
+struct SteamPS3Params_t
+{
+ uint32 m_unVersion; // set to STEAM_PS3_CURRENT_PARAMS_VER
+
+ void *pReserved;
+ uint32 m_nAppId; // set to your game's appid
+
+ char m_rgchInstallationPath[ STEAM_PS3_PATH_MAX ]; // directory containing latest steam prx's and sdata. Can be read only (BDVD)
+ char m_rgchSystemCache[ STEAM_PS3_PATH_MAX ]; // temp working cache, not persistent
+ char m_rgchGameData[ STEAM_PS3_PATH_MAX ]; // persistent game data path for storing user data
+ char m_rgchNpServiceID[ STEAM_PS3_SERVICE_ID_MAX ];
+ char m_rgchNpCommunicationID[ STEAM_PS3_COMMUNICATION_ID_MAX ];
+ char m_rgchNpCommunicationSig[ STEAM_PS3_COMMUNICATION_SIG_MAX ];
+
+ // Language should be one of the following. must be zero terminated
+ // danish
+ // dutch
+ // english
+ // finnish
+ // french
+ // german
+ // italian
+ // korean
+ // norwegian
+ // polish
+ // portuguese
+ // russian
+ // schinese
+ // spanish
+ // swedish
+ // tchinese
+ char m_rgchSteamLanguage[ STEAM_PS3_LANGUAGE_MAX ];
+
+ // region codes are "SCEA", "SCEE", "SCEJ". must be zero terminated
+ char m_rgchRegionCode[ STEAM_PS3_REGION_CODE_MAX ];
+
+ // Should be SYS_TTYP3 through SYS_TTYP10, if it's 0 then Steam won't spawn a
+ // thread to read console input at all. Using this let's you use Steam console commands
+ // like: profile_on, profile_off, profile_dump, mem_stats, mem_validate.
+ unsigned int m_cSteamInputTTY;
+
+ struct Ps3netInit_t
+ {
+ bool m_bNeedInit;
+ void *m_pMemory;
+ int m_nMemorySize;
+ int m_flags;
+ } m_sysNetInitInfo;
+
+ struct Ps3jpgInit_t
+ {
+ bool m_bNeedInit;
+ } m_sysJpgInitInfo;
+
+ struct Ps3pngInit_t
+ {
+ bool m_bNeedInit;
+ } m_sysPngInitInfo;
+
+ struct Ps3sysutilUserInfo_t
+ {
+ bool m_bNeedInit;
+ } m_sysSysUtilUserInfo;
+
+ bool m_bIncludeNewsPage;
+};
+
+
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+// PlayStation 3 memory structure
+//----------------------------------------------------------------------------------------------------------------------------------------------------------//
+#define STEAMPS3_MALLOC_INUSE 0x53D04A51
+#define STEAMPS3_MALLOC_SYSTEM 0x0D102C48
+#define STEAMPS3_MALLOC_OK 0xFFD04A51
+struct SteamPS3Memory_t
+{
+ bool m_bSingleAllocation; // If true, Steam will request one 6MB allocation and use the returned memory for all future allocations
+ // If false, Steam will make call malloc for each allocation
+
+ // required function pointers
+ void* (*m_pfMalloc)(size_t);
+ void* (*m_pfRealloc)(void *, size_t);
+ void (*m_pfFree)(void *);
+ size_t (*m_pUsable_size)(void*);
+};
+
+
+#endif // STEAMPS3PARAMS_H
diff --git a/dep/steam_api/steamtypes.h b/dep/steam_api/steamtypes.h
new file mode 100644
index 0000000..f74df1a
--- /dev/null
+++ b/dep/steam_api/steamtypes.h
@@ -0,0 +1,181 @@
+//========= Copyright 1996-2008, Valve LLC, All rights reserved. ============
+//
+// Purpose:
+//
+//=============================================================================
+
+#ifndef STEAMTYPES_H
+#define STEAMTYPES_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+#define S_CALLTYPE __cdecl
+
+// Steam-specific types. Defined here so this header file can be included in other code bases.
+#ifndef WCHARTYPES_H
+typedef unsigned char uint8;
+#endif
+
+#if defined( __GNUC__ ) && !defined(POSIX)
+ #if __GNUC__ < 4
+ #error "Steamworks requires GCC 4.X (4.2 or 4.4 have been tested)"
+ #endif
+ #define POSIX 1
+#endif
+
+#if defined(__x86_64__) || defined(_WIN64)
+#define X64BITS
+#endif
+
+// Make sure VALVE_BIG_ENDIAN gets set on PS3, may already be set previously in Valve internal code.
+#if !defined(VALVE_BIG_ENDIAN) && defined(_PS3)
+#define VALVE_BIG_ENDIAN
+#endif
+
+typedef unsigned char uint8;
+typedef signed char int8;
+
+#if defined( _WIN32 )
+
+typedef __int16 int16;
+typedef unsigned __int16 uint16;
+typedef __int32 int32;
+typedef unsigned __int32 uint32;
+typedef __int64 int64;
+typedef unsigned __int64 uint64;
+
+typedef int64 lint64;
+typedef uint64 ulint64;
+
+#ifdef X64BITS
+typedef __int64 intp; // intp is an integer that can accomodate a pointer
+typedef unsigned __int64 uintp; // (ie, sizeof(intp) >= sizeof(int) && sizeof(intp) >= sizeof(void *)
+#else
+typedef __int32 intp;
+typedef unsigned __int32 uintp;
+#endif
+
+#else // _WIN32
+
+typedef short int16;
+typedef unsigned short uint16;
+typedef int int32;
+typedef unsigned int uint32;
+typedef long long int64;
+typedef unsigned long long uint64;
+
+// [u]int64 are actually defined as 'long long' and gcc 64-bit
+// doesn't automatically consider them the same as 'long int'.
+// Changing the types for [u]int64 is complicated by
+// there being many definitions, so we just
+// define a 'long int' here and use it in places that would
+// otherwise confuse the compiler.
+typedef long int lint64;
+typedef unsigned long int ulint64;
+
+#ifdef X64BITS
+typedef long long intp;
+typedef unsigned long long uintp;
+#else
+typedef int intp;
+typedef unsigned int uintp;
+#endif
+
+#endif // else _WIN32
+
+#ifdef API_GEN
+# define CLANG_ATTR(ATTR) __attribute__((annotate( ATTR )))
+#else
+# define CLANG_ATTR(ATTR)
+#endif
+
+#define METHOD_DESC(DESC) CLANG_ATTR( "desc:" #DESC ";" )
+#define IGNOREATTR() CLANG_ATTR( "ignore" )
+#define OUT_STRUCT() CLANG_ATTR( "out_struct: ;" )
+#define OUT_STRING() CLANG_ATTR( "out_string: ;" )
+#define OUT_ARRAY_CALL(COUNTER,FUNCTION,PARAMS) CLANG_ATTR( "out_array_call:" #COUNTER "," #FUNCTION "," #PARAMS ";" )
+#define OUT_ARRAY_COUNT(COUNTER, DESC) CLANG_ATTR( "out_array_count:" #COUNTER ";desc:" #DESC )
+#define ARRAY_COUNT(COUNTER) CLANG_ATTR( "array_count:" #COUNTER ";" )
+#define ARRAY_COUNT_D(COUNTER, DESC) CLANG_ATTR( "array_count:" #COUNTER ";desc:" #DESC )
+#define BUFFER_COUNT(COUNTER) CLANG_ATTR( "buffer_count:" #COUNTER ";" )
+#define OUT_BUFFER_COUNT(COUNTER) CLANG_ATTR( "out_buffer_count:" #COUNTER ";" )
+#define OUT_STRING_COUNT(COUNTER) CLANG_ATTR( "out_string_count:" #COUNTER ";" )
+#define DESC(DESC) CLANG_ATTR("desc:" #DESC ";")
+#define CALL_RESULT(RESULT_TYPE) CLANG_ATTR("callresult:" #RESULT_TYPE ";")
+#define CALL_BACK(RESULT_TYPE) CLANG_ATTR("callback:" #RESULT_TYPE ";")
+
+const int k_cubSaltSize = 8;
+typedef uint8 Salt_t[ k_cubSaltSize ];
+
+//-----------------------------------------------------------------------------
+// GID (GlobalID) stuff
+// This is a globally unique identifier. It's guaranteed to be unique across all
+// racks and servers for as long as a given universe persists.
+//-----------------------------------------------------------------------------
+// NOTE: for GID parsing/rendering and other utils, see gid.h
+typedef uint64 GID_t;
+
+const GID_t k_GIDNil = 0xffffffffffffffffull;
+
+// For convenience, we define a number of types that are just new names for GIDs
+typedef uint64 JobID_t; // Each Job has a unique ID
+typedef GID_t TxnID_t; // Each financial transaction has a unique ID
+
+const GID_t k_TxnIDNil = k_GIDNil;
+const GID_t k_TxnIDUnknown = 0;
+
+const JobID_t k_JobIDNil = 0xffffffffffffffffull;
+
+// this is baked into client messages and interfaces as an int,
+// make sure we never break this.
+typedef uint32 PackageId_t;
+const PackageId_t k_uPackageIdFreeSub = 0x0;
+const PackageId_t k_uPackageIdInvalid = 0xFFFFFFFF;
+
+typedef uint32 BundleId_t;
+const BundleId_t k_uBundleIdInvalid = 0;
+
+// this is baked into client messages and interfaces as an int,
+// make sure we never break this.
+typedef uint32 AppId_t;
+const AppId_t k_uAppIdInvalid = 0x0;
+
+typedef uint64 AssetClassId_t;
+const AssetClassId_t k_ulAssetClassIdInvalid = 0x0;
+
+typedef uint32 PhysicalItemId_t;
+const PhysicalItemId_t k_uPhysicalItemIdInvalid = 0x0;
+
+
+// this is baked into client messages and interfaces as an int,
+// make sure we never break this. AppIds and DepotIDs also presently
+// share the same namespace, but since we'd like to change that in the future
+// I've defined it seperately here.
+typedef uint32 DepotId_t;
+const DepotId_t k_uDepotIdInvalid = 0x0;
+
+// RTime32
+// We use this 32 bit time representing real world time.
+// It offers 1 second resolution beginning on January 1, 1970 (Unix time)
+typedef uint32 RTime32;
+
+typedef uint32 CellID_t;
+const CellID_t k_uCellIDInvalid = 0xFFFFFFFF;
+
+// handle to a Steam API call
+typedef uint64 SteamAPICall_t;
+const SteamAPICall_t k_uAPICallInvalid = 0x0;
+
+typedef uint32 AccountID_t;
+
+typedef uint32 PartnerId_t;
+const PartnerId_t k_uPartnerIdInvalid = 0;
+
+// ID for a depot content manifest
+typedef uint64 ManifestId_t;
+const ManifestId_t k_uManifestIdInvalid = 0;
+
+
+
+#endif // STEAMTYPES_H
diff --git a/dep/steam_api/steamuniverse.h b/dep/steam_api/steamuniverse.h
new file mode 100644
index 0000000..dd384dc
--- /dev/null
+++ b/dep/steam_api/steamuniverse.h
@@ -0,0 +1,27 @@
+//========= Copyright � 1996-2008, Valve LLC, All rights reserved. ============
+//
+// Purpose:
+//
+//=============================================================================
+
+#ifndef STEAMUNIVERSE_H
+#define STEAMUNIVERSE_H
+#ifdef _WIN32
+#pragma once
+#endif
+
+
+// Steam universes. Each universe is a self-contained Steam instance.
+enum EUniverse
+{
+ k_EUniverseInvalid = 0,
+ k_EUniversePublic = 1,
+ k_EUniverseBeta = 2,
+ k_EUniverseInternal = 3,
+ k_EUniverseDev = 4,
+ // k_EUniverseRC = 5, // no such universe anymore
+ k_EUniverseMax
+};
+
+
+#endif // STEAMUNIVERSE_H
diff --git a/dep/zlib.lua b/dep/zlib.lua
new file mode 100644
index 0000000..0dc202f
--- /dev/null
+++ b/dep/zlib.lua
@@ -0,0 +1,39 @@
+zlib = {}
+
+function zlib:include()
+ includedirs {
+ path.join(DependencyFolder(), "zlib")
+ }
+end
+
+function zlib:link()
+ self:include()
+ links {
+ "zlib"
+ }
+end
+
+function zlib:project()
+ local folder = DependencyFolder();
+
+ project "zlib"
+
+ location "%{wks.location}/dep"
+ kind "StaticLib"
+ language "C"
+
+ files {
+ path.join(folder, "zlib/*.h"),
+ path.join(folder, "zlib/*.c")
+ }
+
+ defines {
+ "_CRT_SECURE_NO_WARNINGS",
+ "_CRT_NONSTDC_NO_DEPRECATE"
+ }
+
+ self:include()
+
+ -- Disable warnings. They do not have any value to us since it is not our code.
+ warnings "off"
+end
diff --git a/dep/zstd.lua b/dep/zstd.lua
new file mode 100644
index 0000000..4616060
--- /dev/null
+++ b/dep/zstd.lua
@@ -0,0 +1,37 @@
+zstd = {}
+
+function zstd:include()
+ local folder = DependencyFolder();
+
+ includedirs {
+ path.join(folder, "zstd/lib"),
+ path.join(folder, "zstd/lib/common")
+ }
+end
+
+function zstd:link()
+ self:include()
+ links {
+ "zstd"
+ }
+end
+
+function zstd:project()
+ local folder = DependencyFolder();
+
+ project "zstd"
+
+ location "%{wks.location}/dep"
+ kind "StaticLib"
+ language "C"
+
+ files {
+ path.join(folder, "zstd/lib/**.h"),
+ path.join(folder, "zstd/lib/**.c")
+ }
+
+ self:include()
+
+ -- Disable warnings. They do not have any value to us since it is not our code.
+ warnings "off"
+end
diff --git a/generate.bat b/generate.bat
new file mode 100644
index 0000000..3e68b64
--- /dev/null
+++ b/generate.bat
@@ -0,0 +1,5 @@
+@echo off
+echo Updating submodules
+git submodule update --init --recursive
+
+tools\premake5.exe vs2019
\ No newline at end of file
diff --git a/plutonium_logo.jpg b/plutonium_logo.jpg
new file mode 100644
index 0000000..e9bd567
Binary files /dev/null and b/plutonium_logo.jpg differ
diff --git a/premake5.lua b/premake5.lua
new file mode 100644
index 0000000..a4da8b1
--- /dev/null
+++ b/premake5.lua
@@ -0,0 +1,123 @@
+newoption {
+ trigger = "set-version",
+ description = "Sets the version information of zonetool",
+}
+
+-- Functions for locating commonly used folders
+local _DependencyFolder = path.getabsolute("dep")
+function DependencyFolder()
+ return path.getrelative(os.getcwd(), _DependencyFolder)
+end
+
+local _ProjectFolder = path.getabsolute("src")
+function ProjectFolder()
+ return path.getrelative(os.getcwd(), _ProjectFolder)
+end
+
+-- ========================
+-- Workspace
+-- ========================
+workspace "zonetool"
+ location "./build"
+ objdir "%{wks.location}/obj"
+ targetdir "%{wks.location}/bin"
+ targetname "%{prj.name}-%{cfg.platform}-%{cfg.buildcfg}"
+ warnings "Off"
+
+ configurations {
+ "debug",
+ "release",
+ }
+
+ platforms {
+ "x86",
+ "x64"
+ }
+
+ filter "platforms:x86"
+ architecture "x86"
+ defines "CPU_32BIT"
+ filter {}
+
+ filter "platforms:x64"
+ architecture "x86_64"
+ defines "CPU_64BIT"
+ filter {}
+
+ buildoptions "/std:c++latest"
+ buildoptions "/Zc:strictStrings-"
+ systemversion "latest"
+ symbols "On"
+ editandcontinue "Off"
+
+ flags {
+ "NoIncrementalLink",
+ "NoMinimalRebuild",
+ "MultiProcessorCompile",
+ "No64BitChecks"
+ }
+
+ filter "configurations:debug"
+ optimize "Debug"
+ defines {
+ "DEBUG",
+ "_DEBUG",
+ }
+ filter {}
+
+ filter "configurations:release"
+ optimize "Full"
+ defines {
+ "NDEBUG",
+ }
+ flags {
+ "FatalCompileWarnings",
+ }
+ filter{}
+
+ includedirs {
+ ProjectFolder()
+ }
+
+ startproject "ZoneTool"
+
+ -- ========================
+ -- Dependencies
+ -- ========================
+
+ include "dep/libtomcrypt.lua"
+ include "dep/libtommath.lua"
+ include "dep/steam_api.lua"
+ include "dep/zlib.lua"
+ include "dep/zstd.lua"
+
+ -- All projects here should be in the thirdparty folder
+ group "thirdparty"
+
+ libtommath:project()
+ libtomcrypt:project()
+ zlib:project()
+ zstd:project()
+
+ -- Reset group
+ group ""
+
+ -- ========================
+ -- Projects
+ -- ========================
+
+ include "src/ImgPak.lua"
+ include "src/ZoneTool.lua"
+ include "src/ZoneUtils.lua"
+ include "src/IW3.lua"
+ include "src/IW4.lua"
+ include "src/IW5.lua"
+ include "src/CODO.lua"
+
+ ImgPak:project()
+ ZoneTool:project()
+ ZoneUtils:project()
+ IW3:project()
+ IW4:project()
+ IW5:project()
+ CODO:project()
\ No newline at end of file
diff --git a/src/CODO.lua b/src/CODO.lua
new file mode 100644
index 0000000..970ae8b
--- /dev/null
+++ b/src/CODO.lua
@@ -0,0 +1,34 @@
+CODO = {}
+
+function CODO:include()
+ includedirs {
+ path.join(ProjectFolder(), "CODO")
+ }
+end
+
+function CODO:link()
+ self:include()
+ links {
+ "CODO"
+ }
+end
+
+function CODO:project()
+ local folder = ProjectFolder();
+
+ project "CODO"
+ kind "StaticLib"
+ language "C++"
+
+ pchheader "stdafx.hpp"
+ pchsource(path.join(folder, "CODO/stdafx.cpp"))
+
+ files {
+ path.join(folder, "CODO/**.h"),
+ path.join(folder, "CODO/**.hpp"),
+ path.join(folder, "CODO/**.cpp")
+ }
+
+ self:include()
+ ZoneUtils:include()
+end
\ No newline at end of file
diff --git a/src/CODO/Assets/LocalizeEntry.cpp b/src/CODO/Assets/LocalizeEntry.cpp
new file mode 100644
index 0000000..82303a3
--- /dev/null
+++ b/src/CODO/Assets/LocalizeEntry.cpp
@@ -0,0 +1,63 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+namespace ZoneTool::CODO
+{
+ ILocalizeEntry::ILocalizeEntry()
+ {
+ }
+
+ ILocalizeEntry::~ILocalizeEntry()
+ {
+ }
+
+ void ILocalizeEntry::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = name;
+ this->asset_ = DB_FindXAssetHeader(this->type(), this->name().data()).localize;
+ }
+
+ void ILocalizeEntry::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void ILocalizeEntry::load_depending(IZone* zone)
+ {
+ }
+
+ std::string ILocalizeEntry::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t ILocalizeEntry::type()
+ {
+ return localize;
+ }
+
+ void ILocalizeEntry::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto data = this->asset_;
+ auto dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->localizedString = buf->write_str(data->localizedString);
+ dest->name = buf->write_str(data->name);
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ void ILocalizeEntry::dump(LocalizeEntry* asset)
+ {
+ }
+}
diff --git a/src/CODO/Assets/LocalizeEntry.hpp b/src/CODO/Assets/LocalizeEntry.hpp
new file mode 100644
index 0000000..7e75437
--- /dev/null
+++ b/src/CODO/Assets/LocalizeEntry.hpp
@@ -0,0 +1,33 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool::CODO
+{
+ class ILocalizeEntry : public IAsset
+ {
+ private:
+ std::string name_;
+ LocalizeEntry* asset_;
+
+ public:
+ ILocalizeEntry();
+ ~ILocalizeEntry();
+
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(LocalizeEntry* asset);
+ };
+}
diff --git a/src/CODO/Assets/StringTable.cpp b/src/CODO/Assets/StringTable.cpp
new file mode 100644
index 0000000..0dfb3d6
--- /dev/null
+++ b/src/CODO/Assets/StringTable.cpp
@@ -0,0 +1,229 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+namespace ZoneTool::CODO
+{
+ // LEGACY ZONETOOL CODE, FIX ME!
+ class CSV
+ {
+ protected:
+ std::string _name;
+ std::vector> _data;
+
+ public:
+ CSV(std::string name, char sep = ',')
+ : _name(name)
+ {
+ auto fp = FileSystem::FileOpen(name, "r"s);
+
+ if (fp)
+ {
+ long len = FileSystem::FileSize(fp);
+ auto buf = std::make_unique(len + 1);
+ memset(buf.get(), 0, len + 1);
+ fread(buf.get(), len, 1, fp);
+ fclose(fp);
+
+ std::vector rows = split(buf.get(), '\n');
+
+ for (auto& row : rows)
+ {
+ // Replace literal characters
+ std::size_t pos;
+ while ((pos = row.find("\\n")) != std::string::npos)
+ {
+ row.replace(pos, 2, "\n");
+ }
+
+ while ((pos = row.find("\\t")) != std::string::npos)
+ {
+ row.replace(pos, 2, "\t");
+ }
+
+ _data.push_back(split(row, sep));
+ }
+ }
+ }
+
+ std::string entry(std::size_t row, std::size_t column)
+ {
+ return _data[row][column];
+ }
+
+ std::size_t rows()
+ {
+ return _data.size();
+ }
+
+ std::size_t columns(std::size_t row)
+ {
+ return _data[row].size();
+ }
+
+ std::size_t max_columns()
+ {
+ std::size_t _max = 0;
+
+ for (std::size_t row = 0; row < this->rows(); row++)
+ {
+ if (_max < this->columns(row))
+ _max = this->columns(row);
+ }
+
+ return _max;
+ }
+
+ void clear()
+ {
+ for (std::size_t i = 0; i < _data.size(); i++)
+ {
+ for (std::size_t j = 0; j < _data[i].size(); j++)
+ _data[i][j].clear();
+
+ _data[i].clear();
+ }
+
+ _data.clear();
+ }
+ };
+
+ int StringTable_Hash(const char* string)
+ {
+ int hash = 0;
+ char* data = _strdup(string);
+
+ while (*data != 0)
+ {
+ hash = tolower(*data) + (31 * hash);
+ data++;
+ }
+
+ return hash;
+ }
+
+ StringTable* StringTable_Parse(std::string name, ZoneMemory* mem)
+ {
+ auto table = std::make_unique(name);
+ auto stringtable = mem->Alloc();
+
+ stringtable->name = _strdup(name.c_str());
+ stringtable->rows = table->rows();
+ stringtable->columns = table->max_columns();
+ stringtable->strings = mem->Alloc(stringtable->rows * stringtable->columns);
+
+ for (int row = 0; row < table->rows(); row++)
+ {
+ for (int col = 0; col < table->columns(row); col++)
+ {
+ int entry = (row * stringtable->columns) + col;
+ stringtable->strings[entry].string = strdup(table->entry(row, col).c_str());
+ stringtable->strings[entry].hash = StringTable_Hash(stringtable->strings[entry].string);
+ }
+ }
+
+ return stringtable;
+ }
+
+ IStringTable::IStringTable()
+ {
+ }
+
+ IStringTable::~IStringTable()
+ {
+ }
+
+ void IStringTable::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = name;
+ this->asset_ = DB_FindXAssetHeader(this->type(), this->name().data()).stringtable;
+
+ if (FileSystem::FileExists(name))
+ {
+ ZONETOOL_INFO("Parsing stringtable %s...", name.data());
+ this->asset_ = StringTable_Parse(name, mem);
+ }
+ }
+
+ void IStringTable::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IStringTable::load_depending(IZone* zone)
+ {
+ }
+
+ std::string IStringTable::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IStringTable::type()
+ {
+ return stringtable;
+ }
+
+ void IStringTable::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto data = this->asset_;
+ auto dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ // TODO
+
+ StringTable;
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->strings)
+ {
+ buf->align(3);
+ auto destStrings = buf->write(data->strings, data->columns * data->rows);
+
+ if (data->columns * data->rows > 0)
+ {
+ for (int i = 0; i < data->columns * data->rows; i++)
+ {
+ destStrings[i].string = buf->write_str(data->strings[i].string);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->strings);
+ }
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ void IStringTable::dump(StringTable* asset)
+ {
+ std::string path = asset->name;
+
+ auto file = FileSystem::FileOpen(path, "w"s);
+
+ for (int row = 0; row < asset->rows; row++)
+ {
+ for (int column = 0; column < asset->columns; column++)
+ {
+ fprintf(
+ file,
+ "%s%s",
+ (asset->strings[(row * asset->columns) + column].string)
+ ? asset->strings[(row * asset->columns) + column].string
+ : "",
+ (column == asset->columns - 1) ? "\n" : ","
+ );
+ }
+ }
+
+ FileSystem::FileClose(file);
+ }
+}
diff --git a/src/CODO/Assets/StringTable.hpp b/src/CODO/Assets/StringTable.hpp
new file mode 100644
index 0000000..5ed49af
--- /dev/null
+++ b/src/CODO/Assets/StringTable.hpp
@@ -0,0 +1,33 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool::CODO
+{
+ class IStringTable : public IAsset
+ {
+ private:
+ std::string name_;
+ StringTable* asset_;
+
+ public:
+ IStringTable();
+ ~IStringTable();
+
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(StringTable* asset);
+ };
+}
diff --git a/src/CODO/CODO.cpp b/src/CODO/CODO.cpp
new file mode 100644
index 0000000..b23222f
--- /dev/null
+++ b/src/CODO/CODO.cpp
@@ -0,0 +1,140 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include
+
+namespace ZoneTool::CODO
+{
+ const char* Linker::version()
+ {
+ return "CODO";
+ }
+
+ bool Linker::is_used()
+ {
+ return false;
+ }
+
+ const char* Linker::GetAssetName(XAssetType type, XAssetHeader header)
+ {
+ // todo
+ if (type == image)
+ {
+ return header.gfximage->name;
+ }
+ if (type == menu)
+ {
+ //
+ }
+ else
+ {
+ return header.rawfile->name;
+ }
+
+ return "";
+ }
+
+ void Linker::startup()
+ {
+ if (this->is_used())
+ {
+ // todo
+ }
+ }
+
+ std::shared_ptr Linker::alloc_zone(const std::string& zone)
+ {
+ // allocate zone
+ auto ptr = std::make_shared(zone, this);
+ return ptr;
+ }
+
+ std::shared_ptr Linker::alloc_buffer()
+ {
+ auto ptr = std::make_shared();
+ ptr->init_streams(8);
+ return ptr;
+ }
+
+ void Linker::load_zone(const std::string& name)
+ {
+ ZONETOOL_INFO("Loading zone \"%s\"...", name.data());
+
+ XZoneInfo zone = {name.data(), 20, 0};
+ // DB_LoadXAssets(&zone, 1, 0);
+
+ ZONETOOL_INFO("Zone \"%s\" loaded.", name.data());
+ }
+
+ void Linker::unload_zones()
+ {
+ }
+
+ bool Linker::is_valid_asset_type(const std::string& type)
+ {
+ return this->type_to_int(type) >= 0;
+ }
+
+ std::int32_t Linker::type_to_int(std::string type)
+ {
+ auto xassettypes = reinterpret_cast(0x00799278);
+
+ for (std::int32_t i = 0; i < max; i++)
+ {
+ if (xassettypes[i] == type)
+ return i;
+ }
+
+ return -1;
+ }
+
+ std::string Linker::type_to_string(std::int32_t type)
+ {
+ auto xassettypes = reinterpret_cast(0x00799278);
+ return xassettypes[type];
+ }
+
+ bool Linker::supports_building()
+ {
+ return false;
+ }
+
+ bool Linker::supports_version(const zone_target_version version)
+ {
+ return false;
+ }
+
+ void Linker::dump_zone(const std::string& name)
+ {
+ //is_dumping_complete = false;
+ //is_dumping = true;
+ //currentDumpingZone = name;
+ load_zone(name);
+
+ //while (!is_dumping_complete)
+ //{
+ // Sleep(1);
+ //}
+ }
+
+ void Linker::verify_zone(const std::string& name)
+ {
+ //isVerifying = true;
+ //currentDumpingZone = name;
+ load_zone(name);
+ }
+
+ Linker::Linker()
+ {
+ }
+
+ Linker::~Linker()
+ {
+ }
+}
diff --git a/src/CODO/CODO.hpp b/src/CODO/CODO.hpp
new file mode 100644
index 0000000..26af6a2
--- /dev/null
+++ b/src/CODO/CODO.hpp
@@ -0,0 +1,45 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+#include
+#include "Functions.hpp"
+#include "Structs.hpp"
+#include "../IW5/Structs.hpp"
+#include "Zone.hpp"
+
+namespace ZoneTool::CODO
+{
+ using GfxImageFileHeader = IW5::GfxImageFileHeader;
+
+ class Linker : public ILinker
+ {
+ public:
+ Linker();
+ ~Linker();
+
+ const char* version() override;
+ bool is_used() override;
+ void startup() override;
+ std::shared_ptr alloc_zone(const std::string& zone) override;
+ std::shared_ptr alloc_buffer() override;
+ void load_zone(const std::string& name) override;
+ void unload_zones() override;
+ bool is_valid_asset_type(const std::string& type) override;
+ std::int32_t type_to_int(std::string type) override;
+ std::string type_to_string(std::int32_t type) override;
+ bool supports_building() override;
+ bool supports_version(const zone_target_version version) override;
+
+ void dump_zone(const std::string& name) override;
+ void verify_zone(const std::string& name) override;
+
+ static const char* GetAssetName(XAssetType type, XAssetHeader header);
+ };
+}
diff --git a/src/CODO/Functions.hpp b/src/CODO/Functions.hpp
new file mode 100644
index 0000000..56e190e
--- /dev/null
+++ b/src/CODO/Functions.hpp
@@ -0,0 +1,32 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool::CODO
+{
+ union XAssetHeader;
+
+ // TODO: fix offsets!
+ static Function DB_FindXAssetHeader = 0x407930;
+ static Function DB_LoadXAssets = 0x4E5930;
+
+ typedef int (__cdecl * DB_GetXAssetSizeHandler_t)();
+ static DB_GetXAssetSizeHandler_t* DB_GetXAssetSizeHandlers = (DB_GetXAssetSizeHandler_t*)0x799488;
+
+ static const char* SL_ConvertToString(std::uint16_t index)
+ {
+ return Memory::func(0x004EC1D0)(index);
+ }
+
+ static short SL_AllocString(const std::string& string)
+ {
+ return Memory::func(0x00436B40)(
+ string.data(), 1, string.size() + 1);
+ }
+}
diff --git a/src/CODO/Structs.hpp b/src/CODO/Structs.hpp
new file mode 100644
index 0000000..30302d7
--- /dev/null
+++ b/src/CODO/Structs.hpp
@@ -0,0 +1,3444 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool::CODO
+{
+ enum FxElemType : char
+ {
+ FX_ELEM_TYPE_SPRITE_BILLBOARD = 0x0,
+ FX_ELEM_TYPE_SPRITE_ORIENTED = 0x1,
+ FX_ELEM_TYPE_TAIL = 0x2,
+ FX_ELEM_TYPE_TRAIL = 0x3,
+ FX_ELEM_TYPE_CLOUD = 0x4,
+ FX_ELEM_TYPE_SPARKCLOUD = 0x5,
+ FX_ELEM_TYPE_SPARKFOUNTAIN = 0x6,
+ FX_ELEM_TYPE_MODEL = 0x7,
+ FX_ELEM_TYPE_OMNI_LIGHT = 0x8,
+ FX_ELEM_TYPE_SPOT_LIGHT = 0x9,
+ FX_ELEM_TYPE_SOUND = 0xA,
+ FX_ELEM_TYPE_DECAL = 0xB,
+ FX_ELEM_TYPE_RUNNER = 0xC,
+ FX_ELEM_TYPE_COUNT = 0xD,
+ FX_ELEM_TYPE_LAST_SPRITE = 0x3,
+ FX_ELEM_TYPE_LAST_DRAWN = 0x9,
+ };
+
+ enum XAssetType : std::int32_t
+ {
+ physpreset,
+ phys_collmap,
+ xanim,
+ xmodelsurfs,
+ xmodel,
+ material,
+ pixelshader,
+ vertexshader,
+ vertexdecl,
+ techset,
+ image,
+ sound,
+ sndcurve,
+ loaded_sound,
+ col_map_sp,
+ col_map_mp,
+ com_map,
+ game_map_sp,
+ game_map_mp,
+ map_ents,
+ fx_map,
+ gfx_map,
+ lightdef,
+ ui_map,
+ // not used
+ font,
+ menufile,
+ menu,
+ localize,
+ weapon,
+ snddriverglobals,
+ // not used
+ fx,
+ impactfx,
+ aitype,
+ // not used
+ mptype,
+ // not used
+ character,
+ // not used
+ xmodelalias,
+ // not used
+ rawfile,
+ stringtable,
+ leaderboarddef,
+ structureddatadef,
+ tracer,
+ vehicle,
+ addon_map_ents,
+ max,
+ };
+
+ typedef float vec4_t[4];
+ typedef float vec3_t[3];
+ typedef float vec2_t[2];
+
+ template
+ struct VecInternal
+ {
+ float data[N];
+ };
+
+ struct RawFile
+ {
+ const char* name;
+ int compressedLen;
+ int len;
+ const char* buffer;
+ };
+
+#pragma pack(push, 4)
+ struct PhysPreset
+ {
+ const char* name;
+ int type;
+ float mass;
+ float bounce;
+ float friction;
+ float bulletForceScale;
+ float explosiveForceScale;
+ const char* sndAliasPrefix;
+ float piecesSpreadFraction;
+ float piecesUpwardVelocity;
+ bool tempDefaultToCylinder;
+ };
+#pragma pack(pop)
+
+
+ struct XModelAngle
+ {
+ short x;
+ short y;
+ short z;
+ short base;
+ };
+
+ struct XModelTagPos
+ {
+ float x;
+ float y;
+ float z;
+ };
+
+ struct DObjAnimMat
+ {
+ float quat[4];
+ float trans[3];
+ float transWeight;
+ };
+
+#pragma pack(push, 4)
+ struct MaterialStreamRouting
+ {
+ char source;
+ char dest;
+ };
+
+ struct VertexDecl
+ {
+ const char* name;
+ char streamCount;
+ bool hasOptionalSource;
+ char pad[2];
+ MaterialStreamRouting streams[13];
+ void* declarations[16];
+ };
+#pragma pack(pop)
+
+ struct PixelShader
+ {
+ const char* name;
+ void* shader;
+ DWORD* bytecode;
+ short codeLen;
+ };
+
+ struct VertexShader
+ {
+ const char* name;
+ void* shader;
+ DWORD* bytecode;
+ short codeLen;
+ };
+
+ struct MaterialArgumentCodeConst
+ {
+ unsigned __int16 index;
+ char firstRow;
+ char rowCount;
+ };
+
+ union MaterialArgumentDef
+ {
+ float* literalConst;
+ MaterialArgumentCodeConst codeConst;
+ unsigned int codeSampler;
+ unsigned int nameHash;
+ };
+
+ struct ShaderArgumentDef
+ {
+ short type;
+ short dest;
+ MaterialArgumentDef u;
+ };
+#pragma pack(push, 4)
+
+ struct MaterialPass
+ {
+ VertexDecl* vertexDecl;
+ VertexShader* vertexShader;
+ PixelShader* pixelShader;
+ char perPrimArgCount;
+ char perObjArgCount;
+ char stableArgCount;
+ char customSamplerFlags;
+ ShaderArgumentDef* argumentDef;
+ };
+#pragma pack(pop)
+ struct MaterialTechniqueHeader
+ {
+ char* name;
+ short unk;
+ short numPasses;
+ };
+
+ struct MaterialTechnique
+ {
+ MaterialTechniqueHeader hdr;
+ MaterialPass pass[1];
+ };
+
+ struct MaterialTechniqueSet
+ {
+ const char* name;
+ int pad;
+ MaterialTechniqueSet* remappedTechniques;
+ MaterialTechnique* techniques[48];
+ };
+
+ struct MaterialConstantDef
+ {
+ int nameHash;
+ char name[12];
+ float literal[4];
+ };
+
+ struct GfxStateBits
+ {
+ unsigned int loadBits[2];
+ };
+
+ struct GfxImageLoadDef // actually a IDirect3DTexture* but this is easier
+ {
+ char mipLevels;
+ char flags;
+ short dimensions[3];
+ int format; // usually the compression Magic
+ int dataSize; // set to zero to load from IWD
+ char* texture; // texture
+ };
+
+ struct GfxImage
+ {
+ GfxImageLoadDef* texture;
+ char mapType; // 5 is cube, 4 is 3d, 3 is 2d
+ char semantic;
+ char category;
+ char flags;
+ int cardMemory;
+ int dataLen1;
+ int dataLen2;
+ short height;
+ short width;
+ short depth;
+ bool loaded;
+ char pad;
+ char* name;
+ };
+
+ struct MaterialImage
+ {
+ unsigned int typeHash; // asset hash of type
+ char firstCharacter; // first character of image name
+ char secondLastCharacter; // second-last character of image name (maybe only in CoD4?!)
+ char sampleState;
+ char semantic;
+ GfxImage* image; // Image* actually
+ };
+
+ struct Material
+ {
+ const char* name; // 0
+ char gameFlags;
+ char sortKey;
+ unsigned char animationX; // 6 // amount of animation frames in X
+ unsigned char animationY; // 7 // amount of animation frames in Y
+ unsigned int subRendererIndex; // 0x00 //+8
+ unsigned int rendererIndex; // 12 // only for 3D models
+ int unknown;
+ unsigned int surfaceTypeBits; //+20
+ char stateBitsEntry[48]; // 32 // 0xFF
+ char numMaps;
+ char constantCount;
+ char stateBitsCount;
+ char stateFlags; // 0x03
+ unsigned short cameraRegion; // 0x04
+ MaterialTechniqueSet* techniqueSet; // '2d' techset
+ MaterialImage* maps; // map references
+ MaterialConstantDef* constantTable;
+ GfxStateBits* stateMap; // might be NULL, need to test
+ };
+
+ //vec3_t should be from idTech3, has to do with camera angles
+ typedef float vec_t;
+ typedef vec_t vec3_t[3];
+
+ struct Bounds
+ {
+ vec3_t midPoint;
+ vec3_t halfSize;
+
+ void compute()
+ {
+ compute(midPoint, halfSize);
+ }
+
+ void compute(vec3_t mins, vec3_t maxs)
+ {
+ for (int i = 0; i < 3; ++i)
+ {
+ this->halfSize[i] = (maxs[i] - mins[i]) / 2;
+ this->midPoint[i] = this->halfSize[i] + mins[i];
+ }
+ }
+ };
+
+ struct XBoneInfo
+ {
+ union
+ {
+ Bounds packedBounds;
+ float bounds[2][3];
+ };
+
+ float radiusSquared;
+ };
+
+ struct Face
+ {
+ unsigned short v1;
+ unsigned short v2;
+ unsigned short v3;
+ };
+
+ // XModel
+ struct XSurfaceVertexInfo
+ {
+ __int16 vertCount[4];
+ unsigned __int16* vertsBlend;
+
+ /*
+ Count... Ok, here we go...
+
+ (((vertCount[2] << 2) + vertCount[2]) +
+ ((vertCount[3] << 3) - vertCount[3]) +
+ ((vertCount[1] << 1) + vertCount[1])
+ + vertCount[0]) << 1*/
+ };
+
+ union GfxColor
+ {
+ unsigned int packed;
+ char array[4];
+ };
+
+ union PackedTexCoords
+ {
+ unsigned int packed;
+ };
+
+ union PackedUnitVec
+ {
+ unsigned int packed;
+ };
+
+ struct GfxPackedVertex
+ {
+ float xyz[3];
+ float binormalSign;
+ GfxColor color;
+ PackedTexCoords texCoord;
+ PackedUnitVec normal;
+ PackedUnitVec tangent;
+ };
+
+ struct XSurfaceCollisionAabb
+ {
+ unsigned __int16 mins[3];
+ unsigned __int16 maxs[3];
+ };
+
+ struct XSurfaceCollisionNode
+ {
+ XSurfaceCollisionAabb aabb;
+ unsigned __int16 childBeginIndex;
+ unsigned __int16 childCount;
+ };
+
+ struct XSurfaceCollisionLeaf
+ {
+ unsigned __int16 triangleBeginIndex;
+ };
+
+ struct XSurfaceCollisionTree
+ {
+ float trans[3];
+ float scale[3];
+ unsigned int nodeCount;
+ XSurfaceCollisionNode* nodes;
+ unsigned int leafCount;
+ XSurfaceCollisionLeaf* leafs;
+ };
+
+ struct XRigidVertList
+ {
+ unsigned __int16 boneOffset;
+ unsigned __int16 vertCount;
+ unsigned __int16 triOffset;
+ unsigned __int16 triCount;
+ XSurfaceCollisionTree* collisionTree;
+ };
+
+ struct XSurface
+ {
+ char tileMode;
+ bool deformed;
+ unsigned short vertCount;
+ unsigned short triCount;
+ unsigned char streamHandle;
+ char zoneHandle;
+ unsigned __int16 baseTriIndex;
+ unsigned __int16 baseVertIndex;
+ Face* triIndices;
+ XSurfaceVertexInfo vertexInfo;
+ GfxPackedVertex* verticies;
+ int vertListCount;
+ XRigidVertList* rigidVertLists;
+ int partBits[6];
+ };
+
+ struct ModelSurface
+ {
+ char* name;
+ XSurface* xSurficies;
+ short xSurficiesCount;
+ //This is a copy of the count, the actual count is loaded from the parent XModelStreamInfo
+ short _pad;
+ int partBits[6]; // partbits etc
+ };
+
+ struct XSurfaceLod
+ {
+ float dist;
+ short numSurfacesInLod;
+ short surfIndex;
+ ModelSurface* surfaces;
+ char pad3[32];
+ };
+
+ struct XModelCollTri_s
+ {
+ float plane[4];
+ float svec[4];
+ float tvec[4];
+ };
+
+ struct XModelCollSurf_s
+ {
+ XModelCollTri_s* tris;
+ int numCollTris;
+ Bounds bounds;
+ int boneIdx;
+ int contents;
+ int surfFlags;
+ };
+
+ struct PhysCollmap;
+
+ struct XModel
+ {
+ char* name;
+ char numBones;
+ char numRootBones;
+ unsigned char numSurfaces;
+ char lodRampType;
+ float scale;
+ unsigned int noScalePartBits[6];
+ short* boneNames;
+ unsigned char* parentList;
+ XModelAngle* tagAngles;
+ XModelTagPos* tagPositions;
+ char* partClassification;
+ DObjAnimMat* animMatrix;
+ Material** materials;
+ XSurfaceLod lods[4];
+ char maxLoadedLod;
+ char numLods;
+ char collLod;
+ char flags;
+ XModelCollSurf_s* colSurf;
+ int numColSurfs;
+ int contents;
+ XBoneInfo* boneInfo;
+ float radius;
+ Bounds bounds;
+ int memUsage;
+ bool bad;
+ char pad[3];
+ PhysPreset* physPreset;
+ PhysCollmap* physCollmap;
+ }; // total size 304
+
+ enum weapFireType_t : int
+ {
+ WEAPON_FIRETYPE_FULLAUTO = 0x0,
+ WEAPON_FIRETYPE_SINGLESHOT = 0x1,
+ WEAPON_FIRETYPE_BURSTFIRE2 = 0x2,
+ WEAPON_FIRETYPE_BURSTFIRE3 = 0x3,
+ WEAPON_FIRETYPE_BURSTFIRE4 = 0x4,
+ WEAPON_FIRETYPE_DOUBLE_BARREL = 0x5,
+ WEAPON_FIRETYPE_MAX
+ };
+
+ enum weapInventoryType_t : int
+ {
+ WEAPINVENTORY_PRIMARY = 0,
+ WEAPINVENTORY_OFFHAND = 1,
+ WEAPINVENTORY_ITEM = 2,
+ WEAPINVENTORY_ALTMODE = 3,
+ WEAPINVENTORY_EXCLUSIVE = 4,
+ WEAPINVENTORY_SCAVENGER = 5,
+ WEAPINVENTORY_MAX
+ };
+
+ enum PenetrateType
+ {
+ PENETRATE_TYPE_NONE = 0x0,
+ PENETRATE_TYPE_SMALL = 0x1,
+ PENETRATE_TYPE_MEDIUM = 0x2,
+ PENETRATE_TYPE_LARGE = 0x3,
+ PENETRATE_TYPE_COUNT = 0x4
+ };
+
+ enum activeReticleType_t : int
+ {
+ VEH_ACTIVE_RETICLE_NONE = 0,
+ VEH_ACTIVE_RETICLE_PIP_ON_A_STICK = 1,
+ VEH_ACTIVE_RETICLE_BOUNCING_DIAMOND = 2,
+ VEH_ACTIVE_RETICLE_MAX
+ };
+
+ enum weapType_t : int
+ {
+ WEAPTYPE_BULLET = 0,
+ WEAPTYPE_GRENADE = 1,
+ WEAPTYPE_PROJECTILE = 2,
+ WEAPTYPE_RIOTSHIELD = 3,
+ WEAPTYPE_MAX
+ };
+
+ enum weapClass_t : int
+ {
+ WEAPCLASS_RIFLE = 0,
+ WEAPCLASS_SNIPER = 1,
+ WEAPCLASS_MG = 2,
+ WEAPCLASS_SMG = 3,
+ WEAPCLASS_SPREAD = 4,
+ WEAPCLASS_PISTOL = 5,
+ WEAPCLASS_GRENADE = 6,
+ WEAPCLASS_ROCKETLAUNCHER = 7,
+ WEAPCLASS_TURRET = 8,
+ WEAPCLASS_THROWINGKNIFE = 9,
+ WEAPCLASS_NON_PLAYER = 10,
+ WEAPCLASS_ITEM = 11,
+ WEAPCLASS_MAX
+ };
+
+ enum OffhandClass : int
+ {
+ OFFHAND_CLASS_NONE = 0,
+ OFFHAND_CLASS_FRAG_GRENADE = 1,
+ OFFHAND_CLASS_SMOKE_GRENADE = 2,
+ OFFHAND_CLASS_FLASH_GRENADE = 3,
+ OFFHAND_CLASS_MAX
+ };
+
+ enum playerAnimType_t : int
+ {
+ PLAER_ANIM_TYPE_NONE = 0x0,
+ PLAER_ANIM_TYPE_OTHER = 0x1,
+ PLAER_ANIM_TYPE_PISTOL = 0x2,
+ PLAER_ANIM_TYPE_SMG = 0x3,
+ PLAER_ANIM_TYPE_AUTORIFLE = 0x4,
+ PLAER_ANIM_TYPE_MG = 0x5,
+ PLAER_ANIM_TYPE_SNIPER = 0x6,
+ PLAER_ANIM_TYPE_ROCKETLAUNCHER = 0x7,
+ PLAER_ANIM_TYPE_EXPLOSIVE = 0x8,
+ PLAER_ANIM_TYPE_GRENADE = 0x9,
+ PLAER_ANIM_TYPE_TURRET = 0xA,
+ PLAER_ANIM_TYPE_C4 = 0xB,
+ PLAER_ANIM_TYPE_M203 = 0xC,
+ PLAER_ANIM_TYPE_HOLD = 0xD,
+ PLAER_ANIM_TYPE_BRIEFCASE = 0xE,
+ PLAER_ANIM_TYPE_RIOTSHIELD = 0xF,
+ PLAER_ANIM_TYPE_LAPTOP = 0x10,
+ PLAER_ANIM_TYPE_THROWINGKNIFE = 0x11
+ };
+
+ enum weapProjExplosion_t
+ {
+ WEAPPROJEXP_GRENADE = 0x0,
+ WEAPPROJEXP_ROCKET = 0x1,
+ WEAPPROJEXP_FLASHBANG = 0x2,
+ WEAPPROJEXP_NONE = 0x3,
+ WEAPPROJEXP_DUD = 0x4,
+ WEAPPROJEXP_SMOKE = 0x5,
+ WEAPPROJEXP_HEAVY = 0x6,
+ WEAPPROJEXP_NUM = 0x7
+ };
+
+ enum WeapStickinessType
+ {
+ WEAPSTICKINESS_NONE = 0x0,
+ WEAPSTICKINESS_ALL = 0x1,
+ WEAPSTICKINESS_ALL_ORIENT = 0x2,
+ WEAPSTICKINESS_GROUND = 0x3,
+ WEAPSTICKINESS_GROUND_WITH_YAW = 0x4,
+ WEAPSTICKINESS_KNIFE = 0x5,
+ WEAPSTICKINESS_COUNT = 0x6
+ };
+
+ enum weaponIconRatioType_t
+ {
+ WEAPON_ICON_RATIO_1TO1 = 0x0,
+ WEAPON_ICON_RATIO_2TO1 = 0x1,
+ WEAPON_ICON_RATIO_4TO1 = 0x2,
+ WEAPON_ICON_RATIO_COUNT = 0x3
+ };
+
+ enum ammoCounterClipType_t
+ {
+ AMMO_COUNTER_CLIP_NONE = 0x0,
+ AMMO_COUNTER_CLIP_MAGAZINE = 0x1,
+ AMMO_COUNTER_CLIP_SHORTMAGAZINE = 0x2,
+ AMMO_COUNTER_CLIP_SHOTGUN = 0x3,
+ AMMO_COUNTER_CLIP_ROCKET = 0x4,
+ AMMO_COUNTER_CLIP_BELTFED = 0x5,
+ AMMO_COUNTER_CLIP_ALTWEAPON = 0x6,
+ AMMO_COUNTER_CLIP_COUNT = 0x7
+ };
+
+ enum weapOverlayReticle_t
+ {
+ WEAPOVERLAYRETICLE_NONE = 0x0,
+ WEAPOVERLAYRETICLE_CROSSHAIR = 0x1,
+ WEAPOVERLAYRETICLE_NUM = 0x2
+ };
+
+ enum weapOverlayInterface_t
+ {
+ WEAPOVERLAYINTERFACE_NONE = 0x0,
+ WEAPOVERLAYINTERFACE_JAVELIN = 0x1,
+ WEAPOVERLAYINTERFACE_TURRETSCOPE = 0x2,
+ WEAPOVERLAYINTERFACECOUNT = 0x3
+ };
+
+ enum weapStance_t
+ {
+ WEAPSTANCE_STAND = 0x0,
+ WEAPSTANCE_DUCK = 0x1,
+ WEAPSTANCE_PRONE = 0x2,
+ WEAPSTANCE_NUM = 0x3
+ };
+
+ enum ImpactType
+ {
+ IMPACT_TYPE_NONE = 0,
+ IMPACT_TYPE_BULLET_SMALL = 1,
+ IMPACT_TYPE_BULLET_LARGE = 2,
+ IMPACT_TYPE_BULLET_AP = 3,
+ IMPACT_TYPE_SHOTGUN_FMJ = 4,
+ IMPACT_TYPE_SHOTGUN = 5,
+ IMPACT_TYPE_GRENADE_BOUNCE = 7,
+ IMPACT_TYPE_GRENADE_EXPLODE = 8,
+ IMPACT_TYPE_ROCKET_EXPLODE = 9,
+ IMPACT_TYPE_PROJECTILE_DUD = 10,
+ IMPACT_TYPE_MAX
+ };
+
+ enum guidedMissileType_t
+ {
+ MISSILE_GUIDANCE_NONE = 0x0,
+ MISSILE_GUIDANCE_SIDEWINDER = 0x1,
+ MISSILE_GUIDANCE_HELLFIRE = 0x2,
+ MISSILE_GUIDANCE_JAVELIN = 0x3,
+ MISSILE_GUIDANCE_MAX
+ };
+
+ // Check knots in FF later!
+#pragma pack(push, 4)
+ struct SndCurve
+ {
+ const char* filename;
+ const char* name;
+ unsigned __int16 knotCount;
+ vec2_t knots[16];
+ };
+#pragma pack(pop)
+
+ // Loaded sound
+#pragma pack(push, 4)
+ struct LoadedSoundStruct
+ {
+ int waveFormat;
+ int unknown1;
+ int dataLength;
+ int sampleRate;
+ int bitPerChannel;
+ int channelCount;
+ int unknown3;
+ int blockAlign;
+ int unknown5;
+ char* soundData;
+ };
+#pragma pack(pop)
+
+ struct LoadedSound
+ {
+ const char* name;
+ LoadedSoundStruct sound;
+ };
+
+ // Sounds
+ struct SpeakerLevels
+ {
+ int speaker;
+ int numLevels;
+ float levels[2];
+ };
+
+ struct ChannelMap
+ {
+ int entryCount; // how many entries are used
+ SpeakerLevels speakers[6];
+ };
+
+ struct SpeakerMap
+ {
+ bool isDefault;
+ char _pad[3];
+ const char* name;
+ ChannelMap channelMaps[2][2];
+ };
+
+ enum snd_alias_type_t : char
+ {
+ SAT_UNKNOWN = 0x0,
+ SAT_LOADED = 0x1,
+ SAT_STREAMED = 0x2,
+ SAT_PRIMED = 0x3,
+ SAT_COUNT = 0x4,
+ };
+
+ struct StreamFileNamePacked
+ {
+ unsigned __int64 offset;
+ unsigned __int64 length;
+ };
+
+ struct StreamFileNameRaw
+ {
+ const char* dir;
+ const char* name;
+ };
+
+ union StreamFileInfo
+ {
+ StreamFileNameRaw raw;
+ StreamFileNamePacked packed;
+ };
+
+ struct StreamFileName
+ {
+ unsigned __int16 isLocalized;
+ unsigned __int16 fileIndex;
+ StreamFileInfo info;
+ };
+
+ /*struct StreamedSound
+ {
+ StreamFileName filename;
+ unsigned int totalMsec;
+ };*/
+ struct StreamedSound
+ {
+ const char* dir;
+ const char* name;
+ };
+
+ struct PrimedSound
+ {
+ StreamFileName filename;
+ LoadedSound* loadedPart;
+ int dataOffset;
+ int totalSize;
+ unsigned int primedCrc;
+ };
+
+ union SoundData
+ {
+ LoadedSound* loadSnd; // SoundFile->type == SAT_LOADED
+ StreamedSound streamSnd; // SoundFile->type == SAT_STREAMED
+ //PrimedSound primedSnd; // SoundFile->type == SAT_PRIMED
+ };
+
+ struct SoundFile // 0x10
+ {
+ char type;
+ bool exists;
+ char _pad[2];
+ SoundData sound;
+ };
+#pragma pack(push, 4)
+ struct snd_alias_t
+ {
+ const char* aliasName;
+ const char* subtitle;
+ const char* secondaryAliasName;
+ const char* chainAliasName;
+ const char* mixerGroup;
+ SoundFile* soundFile;
+ int sequence;
+ float volMin;
+ float volMax;
+ float pitchMin;
+ float pitchMax;
+ float distMin;
+ float distMax;
+ int flags;
+ float slavePercentage;
+ float probability;
+ float lfePercentage;
+ float centerPercentage;
+ int startDelay;
+ int pad2;
+ SndCurve* volumeFalloffCurve;
+ float envelopMin;
+ float envelopMax;
+ float envelopPercentage;
+ SpeakerMap* speakerMap;
+ };
+#pragma pack(pop)
+ struct snd_alias_list_t
+ {
+ union
+ {
+ const char* aliasName;
+ const char* name;
+ };
+
+ snd_alias_t* head;
+ int count;
+ };
+
+ union snd_alias_list_name
+ {
+ const char* name;
+ snd_alias_list_t* asset;
+ };
+
+ // Tracers
+ struct TracerDef
+ {
+ const char* name;
+ Material* material;
+ unsigned int drawInterval;
+ float speed;
+ float beamLength;
+ float beamWidth;
+ float screwRadius;
+ float screwDist;
+ float colors[5][4];
+ };
+
+ struct WeaponDef
+ {
+ union
+ {
+ struct
+ {
+ const char* szOverlayName;
+ XModel** gunXModel;
+ XModel* handXModel;
+ const char** szXAnimsRightHanded;
+ const char** szXAnimsLeftHanded;
+ const char* szModeName;
+ unsigned __int16* notetrackSoundMapKeys;
+ unsigned __int16* notetrackSoundMapValues;
+ unsigned __int16* notetrackRumbleMapKeys;
+ unsigned __int16* notetrackRumbleMapValues;
+ int playerAnimType;
+ weapType_t weapType;
+ weapClass_t weapClass;
+ PenetrateType penetrateType;
+ weapInventoryType_t inventoryType;
+ weapFireType_t fireType;
+ OffhandClass offhandClass;
+ weapStance_t stance;
+ void* viewFlashEffect; // FxEffectDef
+ void* worldFlashEffect; // FxEffectDef
+ snd_alias_list_t* pickupSound;
+ snd_alias_list_t* pickupSoundPlayer;
+ snd_alias_list_t* ammoPickupSound;
+ snd_alias_list_t* ammoPickupSoundPlayer;
+ snd_alias_list_t* projectileSound;
+ snd_alias_list_t* pullbackSound;
+ snd_alias_list_t* pullbackSoundPlayer;
+ snd_alias_list_t* fireSound;
+ snd_alias_list_t* fireSoundPlayer;
+ snd_alias_list_t* fireSoundPlayerAkimbo;
+ snd_alias_list_t* fireLoopSound;
+ snd_alias_list_t* fireLoopSoundPlayer;
+ snd_alias_list_t* fireStopSound;
+ snd_alias_list_t* fireStopSoundPlayer;
+ snd_alias_list_t* fireLastSound;
+ snd_alias_list_t* fireLastSoundPlayer;
+ snd_alias_list_t* emptyFireSound;
+ snd_alias_list_t* emptyFireSoundPlayer;
+ snd_alias_list_t* meleeSwipeSound;
+ snd_alias_list_t* meleeSwipeSoundPlayer;
+ snd_alias_list_t* meleeHitSound;
+ snd_alias_list_t* meleeMissSound;
+ snd_alias_list_t* rechamberSound;
+ snd_alias_list_t* rechamberSoundPlayer;
+ snd_alias_list_t* reloadSound;
+ snd_alias_list_t* reloadSoundPlayer;
+ snd_alias_list_t* reloadEmptySound;
+ snd_alias_list_t* reloadEmptySoundPlayer;
+ snd_alias_list_t* reloadStartSound;
+ snd_alias_list_t* reloadStartSoundPlayer;
+ snd_alias_list_t* reloadEndSound;
+ snd_alias_list_t* reloadEndSoundPlayer;
+ snd_alias_list_t* detonateSound;
+ snd_alias_list_t* detonateSoundPlayer;
+ snd_alias_list_t* nightVisionWearSound;
+ snd_alias_list_t* nightVisionWearSoundPlayer;
+ snd_alias_list_t* nightVisionRemoveSound;
+ snd_alias_list_t* nightVisionRemoveSoundPlayer;
+ snd_alias_list_t* altSwitchSound;
+ snd_alias_list_t* altSwitchSoundPlayer;
+ snd_alias_list_t* raiseSound;
+ snd_alias_list_t* raiseSoundPlayer;
+ snd_alias_list_t* firstRaiseSound;
+ snd_alias_list_t* firstRaiseSoundPlayer;
+ snd_alias_list_t* putawaySound;
+ snd_alias_list_t* putawaySoundPlayer;
+ snd_alias_list_t* scanSound;
+ };
+
+ char _portpad0[268];
+ };
+
+ snd_alias_list_t** bounceSound;
+
+ union
+ {
+ struct
+ {
+ void* viewShellEjectEffect;
+ void* worldShellEjectEffect;
+ void* viewLastShotEjectEffect;
+ void* worldLastShotEjectEffect;
+ Material* reticleCenter;
+ Material* reticleSide;
+ int iReticleCenterSize;
+ int iReticleSideSize;
+ int iReticleMinOfs;
+ activeReticleType_t activeReticleType;
+ float vStandMove[3];
+ float vStandRot[3];
+ float strafeMove[3];
+ float strafeRot[3];
+ float vDuckedOfs[3];
+ float vDuckedMove[3];
+ float vDuckedRot[3];
+ float vProneOfs[3];
+ float vProneMove[3];
+ float vProneRot[3];
+ float fPosMoveRate;
+ float fPosProneMoveRate;
+ float fStandMoveMinSpeed;
+ float fDuckedMoveMinSpeed;
+ float fProneMoveMinSpeed;
+ float fPosRotRate;
+ float fPosProneRotRate;
+ float fStandRotMinSpeed;
+ float fDuckedRotMinSpeed;
+ float fProneRotMinSpeed;
+ XModel** worldModel;
+ XModel* worldClipModel;
+ XModel* rocketModel;
+ XModel* knifeModel;
+ XModel* worldKnifeModel;
+ Material* hudIcon;
+ weaponIconRatioType_t hudIconRatio;
+ Material* pickupIcon;
+ weaponIconRatioType_t pickupIconRatio;
+ Material* ammoCounterIcon;
+ weaponIconRatioType_t ammoCounterIconRatio;
+ ammoCounterClipType_t ammoCounterClip;
+ int iStartAmmo;
+ const char* szAmmoName;
+ int iAmmoIndex;
+ const char* szClipName;
+ int iClipIndex;
+ int iMaxAmmo;
+ int shotCount;
+ const char* szSharedAmmoCapName;
+ int iSharedAmmoCapIndex;
+ int iSharedAmmoCap;
+ int damage;
+ int playerDamage;
+ int iMeleeDamage;
+ int iDamageType;
+ int iFireDelay;
+ int iMeleeDelay;
+ int meleeChargeDelay;
+ int iDetonateDelay;
+ int iRechamberTime;
+ int rechamberTimeOneHanded;
+ int iRechamberBoltTime;
+ int iHoldFireTime;
+ int iDetonateTime;
+ int iMeleeTime;
+ int meleeChargeTime;
+ int iReloadTime;
+ int reloadShowRocketTime;
+ int iReloadEmptyTime;
+ int iReloadAddTime;
+ int iReloadStartTime;
+ int iReloadStartAddTime;
+ int iReloadEndTime;
+ int iDropTime;
+ int iRaiseTime;
+ int iAltDropTime;
+ int quickDropTime;
+ int quickRaiseTime;
+ int iBreachRaiseTime;
+ int iEmptyRaiseTime;
+ int iEmptyDropTime;
+ int sprintInTime;
+ int sprintLoopTime;
+ int sprintOutTime;
+ int stunnedTimeBegin;
+ int stunnedTimeLoop;
+ int stunnedTimeEnd;
+ int nightVisionWearTime;
+ int nightVisionWearTimeFadeOutEnd;
+ int nightVisionWearTimePowerUp;
+ int nightVisionRemoveTime;
+ int nightVisionRemoveTimePowerDown;
+ int nightVisionRemoveTimeFadeInStart;
+ int fuseTime;
+ int aiFuseTime;
+ };
+
+ char _portpad1[464];
+ };
+
+ union
+ {
+ struct
+ {
+ float autoAimRange;
+ float aimAssistRange;
+ float aimAssistRangeAds;
+ float aimPadding;
+ float enemyCrosshairRange;
+ float moveSpeedScale;
+ float adsMoveSpeedScale;
+ float sprintDurationScale;
+ float fAdsZoomInFrac;
+ float fAdsZoomOutFrac;
+ Material* overlayMaterial;
+ Material* overlayMaterialLowRes;
+ Material* overlayMaterialEMP;
+ Material* overlayMaterialEMPLowRes;
+ weapOverlayReticle_t overlayReticle;
+ int overlayInterface;
+ float overlayWidth;
+ float overlayHeight;
+ float overlayWidthSplitscreen;
+ float overlayHeightSplitscreen;
+ float fAdsBobFactor;
+ float fAdsViewBobMult;
+ float fHipSpreadStandMin;
+ float fHipSpreadDuckedMin;
+ float fHipSpreadProneMin;
+ float hipSpreadStandMax;
+ float hipSpreadDuckedMax;
+ float hipSpreadProneMax;
+ float fHipSpreadDecayRate;
+ float fHipSpreadFireAdd;
+ float fHipSpreadTurnAdd;
+ float fHipSpreadMoveAdd;
+ float fHipSpreadDuckedDecay;
+ float fHipSpreadProneDecay;
+ float fHipReticleSidePos;
+ float fAdsIdleAmount;
+ float fHipIdleAmount;
+ };
+
+ char _portpad6[148];
+ };
+
+ union
+ {
+ struct
+ {
+ float adsIdleSpeed;
+ float hipIdleSpeed;
+ float fIdleCrouchFactor;
+ float fIdleProneFactor;
+ float fGunMaxPitch;
+ float fGunMaxYaw;
+ float swayMaxAngle;
+ float swayLerpSpeed;
+ float swayPitchScale;
+ float swayYawScale;
+ float swayHorizScale;
+ float swayVertScale;
+ float swayShellShockScale;
+ float adsSwayMaxAngle;
+ float adsSwayLerpSpeed;
+ float adsSwayPitchScale;
+ float adsSwayYawScale;
+ float adsSwayHorizScale;
+ float adsSwayVertScale;
+ float adsViewErrorMin;
+ float adsViewErrorMax;
+ };
+
+ char _portpad2[84];
+ };
+
+ union
+ {
+ struct
+ {
+ PhysCollmap* physCollmap;
+ float dualWieldViewModelOffset;
+ weaponIconRatioType_t killIconRatio;
+ int iReloadAmmoAdd;
+ int iReloadStartAdd;
+ int ammoDropStockMin;
+ int ammoDropClipPercentMin;
+ int ammoDropClipPercentMax;
+ int iExplosionRadius;
+ int iExplosionRadiusMin;
+ int iExplosionInnerDamage;
+ int iExplosionOuterDamage;
+ float damageConeAngle;
+ float bulletExplDmgMult;
+ float bulletExplRadiusMult;
+ int iProjectileSpeed;
+ int iProjectileSpeedUp;
+ int iProjectileSpeedForward;
+ int iProjectileActivateDist;
+ float projLifetime;
+ float timeToAccelerate;
+ float projectileCurvature;
+ XModel* projectileModel;
+ int projExplosion;
+ void* projExplosionEffect;
+ void* projDudEffect;
+ snd_alias_list_t* projExplosionSound;
+ snd_alias_list_t* projDudSound;
+ WeapStickinessType stickiness;
+ float lowAmmoWarningThreshold;
+ float ricochetChance;
+ float* parallelBounce;
+ float* perpendicularBounce;
+ };
+
+ char _portpad3[132];
+ };
+
+ union
+ {
+ struct
+ {
+ void* projTrailEffect;
+ void* projBeaconEffect;
+ float vProjectileColor[3];
+ guidedMissileType_t guidedMissileType;
+ float maxSteeringAccel;
+ int projIgnitionDelay;
+ void* projIgnitionEffect;
+ snd_alias_list_t* projIgnitionSound;
+ float fAdsAimPitch;
+ float fAdsCrosshairInFrac;
+ float fAdsCrosshairOutFrac;
+ int adsGunKickReducedKickBullets;
+ float adsGunKickReducedKickPercent;
+ float fAdsGunKickPitchMin;
+ float fAdsGunKickPitchMax;
+ float fAdsGunKickYawMin;
+ float fAdsGunKickYawMax;
+ float fAdsGunKickAccel;
+ float fAdsGunKickSpeedMax;
+ float fAdsGunKickSpeedDecay;
+ float fAdsGunKickStaticDecay;
+ float fAdsViewKickPitchMin;
+ float fAdsViewKickPitchMax;
+ float fAdsViewKickYawMin;
+ float fAdsViewKickYawMax;
+ float fAdsViewScatterMin;
+ float fAdsViewScatterMax;
+ float fAdsSpread;
+ int hipGunKickReducedKickBullets;
+ float hipGunKickReducedKickPercent;
+ float fHipGunKickPitchMin;
+ float fHipGunKickPitchMax;
+ float fHipGunKickYawMin;
+ float fHipGunKickYawMax;
+ float fHipGunKickAccel;
+ float fHipGunKickSpeedMax;
+ float fHipGunKickSpeedDecay;
+ float fHipGunKickStaticDecay;
+ float fHipViewKickPitchMin;
+ float fHipViewKickPitchMax;
+ float fHipViewKickYawMin;
+ float fHipViewKickYawMax;
+ float fHipViewScatterMin;
+ float fHipViewScatterMax;
+ float fightDist;
+ float maxDist;
+ const char* accuracyGraphName[2];
+ float (*originalAccuracyGraphKnots[2])[2];
+ unsigned __int16 originalAccuracyGraphKnotCount[2];
+ int iPositionReloadTransTime;
+ float leftArc;
+ float rightArc;
+ float topArc;
+ float bottomArc;
+ float accuracy;
+ float aiSpread;
+ float playerSpread;
+ float minTurnSpeed[2];
+ float maxTurnSpeed[2];
+ float pitchConvergenceTime;
+ float yawConvergenceTime;
+ float suppressTime;
+ float maxRange;
+ float fAnimHorRotateInc;
+ float fPlayerPositionDist;
+ const char* szUseHintString;
+ const char* dropHintString;
+ int iUseHintStringIndex;
+ int dropHintStringIndex;
+ float horizViewJitter;
+ float vertViewJitter;
+ float scanSpeed;
+ float scanAccel;
+ int scanPauseTime;
+ const char* szScript;
+ float fOOPosAnimLength[2];
+ int minDamage;
+ int minPlayerDamage;
+ float fMaxDamageRange;
+ float fMinDamageRange;
+ float destabilizationRateTime;
+ float destabilizationCurvatureMax;
+ int destabilizeDistance;
+ float* locationDamageMultipliers;
+ const char* fireRumble;
+ const char* meleeImpactRumble;
+ TracerDef* tracerType;
+ float turretScopeZoomRate;
+ float turretScopeZoomMin;
+ float turretScopeZoomMax;
+ float turretOverheatUpRate;
+ float turretOverheatDownRate;
+ float turretOverheatPenalty;
+ };
+
+ char _portpad4[400];
+ };
+
+ union
+ {
+ struct
+ {
+ snd_alias_list_t* turretOverheatSound;
+ void* turretOverheatEffect;
+ const char* turretBarrelSpinRumble;
+ float turretBarrelSpinSpeed;
+ float turretBarrelSpinUpTime;
+ float turretBarrelSpinDownTime;
+ snd_alias_list_t* turretBarrelSpinMaxSnd;
+ snd_alias_list_t* turretBarrelSpinUpSnd[4];
+ snd_alias_list_t* turretBarrelSpinDownSnd[4];
+ snd_alias_list_t* missileConeSoundAlias;
+ snd_alias_list_t* missileConeSoundAliasAtBase;
+ float missileConeSoundRadiusAtTop;
+ float missileConeSoundRadiusAtBase;
+ float missileConeSoundHeight;
+ float missileConeSoundOriginOffset;
+ float missileConeSoundVolumescaleAtCore;
+ float missileConeSoundVolumescaleAtEdge;
+ float missileConeSoundVolumescaleCoreSize;
+ float missileConeSoundPitchAtTop;
+ float missileConeSoundPitchAtBottom;
+ float missileConeSoundPitchTopSize;
+ float missileConeSoundPitchBottomSize;
+ float missileConeSoundCrossfadeTopSize;
+ float missileConeSoundCrossfadeBottomSize;
+ bool sharedAmmo;
+ bool lockonSupported;
+ bool requireLockonToFire;
+ bool bigExplosion;
+ bool noAdsWhenMagEmpty;
+ bool avoidDropCleanup;
+ bool inheritsPerks;
+ bool crosshairColorChange;
+ bool bRifleBullet;
+ bool armorPiercing;
+ bool bBoltAction;
+ bool aimDownSight;
+ bool bRechamberWhileAds;
+ bool bBulletExplosiveDamage;
+ bool bCookOffHold;
+ bool bClipOnly;
+ bool noAmmoPickup;
+ bool adsFireOnly;
+ bool cancelAutoHolsterWhenEmpty;
+ bool disableSwitchToWhenEmpty;
+ bool suppressAmmoReserveDisplay;
+ bool laserSightDuringNightvision;
+ bool markableViewmodel;
+ bool noDualWield;
+ bool flipKillIcon;
+ bool bNoPartialReload;
+ bool bSegmentedReload;
+ bool blocksProne;
+ bool silenced;
+ bool isRollingGrenade;
+ bool projExplosionEffectForceNormalUp;
+ bool bProjImpactExplode;
+ bool stickToPlayers;
+ bool hasDetonator;
+ bool disableFiring;
+ bool timedDetonation;
+ bool rotate;
+ bool holdButtonToThrow;
+ bool freezeMovementWhenFiring;
+ bool thermalScope;
+ bool altModeSameWeapon;
+ bool turretBarrelSpinEnabled;
+ bool missileConeSoundEnabled;
+ bool missileConeSoundPitchshiftEnabled;
+ bool missileConeSoundCrossfadeEnabled;
+ bool offhandHoldIsCancelable;
+
+ void test()
+ {
+ sizeof(*this);
+ }
+ };
+
+ char _portpad5[168];
+ };
+ };
+
+ struct WeaponCompleteDef
+ {
+ union
+ {
+ struct
+ {
+ const char* szInternalName;
+ WeaponDef* weapDef;
+ const char* szDisplayName;
+ unsigned __int16* hideTags;
+ };
+
+ char _portpad0[16];
+ };
+
+ const char** szXAnims;
+
+ union
+ {
+ struct
+ {
+ float fAdsZoomFov;
+ int iAdsTransInTime;
+ int iAdsTransOutTime;
+ int iClipSize;
+ ImpactType impactType;
+ int iFireTime;
+ };
+
+ char _portpad1[24];
+ };
+
+ union
+ {
+ struct
+ {
+ weaponIconRatioType_t dpadIconRatio;
+ float penetrateMultiplier;
+ float fAdsViewKickCenterSpeed;
+ float fHipViewKickCenterSpeed;
+ const char* szAltWeaponName;
+ unsigned int altWeaponIndex;
+ int iAltRaiseTime;
+ };
+
+ char _portpad2[28];
+ };
+
+ union
+ {
+ struct
+ {
+ Material* killIcon;
+ Material* dpadIcon;
+ int fireAnimLength;
+ int iFirstRaiseTime;
+ };
+
+ char _portpad3[16];
+ };
+
+ union
+ {
+ struct
+ {
+ int ammoDropStockMax;
+ float adsDofStart;
+ float adsDofEnd;
+ unsigned __int16 accuracyGraphKnotCount[2];
+ float (*accuracyGraphKnots[2])[2];
+ bool motionTracker;
+ bool enhanced;
+ bool dpadIconShowsAmmo;
+ };
+
+ char _portpad4[28];
+ };
+ };
+
+ struct Glyph
+ {
+ unsigned __int16 letter;
+ char x0;
+ char y0;
+ char dx;
+ char pixelWidth;
+ char pixelHeight;
+ float s0;
+ float t0;
+ float s1;
+ float t1;
+ };
+
+#pragma pack(push, 4)
+ struct cplane_s
+ {
+ float normal[3];
+ float dist;
+ char type;
+ char signbits;
+ };
+#pragma pack(pop)
+
+ /* 1003 */
+ struct Font_s
+ {
+ const char* fontName;
+ int pixelHeight;
+ int glyphCount;
+ Material* material;
+ Material* glowMaterial;
+ Glyph* glyphs;
+ };
+
+ struct cbrushside_t
+ {
+ cplane_s* plane;
+ unsigned int materialNum;
+ /*unsigned __int16 materialNum;
+ char firstAdjacentSideOffset;
+ char edgeCount;*/
+ };
+
+ // ClipMap
+ typedef char cbrushedge_t;
+
+ struct cbrush_t
+ {
+ unsigned __int16 numsides;
+ unsigned __int16 glassPieceIndex;
+ cbrushside_t* sides;
+ cbrushedge_t* edge;
+ __int16 axialMaterialNum[2][3];
+ char firstAdjacentSideOffsets[2][3];
+ char edgeCount[2][3];
+ };
+
+ struct BrushWrapper
+ {
+ float mins[3];
+ float maxs[3];
+ unsigned int numPlaneSide;
+ cbrushside_t* side;
+ char* edge;
+ __int16 axialMaterialNum[2][3];
+ __int16 firstAdjacentSideOffsets[2][3];
+ int numEdge;
+ cplane_s* plane;
+ };
+
+ //struct BrushWrapper
+ //{
+ // Bounds bounds; // 24
+ // cbrush_t brush; // 36
+ // cbrushside_t *side; // 4
+ // int totalEdgeCount; // 4
+ // cplane_s *plane; // 4
+ // short numPlaneSide; // 2
+ // char *edge; // 4
+ // int numEdge; // 4
+ //}; // 82 bytes total
+
+ struct PhysGeomInfo
+ {
+ BrushWrapper* brush;
+ int type;
+ float orientation[3][3];
+ Bounds bounds;
+ };
+
+ struct PhysMass
+ {
+ float centerOfMass[3];
+ float momentsOfInertia[3];
+ float productsOfInertia[3];
+ // int contents;
+ };
+
+ struct PhysCollmap
+ {
+ const char* name;
+ unsigned int numInfo;
+ PhysGeomInfo* info;
+ PhysMass mass;
+ Bounds bounds;
+ };
+
+ struct G_GlassName
+ {
+ char* nameStr;
+ unsigned __int16 name;
+ unsigned __int16 pieceCount;
+ unsigned __int16* pieceIndices;
+ };
+
+#pragma pack(push, 2)
+ struct G_GlassPiece
+ {
+ unsigned __int16 damageTaken;
+ unsigned __int16 collapseTime;
+ int lastStateChangeTime;
+ char impactDir;
+ char impactPos[2];
+ };
+#pragma pack(pop)
+
+ struct G_GlassData
+ {
+ G_GlassPiece* glassPieces;
+ unsigned int pieceCount;
+ unsigned __int16 damageToWeaken;
+ unsigned __int16 damageToDestroy;
+ unsigned int glassNameCount;
+ G_GlassName* glassNames;
+ char pad[108];
+ };
+
+ struct GameWorldMp
+ {
+ const char* name;
+ G_GlassData* g_glassData;
+ };
+
+ struct GameWorldSp
+ {
+ const char* name;
+ char useless_sp_shit[48];
+ G_GlassData* g_glassData;
+ };
+
+ // FxWorld
+#pragma pack(push, 4)
+
+ struct FxGlassDef
+ {
+ float halfThickness;
+ float texVecs[2][2];
+ GfxColor color;
+ Material* material;
+ Material* materialShattered;
+ PhysPreset* physPreset;
+ };
+
+ struct FxSpatialFrame
+ {
+ float quat[4];
+ float origin[3];
+ };
+
+ union FxGlassPiecePlace
+ {
+ struct
+ {
+ FxSpatialFrame frame;
+ float radius;
+ };
+
+ unsigned int nextFree;
+ };
+
+ struct FxGlassPieceState
+ {
+ float texCoordOrigin[2];
+ unsigned int supportMask;
+ unsigned __int16 initIndex;
+ unsigned __int16 geoDataStart;
+ unsigned __int16 lightingIndex;
+ char defIndex;
+ char pad[3];
+ char vertCount;
+ char holeDataCount;
+ char crackDataCount;
+ char fanDataCount;
+ unsigned __int16 flags;
+ float areaX2;
+ };
+
+ struct FxGlassPieceDynamics
+ {
+ int fallTime;
+ __int32 physObjId;
+ __int32 physJointId;
+ float vel[3];
+ float avel[3];
+ };
+
+ struct FxGlassVertex
+ {
+ __int16 x;
+ __int16 y;
+ };
+
+ struct FxGlassHoleHeader
+ {
+ unsigned __int16 uniqueVertCount;
+ char touchVert;
+ char pad[1];
+ };
+
+ struct FxGlassCrackHeader
+ {
+ unsigned __int16 uniqueVertCount;
+ char beginVertIndex;
+ char endVertIndex;
+ };
+
+ union FxGlassGeometryData
+ {
+ FxGlassVertex vert;
+ FxGlassHoleHeader hole;
+ FxGlassCrackHeader crack;
+ char asBytes[4];
+ __int16 anonymous[2];
+ };
+
+ struct FxGlassInitPieceState //Note, on MW3 this is missing 4 bytes, just not sure whats missing yet
+ {
+ FxSpatialFrame frame;
+ float radius;
+ float texCoordOrigin[2];
+ unsigned int supportMask;
+ //float areaX2; // Commented out a random thing so the size fits. Most probably wrong since it was random.
+ unsigned __int16 lightingIndex;
+ char defIndex;
+ char vertCount;
+ char fanDataCount;
+ char pad[1];
+ };
+
+ struct FxGlassSystem
+ {
+ int time; // 4
+ int prevTime; // 4
+ unsigned int defCount; // 4
+ unsigned int pieceLimit; // 4
+ unsigned int pieceWordCount; // 4
+ unsigned int initPieceCount; // 4
+ unsigned int cellCount; // 4
+ unsigned int activePieceCount; // 4
+ unsigned int firstFreePiece; // 4
+ unsigned int geoDataLimit; // 4
+ unsigned int geoDataCount; // 4
+ unsigned int initGeoDataCount; // 4
+ FxGlassDef* defs; // 4
+ FxGlassPiecePlace* piecePlaces; // 4
+ FxGlassPieceState* pieceStates; // 4
+ FxGlassPieceDynamics* pieceDynamics; // 4
+ FxGlassGeometryData* geoData; // 4
+ unsigned int* isInUse; // 4
+ unsigned int* cellBits; // 4
+ char* visData; // 4
+ VecInternal<3>* linkOrg;
+ float* halfThickness; // 4
+ unsigned __int16* lightingHandles; // 4
+ FxGlassInitPieceState* initPieceStates; // 4
+ FxGlassGeometryData* initGeoData; // 4
+ bool needToCompactData; // 1
+ char initCount;
+ short pad;
+ float effectChanceAccum; // 4
+ int lastPieceDeletionTime; // 4
+ };
+
+ struct FxWorld
+ {
+ char* name;
+ FxGlassSystem glassSys;
+ };
+#pragma pack(pop)
+
+ // MapEnts
+ struct TriggerModel
+ {
+ int contents;
+ unsigned short hullCount;
+ unsigned short firstHull;
+ };
+
+ struct TriggerHull
+ {
+ Bounds bounds;
+ int contents;
+ unsigned short slabCount;
+ unsigned short firstSlab;
+ };
+
+ struct TriggerSlab
+ {
+ vec3_t dir;
+ float midPoint;
+ float halfSize;
+ };
+
+ struct MapTriggers
+ {
+ int modelCount;
+ TriggerModel* models; // sizeof 8
+ int hullCount;
+ TriggerHull* hulls; // sizeof 32
+ int slabCount;
+ TriggerSlab* slabs; // sizeof 20
+ };
+#pragma pack(push, 1)
+ struct Stage
+ {
+ char* stageName;
+ float offset[3];
+ int flags;
+ };
+
+ struct MapEnts
+ {
+ const char* name; // 0
+ const char* entityString; // 4
+ int numEntityChars; // 8
+ MapTriggers trigger; // 12
+ Stage* stageNames; // 36
+ char stageCount; // 40
+ char pad[3];
+ };
+#pragma pack(pop)
+
+#pragma pack(push, 1)
+ struct ComPrimaryLight
+ {
+ union
+ {
+ char _portpad0[28];
+
+ struct
+ {
+ char type;
+ char canUseShadowMap;
+ char exponent;
+ char unused;
+ float color[3];
+ float dir[3];
+ };
+ };
+
+ union
+ {
+ char _portpad1[40];
+
+ struct
+ {
+ float origin[3];
+ float radius;
+ float cosHalfFovOuter;
+ float cosHalfFovInner;
+ float cosHalfFovExpanded;
+ float rotationLimit;
+ float translationLimit;
+ const char* defName;
+ };
+ };
+ };
+#pragma pack(pop)
+
+ struct ComWorld
+ {
+ const char* name;
+ int isInUse;
+ unsigned int primaryLightCount;
+ ComPrimaryLight* primaryLights;
+ };
+
+
+ union XAnimIndices
+ {
+ char* _1;
+ unsigned __int16* _2;
+ void* data;
+ };
+
+ union XAnimDynamicFrames
+ {
+ char (*_1)[3];
+ unsigned __int16 (*_2)[3];
+ };
+
+ union XAnimDynamicIndices
+ {
+ char _1[1];
+ unsigned __int16 _2[1];
+ };
+
+ struct XAnimPartTransFrames
+ {
+ float mins[3];
+ float size[3];
+ XAnimDynamicFrames frames;
+ XAnimDynamicIndices indices;
+ };
+
+ union XAnimPartTransData
+ {
+ XAnimPartTransFrames frames;
+ float frame0[3];
+ };
+
+ struct XAnimPartTrans
+ {
+ unsigned __int16 size;
+ char smallTrans;
+ __declspec(align(2)) XAnimPartTransData u;
+ };
+
+ struct XAnimDeltaPartQuatDataFrames2
+ {
+ __int16* frames;
+ char indices[1];
+ };
+
+ union XAnimDeltaPartQuatData2
+ {
+ XAnimDeltaPartQuatDataFrames2 frames;
+ __int16 frame0[2];
+ };
+
+ struct XAnimDeltaPartQuat2
+ {
+ unsigned __int16 size;
+ XAnimDeltaPartQuatData2 u;
+ };
+
+ struct XAnimDeltaPartQuatDataFrames
+ {
+ __int16 (*frames)[2];
+ XAnimDynamicIndices indices;
+ };
+
+ union XAnimDeltaPartQuatData
+ {
+ XAnimDeltaPartQuatDataFrames frames;
+ __int16 frame0[2];
+ };
+
+ struct XAnimDeltaPartQuat
+ {
+ unsigned __int16 size;
+ __declspec(align(4)) XAnimDeltaPartQuatData u;
+ };
+
+ struct XAnimDeltaPart
+ {
+ XAnimPartTrans* trans;
+ XAnimDeltaPartQuat2* quat2;
+ XAnimDeltaPartQuat* quat;
+ };
+
+#pragma pack(push, 4)
+ struct XAnimNotifyInfo
+ {
+ short name;
+ float time;
+ };
+
+ struct XAnimParts
+ {
+ char* name; // 0
+ unsigned short dataByteCount; // 4
+ unsigned short dataShortCount; // 6
+ unsigned short dataIntCount; // 8
+ unsigned short randomDataByteCount; // 10 - 0xA
+ unsigned short randomDataIntCount; // 12 - 0xC
+ unsigned short framecount; // 14 - 0xE
+ char flags; // 16
+ unsigned char boneCount[10]; // 17
+ char notetrackCount; // 27
+ bool bLoop; // 28
+ bool bDelta; // 29
+ char assetType; // 30
+ char ikType; // 31
+ unsigned int randomDataShortCount; // 32 - 0x20
+ unsigned int indexcount; // 36 - 0x24
+ float framerate; // 40 - 0x28
+ float frequency; // 44 - 0x2C
+ unsigned short* tagnames; // 48 - 0x30
+ char* dataByte; // 52 - 0x34
+ short* dataShort; // 56 - 0x38
+ int* dataInt; // 60 - 0x3C
+ short* randomDataShort; // 64 - 0x40
+ char* randomDataByte; // 68 - 0x44
+ int* randomDataInt; // 72 - 0x48
+ XAnimIndices indices; // 76 - 0x4C
+ XAnimNotifyInfo* notetracks; // 80 - 0x50
+ XAnimDeltaPart* delta; // 84 - 0x54
+ };
+#pragma pack(pop)
+
+ // Localized Strings
+ struct LocalizeEntry
+ {
+ const char* localizedString;
+ const char* name;
+ };
+
+ // Stringtables
+ struct StringTableCell
+ {
+ char* string; // 0
+ int hash; // 4
+ };
+
+ struct StringTable
+ {
+ const char* name; // 0
+ int columns; // 4
+ int rows; // 8
+ StringTableCell* strings; // 12
+ };
+
+ // Fx
+ struct FxEffectDef;
+
+ /* struct FxElemMarkVisuals
+ {
+ Material *materials[2];
+ };*/
+ struct FxImpactEntry
+ {
+ FxEffectDef* nonflesh[31];
+ FxEffectDef* flesh[4];
+ };
+
+ union FxEffectDefRef
+ {
+ FxEffectDef* handle;
+ const char* name;
+ };
+
+ union FxElemVisuals
+ {
+ const void* anonymous;
+ Material* material;
+ XModel* xmodel;
+ FxEffectDefRef* effectDef;
+ const char* soundName;
+ };
+
+ typedef Material* FxElemMarkVisuals[2];
+
+ union FxElemDefVisuals
+ {
+ FxElemVisuals instance;
+ FxElemVisuals* array;
+ FxElemMarkVisuals* markArray;
+ };
+
+ struct FxTrailVertex
+ {
+ float pos[2];
+ float normal[2];
+ float texCoord;
+ };
+
+ struct FxTrailDef
+ {
+ int scrollTimeMsec;
+ int repeatDist;
+ float invSplitDist;
+ float invSplitArcDist;
+ float invSplitTime;
+ int vertCount;
+ FxTrailVertex* verts;
+ int indCount;
+ unsigned __int16* inds;
+ };
+
+ struct FxSparkFountainDef
+ {
+ float gravity;
+ float bounceFrac;
+ float bounceRand;
+ float sparkSpacing;
+ float sparkLength;
+ int sparkCount;
+ float loopTime;
+ float velMin;
+ float velMax;
+ float velConeFrac;
+ float restSpeed;
+ float boostTime;
+ float boostFactor;
+ };
+
+ union FxElemExtendedDefPtr
+ {
+ FxTrailDef* trailDef;
+ FxSparkFountainDef* sparkFountain;
+ char* unknownDef;
+ };
+
+ struct FxSpawnDefLooping
+ {
+ int intervalMsec;
+ int count;
+ };
+
+ struct FxIntRange
+ {
+ int base;
+ int amplitude;
+ };
+
+ struct FxFloatRange
+ {
+ float base;
+ float amplitude;
+ };
+
+ struct FxSpawnDefOneShot
+ {
+ FxIntRange count;
+ };
+
+ union FxSpawnDef
+ {
+ FxSpawnDefLooping looping;
+ FxSpawnDefOneShot oneShot;
+ };
+
+ struct FxElemAtlas
+ {
+ char behavior;
+ char index;
+ char fps;
+ char loopCount;
+ char colIndexBits;
+ char rowIndexBits;
+ __int16 entryCount;
+ };
+
+ struct FxElemVec3Range
+ {
+ float base[3];
+ float amplitude[3];
+ };
+
+ struct FxElemVelStateInFrame
+ {
+ FxElemVec3Range velocity;
+ FxElemVec3Range totalDelta;
+ };
+
+ const struct FxElemVelStateSample
+ {
+ FxElemVelStateInFrame local;
+ FxElemVelStateInFrame world;
+ };
+
+ struct FxElemVisualState
+ {
+ char color[4];
+ float rotationDelta;
+ float rotationTotal;
+ float size[2];
+ float scale;
+ };
+
+ const struct FxElemVisStateSample
+ {
+ FxElemVisualState base;
+ FxElemVisualState amplitude;
+ };
+
+ struct FxElemDef
+ {
+ int flags;
+ FxSpawnDef spawn;
+ FxFloatRange spawnRange;
+ FxFloatRange fadeInRange;
+ FxFloatRange fadeOutRange;
+ float spawnFrustumCullRadius;
+ FxIntRange spawnDelayMsec;
+ FxIntRange lifeSpanMsec;
+ FxFloatRange spawnOrigin[3];
+ FxFloatRange spawnOffsetRadius;
+ FxFloatRange spawnOffsetHeight;
+ FxFloatRange spawnAngles[3];
+ FxFloatRange angularVelocity[3];
+ FxFloatRange initialRotation;
+ FxFloatRange gravity;
+ FxFloatRange reflectionFactor;
+ FxElemAtlas atlas;
+ char elemType;
+ char visualCount;
+ char velIntervalCount;
+ char visStateIntervalCount;
+ FxElemVelStateSample* velSamples;
+ FxElemVisStateSample* visSamples;
+ FxElemDefVisuals visuals;
+ Bounds collBounds;
+ FxEffectDefRef* effectOnImpact;
+ FxEffectDefRef* effectOnDeath;
+ FxEffectDefRef* effectEmitted;
+ FxFloatRange emitDist;
+ FxFloatRange emitDistVariance;
+ FxElemExtendedDefPtr extended;
+ char sortOrder;
+ char lightingFrac;
+ char useItemClip;
+ char fadeInfo;
+ };
+
+ struct FxEffectDef
+ {
+ const char* name;
+ int flags;
+ int totalSize;
+ int msecLoopingLife;
+ int elemDefCountLooping;
+ int elemDefCountOneShot;
+ int elemDefCountEmission;
+ FxElemDef* elemDefs;
+ };
+
+ // GfxWorld
+#pragma pack(push, 4)
+ struct GfxLightImage
+ {
+ GfxImage* image;
+ char samplerState;
+ };
+#pragma pack(pop)
+
+ struct GfxLightDef
+ {
+ const char* name;
+ GfxLightImage attenuation;
+ int lmapLookupStart;
+ };
+
+ struct GfxSky
+ {
+ int skySurfCount;
+ std::uint32_t* skyStartSurfs;
+ GfxImage* skyImage;
+ char skySamplerState;
+ char pad[3];
+ };
+
+ struct GfxWorldDpvsPlanes
+ {
+ int cellCount;
+ cplane_s* planes;
+ unsigned __int16* nodes;
+ unsigned char* sceneEntCellBits; //Size = cellCount << 11
+ };
+
+ struct GfxAabbTree
+ {
+ union
+ {
+ Bounds bounds;
+
+ struct
+ {
+ float mins[3]; // 12
+ float maxs[3]; // 12
+ };
+ };
+
+ int unkn;
+ unsigned __int16 childCount; // 2
+ unsigned __int16 surfaceCount; // 2
+ unsigned __int16 startSurfIndex; // 2
+ unsigned __int16 smodelIndexCount; // 2
+ unsigned __int16* smodelIndexes; // 4
+ int childrenOffset; // 4
+ }; // Size: 0x2C
+
+ struct GfxCellTree
+ {
+ // Best struct ever
+ GfxAabbTree* aabbtree;
+ };
+
+ struct GfxPortalWritable
+ {
+ bool isQueued;
+ bool isAncestor;
+ char recursionDepth;
+ char hullPointCount;
+ //float(*hullPoints)[2];
+ };
+
+ struct DpvsPlane
+ {
+ float coeffs[4];
+ char side[3];
+ };
+
+ struct GfxPortal // Needs to be investigated
+ {
+ GfxPortalWritable writable; // 4
+ DpvsPlane plane; // 20
+ int unknown1;
+ float (*vertices)[3];
+ short unknown2;
+ char vertexCount;
+ //char unknown2[2];
+ float hullAxis[2][3];
+ };
+
+#pragma pack(push, 4)
+ struct GfxCell
+ {
+ union
+ {
+ Bounds bounds;
+
+ struct
+ {
+ float mins[3];
+ float maxs[3];
+ };
+ };
+
+ int portalCount;
+ GfxPortal* portals;
+ char reflectionProbeCount;
+ char* reflectionProbes;
+ };
+#pragma pack(pop)
+
+ struct GfxCell_IW5
+ {
+ float mins[3];
+ float maxs[3];
+ int portalCount;
+ GfxPortal* portals;
+ char reflectionProbeCount;
+ char* reflectionProbes;
+ char reflectionProbeReferenceCount;
+ char* reflectionProbeReferences;
+ };
+
+ struct GfxReflectionProbe
+ {
+ float offset[3];
+ };
+
+ typedef char GfxTexture[0x04];
+
+ struct GfxLightmapArray
+ {
+ GfxImage* primary;
+ GfxImage* secondary;
+ };
+
+ struct GfxWorldVertex
+ {
+ float xyz[3];
+ float binormalSign;
+ GfxColor color;
+ float texCoord[2];
+ float lmapCoord[2];
+ PackedUnitVec normal;
+ PackedUnitVec tangent;
+ };
+
+ struct GfxWorldVertexData
+ {
+ GfxWorldVertex* vertices;
+ void* worldVb; // D3DVertexBuffer
+ };
+
+ struct GfxWorldVertexLayerData
+ {
+ char* data;
+ void* layerVb; // D3DVertexBuffer
+ };
+
+ struct GfxWorldDraw
+ {
+ union
+ {
+ char _portpad0[16];
+
+ struct
+ {
+ unsigned int reflectionProbeCount; // 4
+ GfxImage* * reflectionImages; // 4
+ GfxReflectionProbe* reflectionProbes; // 4
+ GfxTexture* reflectionProbeTextures; //Count = reflectionProbeCount // 4
+ };
+ };
+
+ union
+ {
+ char _portpad1[56];
+
+ struct
+ {
+ int lightmapCount; // 4
+ GfxLightmapArray* lightmaps; // 4
+ GfxTexture* lightmapPrimaryTextures; //Count = lightmapCount // 4
+ GfxTexture* lightmapSecondaryTextures; //Count = lightmapCount // 4
+ GfxImage* skyImage; // 4
+ GfxImage* outdoorImage; // 4
+ unsigned int vertexCount; // 4
+ GfxWorldVertexData vd;
+ unsigned int vertexLayerDataSize;
+ GfxWorldVertexLayerData vld;
+ int indexCount;
+ unsigned __int16* indices;
+ };
+ };
+ };
+
+ struct GfxWorldDraw_IW5
+ {
+ union
+ {
+ char _portpad0[16];
+
+ struct
+ {
+ unsigned int reflectionProbeCount; // 4
+ GfxImage* * reflectionImages; // 4
+ GfxReflectionProbe* reflectionProbes; // 4
+ GfxTexture* reflectionProbeTextures; //Count = reflectionProbeCount // 4
+ };
+ };
+
+ char cancer[12];
+
+ union
+ {
+ char _portpad1[56];
+
+ struct
+ {
+ int lightmapCount; // 4
+ GfxLightmapArray* lightmaps; // 4
+ GfxTexture* lightmapPrimaryTextures; //Count = lightmapCount // 4
+ GfxTexture* lightmapSecondaryTextures; //Count = lightmapCount // 4
+ GfxImage* skyImage; // 4
+ GfxImage* outdoorImage; // 4
+ unsigned int vertexCount; // 4
+ GfxWorldVertexData vd;
+ unsigned int vertexLayerDataSize;
+ GfxWorldVertexLayerData vld;
+ int indexCount;
+ unsigned __int16* indices;
+ };
+ };
+ };
+
+ struct GfxLightGridEntry
+ {
+ unsigned __int16 colorsIndex;
+ char primaryLightIndex;
+ char needsTrace;
+ };
+
+ struct GfxLightGridColors
+ {
+ char rgb[56][3];
+ };
+
+ struct GfxLightGrid
+ {
+ bool hasLightRegions; // 4
+ unsigned int sunPrimaryLightIndex; // 4
+ unsigned __int16 mins[3]; // 6
+ unsigned __int16 maxs[3]; // 6
+ unsigned int rowAxis; // 4
+ unsigned int colAxis; // 4
+ unsigned __int16* rowDataStart;
+ // Size: (varGfxLightGrid->maxs[varGfxLightGrid->rowAxis] - varGfxLightGrid->mins[varGfxLightGrid->rowAxis] + 1) * 2
+ unsigned int rawRowDataSize;
+ char* rawRowData;
+ unsigned int entryCount;
+ GfxLightGridEntry* entries;
+ unsigned int colorCount;
+ GfxLightGridColors* colors;
+ };
+
+ struct GfxBrushModelWritable
+ {
+ union
+ {
+ Bounds bounds;
+
+ struct
+ {
+ float mins[3];
+ float maxs[3];
+ };
+ };
+
+ float mip1radiusSq;
+ };
+
+ struct GfxBrushModel
+ {
+ GfxBrushModelWritable writable;
+
+ union
+ {
+ Bounds bounds;
+
+ struct
+ {
+ float mins[3];
+ float maxs[3];
+ };
+ };
+
+ unsigned int surfaceCount;
+ unsigned int startSurfIndex;
+ };
+
+ struct MaterialMemory
+ {
+ Material* material;
+ int memory;
+ };
+
+ struct sunflare_t
+ {
+ bool hasValidData;
+ Material* spriteMaterial;
+ Material* flareMaterial;
+ float spriteSize;
+ float flareMinSize;
+ float flareMinDot;
+ float flareMaxSize;
+ float flareMaxDot;
+ float flareMaxAlpha;
+ int flareFadeInTime;
+ int flareFadeOutTime;
+ float blindMinDot;
+ float blindMaxDot;
+ float blindMaxDarken;
+ int blindFadeInTime;
+ int blindFadeOutTime;
+ float glareMinDot;
+ float glareMaxDot;
+ float glareMaxLighten;
+ int glareFadeInTime;
+ int glareFadeOutTime;
+ float sunFxPosition[3];
+ };
+
+ struct XModelDrawInfo
+ {
+ unsigned __int16 lod;
+ unsigned __int16 surfId;
+ };
+
+ struct GfxSceneDynModel
+ {
+ XModelDrawInfo info;
+ unsigned __int16 dynEntId;
+ };
+
+ struct BModelDrawInfo
+ {
+ unsigned __int16 surfId;
+ };
+
+ struct GfxSceneDynBrush
+ {
+ BModelDrawInfo info;
+ unsigned __int16 dynEntId;
+ };
+
+ struct GfxShadowGeometry
+ {
+ unsigned __int16 surfaceCount;
+ unsigned __int16 smodelCount;
+ unsigned __int16* sortedSurfIndex;
+ unsigned __int16* smodelIndex;
+ };
+
+ struct GfxLightRegionAxis
+ {
+ float dir[3];
+ float midPoint;
+ float halfSize;
+ };
+
+ struct GfxLightRegionHull
+ {
+ float kdopMidPoint[9];
+ float kdopHalfSize[9];
+ unsigned int axisCount;
+ GfxLightRegionAxis* axis;
+ };
+
+ struct GfxLightRegion
+ {
+ unsigned int hullCount;
+ GfxLightRegionHull* hulls;
+ };
+
+ struct GfxStaticModelInst
+ {
+ float mins[3];
+ float maxs[3];
+ float lightingOrigin[3];
+ };
+
+ struct srfTriangles_t
+ {
+ int vertexLayerData;
+ int firstVertex;
+ unsigned __int16 vertexCount;
+ unsigned __int16 triCount;
+ int baseIndex;
+ };
+
+ struct GfxSurface
+ {
+ srfTriangles_t tris;
+ Material* material;
+ char lightmapIndex;
+ char reflectionProbeIndex;
+ char primaryLightIndex;
+ bool castsSunShadow;
+ };
+
+ struct GfxCullGroup
+ {
+ float mins[3];
+ float maxs[3];
+ //int surfaceCount;
+ //int startSurfIndex;
+ };
+
+ struct GfxDrawSurfFields
+ {
+ __int64 _bf0;
+ };
+
+ union GfxDrawSurf
+ {
+ GfxDrawSurfFields fields;
+ unsigned __int64 packed;
+ };
+
+#pragma pack(push, 4)
+ struct GfxPackedPlacement
+ {
+ float origin[3];
+ float axis[3][3];
+ float scale;
+ };
+
+ struct GfxStaticModelDrawInst
+ {
+ GfxPackedPlacement placement;
+ XModel* model;
+ unsigned __int16 smodelCacheIndex[4];
+ float cullDist;
+ char reflectionProbeIndex;
+ char primaryLightIndex;
+ unsigned __int16 lightingHandle;
+ char flags;
+ };
+
+ struct GfxWorldDpvsDynamic
+ {
+ unsigned int dynEntClientWordCount[2];
+ unsigned int dynEntClientCount[2];
+ unsigned int* dynEntCellBits[2];
+ char* dynEntVisData[2][3];
+ };
+
+#pragma pack(pop)
+
+ struct GfxWorldDpvsStatic
+ {
+ unsigned int smodelCount;
+ unsigned int staticSurfaceCount;
+ unsigned int staticSurfaceCountNoDecal;
+ unsigned int litOpaqueSurfsBegin;
+ unsigned int litOpaqueSurfsEnd;
+ unsigned int litTransSurfsBegin;
+ unsigned int litTransSurfsEnd;
+ unsigned int shadowCasterSurfsBegin;
+ unsigned int shadowCasterSurfsEnd;
+ unsigned int emissiveSurfsBegin;
+ unsigned int emissiveSurfsEnd;
+ unsigned int smodelVisDataCount;
+ unsigned int surfaceVisDataCount;
+ char* smodelVisData[3];
+ char* surfaceVisData[3];
+ unsigned __int16* sortedSurfIndex;
+ GfxStaticModelInst* smodelInsts;
+ GfxSurface* surfaces;
+ GfxCullGroup* cullGroups;
+ GfxStaticModelDrawInst* smodelDrawInsts;
+ GfxDrawSurf* surfaceMaterials;
+ unsigned int* surfaceCastsSunShadow;
+ volatile int usageCount;
+ };
+
+ struct GfxHeroLight
+ {
+ char type;
+ char pad[3];
+ float color[3];
+ float dir[3];
+ float origin[3];
+ float radius;
+ float cosHalfFovOuter;
+ float cosHalfFovInner;
+ int exponent;
+ };
+
+ struct GfxCellTreeCount
+ {
+ int aabbTreeCount;
+ };
+
+#pragma pack(push, 4)
+ struct GfxWorld
+ {
+ const char* name; // 4
+ const char* baseName; // 4
+ int planeCount; // 4
+ int nodeCount; // 4 // = 16
+ int indexCount; // 4
+ unsigned int skyCount; // 4
+ GfxSky* skies; // 4
+ int sunPrimaryLightIndex; // 4 // = 32
+ int primaryLightCount; // 4
+ int primaryLightEnvCount; // 4
+ char unknown1[12]; // 16 // = 56 // Sortkeys. Don't know which ones though
+ GfxWorldDpvsPlanes dpvsPlanes; // 16
+ GfxCellTreeCount* aabbTreeCounts; // Size: 4 * dpvsPlanes.cellCount // 4
+ GfxCellTree* aabbTree; // 4
+ GfxCell* cells; // 4 // = 80
+ GfxWorldDraw worldDraw; // 72
+ GfxLightGrid lightGrid; // 56 // = 208
+ int modelCount; // 4
+ GfxBrushModel* models; // 4 // = 216
+ union
+ {
+ Bounds bounds;
+
+ struct
+ {
+ float mins[3]; // 12
+ float maxs[3]; // 12
+ };
+ };
+
+ unsigned int checksum; // 4
+ int materialMemoryCount; // 4 // = 248
+ MaterialMemory* materialMemory; // 4
+ sunflare_t sun; // 96 // = 348
+ float outdoorLookupMatrix[4][4]; // 64
+ GfxImage* outdoorImage; // 4 // = 416
+ unsigned int* cellCasterBits[2]; // 8
+ GfxSceneDynModel* sceneDynModel; // 4
+ GfxSceneDynBrush* sceneDynBrush; // 4 // = 432
+ unsigned char* primaryLightEntityShadowVis;
+ unsigned int* primaryLightDynEntShadowVis[2];
+ char* primaryLightForModelDynEnt;
+ GfxShadowGeometry* shadowGeom;
+ GfxLightRegion* lightRegion;
+ GfxWorldDpvsStatic dpvs;
+ GfxWorldDpvsDynamic dpvsDyn;
+ unsigned int mapVtxChecksum;
+ unsigned int heroLightCount;
+ GfxHeroLight* heroLights;
+ char fogTypesAllowed;
+ char pad2[3];
+ };
+#pragma pack(pop)
+
+#pragma pack(push, 4)
+ struct cStaticModel_s
+ {
+ XModel* xmodel;
+ float origin[3];
+ float invScaledAxis[3][3];
+ float absmin[3];
+ float absmax[3];
+ };
+
+ struct dmaterial_t
+ {
+ char* material;
+ int surfaceFlags;
+ int contentFlags;
+ };
+
+ struct cNode_t
+ {
+ cplane_s* plane;
+ __int16 children[2];
+ };
+
+ struct cLeaf_t
+ {
+ unsigned __int16 firstCollAabbIndex; // + 0
+ unsigned __int16 collAabbCount; // + 2
+ int brushContents; // + 6
+ int terrainContents; // + 10
+ float mins[3]; // + 22
+ float maxs[3]; // + 34
+ int leafBrushNode; // + 38
+ };
+
+ struct cLeafBrushNodeLeaf_t
+ {
+ unsigned __int16* brushes;
+ };
+
+ struct cLeafBrushNodeChildren_t
+ {
+ unsigned __int16 childOffset[6];
+ };
+
+ union cLeafBrushNodeData_t
+ {
+ cLeafBrushNodeLeaf_t leaf;
+ cLeafBrushNodeChildren_t children;
+ };
+
+ struct cLeafBrushNode_s
+ {
+ char axis;
+ short leafBrushCount;
+ int contents;
+ cLeafBrushNodeData_t data;
+ };
+
+ struct CollisionBorder
+ {
+ float distEq[3];
+ float zBase;
+ float zSlope;
+ float start;
+ float length;
+ };
+
+ struct CollisionPartition
+ {
+ char triCount;
+ char borderCount;
+ int firstTri;
+ CollisionBorder* borders;
+ };
+
+ union CollisionAabbTreeIndex
+ {
+ int firstChildIndex;
+ int partitionIndex;
+ };
+
+ struct CollisionAabbTree
+ {
+ float origin[3];
+ unsigned __int16 materialIndex;
+ unsigned __int16 childCount;
+ float halfSize[3];
+ CollisionAabbTreeIndex u;
+ };
+
+ enum DynEntityType
+ {
+ DYNENT_TYPE_INVALID = 0x0,
+ DYNENT_TYPE_CLUTTER = 0x1,
+ DYNENT_TYPE_DESTRUCT = 0x2,
+ DYNENT_TYPE_COUNT = 0x3,
+ };
+
+ struct GfxPlacement
+ {
+ float quat[4];
+ float origin[3];
+ };
+
+ struct DynEntityDef
+ {
+ DynEntityType type;
+ GfxPlacement pose;
+ XModel* xModel;
+ unsigned __int16 brushModel;
+ unsigned __int16 physicsBrushModel;
+ void* destroyFx; // FxEffectDef
+ PhysPreset* physPreset;
+ int health;
+ PhysMass mass;
+ //char *unknown;
+ };
+
+ struct DynEntityPose
+ {
+ GfxPlacement pose;
+ float radius;
+ };
+
+ struct DynEntityClient
+ {
+ int physObjId;
+ unsigned __int16 flags;
+ unsigned __int16 lightingHandle;
+ int health;
+ };
+
+ struct DynEntityColl
+ {
+ unsigned __int16 sector;
+ unsigned __int16 nextEntInSector;
+ float linkMins[2];
+ float linkMaxs[2];
+ };
+
+ struct unknownInternalClipMapStruct1
+ {
+ int planeCount;
+ cplane_s* planes;
+ unsigned int numMaterials;
+ dmaterial_t* materials;
+ unsigned int numBrushSides;
+ cbrushside_t* brushsides;
+ unsigned int numBrushEdges;
+ cbrushedge_t* brushEdges;
+ unsigned int leafbrushNodesCount;
+ cLeafBrushNode_s* leafbrushNodes;
+ unsigned int numLeafBrushes;
+ unsigned __int16* leafbrushes;
+ unsigned __int16 numBrushes;
+ cbrush_t* brushes;
+ char* unknown1; //Size = ((numBrushes << 1) + numBrushes) << 3
+ unsigned int* leafsurfaces; //Count = numBrushes
+ };
+
+ struct unknownInternalClipMapStruct2
+ {
+ char* unknownString;
+ char unknown[0x10];
+ };
+
+ struct unknownInternalClipMapStruct3
+ {
+ char _pad[28];
+ unknownInternalClipMapStruct1* unkArrayPtr;
+ char _pad2[40];
+ };
+
+ struct cmodel_t
+ {
+ union
+ {
+ char _portpad0[28];
+
+ struct
+ {
+ Bounds bounds;
+ float radius;
+ };
+ };
+
+ union
+ {
+ char _portpad1[40];
+
+ struct
+ {
+ cLeaf_t leaf;
+ };
+ };
+ };
+
+ struct SModelAabbNode
+ {
+ Bounds bounds;
+ short firstChild;
+ short childCount;
+ };
+
+ struct DynEntityDef_IW5
+ {
+ DynEntityType type;
+ GfxPlacement pose;
+ XModel* xModel;
+ unsigned __int16 brushModel;
+ unsigned __int16 physicsBrushModel;
+ void* destroyFx; // FxEffectDef
+ PhysPreset* physPreset;
+ int health;
+ void* hinge;
+ PhysMass mass;
+ };
+
+ struct cmodel_t_IW5
+ {
+ Bounds bounds;
+ float radius;
+ void* info;
+ cLeaf_t leaf;
+ };
+
+ struct clipMap_t
+ {
+ const char* name; // 4
+ bool isInUse; // 4
+ int numCPlanes; // +8
+ cplane_s* cPlanes; // sizeof 20, +12
+ int numStaticModels; // +16
+ cStaticModel_s* staticModelList; // sizeof 76, +20
+ int numMaterials; // +24
+ dmaterial_t* materials; // sizeof 12 with a string (possibly name?), +28
+ int numCBrushSides; // +32
+ cbrushside_t* cBrushSides; // sizeof 8, +36
+ int numCBrushEdges; // +40 NOT USED IN T5
+ cbrushedge_t* cBrushEdges; // +44 NOT USED IN T5
+ int numCNodes; // +48
+ cNode_t* cNodes; // sizeof 8, +52
+ int numCLeaf; // +56
+ cLeaf_t* cLeaf; // +60
+ int numCLeafBrushNodes; // +64
+ cLeafBrushNode_s* cLeafBrushNodes; // +68
+ int numLeafBrushes; // +72
+ short* leafBrushes; // +76
+ int numLeafSurfaces; // +80
+ int* leafSurfaces; // +84
+ int numVerts; // +88
+ VecInternal<3>* verts; // +92
+ int numTriIndices; // +96
+ short* triIndices; // +100
+ char* triEdgeIsWalkable; // +104
+ int numCollisionBorders; // +108
+ CollisionBorder* collisionBorders; // sizeof 28, +112
+ int numCollisionPartitions; // +116
+ CollisionPartition* collisionPartitions; // sizeof 12, +120
+ int numCollisionAABBTrees; // +124
+ CollisionAabbTree* collisionAABBTrees; // sizeof 32, +128
+ int numCModels; // +132
+ cmodel_t* cModels; // sizeof 68, +136
+ short numBrushes; // +140
+ short pad2; // +142
+ cbrush_t* brushes; // sizeof 36, +144
+ Bounds* brushBounds; // same count as cBrushes, +148
+ int* brushContents; // same count as cBrushes, +152
+ MapEnts* mapEnts; // +156
+ short smodelNodeCount; // +160
+ short pad3;
+ SModelAabbNode* smodelNodes; // +164
+ unsigned __int16 dynEntCount[2];
+ DynEntityDef* dynEntDefList[2];
+ DynEntityPose* dynEntPoseList[2];
+ DynEntityClient* dynEntClientList[2];
+ DynEntityColl* dynEntCollList[2];
+ unsigned int checksum;
+ char unknown5[48];
+ }; // +256
+#pragma pack(pop)
+
+ union XAssetHeader
+ {
+ RawFile* rawfile;
+ VertexDecl* vertexdecl;
+ PixelShader* pixelshader;
+ VertexShader* vertexshader;
+ MaterialTechniqueSet* techset;
+ GfxImage* gfximage;
+ GfxImage* image;
+ Material* material;
+ PhysPreset* physpreset;
+ PhysCollmap* physcollmap;
+ PhysCollmap* phys_collmap;
+ XAnimParts* xanimparts;
+ XAnimParts* xanim;
+ ModelSurface* xsurface;
+ ModelSurface* xmodelsurfs;
+ clipMap_t* clipmap;
+ clipMap_t* col_map_mp;
+ GfxWorld* gfxworld;
+ GfxWorld* gfx_map;
+ GameWorldMp* gameworldmp;
+ GameWorldSp* gameworldsp;
+ GameWorldMp* game_map_mp;
+ GameWorldSp* game_map_sp;
+ FxWorld* fxworld;
+ FxWorld* fx_map;
+ MapEnts* mapents;
+ MapEnts* map_ents;
+ XModel* xmodel;
+ StringTable* stringtable;
+ ComWorld* comworld;
+ ComWorld* com_map;
+ LocalizeEntry* localize;
+ SndCurve* soundcurve;
+ SndCurve* sndcurve;
+ TracerDef* tracer;
+ //leaderboarddef* leaderboard;
+ Font_s* font;
+ WeaponCompleteDef* weapon;
+ FxEffectDef* fx;
+ snd_alias_list_t* sound;
+ LoadedSound* loadedsound;
+ LoadedSound* loaded_sound;
+ //structureddatadefset* structureddatadef;
+ //menudef_t* menu;
+ GfxLightDef* lightdef;
+ };
+
+ enum MaterialTechniqueType
+ {
+ TECHNIQUE_DEPTH_PREPASS = 0x0,
+ TECHNIQUE_BUILD_FLOAT_Z = 0x1,
+ TECHNIQUE_BUILD_SHADOWMAP_DEPTH = 0x2,
+ TECHNIQUE_BUILD_SHADOWMAP_COLOR = 0x3,
+ TECHNIQUE_UNLIT = 0x4,
+ TECHNIQUE_EMISSIVE = 0x5,
+ TECHNIQUE_EMISSIVE_DFOG = 0x6,
+ TECHNIQUE_EMISSIVE_SHADOW = 0x7,
+ TECHNIQUE_EMISSIVE_SHADOW_DFOG = 0x8,
+ TECHNIQUE_LIT_BEGIN = 0x9,
+ TECHNIQUE_LIT = 0x9,
+ TECHNIQUE_LIT_DFOG = 0xA,
+ TECHNIQUE_LIT_SUN = 0xB,
+ TECHNIQUE_LIT_SUN_DFOG = 0xC,
+ TECHNIQUE_LIT_SUN_SHADOW = 0xD,
+ TECHNIQUE_LIT_SUN_SHADOW_DFOG = 0xE,
+ TECHNIQUE_LIT_SPOT = 0xF,
+ TECHNIQUE_LIT_SPOT_DFOG = 0x10,
+ TECHNIQUE_LIT_SPOT_SHADOW = 0x11,
+ TECHNIQUE_LIT_SPOT_SHADOW_DFOG = 0x12,
+ TECHNIQUE_LIT_OMNI = 0x13,
+ TECHNIQUE_LIT_OMNI_DFOG = 0x14,
+ TECHNIQUE_LIT_OMNI_SHADOW = 0x15,
+ TECHNIQUE_LIT_OMNI_SHADOW_DFOG = 0x16,
+ TECHNIQUE_LIT_INSTANCED = 0x17,
+ TECHNIQUE_LIT_INSTANCED_DFOG = 0x18,
+ TECHNIQUE_LIT_INSTANCED_SUN = 0x19,
+ TECHNIQUE_LIT_INSTANCED_SUN_DFOG = 0x1A,
+ TECHNIQUE_LIT_INSTANCED_SUN_SHADOW = 0x1B,
+ TECHNIQUE_LIT_INSTANCED_SUN_SHADOW_DFOG = 0x1C,
+ TECHNIQUE_LIT_INSTANCED_SPOT = 0x1D,
+ TECHNIQUE_LIT_INSTANCED_SPOT_DFOG = 0x1E,
+ TECHNIQUE_LIT_INSTANCED_SPOT_SHADOW = 0x1F,
+ TECHNIQUE_LIT_INSTANCED_SPOT_SHADOW_DFOG = 0x20,
+ TECHNIQUE_LIT_INSTANCED_OMNI = 0x21,
+ TECHNIQUE_LIT_INSTANCED_OMNI_DFOG = 0x22,
+ TECHNIQUE_LIT_INSTANCED_OMNI_SHADOW = 0x23,
+ TECHNIQUE_LIT_INSTANCED_OMNI_SHADOW_DFOG = 0x24,
+ TECHNIQUE_LIT_END = 0x25,
+ TECHNIQUE_LIGHT_SPOT = 0x25,
+ TECHNIQUE_LIGHT_OMNI = 0x26,
+ TECHNIQUE_LIGHT_SPOT_SHADOW = 0x27,
+ TECHNIQUE_FAKELIGHT_NORMAL = 0x28,
+ TECHNIQUE_FAKELIGHT_VIEW = 0x29,
+ TECHNIQUE_SUNLIGHT_PREVIEW = 0x2A,
+ TECHNIQUE_CASE_TEXTURE = 0x2B,
+ TECHNIQUE_WIREFRAME_SOLID = 0x2C,
+ TECHNIQUE_WIREFRAME_SHADED = 0x2D,
+ TECHNIQUE_DEBUG_BUMPMAP = 0x2E,
+ TECHNIQUE_DEBUG_BUMPMAP_INSTANCED = 0x2F,
+ TECHNIQUE_COUNT = 0x30,
+ TECHNIQUE_TOTAL_COUNT = 0x31,
+ TECHNIQUE_NONE = 0x32,
+ };
+
+ enum $949C82572B6A70952C455E749D3B3D56
+ {
+ CONST_SRC_CODE_MAYBE_DIRTY_PS_BEGIN = 0x0,
+ CONST_SRC_CODE_LIGHT_POSITION = 0x0,
+ CONST_SRC_CODE_LIGHT_DIFFUSE = 0x1,
+ CONST_SRC_CODE_LIGHT_SPECULAR = 0x2,
+ CONST_SRC_CODE_LIGHT_SPOTDIR = 0x3,
+ CONST_SRC_CODE_LIGHT_SPOTFACTORS = 0x4,
+ CONST_SRC_CODE_LIGHT_FALLOFF_PLACEMENT = 0x5,
+ CONST_SRC_CODE_PARTICLE_CLOUD_COLOR = 0x6,
+ CONST_SRC_CODE_GAMETIME = 0x7,
+ CONST_SRC_CODE_MAYBE_DIRTY_PS_END = 0x8,
+ CONST_SRC_CODE_ALWAYS_DIRTY_PS_BEGIN = 0x8,
+ CONST_SRC_CODE_PIXEL_COST_FRACS = 0x8,
+ CONST_SRC_CODE_PIXEL_COST_DECODE = 0x9,
+ CONST_SRC_CODE_FILTER_TAP_0 = 0xA,
+ CONST_SRC_CODE_FILTER_TAP_1 = 0xB,
+ CONST_SRC_CODE_FILTER_TAP_2 = 0xC,
+ CONST_SRC_CODE_FILTER_TAP_3 = 0xD,
+ CONST_SRC_CODE_FILTER_TAP_4 = 0xE,
+ CONST_SRC_CODE_FILTER_TAP_5 = 0xF,
+ CONST_SRC_CODE_FILTER_TAP_6 = 0x10,
+ CONST_SRC_CODE_FILTER_TAP_7 = 0x11,
+ CONST_SRC_CODE_COLOR_MATRIX_R = 0x12,
+ CONST_SRC_CODE_COLOR_MATRIX_G = 0x13,
+ CONST_SRC_CODE_COLOR_MATRIX_B = 0x14,
+ CONST_SRC_CODE_SHADOWMAP_POLYGON_OFFSET = 0x15,
+ CONST_SRC_CODE_RENDER_TARGET_SIZE = 0x16,
+ CONST_SRC_CODE_ALWAYS_DIRTY_PS_END = 0x17,
+ CONST_SRC_CODE_FIXED_PS_BEGIN = 0x17,
+ CONST_SRC_CODE_DOF_EQUATION_VIEWMODEL_AND_FAR_BLUR = 0x17,
+ CONST_SRC_CODE_DOF_EQUATION_SCENE = 0x18,
+ CONST_SRC_CODE_DOF_LERP_SCALE = 0x19,
+ CONST_SRC_CODE_DOF_LERP_BIAS = 0x1A,
+ CONST_SRC_CODE_DOF_ROW_DELTA = 0x1B,
+ CONST_SRC_CODE_MOTION_MATRIX_X = 0x1C,
+ CONST_SRC_CODE_MOTION_MATRIX_Y = 0x1D,
+ CONST_SRC_CODE_MOTION_MATRIX_W = 0x1E,
+ CONST_SRC_CODE_SHADOWMAP_SWITCH_PARTITION = 0x1F,
+ CONST_SRC_CODE_SHADOWMAP_SCALE = 0x20,
+ CONST_SRC_CODE_ZNEAR = 0x21,
+ CONST_SRC_CODE_LIGHTING_LOOKUP_SCALE = 0x22,
+ CONST_SRC_CODE_DEBUG_BUMPMAP = 0x23,
+ CONST_SRC_CODE_MATERIAL_COLOR = 0x24,
+ CONST_SRC_CODE_FOG = 0x25,
+ CONST_SRC_CODE_FOG_COLOR_LINEAR = 0x26,
+ CONST_SRC_CODE_FOG_COLOR_GAMMA = 0x27,
+ CONST_SRC_CODE_FOG_SUN_CONSTS = 0x28,
+ CONST_SRC_CODE_FOG_SUN_COLOR_LINEAR = 0x29,
+ CONST_SRC_CODE_FOG_SUN_COLOR_GAMMA = 0x2A,
+ CONST_SRC_CODE_FOG_SUN_DIR = 0x2B,
+ CONST_SRC_CODE_GLOW_SETUP = 0x2C,
+ CONST_SRC_CODE_GLOW_APPLY = 0x2D,
+ CONST_SRC_CODE_COLOR_BIAS = 0x2E,
+ CONST_SRC_CODE_COLOR_TINT_BASE = 0x2F,
+ CONST_SRC_CODE_COLOR_TINT_DELTA = 0x30,
+ CONST_SRC_CODE_COLOR_TINT_QUADRATIC_DELTA = 0x31,
+ CONST_SRC_CODE_OUTDOOR_FEATHER_PARMS = 0x32,
+ CONST_SRC_CODE_ENVMAP_PARMS = 0x33,
+ CONST_SRC_CODE_SUN_SHADOWMAP_PIXEL_ADJUST = 0x34,
+ CONST_SRC_CODE_SPOT_SHADOWMAP_PIXEL_ADJUST = 0x35,
+ CONST_SRC_CODE_COMPOSITE_FX_DISTORTION = 0x36,
+ CONST_SRC_CODE_POSTFX_FADE_EFFECT = 0x37,
+ CONST_SRC_CODE_VIEWPORT_DIMENSIONS = 0x38,
+ CONST_SRC_CODE_FRAMEBUFFER_READ = 0x39,
+ CONST_SRC_CODE_FIXED_PS_END = 0x3A,
+ CONST_SRC_CODE_NON_PS_BEGIN = 0x3A,
+ CONST_SRC_CODE_BASE_LIGHTING_COORDS = 0x3A,
+ CONST_SRC_CODE_LIGHT_PROBE_AMBIENT = 0x3B,
+ CONST_SRC_CODE_NEARPLANE_ORG = 0x3C,
+ CONST_SRC_CODE_NEARPLANE_DX = 0x3D,
+ CONST_SRC_CODE_NEARPLANE_DY = 0x3E,
+ CONST_SRC_CODE_CLIP_SPACE_LOOKUP_SCALE = 0x3F,
+ CONST_SRC_CODE_CLIP_SPACE_LOOKUP_OFFSET = 0x40,
+ CONST_SRC_CODE_PARTICLE_CLOUD_MATRIX0 = 0x41,
+ CONST_SRC_CODE_PARTICLE_CLOUD_MATRIX1 = 0x42,
+ CONST_SRC_CODE_PARTICLE_CLOUD_MATRIX2 = 0x43,
+ CONST_SRC_CODE_PARTICLE_CLOUD_SPARK_COLOR0 = 0x44,
+ CONST_SRC_CODE_PARTICLE_CLOUD_SPARK_COLOR1 = 0x45,
+ CONST_SRC_CODE_PARTICLE_CLOUD_SPARK_COLOR2 = 0x46,
+ CONST_SRC_CODE_PARTICLE_FOUNTAIN_PARM0 = 0x47,
+ CONST_SRC_CODE_PARTICLE_FOUNTAIN_PARM1 = 0x48,
+ CONST_SRC_CODE_DEPTH_FROM_CLIP = 0x49,
+ CONST_SRC_CODE_CODE_MESH_ARG_0 = 0x4A,
+ CONST_SRC_CODE_CODE_MESH_ARG_1 = 0x4B,
+ CONST_SRC_CODE_CODE_MESH_ARG_LAST = 0x4B,
+ CONST_SRC_CODE_NON_PS_END = 0x4C,
+ CONST_SRC_CODE_COUNT_FLOAT4 = 0x4C,
+ CONST_SRC_FIRST_CODE_MATRIX = 0x4C,
+ CONST_SRC_CODE_VIEW_MATRIX = 0x4C,
+ CONST_SRC_CODE_INVERSE_VIEW_MATRIX = 0x4D,
+ CONST_SRC_CODE_TRANSPOSE_VIEW_MATRIX = 0x4E,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_MATRIX = 0x4F,
+ CONST_SRC_CODE_PROJECTION_MATRIX = 0x50,
+ CONST_SRC_CODE_INVERSE_PROJECTION_MATRIX = 0x51,
+ CONST_SRC_CODE_TRANSPOSE_PROJECTION_MATRIX = 0x52,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_PROJECTION_MATRIX = 0x53,
+ CONST_SRC_CODE_VIEW_PROJECTION_MATRIX = 0x54,
+ CONST_SRC_CODE_INVERSE_VIEW_PROJECTION_MATRIX = 0x55,
+ CONST_SRC_CODE_TRANSPOSE_VIEW_PROJECTION_MATRIX = 0x56,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_PROJECTION_MATRIX = 0x57,
+ CONST_SRC_CODE_SHADOW_LOOKUP_MATRIX = 0x58,
+ CONST_SRC_CODE_INVERSE_SHADOW_LOOKUP_MATRIX = 0x59,
+ CONST_SRC_CODE_TRANSPOSE_SHADOW_LOOKUP_MATRIX = 0x5A,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_SHADOW_LOOKUP_MATRIX = 0x5B,
+ CONST_SRC_CODE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x5C,
+ CONST_SRC_CODE_INVERSE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x5D,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x5E,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x5F,
+ CONST_SRC_CODE_WORLD_MATRIX0 = 0x60,
+ CONST_SRC_CODE_INVERSE_WORLD_MATRIX0 = 0x61,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_MATRIX0 = 0x62,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_MATRIX0 = 0x63,
+ CONST_SRC_CODE_WORLD_VIEW_MATRIX0 = 0x64,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_MATRIX0 = 0x65,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_MATRIX0 = 0x66,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX0 = 0x67,
+ CONST_SRC_CODE_WORLD_VIEW_PROJECTION_MATRIX0 = 0x68,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_PROJECTION_MATRIX0 = 0x69,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX0 = 0x6A,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX0 = 0x6B,
+ CONST_SRC_CODE_WORLD_MATRIX1 = 0x6C,
+ CONST_SRC_CODE_INVERSE_WORLD_MATRIX1 = 0x6D,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_MATRIX1 = 0x6E,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_MATRIX1 = 0x6F,
+ CONST_SRC_CODE_WORLD_VIEW_MATRIX1 = 0x70,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_MATRIX1 = 0x71,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_MATRIX1 = 0x72,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX1 = 0x73,
+ CONST_SRC_CODE_WORLD_VIEW_PROJECTION_MATRIX1 = 0x74,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_PROJECTION_MATRIX1 = 0x75,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX1 = 0x76,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX1 = 0x77,
+ CONST_SRC_CODE_WORLD_MATRIX2 = 0x78,
+ CONST_SRC_CODE_INVERSE_WORLD_MATRIX2 = 0x79,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_MATRIX2 = 0x7A,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_MATRIX2 = 0x7B,
+ CONST_SRC_CODE_WORLD_VIEW_MATRIX2 = 0x7C,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_MATRIX2 = 0x7D,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_MATRIX2 = 0x7E,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX2 = 0x7F,
+ CONST_SRC_CODE_WORLD_VIEW_PROJECTION_MATRIX2 = 0x80,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_PROJECTION_MATRIX2 = 0x81,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX2 = 0x82,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX2 = 0x83,
+ CONST_SRC_TOTAL_COUNT = 0x84,
+ CONST_SRC_NONE = 0x85,
+ };
+}
+
+namespace IW3
+{
+ enum MaterialTechniqueType
+ {
+ TECHNIQUE_DEPTH_PREPASS = 0x0,
+ TECHNIQUE_BUILD_FLOAT_Z = 0x1,
+ TECHNIQUE_BUILD_SHADOWMAP_DEPTH = 0x2,
+ TECHNIQUE_BUILD_SHADOWMAP_COLOR = 0x3,
+ TECHNIQUE_UNLIT = 0x4,
+ TECHNIQUE_EMISSIVE = 0x5,
+ TECHNIQUE_EMISSIVE_SHADOW = 0x6,
+ TECHNIQUE_LIT_BEGIN = 0x7,
+ TECHNIQUE_LIT = 0x7,
+ TECHNIQUE_LIT_SUN = 0x8,
+ TECHNIQUE_LIT_SUN_SHADOW = 0x9,
+ TECHNIQUE_LIT_SPOT = 0xA,
+ TECHNIQUE_LIT_SPOT_SHADOW = 0xB,
+ TECHNIQUE_LIT_OMNI = 0xC,
+ TECHNIQUE_LIT_OMNI_SHADOW = 0xD,
+ TECHNIQUE_LIT_INSTANCED = 0xE,
+ TECHNIQUE_LIT_INSTANCED_SUN = 0xF,
+ TECHNIQUE_LIT_INSTANCED_SUN_SHADOW = 0x10,
+ TECHNIQUE_LIT_INSTANCED_SPOT = 0x11,
+ TECHNIQUE_LIT_INSTANCED_SPOT_SHADOW = 0x12,
+ TECHNIQUE_LIT_INSTANCED_OMNI = 0x13,
+ TECHNIQUE_LIT_INSTANCED_OMNI_SHADOW = 0x14,
+ TECHNIQUE_LIT_END = 0x15,
+ TECHNIQUE_LIGHT_SPOT = 0x15,
+ TECHNIQUE_LIGHT_OMNI = 0x16,
+ TECHNIQUE_LIGHT_SPOT_SHADOW = 0x17,
+ TECHNIQUE_FAKELIGHT_NORMAL = 0x18,
+ TECHNIQUE_FAKELIGHT_VIEW = 0x19,
+ TECHNIQUE_SUNLIGHT_PREVIEW = 0x1A,
+ TECHNIQUE_CASE_TEXTURE = 0x1B,
+ TECHNIQUE_WIREFRAME_SOLID = 0x1C,
+ TECHNIQUE_WIREFRAME_SHADED = 0x1D,
+ TECHNIQUE_SHADOWCOOKIE_CASTER = 0x1E,
+ TECHNIQUE_SHADOWCOOKIE_RECEIVER = 0x1F,
+ TECHNIQUE_DEBUG_BUMPMAP = 0x20,
+ TECHNIQUE_DEBUG_BUMPMAP_INSTANCED = 0x21,
+ TECHNIQUE_COUNT = 0x22,
+ TECHNIQUE_TOTAL_COUNT = 0x23,
+ TECHNIQUE_NONE = 0x24,
+ };
+
+ enum $D8CAED6A392807092A83572483F14017
+ {
+ CONST_SRC_CODE_MAYBE_DIRTY_PS_BEGIN = 0x0,
+ CONST_SRC_CODE_LIGHT_POSITION = 0x0,
+ CONST_SRC_CODE_LIGHT_DIFFUSE = 0x1,
+ CONST_SRC_CODE_LIGHT_SPECULAR = 0x2,
+ CONST_SRC_CODE_LIGHT_SPOTDIR = 0x3,
+ CONST_SRC_CODE_LIGHT_SPOTFACTORS = 0x4,
+ CONST_SRC_CODE_NEARPLANE_ORG = 0x5,
+ CONST_SRC_CODE_NEARPLANE_DX = 0x6,
+ CONST_SRC_CODE_NEARPLANE_DY = 0x7,
+ CONST_SRC_CODE_SHADOW_PARMS = 0x8,
+ CONST_SRC_CODE_SHADOWMAP_POLYGON_OFFSET = 0x9,
+ CONST_SRC_CODE_RENDER_TARGET_SIZE = 0xA,
+ CONST_SRC_CODE_LIGHT_FALLOFF_PLACEMENT = 0xB,
+ CONST_SRC_CODE_DOF_EQUATION_VIEWMODEL_AND_FAR_BLUR = 0xC,
+ CONST_SRC_CODE_DOF_EQUATION_SCENE = 0xD,
+ CONST_SRC_CODE_DOF_LERP_SCALE = 0xE,
+ CONST_SRC_CODE_DOF_LERP_BIAS = 0xF,
+ CONST_SRC_CODE_DOF_ROW_DELTA = 0x10,
+ CONST_SRC_CODE_PARTICLE_CLOUD_COLOR = 0x11,
+ CONST_SRC_CODE_GAMETIME = 0x12,
+ CONST_SRC_CODE_MAYBE_DIRTY_PS_END = 0x13,
+ CONST_SRC_CODE_ALWAYS_DIRTY_PS_BEGIN = 0x13,
+ CONST_SRC_CODE_PIXEL_COST_FRACS = 0x13,
+ CONST_SRC_CODE_PIXEL_COST_DECODE = 0x14,
+ CONST_SRC_CODE_FILTER_TAP_0 = 0x15,
+ CONST_SRC_CODE_FILTER_TAP_1 = 0x16,
+ CONST_SRC_CODE_FILTER_TAP_2 = 0x17,
+ CONST_SRC_CODE_FILTER_TAP_3 = 0x18,
+ CONST_SRC_CODE_FILTER_TAP_4 = 0x19,
+ CONST_SRC_CODE_FILTER_TAP_5 = 0x1A,
+ CONST_SRC_CODE_FILTER_TAP_6 = 0x1B,
+ CONST_SRC_CODE_FILTER_TAP_7 = 0x1C,
+ CONST_SRC_CODE_COLOR_MATRIX_R = 0x1D,
+ CONST_SRC_CODE_COLOR_MATRIX_G = 0x1E,
+ CONST_SRC_CODE_COLOR_MATRIX_B = 0x1F,
+ CONST_SRC_CODE_ALWAYS_DIRTY_PS_END = 0x20,
+ CONST_SRC_CODE_NEVER_DIRTY_PS_BEGIN = 0x20,
+ CONST_SRC_CODE_SHADOWMAP_SWITCH_PARTITION = 0x20,
+ CONST_SRC_CODE_SHADOWMAP_SCALE = 0x21,
+ CONST_SRC_CODE_ZNEAR = 0x22,
+ CONST_SRC_CODE_SUN_POSITION = 0x23,
+ CONST_SRC_CODE_SUN_DIFFUSE = 0x24,
+ CONST_SRC_CODE_SUN_SPECULAR = 0x25,
+ CONST_SRC_CODE_LIGHTING_LOOKUP_SCALE = 0x26,
+ CONST_SRC_CODE_DEBUG_BUMPMAP = 0x27,
+ CONST_SRC_CODE_MATERIAL_COLOR = 0x28,
+ CONST_SRC_CODE_FOG = 0x29,
+ CONST_SRC_CODE_FOG_COLOR = 0x2A,
+ CONST_SRC_CODE_GLOW_SETUP = 0x2B,
+ CONST_SRC_CODE_GLOW_APPLY = 0x2C,
+ CONST_SRC_CODE_COLOR_BIAS = 0x2D,
+ CONST_SRC_CODE_COLOR_TINT_BASE = 0x2E,
+ CONST_SRC_CODE_COLOR_TINT_DELTA = 0x2F,
+ CONST_SRC_CODE_OUTDOOR_FEATHER_PARMS = 0x30,
+ CONST_SRC_CODE_ENVMAP_PARMS = 0x31,
+ CONST_SRC_CODE_SPOT_SHADOWMAP_PIXEL_ADJUST = 0x32,
+ CONST_SRC_CODE_CLIP_SPACE_LOOKUP_SCALE = 0x33,
+ CONST_SRC_CODE_CLIP_SPACE_LOOKUP_OFFSET = 0x34,
+ CONST_SRC_CODE_PARTICLE_CLOUD_MATRIX = 0x35,
+ CONST_SRC_CODE_DEPTH_FROM_CLIP = 0x36,
+ CONST_SRC_CODE_CODE_MESH_ARG_0 = 0x37,
+ CONST_SRC_CODE_CODE_MESH_ARG_1 = 0x38,
+ CONST_SRC_CODE_CODE_MESH_ARG_LAST = 0x38,
+ CONST_SRC_CODE_BASE_LIGHTING_COORDS = 0x39,
+ CONST_SRC_CODE_NEVER_DIRTY_PS_END = 0x3A,
+ CONST_SRC_CODE_COUNT_FLOAT4 = 0x3A,
+ CONST_SRC_FIRST_CODE_MATRIX = 0x3A,
+ CONST_SRC_CODE_WORLD_MATRIX = 0x3A,
+ CONST_SRC_CODE_INVERSE_WORLD_MATRIX = 0x3B,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_MATRIX = 0x3C,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_MATRIX = 0x3D,
+ CONST_SRC_CODE_VIEW_MATRIX = 0x3E,
+ CONST_SRC_CODE_INVERSE_VIEW_MATRIX = 0x3F,
+ CONST_SRC_CODE_TRANSPOSE_VIEW_MATRIX = 0x40,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_MATRIX = 0x41,
+ CONST_SRC_CODE_PROJECTION_MATRIX = 0x42,
+ CONST_SRC_CODE_INVERSE_PROJECTION_MATRIX = 0x43,
+ CONST_SRC_CODE_TRANSPOSE_PROJECTION_MATRIX = 0x44,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_PROJECTION_MATRIX = 0x45,
+ CONST_SRC_CODE_WORLD_VIEW_MATRIX = 0x46,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_MATRIX = 0x47,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_MATRIX = 0x48,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX = 0x49,
+ CONST_SRC_CODE_VIEW_PROJECTION_MATRIX = 0x4A,
+ CONST_SRC_CODE_INVERSE_VIEW_PROJECTION_MATRIX = 0x4B,
+ CONST_SRC_CODE_TRANSPOSE_VIEW_PROJECTION_MATRIX = 0x4C,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_PROJECTION_MATRIX = 0x4D,
+ CONST_SRC_CODE_WORLD_VIEW_PROJECTION_MATRIX = 0x4E,
+ CONST_SRC_CODE_INVERSE_WORLD_VIEW_PROJECTION_MATRIX = 0x4F,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX = 0x50,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX = 0x51,
+ CONST_SRC_CODE_SHADOW_LOOKUP_MATRIX = 0x52,
+ CONST_SRC_CODE_INVERSE_SHADOW_LOOKUP_MATRIX = 0x53,
+ CONST_SRC_CODE_TRANSPOSE_SHADOW_LOOKUP_MATRIX = 0x54,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_SHADOW_LOOKUP_MATRIX = 0x55,
+ CONST_SRC_CODE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x56,
+ CONST_SRC_CODE_INVERSE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x57,
+ CONST_SRC_CODE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x58,
+ CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX = 0x59,
+ CONST_SRC_TOTAL_COUNT = 0x5A,
+ CONST_SRC_NONE = 0x5B,
+ };
+}
diff --git a/src/CODO/Zone.cpp b/src/CODO/Zone.cpp
new file mode 100644
index 0000000..a678650
--- /dev/null
+++ b/src/CODO/Zone.cpp
@@ -0,0 +1,298 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+namespace ZoneTool::CODO
+{
+ IAsset* Zone::find_asset(std::int32_t type, const std::string& name)
+ {
+ for (auto idx = 0u; idx < m_assets.size(); idx++)
+ {
+ if (m_assets[idx]->type() == type && m_assets[idx]->name() == name)
+ {
+ return m_assets[idx].get();
+ }
+ }
+
+ return nullptr;
+ }
+
+ void* Zone::get_asset_pointer(std::int32_t type, const std::string& name)
+ {
+ for (auto idx = 0u; idx < m_assets.size(); idx++)
+ {
+ if (m_assets[idx]->type() == type && m_assets[idx]->name() == name)
+ {
+ auto ptr = reinterpret_cast((3 << 28) | ((this->m_assetbase + (8 * idx) + 4) & 0x0FFFFFFF) +
+ 1);
+ // ZONETOOL_INFO("Asset pointer is %u", ptr);
+ return ptr;
+ }
+ }
+
+ return nullptr;
+ }
+
+ void Zone::add_asset_of_type_by_pointer(std::int32_t type, void* pointer)
+ {
+#ifdef USE_VMPROTECT
+ VMProtectBeginUltra("IW4::Zone::AddAssetOfTypePtr");
+#endif
+
+ // don't add asset if it already exists
+ for (std::size_t idx = 0; idx < m_assets.size(); idx++)
+ {
+ if (m_assets[idx]->type() == type && m_assets[idx]->pointer() == pointer)
+ {
+ return;
+ }
+ }
+
+#define DECLARE_ASSET(__type__, __interface__) \
+ if (type == __type__) \
+ { \
+ auto asset = std::make_shared < __interface__ >(); \
+ asset->init(pointer, this->m_zonemem); \
+ asset->load_depending(this); \
+ m_assets.push_back(asset); \
+ }
+
+ // declare asset interfaces
+ // DECLARE_ASSET(xmodelsurfs, IXSurface);
+ // DECLARE_ASSET(image, IGfxImage);
+ // DECLARE_ASSET(pixelshader, IPixelShader);
+ // DECLARE_ASSET(vertexshader, IVertexShader);
+ // DECLARE_ASSET(vertexdecl, IVertexDecl);
+
+#ifdef USE_VMPROTECT
+ VMProtectEnd();
+#endif
+ }
+
+ void Zone::add_asset_of_type(std::int32_t type, const std::string& name)
+ {
+#ifdef USE_VMPROTECT
+ VMProtectBeginUltra("IW4::Zone::AddAssetOfType");
+#endif
+
+ // don't add asset if it already exists
+ if (get_asset_pointer(type, name))
+ {
+ return;
+ }
+
+#define DECLARE_ASSET(__type__, __interface__) \
+ if (type == __type__) \
+ { \
+ auto asset = std::make_shared < __interface__ >(); \
+ asset->init(name, this->m_zonemem.get()); \
+ asset->load_depending(this); \
+ m_assets.push_back(asset); \
+ }
+
+ // declare asset interfaces
+ // DECLARE_ASSET(xanim, IXAnimParts);
+ // DECLARE_ASSET(pixelshader, IPixelShader);
+ // DECLARE_ASSET(vertexdecl, IVertexDecl);
+ // DECLARE_ASSET(vertexshader, IVertexShader);
+ // DECLARE_ASSET(techset, ITechset);
+ // DECLARE_ASSET(image, IGfxImage);
+ // DECLARE_ASSET(material, IMaterial)
+ // DECLARE_ASSET(xmodelsurfs, IXSurface);
+ // DECLARE_ASSET(xmodel, IXModel);
+ // DECLARE_ASSET(map_ents, IMapEnts);
+ // DECLARE_ASSET(rawfile, IRawFile);
+ // DECLARE_ASSET(com_map, IComWorld);
+ // DECLARE_ASSET(font, IFontDef);
+ DECLARE_ASSET(localize, ILocalizeEntry);
+ // DECLARE_ASSET(physpreset, IPhysPreset);
+ // DECLARE_ASSET(phys_collmap, IPhysCollmap);
+ DECLARE_ASSET(stringtable, IStringTable);
+ // DECLARE_ASSET(sound, ISound);
+ // DECLARE_ASSET(loaded_sound, ILoadedSound);
+ // DECLARE_ASSET(sndcurve, ISoundCurve);
+ // DECLARE_ASSET(game_map_mp, IGameWorldMp);
+ // DECLARE_ASSET(game_map_sp, IGameWorldSp);
+ // DECLARE_ASSET(fx_map, IFxWorld);
+ // DECLARE_ASSET(tracer, ITracerDef);
+ // DECLARE_ASSET(gfx_map, IGfxWorld);
+ // DECLARE_ASSET(col_map_mp, IClipMap);
+ // DECLARE_ASSET(fx, IFxEffectDef);
+ // DECLARE_ASSET(lightdef, ILightDef);
+ //DECLARE_ASSET(weapon, IWeaponDef); //still a work in progress, the CPP file isnt complete
+ //DECLARE_ASSET(structureddatadef, IStructuredDataDef);
+
+#ifdef USE_VMPROTECT
+ VMProtectEnd();
+#endif
+ }
+
+ void Zone::add_asset_of_type(const std::string& type, const std::string& name)
+ {
+ std::int32_t itype = m_linker->type_to_int(type);
+ this->add_asset_of_type(itype, name);
+ }
+
+ std::int32_t Zone::get_type_by_name(const std::string& type)
+ {
+ return m_linker->type_to_int(type);
+ }
+
+ void Zone::build(ZoneBuffer* buf)
+ {
+ auto startTime = GetTickCount64();
+
+ // make a folder in main, for the map images
+ std::filesystem::create_directories("main\\" + this->name_ + "\\images");
+
+ ZONETOOL_INFO("Compiling fastfile \"%s\"...", this->name_.data());
+
+ constexpr std::size_t num_streams = 8;
+ XZoneMemory mem;
+
+ std::size_t headersize = sizeof XZoneMemory;
+ memset(&mem, 0, headersize);
+
+ auto zone = buf->at>();
+
+ // write zone header
+ buf->write(&mem);
+
+ std::uintptr_t pad = 0xFFFFFFFF;
+ std::uintptr_t zero = 0;
+
+ // write asset types to header
+ for (auto i = 0u; i < m_assets.size(); i++)
+ {
+ m_assets[i]->prepare(buf, this->m_zonemem.get());
+ }
+
+ // write scriptstring count
+ std::uint32_t stringcount = buf->scriptstring_count();
+ buf->write(&stringcount);
+ buf->write(stringcount > 0 ? (&pad) : (&zero));
+
+ // write asset count
+ std::uint32_t asset_count = m_assets.size();
+ buf->write(&asset_count);
+ buf->write(asset_count > 0 ? (&pad) : (&zero));
+
+ // push stream
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ if (stringcount)
+ {
+ // write pointer for every scriptstring
+ for (std::size_t idx = 0; idx < stringcount; idx++)
+ {
+ buf->write(&pad);
+ }
+
+ // write scriptstrings
+ buf->align(3);
+ for (std::size_t idx = 0; idx < stringcount; idx++)
+ {
+ buf->write_str(buf->get_scriptstring(idx));
+ }
+ }
+
+ buf->pop_stream();
+ buf->push_stream(3);
+
+ // align buffer
+ buf->align(3);
+
+ // set asset ptr base
+ this->m_assetbase = buf->stream_offset(3);
+
+ // write asset types to header
+ for (auto i = 0u; i < asset_count; i++)
+ {
+ // write asset data to zone
+ auto type = m_assets[i]->type();
+ buf->write(&type);
+ buf->write(&pad);
+ }
+
+ // write assets
+ for (auto& asset : m_assets)
+ {
+ // push stream
+ buf->push_stream(0);
+ buf->align(3);
+
+ // write asset
+ asset->write(this, buf);
+
+ // pop stream
+ buf->pop_stream();
+ }
+
+ // pop stream
+ END_LOG_STREAM;
+ buf->pop_stream();
+
+ // update zone header
+ zone->size = buf->size() - headersize;
+ zone->externalsize = 0;
+
+ // Update stream data
+ for (int i = 0; i < num_streams; i++)
+ {
+ zone->streams[i] = buf->stream_offset(i);
+ }
+
+ // Dump zone to disk (DEBUGGING PURPOSES)
+ buf->save("debug\\" + this->name_ + ".zone");
+
+ // Compress buffer
+ auto buf_compressed = buf->compress_zlib();
+
+ // Generate FF header
+ auto header = this->m_zonemem->Alloc();
+ strcpy(header->header, "IWffu100");
+ header->version = 423;
+ header->allowOnlineUpdate = 0;
+
+ // Encrypt fastfile
+ // ZoneBuffer encrypted(buf_compressed);
+ // encrypted.encrypt();
+
+ // Save fastfile
+ ZoneBuffer fastfile(buf_compressed.size() + 21);
+ fastfile.init_streams(1);
+ fastfile.write_stream(header, 21);
+
+ fastfile.write(buf_compressed.data(), buf_compressed.size());
+
+ fastfile.save("zone\\english\\" + this->name_ + ".ff");
+
+ ZONETOOL_INFO("Successfully compiled fastfile \"%s\"!", this->name_.data());
+ ZONETOOL_INFO("Compiling took %u msec.", GetTickCount64() - startTime);
+
+ // this->m_linker->UnloadZones();
+ }
+
+ Zone::Zone(std::string name, ILinker* linker)
+ {
+ currentzone = name;
+
+ this->m_linker = linker;
+ this->name_ = name;
+
+ this->m_zonemem = std::make_shared(MAX_ZONE_SIZE);
+ }
+
+ Zone::~Zone()
+ {
+ // wipe all assets
+ m_assets.clear();
+ }
+}
diff --git a/src/CODO/Zone.hpp b/src/CODO/Zone.hpp
new file mode 100644
index 0000000..f79f5ca
--- /dev/null
+++ b/src/CODO/Zone.hpp
@@ -0,0 +1,69 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+extern std::string currentzone;
+
+// #include "Assets/RawFile.hpp"
+// #include "Assets/PhysPreset.hpp"
+// #include "Assets/WeaponDef.hpp"
+// #include "Assets/VertexDecl.hpp"
+// #include "Assets/PixelShader.hpp"
+// #include "Assets/VertexShader.hpp"
+// #include "Assets/Techset.hpp"
+// #include "Assets/GfxImage.hpp"
+// #include "Assets/Material.hpp"
+// #include "Assets/XSurface.hpp"
+// #include "Assets/Sound.hpp"
+// #include "Assets/LoadedSound.hpp"
+// #include "Assets/SoundCurve.hpp"
+// #include "Assets/FontDef.hpp"
+// #include "Assets/PhysCollmap.hpp"
+// #include "Assets/Xmodel.hpp"
+// #include "Assets/GameWorldMp.hpp"
+// #include "Assets/GameWorldSp.hpp"
+// #include "Assets/FxWorld.hpp"
+// #include "Assets/MapEnts.hpp"
+// #include "Assets/ComWorld.hpp"
+// #include "Assets/XAnimParts.hpp"
+#include "Assets/StringTable.hpp"
+#include "Assets/LocalizeEntry.hpp"
+// #include "Assets/TracerDef.hpp"
+// #include "Assets/GfxWorld.hpp"
+// #include "Assets/ClipMap.hpp"
+// #include "Assets/FxEffectDef.hpp"
+// #include "Assets/LightDef.hpp"
+
+namespace ZoneTool::CODO
+{
+ class Zone : public IZone
+ {
+ private:
+ std::uintptr_t m_assetbase;
+ std::string name_;
+ ILinker* m_linker;
+ std::vector> m_assets;
+ std::shared_ptr m_zonemem;
+
+ public:
+ Zone(std::string name, ILinker* linker);
+ ~Zone();
+
+ IAsset* find_asset(std::int32_t type, const std::string& name) override;
+ void* Zone::get_asset_pointer(std::int32_t type, const std::string& name) override;
+
+ void add_asset_of_type_by_pointer(std::int32_t type, void* pointer) override;
+
+ void add_asset_of_type(std::int32_t type, const std::string& name) override;
+ void add_asset_of_type(const std::string& type, const std::string& name) override;
+ std::int32_t get_type_by_name(const std::string& type) override;
+
+ void build(ZoneBuffer* buf) override;
+ };
+}
diff --git a/src/CODO/stdafx.cpp b/src/CODO/stdafx.cpp
new file mode 100644
index 0000000..a55cad6
--- /dev/null
+++ b/src/CODO/stdafx.cpp
@@ -0,0 +1,9 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
diff --git a/src/CODO/stdafx.hpp b/src/CODO/stdafx.hpp
new file mode 100644
index 0000000..8c80879
--- /dev/null
+++ b/src/CODO/stdafx.hpp
@@ -0,0 +1,29 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+#define WIN32_LEAN_AND_MEAN
+#define _CRT_SECURE_NO_WARNINGS
+
+#include
+
+#undef min
+#undef max
+#undef add
+
+#include
+#include
+#include
+#include
+
+// Namespaces
+using namespace std::literals;
+using namespace string_literals;
+
+#include "CODO.hpp"
diff --git a/src/IW3.lua b/src/IW3.lua
new file mode 100644
index 0000000..588ada4
--- /dev/null
+++ b/src/IW3.lua
@@ -0,0 +1,35 @@
+IW3 = {}
+
+function IW3:include()
+ includedirs {
+ path.join(ProjectFolder(), "IW3")
+ }
+end
+
+function IW3:link()
+ self:include()
+ links {
+ "IW3"
+ }
+end
+
+function IW3:project()
+ local folder = ProjectFolder();
+
+ project "IW3"
+ kind "StaticLib"
+ language "C++"
+
+ pchheader "stdafx.hpp"
+ pchsource(path.join(folder, "IW3/stdafx.cpp"))
+
+ files {
+ path.join(folder, "IW3/**.h"),
+ path.join(folder, "IW3/**.hpp"),
+ path.join(folder, "IW3/**.cpp")
+ }
+
+ self:include()
+ IW4:include()
+ ZoneUtils:include()
+end
\ No newline at end of file
diff --git a/src/IW3/Assets/ClipMap.cpp b/src/IW3/Assets/ClipMap.cpp
new file mode 100644
index 0000000..0c2b7e9
--- /dev/null
+++ b/src/IW3/Assets/ClipMap.cpp
@@ -0,0 +1,215 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: momo5502 (https://github.com/momo5502)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW4/Assets/ClipMap.hpp"
+#include "ClipMap.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void IClipMap::dump(clipMap_t* asset, ZoneMemory* mem)
+ {
+ if (!asset) return;
+
+ auto* iw4_clipmap = mem->Alloc();
+ memset(iw4_clipmap, 0, sizeof IW4::clipMap_t);
+
+ // convert clipmap to IW4 format
+ iw4_clipmap->name = asset->name;
+ iw4_clipmap->isInUse = asset->isInUse;
+
+ iw4_clipmap->numCPlanes = asset->planeCount;
+ iw4_clipmap->cPlanes = (IW4::cplane_s*)asset->planes;
+
+ iw4_clipmap->numStaticModels = (int)asset->numStaticModels;
+ iw4_clipmap->staticModelList = mem->Alloc(iw4_clipmap->numStaticModels);
+ for (unsigned int i = 0; i < asset->numStaticModels; ++i)
+ {
+ std::memcpy(&iw4_clipmap->staticModelList[i], &asset->staticModelList[i].xmodel,
+ sizeof(IW4::cStaticModel_s));
+ iw4_clipmap->staticModelList[i].absBounds.compute();
+ }
+
+ iw4_clipmap->numMaterials = (int)asset->numMaterials;
+ iw4_clipmap->materials = mem->Alloc(iw4_clipmap->numMaterials);
+ for (auto i = 0u; i < iw4_clipmap->numMaterials; i++)
+ {
+ iw4_clipmap->materials[i].material = mem->StrDup(asset->materials[i].material);
+ iw4_clipmap->materials[i].contentFlags = asset->materials[i].contentFlags;
+ iw4_clipmap->materials[i].surfaceFlags = asset->materials[i].surfaceFlags;
+ }
+
+ iw4_clipmap->numCBrushSides = (int)asset->numBrushSides;
+ iw4_clipmap->cBrushSides = mem->Alloc(iw4_clipmap->numCBrushSides);
+
+ std::unordered_map mapped_brush_sides;
+
+ for (unsigned int i = 0; i < asset->numBrushSides; ++i)
+ {
+ mapped_brush_sides[&asset->brushsides[i]] = &iw4_clipmap->cBrushSides[i];
+
+ iw4_clipmap->cBrushSides[i].plane = (IW4::cplane_s*)asset->brushsides[i].plane;
+ iw4_clipmap->cBrushSides[i].materialNum = asset->brushsides[i].materialNum;
+ iw4_clipmap->cBrushSides[i].firstAdjacentSideOffset = (char)asset->brushsides[i].firstAdjacentSideOffset;
+ iw4_clipmap->cBrushSides[i].edgeCount = asset->brushsides[i].edgeCount;
+ }
+
+ iw4_clipmap->numCBrushEdges = (int)asset->numBrushEdges;
+ iw4_clipmap->cBrushEdges = (IW4::cbrushedge_t*)asset->brushEdges;
+
+ iw4_clipmap->numCNodes = (int)asset->numNodes;
+ iw4_clipmap->cNodes = (IW4::cNode_t*)asset->nodes;
+
+ iw4_clipmap->numCLeaf = (int)asset->numLeafs;
+ iw4_clipmap->cLeaf = mem->Alloc(iw4_clipmap->numCLeaf);
+ for (unsigned int i = 0; i < asset->numLeafs; ++i)
+ {
+ std::memcpy(&iw4_clipmap->cLeaf[i], &asset->leafs[i], sizeof(IW4::cLeaf_t));
+ iw4_clipmap->cLeaf[i].bounds.compute();
+ }
+
+ iw4_clipmap->numCLeafBrushNodes = (int)asset->leafbrushNodesCount;
+ iw4_clipmap->cLeafBrushNodes = (IW4::cLeafBrushNode_s*)asset->leafbrushNodes;
+
+ iw4_clipmap->numLeafBrushes = (int)asset->numLeafBrushes;
+ iw4_clipmap->leafBrushes = (short*)asset->leafbrushes;
+
+ iw4_clipmap->numLeafSurfaces = (int)asset->numLeafSurfaces;
+ iw4_clipmap->leafSurfaces = (int*)asset->leafsurfaces;
+
+ iw4_clipmap->numVerts = (int)asset->vertCount;
+ iw4_clipmap->verts = (IW4::VecInternal<3>*)asset->verts;
+
+ iw4_clipmap->numTriIndices = asset->triCount;
+ iw4_clipmap->triIndices = (short*)asset->triIndices;
+ iw4_clipmap->triEdgeIsWalkable = asset->triEdgeIsWalkable;
+
+ iw4_clipmap->numCollisionBorders = asset->borderCount;
+ iw4_clipmap->collisionBorders = (IW4::CollisionBorder*)asset->borders;
+
+ iw4_clipmap->numCollisionPartitions = asset->partitionCount;
+ iw4_clipmap->collisionPartitions = (IW4::CollisionPartition*)asset->partitions;
+
+ iw4_clipmap->numCollisionAABBTrees = asset->aabbTreeCount;
+ iw4_clipmap->collisionAABBTrees = mem->Alloc(iw4_clipmap->numCollisionAABBTrees);
+ for (int i = 0; i < asset->aabbTreeCount; ++i)
+ {
+ std::memcpy(&iw4_clipmap->collisionAABBTrees[i].origin, &asset->aabbTrees[i].origin, 12);
+ std::memcpy(&iw4_clipmap->collisionAABBTrees[i].halfSize, &asset->aabbTrees[i].halfSize, 12);
+ iw4_clipmap->collisionAABBTrees[i].materialIndex = asset->aabbTrees[i].materialIndex;
+ iw4_clipmap->collisionAABBTrees[i].childCount = asset->aabbTrees[i].childCount;
+ iw4_clipmap->collisionAABBTrees[i].u.firstChildIndex = asset->aabbTrees[i].u.firstChildIndex;
+ }
+
+ // cmodels!
+ iw4_clipmap->numCModels = (int)asset->numSubModels;
+ iw4_clipmap->cModels = mem->Alloc(iw4_clipmap->numCModels);
+ for (unsigned int i = 0; i < asset->numSubModels; ++i)
+ {
+ std::memcpy(&iw4_clipmap->cModels[i], &asset->cmodels[i], sizeof(IW4::cmodel_t));
+ iw4_clipmap->cModels[i].bounds.compute();
+ iw4_clipmap->cModels[i].leaf.bounds.compute();
+ }
+
+ iw4_clipmap->numBrushes = (short)asset->numBrushes;
+ iw4_clipmap->brushes = mem->Alloc(iw4_clipmap->numBrushes);
+ iw4_clipmap->brushBounds = mem->Alloc(iw4_clipmap->numBrushes);
+ iw4_clipmap->brushContents = mem->Alloc(iw4_clipmap->numBrushes);
+ for (unsigned int i = 0; i < asset->numBrushes; ++i)
+ {
+ std::memcpy(&iw4_clipmap->brushes[i].axialMaterialNum, &asset->brushes[i].axialMaterialNum,
+ sizeof(iw4_clipmap->brushes[i].axialMaterialNum));
+ std::memcpy(&iw4_clipmap->brushes[i].firstAdjacentSideOffsets,
+ &asset->brushes[i].firstAdjacentSideOffsets,
+ sizeof(iw4_clipmap->brushes[i].firstAdjacentSideOffsets));
+ std::memcpy(&iw4_clipmap->brushes[i].edgeCount, &asset->brushes[i].edgeCount,
+ sizeof(iw4_clipmap->brushes[i].edgeCount));
+
+ iw4_clipmap->brushes[i].numsides = asset->brushes[i].numsides;
+ iw4_clipmap->brushes[i].sides = mapped_brush_sides.find(asset->brushes[i].sides)->second;
+ iw4_clipmap->brushes[i].edge = asset->brushes[i].baseAdjacentSide;
+ iw4_clipmap->brushes[i].numsides = asset->brushes[i].numsides;
+
+ iw4_clipmap->brushBounds[i].compute(asset->brushes[i].mins, asset->brushes[i].maxs);
+
+ iw4_clipmap->brushContents[i] = asset->brushes[i].contents;
+ }
+
+ iw4_clipmap->smodelNodeCount = 1;
+ iw4_clipmap->smodelNodes = mem->Alloc();
+ if (asset->numStaticModels == 0)
+ {
+ iw4_clipmap->smodelNodes[0].bounds.halfSize[0] = -131072.000f;
+ iw4_clipmap->smodelNodes[0].bounds.halfSize[1] = -131072.000f;
+ iw4_clipmap->smodelNodes[0].bounds.halfSize[2] = -131072.000f;
+ }
+ else
+ {
+ float maxs[3];
+ float mins[3];
+
+ maxs[0] = asset->staticModelList[0].absmax[0];
+ maxs[1] = asset->staticModelList[1].absmax[1];
+ maxs[2] = asset->staticModelList[2].absmax[2];
+
+ mins[0] = asset->staticModelList[0].absmin[0];
+ mins[1] = asset->staticModelList[1].absmin[1];
+ mins[2] = asset->staticModelList[2].absmin[2];
+
+ for (unsigned int i = 1; i < asset->numStaticModels; i++)
+ {
+ maxs[0] = max(maxs[0], asset->staticModelList[i].absmax[0]);
+ maxs[1] = max(maxs[1], asset->staticModelList[i].absmax[1]);
+ maxs[2] = max(maxs[2], asset->staticModelList[i].absmax[2]);
+
+ mins[0] = min(mins[0], asset->staticModelList[i].absmin[0]);
+ mins[1] = min(mins[1], asset->staticModelList[i].absmin[1]);
+ mins[2] = min(mins[2], asset->staticModelList[i].absmin[2]);
+ }
+
+ iw4_clipmap->smodelNodes[0].bounds.compute(mins, maxs);
+ iw4_clipmap->smodelNodes[0].childCount = static_cast(asset->numStaticModels);
+ iw4_clipmap->smodelNodes[0].firstChild = 0;
+ }
+
+ iw4_clipmap->mapEnts = mem->Alloc(); // asset->mapEnts;
+ memcpy(iw4_clipmap->mapEnts, asset->mapEnts, sizeof MapEnts);
+
+ iw4_clipmap->mapEnts->stageCount = 1;
+ iw4_clipmap->mapEnts->stageNames = mem->Alloc();
+ iw4_clipmap->mapEnts->stageNames[0].stageName = mem->StrDup("stage 0");
+ iw4_clipmap->mapEnts->stageNames[0].triggerIndex = 0x400;
+ iw4_clipmap->mapEnts->stageNames[0].sunPrimaryLightIndex = 0x1;
+
+ iw4_clipmap->dynEntCount[0] = asset->dynEntCount[0];
+ iw4_clipmap->dynEntCount[1] = asset->dynEntCount[1];
+
+ iw4_clipmap->dynEntDefList[0] = (IW4::DynEntityDef*)asset->dynEntDefList[0];
+ iw4_clipmap->dynEntDefList[1] = (IW4::DynEntityDef*)asset->dynEntDefList[1];
+
+ iw4_clipmap->dynEntPoseList[0] = (IW4::DynEntityPose*)asset->dynEntPoseList[0];
+ iw4_clipmap->dynEntPoseList[1] = (IW4::DynEntityPose*)asset->dynEntPoseList[1];
+
+ iw4_clipmap->dynEntClientList[0] = (IW4::DynEntityClient*)asset->dynEntClientList[0];
+ iw4_clipmap->dynEntClientList[1] = (IW4::DynEntityClient*)asset->dynEntClientList[1];
+
+ iw4_clipmap->dynEntCollList[0] = (IW4::DynEntityColl*)asset->dynEntCollList[0];
+ iw4_clipmap->dynEntCollList[1] = (IW4::DynEntityColl*)asset->dynEntCollList[1];
+
+ iw4_clipmap->checksum = asset->checksum;
+
+ //iw4_clipmap->stageCount = 1;
+ //iw4_clipmap-> = mem->Alloc();
+
+
+ IW4::IClipMap::dump(iw4_clipmap);
+ }
+ }
+}
diff --git a/src/IW3/Assets/ClipMap.hpp b/src/IW3/Assets/ClipMap.hpp
new file mode 100644
index 0000000..fc2c88c
--- /dev/null
+++ b/src/IW3/Assets/ClipMap.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: momo5502 (https://github.com/momo5502)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IClipMap
+ {
+ public:
+ static void dump(clipMap_t* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/ComWorld.cpp b/src/IW3/Assets/ComWorld.cpp
new file mode 100644
index 0000000..48200bb
--- /dev/null
+++ b/src/IW3/Assets/ComWorld.cpp
@@ -0,0 +1,18 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "IW4/Assets/ComWorld.hpp"
+
+namespace ZoneTool::IW3
+{
+ void IComWorld::dump(ComWorld* asset, [[maybe_unused]] ZoneMemory* mem)
+ {
+ IW4::IComWorld::dump(reinterpret_cast(asset));
+ }
+}
diff --git a/src/IW3/Assets/ComWorld.hpp b/src/IW3/Assets/ComWorld.hpp
new file mode 100644
index 0000000..f2f7cf7
--- /dev/null
+++ b/src/IW3/Assets/ComWorld.hpp
@@ -0,0 +1,18 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool::IW3
+{
+ class IComWorld
+ {
+ public:
+ static void dump(ComWorld* asset, ZoneMemory* mem);
+ };
+}
\ No newline at end of file
diff --git a/src/IW3/Assets/FxEffectDef.cpp b/src/IW3/Assets/FxEffectDef.cpp
new file mode 100644
index 0000000..f5545d5
--- /dev/null
+++ b/src/IW3/Assets/FxEffectDef.cpp
@@ -0,0 +1,54 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "IW4/Assets/FxEffectDef.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void IFxEffectDef::dump(FxEffectDef* asset, ZoneMemory* mem)
+ {
+ const auto iw4_fx = mem->Alloc();
+ memcpy(iw4_fx, asset, sizeof IW4::FxEffectDef);
+
+ const auto elem_count = iw4_fx->elemDefCountEmission + iw4_fx->elemDefCountOneShot + iw4_fx->elemDefCountLooping;
+ iw4_fx->elemDefs = mem->Alloc(elem_count);
+
+ for (auto i = 0; i < elem_count; i++)
+ {
+ memcpy(&iw4_fx->elemDefs[i], &asset->elemDefs[i], sizeof IW4::FxElemDef);
+
+ if (iw4_fx->elemDefs[i].elemType >= 5)
+ {
+ iw4_fx->elemDefs[i].elemType += 2;
+ }
+
+ iw4_fx->elemDefs[i].collBounds.compute(iw4_fx->elemDefs[i].collBounds.midPoint, iw4_fx->elemDefs[i].collBounds.halfSize);
+
+ if (iw4_fx->elemDefs[i].elemType == 3 && iw4_fx->elemDefs[i].extended.trailDef)
+ {
+ iw4_fx->elemDefs[i].extended.trailDef = mem->Alloc();
+ iw4_fx->elemDefs[i].extended.trailDef->scrollTimeMsec = asset->elemDefs[i].trailDef->scrollTimeMsec;
+ iw4_fx->elemDefs[i].extended.trailDef->repeatDist = asset->elemDefs[i].trailDef->repeatDist;
+ iw4_fx->elemDefs[i].extended.trailDef->vertCount = asset->elemDefs[i].trailDef->vertCount;
+ iw4_fx->elemDefs[i].extended.trailDef->verts = reinterpret_cast(asset->elemDefs[i].trailDef->verts);
+ iw4_fx->elemDefs[i].extended.trailDef->indCount = asset->elemDefs[i].trailDef->indCount;
+ iw4_fx->elemDefs[i].extended.trailDef->inds = asset->elemDefs[i].trailDef->inds;
+ }
+ else
+ {
+ iw4_fx->elemDefs[i].extended.trailDef = nullptr;
+ }
+ }
+
+ IW4::IFxEffectDef::dump(iw4_fx);
+ }
+ }
+}
diff --git a/src/IW3/Assets/FxEffectDef.hpp b/src/IW3/Assets/FxEffectDef.hpp
new file mode 100644
index 0000000..e8787a5
--- /dev/null
+++ b/src/IW3/Assets/FxEffectDef.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IFxEffectDef
+ {
+ public:
+ static void dump(FxEffectDef* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/GameWorldMp.cpp b/src/IW3/Assets/GameWorldMp.cpp
new file mode 100644
index 0000000..d9814b0
--- /dev/null
+++ b/src/IW3/Assets/GameWorldMp.cpp
@@ -0,0 +1,20 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void IGameWorldMp::dump(GameWorldMp* asset)
+ {
+ // lol, GameWorldMp contains no data in IW3
+ }
+ }
+}
diff --git a/src/IW3/Assets/GameWorldMp.hpp b/src/IW3/Assets/GameWorldMp.hpp
new file mode 100644
index 0000000..dd42f8a
--- /dev/null
+++ b/src/IW3/Assets/GameWorldMp.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IGameWorldMp
+ {
+ public:
+ static void dump(GameWorldMp* asset);
+ };
+ }
+}
diff --git a/src/IW3/Assets/GfxImage.cpp b/src/IW3/Assets/GfxImage.cpp
new file mode 100644
index 0000000..a2b739b
--- /dev/null
+++ b/src/IW3/Assets/GfxImage.cpp
@@ -0,0 +1,54 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW4/Assets/GfxImage.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ IW4::GfxImage* IGfxImage::GenerateIW4Image(GfxImage* image, ZoneMemory* mem)
+ {
+ auto* iw4_image = mem->Alloc();
+
+ // copy image data
+ iw4_image->mapType = image->mapType;
+ iw4_image->semantic = image->semantic;
+ iw4_image->category = image->category;
+ iw4_image->dataLen1 = image->cardMemory.platform[0];
+ iw4_image->dataLen2 = image->cardMemory.platform[1];
+ iw4_image->width = image->width;
+ iw4_image->height = image->height;
+ iw4_image->depth = image->depth;
+ iw4_image->pad = image->delayLoadPixels;
+ iw4_image->name = (char*)image->name;
+
+ // alloc texture
+ iw4_image->texture = (IW4::GfxImageLoadDef*)image->texture.loadDef;
+
+ return iw4_image;
+ }
+
+ void IGfxImage::dump(GfxImage* asset, ZoneMemory* mem)
+ {
+ if (!asset)
+ {
+ return;
+ }
+
+ ZONETOOL_INFO("dumping map image %s", asset->name);
+
+ // alloc IW4 image
+ auto* iw4_image = IGfxImage::GenerateIW4Image(asset, mem);
+
+ // dump IW4 image
+ IW4::IGfxImage::dump(iw4_image);
+ }
+ }
+}
diff --git a/src/IW3/Assets/GfxImage.hpp b/src/IW3/Assets/GfxImage.hpp
new file mode 100644
index 0000000..afb084c
--- /dev/null
+++ b/src/IW3/Assets/GfxImage.hpp
@@ -0,0 +1,22 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IGfxImage
+ {
+ public:
+ static IW4::GfxImage* GenerateIW4Image(GfxImage* image, ZoneMemory* mem);
+ static void dump(GfxImage* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/GfxWorld.cpp b/src/IW3/Assets/GfxWorld.cpp
new file mode 100644
index 0000000..cfd3581
--- /dev/null
+++ b/src/IW3/Assets/GfxWorld.cpp
@@ -0,0 +1,353 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW4/Assets/GfxWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void IGfxWorld::dump(GfxWorld* world, ZoneMemory* mem)
+ {
+ if (!world) return;
+
+ IW4::GfxSky sky;
+ IW4::GfxWorld map;
+ ZeroMemory(&sky, sizeof(sky));
+ ZeroMemory(&map, sizeof(map));
+
+ map.name = world->name;
+ map.baseName = world->baseName;
+ map.planeCount = world->planeCount;
+ map.nodeCount = world->nodeCount;
+ map.surfaceCount = world->surfaceCount;
+
+ map.skyCount = 1;
+ map.skies = &sky;
+
+ sky.skyImage = (IW4::GfxImage*)world->skyImage;
+ sky.skySamplerState = world->skySamplerState & 0xFF;
+ sky.skyStartSurfs = (uint32_t*)world->skyStartSurfs;
+ sky.skySurfCount = world->skySurfCount;
+
+ map.sunPrimaryLightIndex = world->sunPrimaryLightIndex;
+ map.primaryLightCount = world->primaryLightCount;
+
+ // map.dpvsPlanes = world->dpvsPlanes;
+ memcpy(&map.dpvsPlanes, &world->dpvsPlanes, sizeof world->dpvsPlanes);
+
+ // AABBTree data is stored as part of the cells.
+ // However, in IW4 it's not, so we have to extract the data
+ if (world->cells)
+ {
+ map.aabbTreeCounts = mem->Alloc(world->dpvsPlanes.cellCount);
+ map.aabbTree = mem->Alloc(world->dpvsPlanes.cellCount);
+ map.cells = mem->Alloc(world->dpvsPlanes.cellCount);
+
+ for (int i = 0; i < world->dpvsPlanes.cellCount; ++i)
+ {
+ map.aabbTreeCounts[i].aabbTreeCount = world->cells[i].aabbTreeCount;
+
+ map.cells[i].bounds.compute(world->cells[i].mins, world->cells[i].maxs); // Verified
+ map.cells[i].portalCount = world->cells[i].portalCount;
+ map.cells[i].reflectionProbeCount = world->cells[i].reflectionProbeCount;
+ map.cells[i].reflectionProbes = world->cells[i].reflectionProbes;
+
+ if (world->cells[i].aabbTree)
+ {
+ map.aabbTree[i].aabbtree = mem->Alloc(world->cells[i].aabbTreeCount);
+ std::memcpy(map.aabbTree[i].aabbtree, world->cells[i].aabbTree, sizeof(IW4::GfxAabbTree) * world->cells[i].aabbTreeCount);
+
+ for (int j = 0; j < world->cells[i].aabbTreeCount; ++j)
+ {
+ static_assert(sizeof IW4::GfxAabbTree == sizeof IW3::GfxAabbTree, "Size mismatch");
+ map.aabbTree[i].aabbtree[j].bounds.compute(world->cells[i].aabbTree[j].mins, world->cells[i].aabbTree[j].maxs); // Verified
+ }
+ }
+
+ if (world->cells[i].portals)
+ {
+ map.cells[i].portals = mem->Alloc(world->cells[i].portalCount);
+
+ // Map all portals, so we have them ready for the next loop (might be unnecessary, as they are mapped at runtime)
+ std::unordered_map portalMap = { { nullptr, nullptr } };
+ for (int j = 0; j < world->cells[i].portalCount; ++j)
+ {
+ portalMap[&world->cells[i].portals[j]] = &map.cells[i].portals[j];
+ }
+
+ for (int j = 0; j < world->cells[i].portalCount; ++j)
+ {
+ IW3::GfxPortal* portal = &world->cells[i].portals[j];
+ IW4::GfxPortal* destPortal = &map.cells[i].portals[j];
+
+ destPortal->cellIndex = static_cast(portal->cell - world->cells);
+ if (destPortal->cellIndex >= static_cast(world->dpvsPlanes.cellCount))
+ {
+ ZONETOOL_FATAL("Unable to calculate cell index. This should not happen!\n");
+ destPortal->cellIndex = 0;
+ }
+
+ destPortal->vertices = portal->vertices;
+ destPortal->vertexCount = portal->vertexCount;
+
+ destPortal->writable.isQueued = portal->writable.isQueued;
+ destPortal->writable.isAncestor = portal->writable.isAncestor;
+ destPortal->writable.recursionDepth = portal->writable.recursionDepth;
+ destPortal->writable.hullPointCount = portal->writable.hullPointCount;
+ destPortal->writable.hullPoints = portal->writable.hullPoints;
+
+ if (portalMap.find(portal->writable.queuedParent) != portalMap.end())
+ {
+ destPortal->writable.queuedParent = portalMap[portal->writable.queuedParent];
+ }
+ else
+ {
+ if (portal->writable.queuedParent) ZONETOOL_ERROR("Unmapped portal. This shouldn't happen. Nulling it...\n");
+ destPortal->writable.queuedParent = nullptr;
+ }
+
+ std::memcpy(destPortal->plane.coeffs, portal->plane.coeffs, sizeof(destPortal->plane.coeffs));
+ std::memcpy(destPortal->hullAxis, portal->hullAxis, sizeof(destPortal->hullAxis));
+ }
+ }
+ }
+ }
+
+ map.draw.reflectionProbeCount = world->reflectionProbeCount;
+ map.draw.reflectionProbeTextures = (IW4::GfxTexture*)world->reflectionProbeTextures;
+ map.draw.lightmapCount = world->lightmapCount;
+ map.draw.lightmaps = mem->Alloc(world->lightmapCount); // (IW4::GfxLightmapArray*)world->lightmaps;
+
+ for (auto i = 0; i < world->lightmapCount; i++)
+ {
+ if (world->lightmaps[i].primary)
+ {
+ IGfxImage::dump(world->lightmaps[i].primary, mem);
+ map.draw.lightmaps[i].primary = IGfxImage::GenerateIW4Image(world->lightmaps[i].primary, mem);
+ }
+
+ if (world->lightmaps[i].secondary)
+ {
+ IGfxImage::dump(world->lightmaps[i].secondary, mem);
+ map.draw.lightmaps[i].secondary = IGfxImage::GenerateIW4Image(world->lightmaps[i].secondary, mem);
+ }
+ }
+
+ map.draw.lightmapPrimaryTextures = (IW4::GfxTexture*)world->lightmapPrimaryTextures;
+ map.draw.lightmapSecondaryTextures = (IW4::GfxTexture*)world->lightmapSecondaryTextures;
+ map.draw.skyImage = IGfxImage::GenerateIW4Image(world->skyImage, mem);
+ map.draw.outdoorImage = IGfxImage::GenerateIW4Image(world->outdoorImage, mem);
+ map.draw.vertexCount = world->vertexCount;
+ memcpy(&map.draw.vd, &world->vd, sizeof world->vd);
+ map.draw.vertexLayerDataSize = world->vertexLayerDataSize;
+ memcpy(&map.draw.vld, &world->vld, sizeof world->vld);
+ map.draw.indexCount = world->indexCount;
+
+ // Split reflection images and probes
+ if (world->reflectionProbes)
+ {
+ map.draw.reflectionImages = mem->Alloc(world->reflectionProbeCount);
+ map.draw.reflectionProbes = mem->Alloc(world->reflectionProbeCount);
+
+ for (unsigned int i = 0; i < world->reflectionProbeCount; ++i)
+ {
+ map.draw.reflectionImages[i] = IGfxImage::GenerateIW4Image(world->reflectionProbes[i].reflectionImage, mem);
+ IGfxImage::dump(world->reflectionProbes[i].reflectionImage, mem);
+
+ std::memcpy(map.draw.reflectionProbes[i].offset, world->reflectionProbes[i].origin, sizeof(map.draw.reflectionProbes[i].offset));
+ }
+ }
+
+ memcpy(&map.lightGrid, &world->lightGrid, sizeof world->lightGrid);
+
+ assert(sizeof IW3::GfxBrushModel == 56);
+ assert(sizeof IW4::GfxBrushModel == 60);
+
+ map.bounds.compute(world->mins, world->maxs);
+
+ map.checksum = world->checksum;
+ map.materialMemoryCount = world->materialMemoryCount;
+ map.materialMemory = (IW4::MaterialMemory*)world->materialMemory;
+ memcpy(&map.sun, &world->sun, sizeof world->sun);
+
+ std::memcpy(map.outdoorLookupMatrix, world->outdoorLookupMatrix, sizeof(map.outdoorLookupMatrix));
+ map.outdoorImage = map.draw.outdoorImage; // (IW4::GfxImage*)world->outdoorImage;
+
+ IGfxImage::dump(world->outdoorImage, mem);
+
+ map.cellCasterBits[0] = world->cellCasterBits;
+ map.cellCasterBits[1] = world->cellCasterBits; // This mustn't be null!
+
+ map.sceneDynModel = (IW4::GfxSceneDynModel*)world->sceneDynModel;
+ map.sceneDynBrush = (IW4::GfxSceneDynBrush*)world->sceneDynBrush;
+
+ map.primaryLightEntityShadowVis = (unsigned char*)world->primaryLightEntityShadowVis;
+ map.primaryLightDynEntShadowVis[0] = world->primaryLightDynEntShadowVis[0];
+ map.primaryLightDynEntShadowVis[1] = world->primaryLightDynEntShadowVis[1];
+ map.primaryLightForModelDynEnt = world->nonSunPrimaryLightForModelDynEnt;
+
+ map.shadowGeom = (IW4::GfxShadowGeometry*)world->shadowGeom;
+ map.lightRegion = (IW4::GfxLightRegion*)world->lightRegion;
+
+ map.dpvs.smodelCount = world->dpvs.smodelCount;
+ map.dpvs.staticSurfaceCount = world->dpvs.staticSurfaceCount;
+ map.dpvs.staticSurfaceCountNoDecal = world->dpvs.staticSurfaceCountNoDecal;
+
+ // Not sure if correct
+ // update: slightly more sure but not much lol
+ map.dpvs.litOpaqueSurfsBegin = world->dpvs.litSurfsBegin;
+ map.dpvs.litOpaqueSurfsEnd = world->dpvs.decalSurfsEnd;
+
+ // these don't exist in iw3 so skip
+ map.dpvs.litTransSurfsBegin = world->dpvs.decalSurfsEnd;
+ map.dpvs.litTransSurfsEnd = world->dpvs.decalSurfsEnd;
+
+ // Skip those as well
+ map.dpvs.shadowCasterSurfsBegin = world->dpvs.decalSurfsEnd;
+ map.dpvs.shadowCasterSurfsEnd = world->dpvs.decalSurfsEnd;
+
+ map.dpvs.emissiveSurfsBegin = world->dpvs.emissiveSurfsBegin;
+ map.dpvs.emissiveSurfsEnd = world->dpvs.emissiveSurfsEnd;
+ map.dpvs.smodelVisDataCount = world->dpvs.smodelVisDataCount;
+ map.dpvs.surfaceVisDataCount = world->dpvs.surfaceVisDataCount;
+
+ std::memcpy(map.dpvs.smodelVisData, world->dpvs.smodelVisData, sizeof(map.dpvs.smodelVisData));
+ std::memcpy(map.dpvs.surfaceVisData, world->dpvs.surfaceVisData, sizeof(map.dpvs.surfaceVisData));
+
+ map.dpvs.sortedSurfIndex = world->dpvs.sortedSurfIndex;
+
+ if (world->dpvs.smodelInsts)
+ {
+ map.dpvs.smodelInsts = mem->Alloc(world->dpvs.smodelCount);
+
+ for (unsigned int i = 0; i < world->dpvs.smodelCount; ++i)
+ {
+ map.dpvs.smodelInsts[i].bounds.compute(world->dpvs.smodelInsts[i].mins, world->dpvs.smodelInsts[i].maxs); // Verified
+
+ // I guess the sun is always a good lighting source ;)
+ map.dpvs.smodelInsts[i].lightingOrigin[0] = world->sun.sunFxPosition[0];
+ map.dpvs.smodelInsts[i].lightingOrigin[1] = world->sun.sunFxPosition[1];
+ map.dpvs.smodelInsts[i].lightingOrigin[2] = world->sun.sunFxPosition[2];
+ }
+ }
+
+ if (world->dpvs.surfaces)
+ {
+ map.dpvs.surfaces = mem->Alloc(world->surfaceCount);
+ map.dpvs.surfacesBounds = mem->Alloc(world->surfaceCount);
+
+ assert(sizeof(IW3::srfTriangles_t) == sizeof(IW4::srfTriangles_t));
+
+ for (auto i = 0; i < world->surfaceCount; ++i)
+ {
+ std::memcpy(&map.dpvs.surfaces[i].tris, &world->dpvs.surfaces[i].tris, sizeof(IW4::srfTriangles_t));
+ map.dpvs.surfaces[i].material = (IW4::Material*)world->dpvs.surfaces[i].material;
+ map.dpvs.surfaces[i].lightmapIndex = world->dpvs.surfaces[i].lightmapIndex;
+ map.dpvs.surfaces[i].reflectionProbeIndex = world->dpvs.surfaces[i].reflectionProbeIndex;
+ map.dpvs.surfaces[i].primaryLightIndex = world->dpvs.surfaces[i].primaryLightIndex;
+ map.dpvs.surfaces[i].flags = world->dpvs.surfaces[i].flags;
+
+ map.dpvs.surfacesBounds[i].bounds.compute(world->dpvs.surfaces[i].bounds[0], world->dpvs.surfaces[i].bounds[1]); // Verified
+
+ assert(map.dpvs.surfaces[i].material != nullptr);
+ }
+ }
+
+ if (world->dpvs.smodelDrawInsts)
+ {
+ map.dpvs.smodelDrawInsts = mem->Alloc(world->dpvs.smodelCount);
+
+ for (unsigned int i = 0; i < world->dpvs.smodelCount; ++i)
+ {
+ std::memcpy(&map.dpvs.smodelDrawInsts[i].placement, &world->dpvs.smodelDrawInsts[i].placement, sizeof(GfxPackedPlacement));
+ std::memcpy(map.dpvs.smodelDrawInsts[i].cacheId, world->dpvs.smodelDrawInsts[i].smodelCacheIndex, sizeof(map.dpvs.smodelDrawInsts[i].cacheId));
+
+ map.dpvs.smodelDrawInsts[i].model = (IW4::XModel*)world->dpvs.smodelDrawInsts[i].model;
+ map.dpvs.smodelDrawInsts[i].cullDist = static_cast(world->dpvs.smodelDrawInsts[i].cullDist);
+ map.dpvs.smodelDrawInsts[i].reflectionProbeIndex = world->dpvs.smodelDrawInsts[i].reflectionProbeIndex;
+ map.dpvs.smodelDrawInsts[i].primaryLightIndex = world->dpvs.smodelDrawInsts[i].primaryLightIndex;
+ map.dpvs.smodelDrawInsts[i].lightingHandle = world->dpvs.smodelDrawInsts[i].lightingHandle;
+ map.dpvs.smodelDrawInsts[i].flags = world->dpvs.smodelDrawInsts[i].flags;
+
+ // This has been moved
+ if (world->dpvs.smodelInsts) map.dpvs.smodelDrawInsts[i].groundLighting.packed = world->dpvs.smodelInsts[i].groundLighting.packed;
+ }
+ }
+
+ map.dpvs.surfaceMaterials = (IW4::GfxDrawSurf*)world->dpvs.surfaceMaterials;
+ map.dpvs.surfaceCastsSunShadow = world->dpvs.surfaceCastsSunShadow;
+ map.dpvs.usageCount = world->dpvs.usageCount;
+
+ memcpy(&map.dpvsDyn, &world->dpvsDyn, sizeof world->dpvsDyn);
+
+ // Should we set that to true? :O
+ map.fogTypesAllowed = 3; // iw4_credits has 0x3
+
+ map.sortKeyLitDecal = 0x6;
+ map.sortKeyEffectDecal = 0x27;
+ map.sortKeyEffectAuto = 0x30;
+ map.sortKeyDistortion = 0x2b;
+
+ // sort models
+ map.modelCount = world->modelCount;
+ if (world->models)
+ {
+ map.models = mem->Alloc(world->modelCount);
+
+ std::vector models;
+ models.resize(world->modelCount);
+
+ for (auto i = 0; i < world->modelCount; ++i)
+ {
+ models[i].writable.bounds.compute(world->models[i].writable.mins, world->models[i].writable.maxs); // Irrelevant, runtime data
+ models[i].bounds.compute(world->models[i].bounds[0], world->models[i].bounds[1]); // Verified
+
+ auto* half_size = models[i].bounds.halfSize;
+ models[i].radius = std::sqrt(std::pow(half_size[0], 2) + std::pow(half_size[1], 2) + std::pow(half_size[2], 2));
+
+ models[i].surfaceCount = world->models[i].surfaceCount;
+ models[i].startSurfIndex = world->models[i].startSurfIndex;
+ models[i].surfaceCountNoDecal = world->models[i].surfaceCountNoDecal;
+ }
+
+ std::sort(models.begin(), models.end(), [](const IW4::GfxBrushModel& m1, const IW4::GfxBrushModel& m2)
+ {
+ return m1.startSurfIndex > m2.startSurfIndex;
+ });
+
+ std::memcpy(map.models, models.data(), sizeof(IW4::GfxBrushModel) * world->modelCount);
+ }
+
+ // sort triangles & vertices
+ auto tri_index = 0;
+ map.draw.indices = mem->Alloc(map.draw.indexCount);
+
+ for (auto i = 0; i < map.surfaceCount; i++)
+ {
+ auto* surface = &map.dpvs.surfaces[i];
+
+ // triangles
+ std::memcpy(&map.draw.indices[tri_index], &world->indices[surface->tris.baseIndex], surface->tris.triCount * 6);
+ surface->tris.baseIndex = tri_index;
+ tri_index += surface->tris.triCount * 3;
+ }
+
+ if (tri_index != map.draw.indexCount)
+ {
+ ZONETOOL_WARNING("Warning: Didn't sort all indicies for draw");
+ }
+
+ // Specify that it's a custom map
+ map.checksum = 0xDEADBEEF;
+
+ IW4::IGfxWorld::dump(&map);
+ }
+ }
+}
diff --git a/src/IW3/Assets/GfxWorld.hpp b/src/IW3/Assets/GfxWorld.hpp
new file mode 100644
index 0000000..c44ef35
--- /dev/null
+++ b/src/IW3/Assets/GfxWorld.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IGfxWorld
+ {
+ public:
+ static void dump(GfxWorld* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/LoadedSound.cpp b/src/IW3/Assets/LoadedSound.cpp
new file mode 100644
index 0000000..7b46518
--- /dev/null
+++ b/src/IW3/Assets/LoadedSound.cpp
@@ -0,0 +1,92 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void ILoadedSound::dump(LoadedSound* asset, ZoneMemory* mem)
+ {
+ if (asset->struct1.waveFormat != 1)
+ {
+ ZONETOOL_ERROR("Audio format other than PCM currently not supported. Sound: %s\n", asset->name);
+ return;
+ }
+
+ const auto fp = FileSystem::FileOpen("loaded_sound\\"s + asset->name, "wb");
+ if (!fp)
+ {
+ return;
+ }
+
+ // --- RIF HEADER
+ // ChunkID
+ char chunkID[] = { 'R', 'I', 'F', 'F' };
+ fwrite(chunkID, 4, 1, fp);
+
+ // ChunkSize
+ int subchunk1Size = 16;
+ int subchunk2Size = asset->struct1.dataLength;
+ int chunkSize = 4 + (8 + subchunk1Size) + (8 + subchunk2Size);
+ fwrite(&chunkSize, 4, 1, fp);
+
+ // Format
+ char format[] = { 'W', 'A', 'V', 'E' };
+ fwrite(format, 4, 1, fp);
+
+
+ // --- FMT SUBCHUNK
+ // Subchunk1ID
+ char subchunk1ID[] = { 'f', 'm', 't', ' ' };
+ fwrite(subchunk1ID, 4, 1, fp);
+
+ // Subchunk1Size
+ fwrite(&subchunk1Size, 4, 1, fp);
+
+ // AudioFormat
+ short audioFormat = asset->struct1.waveFormat;
+ fwrite(&audioFormat, 2, 1, fp);
+
+ // NumChannels
+ short numChannels = asset->struct1.channelCount;
+ fwrite(&numChannels, 2, 1, fp);
+
+ // SampleRate
+ int sampleRate = asset->struct1.sampleRate;
+ fwrite(&sampleRate, 4, 1, fp);
+
+ // ByteRate
+ int byteRate = asset->struct1.sampleRate * asset->struct1.channelCount * asset->struct1.bitPerChannel / 8;
+ fwrite(&byteRate, 4, 1, fp);
+
+ // BlockAlign
+ short blockAlign = asset->struct1.blockAlign;
+ fwrite(&blockAlign, 2, 1, fp);
+
+ // BitsPerSample
+ short bitsPerSample = asset->struct1.bitPerChannel;
+ fwrite(&bitsPerSample, 2, 1, fp);
+
+
+ // --- DATA SUBCHUNK
+ // Subchunk2ID
+ char subchunk2ID[] = { 'd', 'a', 't', 'a' };
+ fwrite(subchunk2ID, 4, 1, fp);
+
+ // Subchunk2Size
+ fwrite(&subchunk2Size, 4, 1, fp);
+
+ // Data
+ fwrite(asset->struct1.soundData, asset->struct1.dataLength, 1, fp);
+
+ FileSystem::FileClose(fp);
+ }
+ }
+}
diff --git a/src/IW3/Assets/LoadedSound.hpp b/src/IW3/Assets/LoadedSound.hpp
new file mode 100644
index 0000000..00bfbd4
--- /dev/null
+++ b/src/IW3/Assets/LoadedSound.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class ILoadedSound
+ {
+ public:
+ static void dump(LoadedSound* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/MapEnts.cpp b/src/IW3/Assets/MapEnts.cpp
new file mode 100644
index 0000000..e74617d
--- /dev/null
+++ b/src/IW3/Assets/MapEnts.cpp
@@ -0,0 +1,261 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: momo5502 (https://github.com/momo5502)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW4/Assets/MapEnts.hpp"
+#include "MapEnts.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ bool StartsWith(const std::string& haystack, const std::string& needle)
+ {
+ return (haystack.size() >= needle.size() && !strncmp(needle.data(), haystack.data(), needle.size()));
+ }
+
+ std::string StrToLower(std::string input)
+ {
+ std::transform(input.begin(), input.end(), input.begin(), ::tolower);
+ return input;
+ }
+
+ class Entities
+ {
+ public:
+ Entities()
+ {
+ };
+
+ Entities(const char* string, size_t lenPlusOne) : Entities(std::string(string, lenPlusOne - 1))
+ {
+ }
+
+ Entities(std::string buffer) : Entities() { this->parse(buffer); };
+
+ Entities(const Entities& obj) : entities(obj.entities)
+ {
+ };
+
+ std::string build()
+ {
+ std::string entityString;
+
+ for (auto& entity : this->entities)
+ {
+ entityString.append("{\n");
+
+ for (auto& property : entity)
+ {
+ entityString.push_back('"');
+ entityString.append(property.first);
+ entityString.append("\" \"");
+ entityString.append(property.second);
+ entityString.append("\"\n");
+ }
+
+ entityString.append("}\n");
+ }
+
+ return entityString;
+ }
+
+ std::vector getModels()
+ {
+ std::vector models;
+
+ for (auto& entity : this->entities)
+ {
+ if (entity.find("model") != entity.end())
+ {
+ std::string model = entity["model"];
+
+ if (!model.empty() && model[0] != '*' && model[0] != '?') // Skip brushmodels
+ {
+ if (std::find(models.begin(), models.end(), model) == models.end())
+ {
+ models.push_back(model);
+ }
+ }
+ }
+ }
+
+ return models;
+ }
+
+ void deleteTriggers()
+ {
+ for (auto i = this->entities.begin(); i != this->entities.end();)
+ {
+ if (i->find("classname") != i->end())
+ {
+ std::string classname = (*i)["classname"];
+ if (StartsWith(classname, "trigger_"))
+ {
+ i = this->entities.erase(i);
+ continue;
+ }
+ }
+
+ ++i;
+ }
+ }
+
+ void deleteWeapons(bool keepTurrets)
+ {
+ for (auto i = this->entities.begin(); i != this->entities.end();)
+ {
+ if (i->find("weaponinfo") != i->end() || (i->find("targetname") != i->end() && (*i)["targetname"] ==
+ "oldschool_pickup"s))
+ {
+ if (!keepTurrets || i->find("classname") == i->end() || (*i)["classname"] != "misc_turret"s)
+ {
+ i = this->entities.erase(i);
+ continue;
+ }
+ }
+
+ ++i;
+ }
+ }
+
+ void convertTurrets()
+ {
+ for (auto& entity : this->entities)
+ {
+ if (entity.find("classname") != entity.end())
+ {
+ if (entity["classname"] == "misc_turret"s)
+ {
+ entity["weaponinfo"] = "turret_minigun_mp";
+ entity["model"] = "weapon_minigun";
+ }
+ }
+ }
+ }
+
+ private:
+ enum
+ {
+ PARSE_AWAIT_KEY,
+ PARSE_READ_KEY,
+ PARSE_AWAIT_VALUE,
+ PARSE_READ_VALUE,
+ };
+
+ std::vector> entities;
+
+ void parse(std::string buffer)
+ {
+ int parseState = 0;
+ std::string key;
+ std::string value;
+ std::unordered_map entity;
+
+ for (unsigned int i = 0; i < buffer.size(); ++i)
+ {
+ const char character = buffer[i];
+ if (character == '{')
+ {
+ entity.clear();
+ }
+
+ switch (character)
+ {
+ case '{':
+ {
+ entity.clear();
+ break;
+ }
+
+ case '}':
+ {
+ this->entities.push_back(entity);
+ entity.clear();
+ break;
+ }
+
+ case '"':
+ {
+ if (parseState == PARSE_AWAIT_KEY)
+ {
+ key.clear();
+ parseState = PARSE_READ_KEY;
+ }
+ else if (parseState == PARSE_READ_KEY)
+ {
+ parseState = PARSE_AWAIT_VALUE;
+ }
+ else if (parseState == PARSE_AWAIT_VALUE)
+ {
+ value.clear();
+ parseState = PARSE_READ_VALUE;
+ }
+ else if (parseState == PARSE_READ_VALUE)
+ {
+ entity[StrToLower(key)] = value;
+ parseState = PARSE_AWAIT_KEY;
+ }
+ else
+ {
+ throw std::runtime_error("Parsing error!");
+ }
+ break;
+ }
+
+ default:
+ {
+ if (parseState == PARSE_READ_KEY) key.push_back(character);
+ else if (parseState == PARSE_READ_VALUE) value.push_back(character);
+
+ break;
+ }
+ }
+ }
+ }
+ };
+
+ void AdaptEntities(IW4::MapEnts* ents, ZoneMemory* mem)
+ {
+ std::string entString(ents->entityString, ents->numEntityChars - 1);
+
+ Entities mapEnts(entString);
+ mapEnts.deleteTriggers();
+ mapEnts.deleteWeapons(/*true*/false); // For now delete turrets, as we can't write weapons
+ mapEnts.convertTurrets();
+ entString = mapEnts.build();
+
+ ents->numEntityChars = entString.size() + 1;
+ ents->entityString = mem->Alloc(ents->numEntityChars);
+ std::memcpy((char*)ents->entityString, entString.data(), ents->numEntityChars);
+ }
+
+ void IMapEnts::dump(MapEnts* asset, ZoneMemory* mem)
+ {
+ if (!asset) return;
+
+ auto* mapents = mem->Alloc();
+ memset(mapents, 0, sizeof IW4::MapEnts);
+
+ mapents->name = asset->name;
+ mapents->entityString = asset->entityString;
+ mapents->numEntityChars = asset->numEntityChars;
+
+ mapents->stageCount = 1;
+ mapents->stageNames = mem->Alloc();
+ mapents->stageNames[0].stageName = mem->StrDup("stage 0");
+ mapents->stageNames[0].triggerIndex = 0x400;
+ mapents->stageNames[0].sunPrimaryLightIndex = 0x1;
+
+ // Remove unsupported stuff
+ AdaptEntities(mapents, mem);
+
+ IW4::IMapEnts::dump(mapents);
+ }
+ }
+}
diff --git a/src/IW3/Assets/MapEnts.hpp b/src/IW3/Assets/MapEnts.hpp
new file mode 100644
index 0000000..1ff7671
--- /dev/null
+++ b/src/IW3/Assets/MapEnts.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: momo5502 (https://github.com/momo5502)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IMapEnts
+ {
+ public:
+ static void dump(MapEnts* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/Material.cpp b/src/IW3/Assets/Material.cpp
new file mode 100644
index 0000000..a4c6bf1
--- /dev/null
+++ b/src/IW3/Assets/Material.cpp
@@ -0,0 +1,249 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+// Material parsing
+#define MATERIAL_INT(entry) \
+ mat->entry = matdata[#entry].get();
+
+#define MATERIAL_DUMP_INT(entry) \
+ matdata[#entry] = mat->entry;
+
+#define MATERIAL_DUMP_STRING(entry) \
+ matdata[#entry] = std::string(mat->entry);
+
+#define MATERIAL_DUMP_MATIMG_ARRAY(entry,size) \
+ nlohmann::json matimg##entry; \
+ for (int i = 0; i < size; i++) \
+ { \
+ nlohmann::json img##entry; \
+ img##entry["image"] = mat->entry[i].image->name; \
+ img##entry["semantic"] = (int)mat->entry[i].semantic; \
+ img##entry["sampleState"] = (int)mat->entry[i].sampleState; \
+ img##entry["lastCharacter"] = (char)mat->entry[i].secondLastCharacter; \
+ img##entry["firstCharacter"] = (char)mat->entry[i].firstCharacter; \
+ img##entry["typeHash"] = (unsigned int)mat->entry[i].typeHash; \
+ matimg##entry[i] = img##entry; \
+ } \
+ matdata[#entry] = matimg##entry;
+
+#define MATERIAL_DUMP_CONST_ARRAY(entry,size) \
+ nlohmann::json carr##entry; \
+ for (int i = 0; i < size; i++) \
+ { \
+ nlohmann::json cent##entry; \
+ cent##entry["name"] = mat->entry[i].name; \
+ nlohmann::json centliteral##entry; \
+ centliteral##entry[0] = mat->entry[i].literal[0]; \
+ centliteral##entry[1] = mat->entry[i].literal[1]; \
+ centliteral##entry[2] = mat->entry[i].literal[2]; \
+ centliteral##entry[3] = mat->entry[i].literal[3]; \
+ cent##entry["nameHash"] = mat->entry[i].nameHash; \
+ cent##entry["literal"] = centliteral##entry; \
+ carr##entry[i] = cent##entry; \
+ } \
+ matdata[#entry] = carr##entry;
+
+#define MATERIAL_DUMP_STATE_MAP(entry,size) \
+ nlohmann::json carr##entry; \
+ for (int i = 0; i < size; i++) \
+ { \
+ nlohmann::json cent##entry; \
+ cent##entry[0] = mat->entry[i].loadBits[0]; \
+ cent##entry[1] = mat->entry[i].loadBits[1]; \
+ carr##entry[i] = cent##entry; \
+ } \
+ matdata[#entry] = carr##entry;
+
+#define MATERIAL_DUMP_BITS_ENTRY(entry,size) \
+ nlohmann::json carr##entry; \
+ for (int i = 0; i < size; i++) \
+ { \
+ carr##entry[i] = mat->entry[i]; \
+ } \
+ matdata[#entry] = carr##entry;
+
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void IMaterial::dump_statebits(Material* mat)
+ {
+ if (mat && mat->techniqueSet)
+ {
+ ITechset::dump_statebits(va("iw3/%s", mat->techniqueSet->name), mat->stateBitsEntry);
+ }
+ }
+
+ //std::map mapped_keys
+ //{
+ // { 0, 43 },
+ // { 3, 0 },
+ // { 4, 1 },
+ // { 5, 2 },
+ // { 6, 3 },
+ // { 7, 4 },
+ // { 8, 5 },
+ // { 9, 6 },
+ // { 10, 7 },
+ // { 11, 8 },
+ // { 12, 9 },
+ // { 24, 13 },
+ // { 38, 24 },
+ // { 39, 25 },
+ // { 40, 26 },
+ // { 41, 27 },
+ // { 42, 28 },
+ // { 43, 29 },
+ // { 48, 48 },
+ // { 58, 51 },
+ // { 59, 33 },
+ //};
+
+ std::map mapped_keys
+ {
+ { 0, 43 },
+ { 3, 0 },
+ { 4, 1 },
+ { 5, 2 },
+ { 9, 6 }, // not sure!
+ { 10, 7 },
+ { 11, 8 }, // not sure!
+ { 12, 0 },
+ { 24, 9 },
+ { 38, 28 }, // not sure!
+ { 39, 29 },
+ { 43, 29 }, // was 47 but that crashes, not sure!
+ { 48, 48 },
+ { 59, 53 },
+ };
+
+ void IMaterial::dump(Material* mat, ZoneMemory* mem)
+ {
+ if (mat)
+ {
+ dump_statebits(mat);
+
+ auto path = "materials\\"s + mat->name;
+
+ auto file = FileSystem::FileOpen(path, "wb");
+ if (!file)
+ {
+ return;
+ }
+
+ nlohmann::json matdata;
+
+ MATERIAL_DUMP_STRING(name);
+
+ if (mat->techniqueSet)
+ {
+ matdata["techniqueSet->name"] = va("iw3/%s", mat->techniqueSet->name);
+ }
+
+ MATERIAL_DUMP_INT(gameFlags);
+ // MATERIAL_DUMP_INT(sortKey);
+ MATERIAL_DUMP_INT(animationX);
+ MATERIAL_DUMP_INT(animationY);
+
+ auto key_itr = mapped_keys.find(mat->sortKey);
+ if (key_itr != mapped_keys.end())
+ {
+ matdata["sortKey"] = key_itr->second;
+ }
+ else
+ {
+ matdata["sortKey"] = mat->sortKey;
+ ZONETOOL_WARNING("[%s]: sortKey %u is not mapped!", mat->name, mat->sortKey);
+ }
+
+ matdata["unknown"] = 0;
+
+ MATERIAL_DUMP_INT(surfaceTypeBits);
+ MATERIAL_DUMP_INT(stateFlags);
+ MATERIAL_DUMP_INT(cameraRegion);
+
+ MATERIAL_DUMP_CONST_ARRAY(constantTable, mat->constantCount);
+ MATERIAL_DUMP_STATE_MAP(stateMap, mat->stateBitsCount);
+
+ nlohmann::json material_images;
+ for (int i = 0; i < mat->numMaps; i++)
+ {
+ nlohmann::json image;
+
+ // watermap
+ if (mat->maps[i].semantic == 11)
+ {
+ water_t* waterData = reinterpret_cast(mat->maps[i].image);
+
+ image["image"] = waterData->image->name;
+
+ nlohmann::json waterdata;
+ waterdata["floatTime"] = waterData->writable.floatTime;
+ waterdata["codeConstant"][0] = waterData->codeConstant[0];
+ waterdata["codeConstant"][1] = waterData->codeConstant[1];
+ waterdata["codeConstant"][2] = waterData->codeConstant[2];
+ waterdata["codeConstant"][3] = waterData->codeConstant[3];
+ waterdata["M"] = waterData->M;
+ waterdata["N"] = waterData->N;
+ waterdata["Lx"] = waterData->Lx;
+ waterdata["Lz"] = waterData->Lz;
+ waterdata["gravity"] = waterData->gravity;
+ waterdata["windvel"] = waterData->windvel;
+ waterdata["winddir"][0] = waterData->winddir[0];
+ waterdata["winddir"][1] = waterData->winddir[1];
+ waterdata["amplitude"] = waterData->amplitude;
+
+ nlohmann::json waterComplexData;
+ nlohmann::json wTerm;
+
+ for (int i = 0; i < waterData->M * waterData->N; i++)
+ {
+ nlohmann::json complexdata;
+ nlohmann::json curWTerm;
+
+ complexdata["real"] = waterData->H0[i].real;
+ complexdata["imag"] = waterData->H0[i].imag;
+
+ curWTerm[i] = waterData->wTerm[i];
+
+ waterComplexData[i] = complexdata;
+ }
+
+ waterdata["complex"] = waterComplexData;
+ waterdata["wTerm"] = wTerm;
+
+ image["waterinfo"] = waterdata;
+ }
+ else
+ {
+ image["image"] = mat->maps[i].image->name;
+ }
+
+ image["semantic"] = mat->maps[i].semantic;
+ image["sampleState"] = mat->maps[i].sampleState;
+ image["lastCharacter"] = mat->maps[i].secondLastCharacter;
+ image["firstCharacter"] = mat->maps[i].firstCharacter;
+ image["typeHash"] = mat->maps[i].typeHash;
+
+ // add image data to material
+ material_images[i] = image;
+ }
+ matdata["maps"] = material_images;
+
+ auto assetData = matdata.dump(4);
+
+ // write data to disk
+ fwrite(&assetData[0], assetData.size(), 1, file);
+ FileSystem::FileClose(file);
+ }
+ }
+ }
+}
diff --git a/src/IW3/Assets/Material.hpp b/src/IW3/Assets/Material.hpp
new file mode 100644
index 0000000..81d6435
--- /dev/null
+++ b/src/IW3/Assets/Material.hpp
@@ -0,0 +1,22 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IMaterial
+ {
+ public:
+ static void dump(Material* asset, ZoneMemory* mem);
+ static void dump_statebits(Material* mat);
+ };
+ }
+}
diff --git a/src/IW3/Assets/Sound.cpp b/src/IW3/Assets/Sound.cpp
new file mode 100644
index 0000000..16e03bc
--- /dev/null
+++ b/src/IW3/Assets/Sound.cpp
@@ -0,0 +1,34 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "IW4/Assets/Sound.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void ISound::dump(snd_alias_list_t* asset, ZoneMemory* mem)
+ {
+ const auto iw4_asset = mem->Alloc(); // new IW4::snd_alias_list_t;
+ memcpy(iw4_asset, asset, sizeof snd_alias_list_t);
+
+ iw4_asset->head = mem->Alloc(iw4_asset->count);
+ memset(iw4_asset->head, 0, sizeof IW4::snd_alias_t * iw4_asset->count);
+
+ for (auto i = 0; i < asset->count; i++)
+ {
+ memcpy(&iw4_asset->head[i], &asset->head[i], 16);
+ memcpy(&iw4_asset->head[i].soundFile, &asset->head[i].soundFile, sizeof snd_alias_t - 16 - 20);
+ memcpy(&iw4_asset->head[i].volumeFalloffCurve, &asset->head[i].volumeFalloffCurve, 20);
+ }
+
+ IW4::ISound::dump(iw4_asset);
+ }
+ }
+}
diff --git a/src/IW3/Assets/Sound.hpp b/src/IW3/Assets/Sound.hpp
new file mode 100644
index 0000000..42e251c
--- /dev/null
+++ b/src/IW3/Assets/Sound.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class ISound
+ {
+ public:
+ static void dump(snd_alias_list_t* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/Techset.cpp b/src/IW3/Assets/Techset.cpp
new file mode 100644
index 0000000..5891969
--- /dev/null
+++ b/src/IW3/Assets/Techset.cpp
@@ -0,0 +1,449 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+#include "../IW4/Assets/VertexDecl.hpp"
+#include "../IW4/Assets/VertexShader.hpp"
+#include "../IW4/Assets/PixelShader.hpp"
+#include "IW4/Assets/Techset.hpp"
+
+static const unsigned int crcTable[] =
+{
+ 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba, 0x076dc419, 0x706af48f,
+ 0xe963a535, 0x9e6495a3, 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988,
+ 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91, 0x1db71064, 0x6ab020f2,
+ 0xf3b97148, 0x84be41de, 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
+ 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec, 0x14015c4f, 0x63066cd9,
+ 0xfa0f3d63, 0x8d080df5, 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172,
+ 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b, 0x35b5a8fa, 0x42b2986c,
+ 0xdbbbc9d6, 0xacbcf940, 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
+ 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116, 0x21b4f4b5, 0x56b3c423,
+ 0xcfba9599, 0xb8bda50f, 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
+ 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d, 0x76dc4190, 0x01db7106,
+ 0x98d220bc, 0xefd5102a, 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
+ 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818, 0x7f6a0dbb, 0x086d3d2d,
+ 0x91646c97, 0xe6635c01, 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e,
+ 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457, 0x65b0d9c6, 0x12b7e950,
+ 0x8bbeb8ea, 0xfcb9887c, 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
+ 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2, 0x4adfa541, 0x3dd895d7,
+ 0xa4d1c46d, 0xd3d6f4fb, 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0,
+ 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9, 0x5005713c, 0x270241aa,
+ 0xbe0b1010, 0xc90c2086, 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
+ 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4, 0x59b33d17, 0x2eb40d81,
+ 0xb7bd5c3b, 0xc0ba6cad, 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a,
+ 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683, 0xe3630b12, 0x94643b84,
+ 0x0d6d6a3e, 0x7a6a5aa8, 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
+ 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe, 0xf762575d, 0x806567cb,
+ 0x196c3671, 0x6e6b06e7, 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc,
+ 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5, 0xd6d6a3e8, 0xa1d1937e,
+ 0x38d8c2c4, 0x4fdff252, 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
+ 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60, 0xdf60efc3, 0xa867df55,
+ 0x316e8eef, 0x4669be79, 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
+ 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f, 0xc5ba3bbe, 0xb2bd0b28,
+ 0x2bb45a92, 0x5cb36a04, 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
+ 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a, 0x9c0906a9, 0xeb0e363f,
+ 0x72076785, 0x05005713, 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38,
+ 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21, 0x86d3d2d4, 0xf1d4e242,
+ 0x68ddb3f8, 0x1fda836e, 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
+ 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c, 0x8f659eff, 0xf862ae69,
+ 0x616bffd3, 0x166ccf45, 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2,
+ 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db, 0xaed16a4a, 0xd9d65adc,
+ 0x40df0b66, 0x37d83bf0, 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
+ 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6, 0xbad03605, 0xcdd70693,
+ 0x54de5729, 0x23d967bf, 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94,
+ 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d
+};
+
+std::uint32_t Crc32(void* buffer, const std::size_t size, const std::uint32_t initialCrc)
+{
+ auto curPtr = reinterpret_cast(buffer);
+ auto remaining = size;
+ auto crc = ~initialCrc;
+
+ for (; remaining--; ++curPtr)
+ {
+ crc = (crc >> 8) ^ crcTable[(crc ^ *curPtr) & 0xFF];
+ }
+
+ return (~crc);
+}
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ std::string GenerateNameForVertexDecl(MaterialVertexDeclaration* vertexDecl)
+ {
+ // base name + crc32
+ auto name = "iw3_vertexdecl_"s;
+ auto crc32 = Crc32(vertexDecl->routing.data, sizeof MaterialVertexDeclaration, 0);
+
+ // append crc32 to vertexdecl name
+ name += std::to_string(crc32);
+
+ // return generated name
+ return name;
+ }
+
+ IW4::VertexDecl* ITechset::dump_vertex_decl(const std::string& name, MaterialVertexDeclaration* vertex, ZoneMemory* mem)
+ {
+ // convert to IW4
+ auto* asset = mem->Alloc();
+
+ asset->name = mem->StrDup(va("iw3/%s", name.data()));
+
+ asset->hasOptionalSource = vertex->hasOptionalSource;
+ asset->streamCount = vertex->streamCount;
+
+ memcpy(asset->streams, vertex->routing.data, sizeof asset->streams);
+ memcpy(asset->declarations, vertex->routing.decl, sizeof(void*) * 16);
+
+ for (auto i = 0; i < asset->streamCount; i++)
+ {
+ if (asset->streams[i].dest >= 4)
+ {
+ asset->streams[i].dest += 1;
+ }
+ }
+
+ // shit out a warning
+ if (asset->streamCount > 13)
+ {
+ ZONETOOL_ERROR("Vertexdecl %s has more than 13 streams.", name.data());
+ }
+
+ // lets pray it works
+ IW4::IVertexDecl::dump(asset);
+
+ return asset;
+ }
+
+ IW4::VertexShader* ITechset::dump_vertex_shader(MaterialVertexShader* shader, ZoneMemory* mem)
+ {
+ // convert to IW4
+ auto* asset = mem->Alloc();
+
+ asset->name = mem->StrDup(va("iw3/%s", shader->name));
+ asset->shader = shader->prog.vs;
+ asset->codeLen = shader->prog.loadDef.programSize;
+ asset->bytecode = PDWORD(shader->prog.loadDef.program);
+
+ // dump shader
+ IW4::IVertexShader::dump(asset);
+
+ return asset;
+ }
+
+ IW4::PixelShader* ITechset::dump_pixel_shader(MaterialPixelShader* shader, ZoneMemory* mem)
+ {
+ // convert to IW4
+ auto* asset = mem->Alloc();
+
+ asset->name = mem->StrDup(va("iw3/%s", shader->name));
+ asset->shader = shader->prog.ps;
+ asset->codeLen = shader->prog.loadDef.programSize;
+ asset->bytecode = PDWORD(shader->prog.loadDef.program);
+
+ // dump shader
+ IW4::IPixelShader::dump(asset);
+
+ return asset;
+ }
+
+ std::unordered_map iw3_technique_map =
+ {
+ {IW3::TECHNIQUE_DEPTH_PREPASS, IW4::TECHNIQUE_DEPTH_PREPASS},
+ {IW3::TECHNIQUE_BUILD_FLOAT_Z, IW4::TECHNIQUE_BUILD_FLOAT_Z},
+ {IW3::TECHNIQUE_BUILD_SHADOWMAP_DEPTH, IW4::TECHNIQUE_BUILD_SHADOWMAP_DEPTH},
+ {IW3::TECHNIQUE_BUILD_SHADOWMAP_COLOR, IW4::TECHNIQUE_BUILD_SHADOWMAP_COLOR},
+ {IW3::TECHNIQUE_UNLIT, IW4::TECHNIQUE_UNLIT},
+ {IW3::TECHNIQUE_EMISSIVE, IW4::TECHNIQUE_EMISSIVE},
+ {IW3::TECHNIQUE_EMISSIVE_SHADOW, IW4::TECHNIQUE_EMISSIVE_SHADOW},
+ {IW3::TECHNIQUE_LIT_BEGIN, IW4::TECHNIQUE_LIT_BEGIN},
+ {IW3::TECHNIQUE_LIT, IW4::TECHNIQUE_LIT},
+ {IW3::TECHNIQUE_LIT_SUN, IW4::TECHNIQUE_LIT_SUN},
+ {IW3::TECHNIQUE_LIT_SUN_SHADOW, IW4::TECHNIQUE_LIT_SUN_SHADOW},
+ {IW3::TECHNIQUE_LIT_SPOT, IW4::TECHNIQUE_LIT_SPOT},
+ {IW3::TECHNIQUE_LIT_SPOT_SHADOW, IW4::TECHNIQUE_LIT_SPOT_SHADOW},
+ {IW3::TECHNIQUE_LIT_OMNI, IW4::TECHNIQUE_LIT_OMNI},
+ {IW3::TECHNIQUE_LIT_OMNI_SHADOW, IW4::TECHNIQUE_LIT_OMNI_SHADOW},
+ {IW3::TECHNIQUE_LIT_INSTANCED, IW4::TECHNIQUE_LIT_INSTANCED},
+ {IW3::TECHNIQUE_LIT_INSTANCED_SUN, IW4::TECHNIQUE_LIT_INSTANCED_SUN},
+ {IW3::TECHNIQUE_LIT_INSTANCED_SUN_SHADOW, IW4::TECHNIQUE_LIT_INSTANCED_SUN_SHADOW},
+ {IW3::TECHNIQUE_LIT_INSTANCED_SPOT, IW4::TECHNIQUE_LIT_INSTANCED_SPOT},
+ {IW3::TECHNIQUE_LIT_INSTANCED_OMNI, IW4::TECHNIQUE_LIT_INSTANCED_OMNI},
+ {IW3::TECHNIQUE_LIT_END, IW4::TECHNIQUE_LIT_END},
+ {IW3::TECHNIQUE_LIGHT_SPOT, IW4::TECHNIQUE_LIGHT_SPOT},
+ {IW3::TECHNIQUE_LIGHT_OMNI, IW4::TECHNIQUE_LIGHT_OMNI},
+ {IW3::TECHNIQUE_LIGHT_SPOT_SHADOW, IW4::TECHNIQUE_LIGHT_SPOT_SHADOW},
+ {IW3::TECHNIQUE_FAKELIGHT_NORMAL, IW4::TECHNIQUE_FAKELIGHT_NORMAL},
+ {IW3::TECHNIQUE_FAKELIGHT_VIEW, IW4::TECHNIQUE_FAKELIGHT_VIEW},
+ {IW3::TECHNIQUE_SUNLIGHT_PREVIEW, IW4::TECHNIQUE_SUNLIGHT_PREVIEW},
+ {IW3::TECHNIQUE_CASE_TEXTURE, IW4::TECHNIQUE_CASE_TEXTURE},
+ {IW3::TECHNIQUE_WIREFRAME_SOLID, IW4::TECHNIQUE_WIREFRAME_SOLID},
+ {IW3::TECHNIQUE_WIREFRAME_SHADED, IW4::TECHNIQUE_WIREFRAME_SHADED},
+ {IW3::TECHNIQUE_SHADOWCOOKIE_CASTER, 0xFFFFFFFF},
+ {IW3::TECHNIQUE_SHADOWCOOKIE_RECEIVER, 0xFFFFFFFF},
+ {IW3::TECHNIQUE_DEBUG_BUMPMAP, IW4::TECHNIQUE_DEBUG_BUMPMAP},
+ {IW3::TECHNIQUE_DEBUG_BUMPMAP_INSTANCED, IW4::TECHNIQUE_DEBUG_BUMPMAP_INSTANCED},
+ {IW3::TECHNIQUE_COUNT, IW4::TECHNIQUE_COUNT},
+ {IW3::TECHNIQUE_TOTAL_COUNT, IW4::TECHNIQUE_TOTAL_COUNT},
+ {IW3::TECHNIQUE_NONE, IW4::TECHNIQUE_NONE},
+ };
+
+ std::unordered_map iw3_code_const_map =
+ {
+ {IW3::CONST_SRC_CODE_LIGHT_POSITION, IW4::CONST_SRC_CODE_LIGHT_POSITION},
+ {IW3::CONST_SRC_CODE_LIGHT_DIFFUSE, IW4::CONST_SRC_CODE_LIGHT_DIFFUSE},
+ {IW3::CONST_SRC_CODE_LIGHT_SPECULAR, IW4::CONST_SRC_CODE_LIGHT_SPECULAR},
+ {IW3::CONST_SRC_CODE_LIGHT_SPOTDIR, IW4::CONST_SRC_CODE_LIGHT_SPOTDIR},
+ {IW3::CONST_SRC_CODE_LIGHT_SPOTFACTORS, IW4::CONST_SRC_CODE_LIGHT_SPOTFACTORS},
+ {IW3::CONST_SRC_CODE_NEARPLANE_ORG, IW4::CONST_SRC_CODE_NEARPLANE_ORG},
+ {IW3::CONST_SRC_CODE_NEARPLANE_DX, IW4::CONST_SRC_CODE_NEARPLANE_DX},
+ {IW3::CONST_SRC_CODE_NEARPLANE_DY, IW4::CONST_SRC_CODE_NEARPLANE_DY},
+
+ {IW3::CONST_SRC_CODE_SHADOWMAP_POLYGON_OFFSET, IW4::CONST_SRC_CODE_SHADOWMAP_POLYGON_OFFSET},
+ {IW3::CONST_SRC_CODE_RENDER_TARGET_SIZE, IW4::CONST_SRC_CODE_RENDER_TARGET_SIZE},
+ {IW3::CONST_SRC_CODE_LIGHT_FALLOFF_PLACEMENT, IW4::CONST_SRC_CODE_LIGHT_FALLOFF_PLACEMENT},
+ {
+ IW3::CONST_SRC_CODE_DOF_EQUATION_VIEWMODEL_AND_FAR_BLUR,
+ IW4::CONST_SRC_CODE_DOF_EQUATION_VIEWMODEL_AND_FAR_BLUR
+ },
+ {IW3::CONST_SRC_CODE_DOF_EQUATION_SCENE, IW4::CONST_SRC_CODE_DOF_EQUATION_SCENE},
+ {IW3::CONST_SRC_CODE_DOF_LERP_SCALE, IW4::CONST_SRC_CODE_DOF_LERP_SCALE},
+ {IW3::CONST_SRC_CODE_DOF_LERP_BIAS, IW4::CONST_SRC_CODE_DOF_LERP_BIAS},
+ {IW3::CONST_SRC_CODE_DOF_ROW_DELTA, IW4::CONST_SRC_CODE_DOF_ROW_DELTA},
+ {IW3::CONST_SRC_CODE_PARTICLE_CLOUD_COLOR, IW4::CONST_SRC_CODE_PARTICLE_CLOUD_COLOR},
+ {IW3::CONST_SRC_CODE_GAMETIME, IW4::CONST_SRC_CODE_GAMETIME},
+
+ {IW3::CONST_SRC_CODE_PIXEL_COST_FRACS, IW4::CONST_SRC_CODE_PIXEL_COST_FRACS},
+ {IW3::CONST_SRC_CODE_PIXEL_COST_DECODE, IW4::CONST_SRC_CODE_PIXEL_COST_DECODE},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_0, IW4::CONST_SRC_CODE_FILTER_TAP_0},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_1, IW4::CONST_SRC_CODE_FILTER_TAP_1},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_2, IW4::CONST_SRC_CODE_FILTER_TAP_2},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_3, IW4::CONST_SRC_CODE_FILTER_TAP_3},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_4, IW4::CONST_SRC_CODE_FILTER_TAP_4},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_5, IW4::CONST_SRC_CODE_FILTER_TAP_5},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_6, IW4::CONST_SRC_CODE_FILTER_TAP_6},
+ {IW3::CONST_SRC_CODE_FILTER_TAP_7, IW4::CONST_SRC_CODE_FILTER_TAP_7},
+ {IW3::CONST_SRC_CODE_COLOR_MATRIX_R, IW4::CONST_SRC_CODE_COLOR_MATRIX_R},
+ {IW3::CONST_SRC_CODE_COLOR_MATRIX_G, IW4::CONST_SRC_CODE_COLOR_MATRIX_G},
+ {IW3::CONST_SRC_CODE_COLOR_MATRIX_B, IW4::CONST_SRC_CODE_COLOR_MATRIX_B},
+
+ {IW3::CONST_SRC_CODE_SHADOWMAP_SWITCH_PARTITION, IW4::CONST_SRC_CODE_SHADOWMAP_SWITCH_PARTITION},
+ {IW3::CONST_SRC_CODE_SHADOWMAP_SCALE, IW4::CONST_SRC_CODE_SHADOWMAP_SCALE},
+ {IW3::CONST_SRC_CODE_ZNEAR, IW4::CONST_SRC_CODE_ZNEAR},
+ {IW3::CONST_SRC_CODE_SUN_POSITION, IW4::CONST_SRC_CODE_LIGHT_POSITION},
+ {IW3::CONST_SRC_CODE_SUN_DIFFUSE, IW4::CONST_SRC_CODE_LIGHT_DIFFUSE},
+ {IW3::CONST_SRC_CODE_SUN_SPECULAR, IW4::CONST_SRC_CODE_LIGHT_SPECULAR},
+ {IW3::CONST_SRC_CODE_LIGHTING_LOOKUP_SCALE, IW4::CONST_SRC_CODE_LIGHTING_LOOKUP_SCALE},
+ {IW3::CONST_SRC_CODE_DEBUG_BUMPMAP, IW4::CONST_SRC_CODE_DEBUG_BUMPMAP},
+ {IW3::CONST_SRC_CODE_MATERIAL_COLOR, IW4::CONST_SRC_CODE_MATERIAL_COLOR},
+ {IW3::CONST_SRC_CODE_FOG, IW4::CONST_SRC_CODE_FOG},
+ {IW3::CONST_SRC_CODE_FOG_COLOR, IW4::CONST_SRC_CODE_FOG_COLOR_LINEAR},
+ {IW3::CONST_SRC_CODE_GLOW_SETUP, IW4::CONST_SRC_CODE_GLOW_SETUP},
+ {IW3::CONST_SRC_CODE_GLOW_APPLY, IW4::CONST_SRC_CODE_GLOW_APPLY},
+ {IW3::CONST_SRC_CODE_COLOR_BIAS, IW4::CONST_SRC_CODE_COLOR_BIAS},
+ {IW3::CONST_SRC_CODE_COLOR_TINT_BASE, IW4::CONST_SRC_CODE_COLOR_TINT_BASE},
+ {IW3::CONST_SRC_CODE_COLOR_TINT_DELTA, IW4::CONST_SRC_CODE_COLOR_TINT_DELTA},
+ {IW3::CONST_SRC_CODE_OUTDOOR_FEATHER_PARMS, IW4::CONST_SRC_CODE_OUTDOOR_FEATHER_PARMS},
+ {IW3::CONST_SRC_CODE_ENVMAP_PARMS, IW4::CONST_SRC_CODE_ENVMAP_PARMS},
+ {IW3::CONST_SRC_CODE_SPOT_SHADOWMAP_PIXEL_ADJUST, IW4::CONST_SRC_CODE_SPOT_SHADOWMAP_PIXEL_ADJUST},
+ {IW3::CONST_SRC_CODE_CLIP_SPACE_LOOKUP_SCALE, IW4::CONST_SRC_CODE_CLIP_SPACE_LOOKUP_SCALE},
+ {IW3::CONST_SRC_CODE_CLIP_SPACE_LOOKUP_OFFSET, IW4::CONST_SRC_CODE_CLIP_SPACE_LOOKUP_OFFSET},
+ {IW3::CONST_SRC_CODE_PARTICLE_CLOUD_MATRIX, IW4::CONST_SRC_CODE_PARTICLE_CLOUD_MATRIX0},
+ {IW3::CONST_SRC_CODE_DEPTH_FROM_CLIP, IW4::CONST_SRC_CODE_DEPTH_FROM_CLIP},
+ {IW3::CONST_SRC_CODE_CODE_MESH_ARG_0, IW4::CONST_SRC_CODE_CODE_MESH_ARG_0},
+ {IW3::CONST_SRC_CODE_CODE_MESH_ARG_1, IW4::CONST_SRC_CODE_CODE_MESH_ARG_1},
+ {IW3::CONST_SRC_CODE_CODE_MESH_ARG_LAST, IW4::CONST_SRC_CODE_CODE_MESH_ARG_LAST},
+ {IW3::CONST_SRC_CODE_BASE_LIGHTING_COORDS, IW4::CONST_SRC_CODE_BASE_LIGHTING_COORDS},
+
+ {IW3::CONST_SRC_CODE_COUNT_FLOAT4, IW4::CONST_SRC_CODE_COUNT_FLOAT4},
+ {IW3::CONST_SRC_FIRST_CODE_MATRIX, IW4::CONST_SRC_FIRST_CODE_MATRIX},
+ {IW3::CONST_SRC_CODE_WORLD_MATRIX, IW4::CONST_SRC_CODE_WORLD_MATRIX0},
+ {IW3::CONST_SRC_CODE_INVERSE_WORLD_MATRIX, IW4::CONST_SRC_CODE_INVERSE_WORLD_MATRIX0},
+ {IW3::CONST_SRC_CODE_TRANSPOSE_WORLD_MATRIX, IW4::CONST_SRC_CODE_TRANSPOSE_WORLD_MATRIX0},
+ {IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_MATRIX, IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_MATRIX0},
+ {IW3::CONST_SRC_CODE_VIEW_MATRIX, IW4::CONST_SRC_CODE_VIEW_MATRIX},
+ {IW3::CONST_SRC_CODE_INVERSE_VIEW_MATRIX, IW4::CONST_SRC_CODE_INVERSE_VIEW_MATRIX},
+ {IW3::CONST_SRC_CODE_TRANSPOSE_VIEW_MATRIX, IW4::CONST_SRC_CODE_TRANSPOSE_VIEW_MATRIX},
+ {IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_MATRIX, IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_MATRIX},
+ {IW3::CONST_SRC_CODE_PROJECTION_MATRIX, IW4::CONST_SRC_CODE_PROJECTION_MATRIX},
+ {IW3::CONST_SRC_CODE_INVERSE_PROJECTION_MATRIX, IW4::CONST_SRC_CODE_INVERSE_PROJECTION_MATRIX},
+ {IW3::CONST_SRC_CODE_TRANSPOSE_PROJECTION_MATRIX, IW4::CONST_SRC_CODE_TRANSPOSE_PROJECTION_MATRIX},
+ {
+ IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_PROJECTION_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_PROJECTION_MATRIX
+ },
+ {IW3::CONST_SRC_CODE_WORLD_VIEW_MATRIX, IW4::CONST_SRC_CODE_WORLD_VIEW_MATRIX0},
+ {IW3::CONST_SRC_CODE_INVERSE_WORLD_VIEW_MATRIX, IW4::CONST_SRC_CODE_INVERSE_WORLD_VIEW_MATRIX0},
+ {IW3::CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_MATRIX, IW4::CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_MATRIX0},
+ {
+ IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_MATRIX0
+ },
+ {IW3::CONST_SRC_CODE_VIEW_PROJECTION_MATRIX, IW4::CONST_SRC_CODE_VIEW_PROJECTION_MATRIX},
+ {IW3::CONST_SRC_CODE_INVERSE_VIEW_PROJECTION_MATRIX, IW4::CONST_SRC_CODE_INVERSE_VIEW_PROJECTION_MATRIX},
+ {
+ IW3::CONST_SRC_CODE_TRANSPOSE_VIEW_PROJECTION_MATRIX,
+ IW4::CONST_SRC_CODE_TRANSPOSE_VIEW_PROJECTION_MATRIX
+ },
+ {
+ IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_PROJECTION_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_VIEW_PROJECTION_MATRIX
+ },
+ {IW3::CONST_SRC_CODE_WORLD_VIEW_PROJECTION_MATRIX, IW4::CONST_SRC_CODE_WORLD_VIEW_PROJECTION_MATRIX0},
+ {
+ IW3::CONST_SRC_CODE_INVERSE_WORLD_VIEW_PROJECTION_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_WORLD_VIEW_PROJECTION_MATRIX0
+ },
+ {
+ IW3::CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX,
+ IW4::CONST_SRC_CODE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX0
+ },
+ {
+ IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_VIEW_PROJECTION_MATRIX0
+ },
+ {IW3::CONST_SRC_CODE_SHADOW_LOOKUP_MATRIX, IW4::CONST_SRC_CODE_SHADOW_LOOKUP_MATRIX},
+ {IW3::CONST_SRC_CODE_INVERSE_SHADOW_LOOKUP_MATRIX, IW4::CONST_SRC_CODE_INVERSE_SHADOW_LOOKUP_MATRIX},
+ {IW3::CONST_SRC_CODE_TRANSPOSE_SHADOW_LOOKUP_MATRIX, IW4::CONST_SRC_CODE_TRANSPOSE_SHADOW_LOOKUP_MATRIX},
+ {
+ IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_SHADOW_LOOKUP_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_SHADOW_LOOKUP_MATRIX
+ },
+ {IW3::CONST_SRC_CODE_WORLD_OUTDOOR_LOOKUP_MATRIX, IW4::CONST_SRC_CODE_WORLD_OUTDOOR_LOOKUP_MATRIX},
+ {
+ IW3::CONST_SRC_CODE_INVERSE_WORLD_OUTDOOR_LOOKUP_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_WORLD_OUTDOOR_LOOKUP_MATRIX
+ },
+ {
+ IW3::CONST_SRC_CODE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX,
+ IW4::CONST_SRC_CODE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX
+ },
+ {
+ IW3::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX,
+ IW4::CONST_SRC_CODE_INVERSE_TRANSPOSE_WORLD_OUTDOOR_LOOKUP_MATRIX
+ },
+ };
+
+ void ITechset::dump_statebits(const std::string& techset, char* statebits)
+ {
+ char iw4_statebits[48];
+ memset(iw4_statebits, 0xFF, sizeof iw4_statebits);
+
+ for (int i = 0; i < 34; i++)
+ {
+ const auto itr = iw3_technique_map.find(i);
+ if (itr != iw3_technique_map.end())
+ {
+ if (itr->second >= 0)
+ {
+ iw4_statebits[itr->second] = statebits[i];
+
+ if (iw4_statebits[itr->second] >= 7)
+ {
+ iw4_statebits[itr->second] += 1;
+ }
+
+ if (itr->second >= 5 && itr->second <= 36)
+ {
+ iw4_statebits[itr->second + 1] = iw4_statebits[itr->second];
+ }
+ }
+ }
+ }
+
+ IW4::ITechset::dump_statebits(techset, iw4_statebits);
+ }
+
+ void ITechset::dump(MaterialTechniqueSet* asset, ZoneMemory* mem)
+ {
+ auto* iw4_techset = mem->Alloc();
+
+ iw4_techset->name = mem->StrDup(va("iw3/%s", asset->name));
+ iw4_techset->pad = asset->pad;
+
+ for (int i = 0; i < 34; i++)
+ {
+ const auto itr = iw3_technique_map.find(i);
+ if (itr != iw3_technique_map.end())
+ {
+ if (asset->techniques[i] && itr->second >= 0)
+ {
+ const auto size = sizeof(IW4::MaterialTechniqueHeader) + (sizeof(IW4::MaterialPass) * asset->techniques[i]->hdr.numPasses);
+ iw4_techset->techniques[itr->second] = mem->ManualAlloc(size);
+
+ if (itr->second >= 5 && itr->second <= 36)
+ {
+ iw4_techset->techniques[itr->second + 1] = iw4_techset->techniques[itr->second];
+ }
+
+ memcpy(iw4_techset->techniques[itr->second], asset->techniques[i], size);
+
+ auto& iw3_technique = asset->techniques[i];
+ auto& technique = iw4_techset->techniques[itr->second];
+
+ technique->hdr.name = mem->StrDup(va("iw3/%s", technique->hdr.name));
+
+ if ((technique->hdr.flags & 0x10) == 0x10)
+ {
+ technique->hdr.flags &= ~0x10;
+ technique->hdr.flags |= 0x40;
+ }
+
+ for (short pass = 0; pass < technique->hdr.passCount; pass++)
+ {
+ auto* iw3_pass_def = &iw3_technique->pass[pass];
+ auto* pass_def = &technique->pass[pass];
+
+ auto vertex_decl_name = GenerateNameForVertexDecl(iw3_pass_def->vertexDecl);
+
+ if (iw3_pass_def->pixelShader) pass_def->pixelShader = dump_pixel_shader(iw3_pass_def->pixelShader, mem);
+ if (iw3_pass_def->vertexDecl) pass_def->vertexDecl = dump_vertex_decl(vertex_decl_name, iw3_pass_def->vertexDecl, mem);
+ if (iw3_pass_def->vertexShader) pass_def->vertexShader = dump_vertex_shader(iw3_pass_def->vertexShader, mem);
+
+ const auto arg_count = pass_def->perPrimArgCount + pass_def->perObjArgCount + pass_def->stableArgCount;
+ if (arg_count > 0)
+ {
+ pass_def->argumentDef = mem->Alloc(arg_count);
+ memcpy(pass_def->argumentDef, iw3_pass_def->args, sizeof(IW4::ShaderArgumentDef) * arg_count);
+ }
+
+ for (auto arg = 0; arg < pass_def->perPrimArgCount + pass_def->perObjArgCount + pass_def->stableArgCount; arg++)
+ {
+ auto* arg_def = &pass_def->argumentDef[arg];
+ if (arg_def->type == 3 || arg_def->type == 5)
+ {
+ if (iw3_code_const_map.find(arg_def->u.codeConst.index) != iw3_code_const_map.end())
+ {
+ arg_def->u.codeConst.index = iw3_code_const_map[arg_def->u.codeConst.index];
+ }
+ else
+ {
+ if (IsDebuggerPresent())
+ {
+ __debugbreak();
+ }
+ else
+ {
+ ZONETOOL_WARNING("Missing const mapping for constant %u!", arg_def->u.codeConst.index);
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+
+ IW4::ITechset::dump(iw4_techset);
+ }
+ }
+}
diff --git a/src/IW3/Assets/Techset.hpp b/src/IW3/Assets/Techset.hpp
new file mode 100644
index 0000000..c1899b1
--- /dev/null
+++ b/src/IW3/Assets/Techset.hpp
@@ -0,0 +1,27 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+#include "IW4/Structs.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class ITechset
+ {
+ public:
+ static void dumpTechniquePass(MaterialTechnique* asset);
+ static void dump(MaterialTechniqueSet* asset, ZoneMemory* mem);
+ static IW4::VertexDecl* dump_vertex_decl(const std::string& name, MaterialVertexDeclaration* vertex, ZoneMemory* mem);
+ static IW4::VertexShader* dump_vertex_shader(MaterialVertexShader* shader, ZoneMemory* mem);
+ static IW4::PixelShader* dump_pixel_shader(MaterialPixelShader* shader, ZoneMemory* mem);
+ static void dump_statebits(const std::string& techset, char* statebits);
+ };
+ }
+}
diff --git a/src/IW3/Assets/XAnimParts.cpp b/src/IW3/Assets/XAnimParts.cpp
new file mode 100644
index 0000000..e3fe8fb
--- /dev/null
+++ b/src/IW3/Assets/XAnimParts.cpp
@@ -0,0 +1,76 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW4/Assets/XAnimParts.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ void IXAnimParts::dump(XAnimParts* anim, ZoneMemory* mem)
+ {
+ if (anim)
+ {
+ auto asset = mem->Alloc();
+
+#define XAE_CopyElement(name) asset->name = anim->name
+
+ XAE_CopyElement(name);
+ XAE_CopyElement(dataByteCount);
+ XAE_CopyElement(dataShortCount);
+ XAE_CopyElement(dataIntCount);
+ XAE_CopyElement(randomDataByteCount);
+ XAE_CopyElement(randomDataIntCount);
+ XAE_CopyElement(framecount);
+
+ asset->flags = 0;
+ if (anim->bLoop)
+ {
+ asset->flags |= IW4::ANIM_LOOP;
+ }
+ if (anim->bDelta)
+ {
+ asset->flags |= IW4::ANIM_DELTA;
+ }
+
+ for (auto i = 0; i < 10; i++)
+ {
+ XAE_CopyElement(boneCount[i]);
+ }
+
+ XAE_CopyElement(notifyCount);
+ XAE_CopyElement(assetType);
+ XAE_CopyElement(isDefault);
+ XAE_CopyElement(randomDataShortCount);
+ XAE_CopyElement(indexcount);
+ XAE_CopyElement(framerate);
+ XAE_CopyElement(frequency);
+ XAE_CopyElement(tagnames);
+ XAE_CopyElement(dataByte);
+ XAE_CopyElement(dataShort);
+ XAE_CopyElement(dataInt);
+ XAE_CopyElement(randomDataShort);
+ XAE_CopyElement(randomDataByte);
+ XAE_CopyElement(randomDataInt);
+ XAE_CopyElement(indices.data);
+ asset->notify = reinterpret_cast(anim->notify);
+
+ if (anim->delta)
+ {
+ asset->delta = mem->Alloc();
+ asset->delta->quat = reinterpret_cast(anim->delta->quat);
+ asset->delta->trans = reinterpret_cast(anim->delta->trans);
+ }
+
+ // dump asset
+ IW4::IXAnimParts::dump(asset, SL_ConvertToString);
+ }
+ }
+ }
+}
diff --git a/src/IW3/Assets/XAnimParts.hpp b/src/IW3/Assets/XAnimParts.hpp
new file mode 100644
index 0000000..ed45ed2
--- /dev/null
+++ b/src/IW3/Assets/XAnimParts.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IXAnimParts
+ {
+ public:
+ static void dump(XAnimParts* anim, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Assets/XModel.cpp b/src/IW3/Assets/XModel.cpp
new file mode 100644
index 0000000..af3b95a
--- /dev/null
+++ b/src/IW3/Assets/XModel.cpp
@@ -0,0 +1,146 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW4/Assets/Xmodel.hpp"
+#include "../IW4/Assets/XSurface.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ IW4::XSurface* GenerateIW4Surface(XSurface* asset, ZoneMemory* mem)
+ {
+ // allocate IW4 XSurface structure
+ const auto xsurface = mem->Alloc();
+
+ xsurface->tileMode = asset->tileMode;
+ xsurface->deformed = asset->deformed;
+ xsurface->vertCount = asset->vertCount;
+ xsurface->triCount = asset->triCount;
+ xsurface->zoneHandle = asset->zoneHandle;
+ xsurface->baseTriIndex = asset->baseTriIndex;
+ xsurface->baseVertIndex = asset->baseVertIndex;
+ xsurface->triIndices = reinterpret_cast(asset->triIndices);
+ memcpy(&xsurface->vertexInfo, &asset->vertInfo, sizeof IW4::XSurfaceVertexInfo);
+ xsurface->verticies = reinterpret_cast(asset->verts0);
+ xsurface->vertListCount = asset->vertListCount;
+ xsurface->rigidVertLists = reinterpret_cast(asset->vertList);
+ memcpy(&xsurface->partBits, &asset->partBits, sizeof(int[4]));
+
+ return xsurface;
+ }
+
+ IW4::XModel* GenerateIW4Model(XModel* asset, ZoneMemory* mem)
+ {
+ // allocate IW4 XModel structure
+ const auto xmodel = mem->Alloc();
+
+ // copy data over
+ xmodel->name = const_cast(asset->name);
+ xmodel->numBones = asset->numBones;
+ xmodel->numRootBones = asset->numRootBones;
+ xmodel->numSurfaces = asset->numsurfs;
+ xmodel->lodRampType = asset->lodRampType;
+ xmodel->scale = 1.0f;
+ memset(xmodel->noScalePartBits, 0, sizeof(int) * 6);
+ xmodel->parentList = reinterpret_cast(asset->parentList);
+ xmodel->boneNames = reinterpret_cast(asset->boneNames);
+
+ xmodel->tagAngles = reinterpret_cast(asset->quats);
+ xmodel->tagPositions = reinterpret_cast(asset->trans);
+
+ xmodel->partClassification = asset->partClassification;
+ xmodel->animMatrix = reinterpret_cast(asset->baseMat);
+ xmodel->materials = reinterpret_cast(asset->materialHandles);
+
+ // convert level of detail data
+ for (int i = 0; i < asset->numLods; i++)
+ {
+ xmodel->lods[i].dist = asset->lodInfo[i].dist;
+ xmodel->lods[i].numSurfacesInLod = asset->lodInfo[i].numsurfs;
+ xmodel->lods[i].surfIndex = asset->lodInfo[i].surfIndex;
+ memcpy(xmodel->lods[i].partBits, asset->lodInfo[i].partBits, sizeof(int[4]));
+ memcpy(&xmodel->lods[i].lod, &asset->lodInfo[i].lod, 3);
+
+ // generate ModelSurface object
+ xmodel->lods[i].surfaces = mem->Alloc();;
+
+ xmodel->lods[i].surfaces->name = mem->StrDup(va("zonetool_%s_%u", xmodel->name, i).data());
+ xmodel->lods[i].surfaces->numsurfs = xmodel->lods[i].numSurfacesInLod;
+ memcpy(xmodel->lods[i].surfaces->partBits, asset->lodInfo[i].partBits, sizeof(int[4]));
+
+ // allocate xsurficies
+ xmodel->lods[i].surfaces->surfs = mem->Alloc(xmodel->lods[i].numSurfacesInLod);
+
+ // loop through surfaces in current Level-of-Detail
+ for (int surf = xmodel->lods[i].surfIndex; surf <
+ xmodel->lods[i].surfIndex + xmodel->lods[i].numSurfacesInLod; surf++)
+ {
+ // generate iw4 surface
+ const auto surface = GenerateIW4Surface(&asset->surfs[surf], mem);
+
+ // copy XSurface into iw4 structure
+ memcpy(
+ &xmodel->lods[i].surfaces->surfs[surf - xmodel->lods[i].surfIndex],
+ surface,
+ sizeof IW4::XSurface
+ );
+ }
+ }
+
+ xmodel->numLods = asset->numLods;
+ xmodel->collLod = asset->collLod;
+ xmodel->flags = asset->flags;
+
+ xmodel->colSurf = reinterpret_cast(asset->collSurfs);
+ xmodel->numColSurfs = asset->numCollSurfs;
+ xmodel->contents = asset->contents;
+
+ // convert colsurf bounds
+ for (int i = 0; i < xmodel->numColSurfs; i++)
+ {
+ xmodel->colSurf[i].bounds.compute();
+ }
+
+ // convert boneinfo
+ xmodel->boneInfo = mem->Alloc(xmodel->numBones);
+ for (int i = 0; i < xmodel->numBones; i++)
+ {
+ memcpy(&xmodel->boneInfo[i].bounds, &asset->boneInfo[i].bounds, sizeof(Bounds));
+
+ xmodel->boneInfo[i].packedBounds.compute();
+ xmodel->boneInfo[i].radiusSquared = asset->boneInfo[i].radiusSquared;
+ }
+
+ xmodel->radius = asset->radius;
+ xmodel->memUsage = asset->memUsage;
+ xmodel->bad = asset->bad;
+ xmodel->physPreset = reinterpret_cast(asset->physPreset);
+
+ xmodel->bounds.compute(asset->mins, asset->maxs);
+
+ return xmodel;
+ }
+
+ void IXModel::dump(XModel* asset, ZoneMemory* mem)
+ {
+ // generate iw4 model
+ auto iw4_model = GenerateIW4Model(asset, mem);
+
+ // dump iw4 model
+ IW4::IXModel::dump(iw4_model, SL_ConvertToString);
+
+ // dump all xsurfaces
+ for (int i = 0; i < iw4_model->numLods; i++)
+ {
+ IW4::IXSurface::dump(iw4_model->lods[i].surfaces);
+ }
+ }
+ }
+}
diff --git a/src/IW3/Assets/XModel.hpp b/src/IW3/Assets/XModel.hpp
new file mode 100644
index 0000000..5c3d8be
--- /dev/null
+++ b/src/IW3/Assets/XModel.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ class IXModel
+ {
+ public:
+ static void dump(XModel* asset, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW3/Functions.hpp b/src/IW3/Functions.hpp
new file mode 100644
index 0000000..38ca8db
--- /dev/null
+++ b/src/IW3/Functions.hpp
@@ -0,0 +1,38 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+//!!!!!!!!!!!!!!!!!
+//!!!!!!!TODO!!!!!!
+//!!!CHANGE OFFSETS
+//!!!!!!!!!!!!!!!!!
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ union XAssetHeader;
+
+ static Function DB_FindXAssetHeader = 0x489570;
+ static Function DB_LoadXAssets; //add offset
+
+ typedef int (__cdecl * DB_GetXAssetSizeHandler_t)();
+ static DB_GetXAssetSizeHandler_t* DB_GetXAssetSizeHandlers = (DB_GetXAssetSizeHandler_t*)0x726A10;
+
+ static const char* SL_ConvertToString(std::uint16_t index)
+ {
+ return reinterpret_cast(*reinterpret_cast(0x14E8A04) + 12 * index + 4);
+ }
+
+ static short SL_AllocString(const std::string& string)
+ {
+ // TODO
+ }
+ }
+}
diff --git a/src/IW3/IW3.cpp b/src/IW3/IW3.cpp
new file mode 100644
index 0000000..fa6b7a9
--- /dev/null
+++ b/src/IW3/IW3.cpp
@@ -0,0 +1,365 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+// #include "ZoneTool.hpp"
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ bool isDumping = false;
+ bool isVerifying = false;
+ auto currentDumpingZone = ""s;
+
+ Linker::Linker()
+ {
+ }
+
+ Linker::~Linker()
+ {
+ }
+
+ const char* Linker::version()
+ {
+ return "CoD4";
+ }
+
+ bool Linker::is_used()
+ {
+ return !strncmp(reinterpret_cast(0x006CF584), this->version(), 4);
+ }
+
+ typedef void*(__cdecl * Dvar_RegisterBool_t)(const char*, bool, unsigned int, const char*);
+ Dvar_RegisterBool_t Dvar_RegisterBool = (Dvar_RegisterBool_t)0x56C600;
+
+ void* Linker::Dedicated_RegisterDvarBool(const char* name, bool defaultValue, unsigned int flags,
+ const char* description)
+ {
+ return Dvar_RegisterBool(name, true, 0x2000, description);
+ }
+
+ void** DB_XAssetPool = (void**)0x7265E0;
+ unsigned int* g_poolSize = (unsigned int*)0x7263A0;
+
+ void* DB_FindXAssetHeader_Unsafe(const XAssetType type, const std::string& name)
+ {
+ const static auto DB_FindXAssetHeader_Internal = 0x4892A0;
+ const auto name_ptr = name.data();
+ const auto type_int = static_cast(type);
+
+ const XAsset* asset_header = nullptr;
+
+ __asm
+ {
+ mov edi, name_ptr;
+ push type_int;
+ call DB_FindXAssetHeader_Internal;
+ add esp, 4;
+ mov asset_header, eax;
+ }
+
+ return (asset_header) ? asset_header->ptr.data : nullptr;
+ }
+
+ const char* Linker::GetAssetName(XAsset* asset)
+ {
+ // todo
+ if (asset->type == image)
+ {
+ return asset->ptr.image->name;
+ }
+ if (asset->type == menu)
+ {
+ // return asset->ptr.menu->name;
+ }
+ else
+ {
+ return asset->ptr.rawfile->name;
+ }
+
+ return "";
+ }
+
+ void Linker::HandleAsset(XAsset* asset)
+ {
+ static std::shared_ptr memory;
+ static std::vector> referencedAssets;
+
+ if (!memory)
+ {
+ memory = std::make_shared(1024 * 1024 * 128); // 128mb
+ }
+
+ // nice meme
+ if (isVerifying)
+ {
+ // print asset name to console
+ ZONETOOL_INFO("Loading asset \"%s\" of type %s.", Linker::GetAssetName(asset), reinterpret_cast(
+0x00726840)[asset->type]);
+ }
+
+#define DECLARE_ASSET(__TYPE__, __ASSET__) \
+ if (asset->type == __TYPE__) \
+ { \
+ __ASSET__::dump(asset->ptr.__TYPE__, memory.get()); \
+ }
+
+ // fastfile name
+ auto fastfile = static_cast(*(const char**)0xE344CC);
+
+ if (asset->type == rawfile && GetAssetName(asset) == currentDumpingZone)
+ {
+ for (auto& ref : referencedAssets)
+ {
+ if (ref.second.length() <= 1 || ref.first == XAssetType::loaded_sound)
+ {
+ continue;
+ }
+
+ const auto asset_name = &ref.second[1];
+ const auto ref_asset = DB_FindXAssetHeader_Unsafe(ref.first, asset_name);
+
+ if (ref_asset == nullptr)
+ {
+ ZONETOOL_ERROR("Could not find referenced asset \"%s\"!", asset_name);
+ continue;
+ }
+
+ XAsset asset;
+ asset.type = ref.first;
+ asset.ptr.data = ref_asset;
+
+ ZONETOOL_INFO("Dumping additional asset \"%s\" because it is referenced by %s.", asset_name, currentDumpingZone.data());
+
+ HandleAsset(&asset);
+ }
+
+ ZONETOOL_INFO("Zone \"%s\" dumped.", &fastfile[0]);
+
+ // clear referenced assets array because we are done dumping
+ referencedAssets.clear();
+
+ // free memory
+ memory->Free();
+ memory = nullptr;
+
+ FileSystem::SetFastFile("");
+ isDumping = false;
+ isVerifying = false;
+ }
+
+ // dump shit
+ if (isDumping)
+ {
+ FileSystem::SetFastFile(fastfile);
+
+ // check if the asset is a reference asset
+ if (GetAssetName(asset)[0] == ',')
+ {
+ referencedAssets.push_back({asset->type, GetAssetName(asset)});
+ }
+ else
+ {
+ // DECLARE_ASSET(image, IGfxImage);
+ DECLARE_ASSET(xmodel, IXModel);
+ DECLARE_ASSET(material, IMaterial);
+ DECLARE_ASSET(xanim, IXAnimParts);
+ DECLARE_ASSET(techset, ITechset);
+ DECLARE_ASSET(loaded_sound, ILoadedSound);
+ DECLARE_ASSET(sound, ISound);
+ DECLARE_ASSET(fx, IFxEffectDef);
+ DECLARE_ASSET(gfx_map, IGfxWorld);
+ DECLARE_ASSET(col_map_mp, IClipMap);
+ DECLARE_ASSET(map_ents, IMapEnts);
+ DECLARE_ASSET(com_map, IComWorld);
+ }
+ }
+ }
+
+ void* Linker::DB_AddXAsset(XAsset* asset, int unk)
+ {
+ HandleAsset(asset);
+
+ // call original function
+ return Memory::func(0x489B00)(asset, unk);
+ }
+
+ void* ReallocateAssetPool(uint32_t type, unsigned int newSize)
+ {
+ int elSize = DB_GetXAssetSizeHandlers[type]();
+
+ void* poolEntry = malloc(newSize * elSize);
+ DB_XAssetPool[type] = poolEntry;
+ g_poolSize[type] = newSize;
+
+ return poolEntry;
+ }
+
+ void* ReallocateAssetPoolM(uint32_t type, int multiplier)
+ {
+ int elSize = DB_GetXAssetSizeHandlers[type]();
+ int newSize = multiplier * g_poolSize[type];
+
+ void* poolEntry = malloc(newSize * elSize);
+ DB_XAssetPool[type] = poolEntry;
+ g_poolSize[type] = newSize;
+
+ return poolEntry;
+ }
+
+ void Com_PrintfHook(int channel, const char* data, int unk)
+ {
+ printf(data);
+ }
+
+ void Linker::startup()
+ {
+ if (this->is_used())
+ {
+ // Realloc asset pools
+ ReallocateAssetPoolM(localize, 2);
+ ReallocateAssetPoolM(material, 2);
+ ReallocateAssetPoolM(font, 2);
+ ReallocateAssetPoolM(image, 2);
+ ReallocateAssetPoolM(techset, 2);
+ ReallocateAssetPoolM(fx, 4);
+ ReallocateAssetPoolM(xanim, 2);
+ ReallocateAssetPoolM(xmodel, 2);
+ ReallocateAssetPoolM(physpreset, 2);
+ ReallocateAssetPoolM(weapon, 2);
+ ReallocateAssetPoolM(game_map_sp, 2);
+ ReallocateAssetPoolM(game_map_mp, 2);
+ ReallocateAssetPoolM(map_ents, 5);
+ ReallocateAssetPoolM(com_map, 5);
+ ReallocateAssetPoolM(col_map_mp, 5);
+ ReallocateAssetPoolM(gfx_map, 5);
+ ReallocateAssetPoolM(rawfile, 2);
+ ReallocateAssetPoolM(loaded_sound, 2);
+ ReallocateAssetPoolM(sound, 2);
+ ReallocateAssetPoolM(stringtable, 2);
+
+ // Asset dump hook
+ Memory(0x00489E72).call(DB_AddXAsset);
+
+ // Always use dedicated mode
+ Memory(0x4FEA9E).call(Dedicated_RegisterDvarBool);
+ Memory(0x4FEAC2).call(Dedicated_RegisterDvarBool);
+ Memory(0x4FFE37).call(Dedicated_RegisterDvarBool);
+ Memory(0x4FFE5D).call(Dedicated_RegisterDvarBool);
+
+ // Don't touch image data
+ Memory(0x616E9C).nop(3);
+
+ // idc if you can't initialise PunkBuster
+ Memory(0x5776DF).nop(5);
+ Memory(0x5776EC).nop(5);
+
+ // Initialise console_mp.log
+ Memory(0x4FCBA3).nop(2);
+
+ // We don't need recommended settings
+ Memory(0x4FE99A).set(0xEB);
+ Memory(0x4FE993).nop(7);
+
+ // We do not need to load the config_mp.cfg
+ Memory(0x55EEA6).set(0xEB);
+
+ // Don't give a frametime warning
+ Memory(0x4FFD9D).nop(5);
+
+ // Disabling loadedsound touching
+ Memory(0x4794C2).nop(5);
+
+ // No huffmann message
+ Memory(0x507982).nop(5);
+
+ // Disable console window
+ Memory(0x0046CE55).nop(5);
+
+ // Obtain console output from IW3
+ Memory(0x4FCC00).call(Com_PrintfHook);
+ }
+ }
+
+ std::shared_ptr Linker::alloc_zone(const std::string& zone)
+ {
+ ZONETOOL_ERROR("AllocZone called but IW3 is not intended to compile zones!");
+ return nullptr;
+ }
+
+ std::shared_ptr Linker::alloc_buffer()
+ {
+ ZONETOOL_ERROR("AllocBuffer called but IW3 is not intended to compile zones!");
+ return nullptr;
+ }
+
+ void Linker::load_zone(const std::string& name)
+ {
+ static XZoneInfo zone;
+ zone.zone = _strdup(&name[0]);
+ zone.loadFlags = 0;
+ zone.unloadFlags = 0;
+
+ Memory::func(0x48A2B0)(&zone, 1, 0);
+ }
+
+ void Linker::unload_zones()
+ {
+ }
+
+ bool Linker::is_valid_asset_type(const std::string& type)
+ {
+ return this->type_to_int(type) >= 0;
+ }
+
+ std::int32_t Linker::type_to_int(std::string type)
+ {
+ auto xassettypes = reinterpret_cast(0x00726840);
+
+ for (std::int32_t i = 0; i < max; i++)
+ {
+ if (xassettypes[i] == type)
+ return i;
+ }
+
+ return -1;
+ }
+
+ std::string Linker::type_to_string(std::int32_t type)
+ {
+ auto xassettypes = reinterpret_cast(0x00726840);
+ return xassettypes[type];
+ }
+
+ bool Linker::supports_building()
+ {
+ return false;
+ }
+
+ bool Linker::supports_version(const zone_target_version version)
+ {
+ return version == zone_target_version::iw3_alpha_253 || version == zone_target_version::iw3_alpha_290 ||
+ version == zone_target_version::iw3_alpha_328;
+ }
+
+ void Linker::dump_zone(const std::string& name)
+ {
+ isDumping = true;
+ currentDumpingZone = name;
+ load_zone(name);
+ }
+
+ void Linker::verify_zone(const std::string& name)
+ {
+ isVerifying = true;
+ currentDumpingZone = name;
+ load_zone(name);
+ }
+ }
+}
diff --git a/src/IW3/IW3.hpp b/src/IW3/IW3.hpp
new file mode 100644
index 0000000..daef362
--- /dev/null
+++ b/src/IW3/IW3.hpp
@@ -0,0 +1,70 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+#include
+#include "Functions.hpp"
+#include "Structs.hpp"
+
+#include "Assets/XModel.hpp"
+#include "Assets/Material.hpp"
+#include "Assets/XAnimParts.hpp"
+#include "Assets/Techset.hpp"
+#include "Assets/GfxWorld.hpp"
+#include "Assets/GfxImage.hpp"
+#include "Assets/GameWorldMp.hpp"
+#include "Assets/LoadedSound.hpp"
+#include "Assets/Sound.hpp"
+#include "Assets/FxEffectDef.hpp"
+#include "Assets/ClipMap.hpp"
+#include "Assets/MapEnts.hpp"
+#include "Assets/ComWorld.hpp"
+
+// oh nee toch niet
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ struct XAsset
+ {
+ XAssetType type;
+ XAssetHeader ptr;
+ };
+
+ class Linker : public ILinker
+ {
+ public:
+ Linker();
+ ~Linker();
+
+ const char* version() override;
+ bool is_used() override;
+ void startup() override;
+ std::shared_ptr alloc_zone(const std::string& zone) override;
+ std::shared_ptr alloc_buffer() override;
+ void load_zone(const std::string& name) override;
+ void unload_zones() override;
+ bool is_valid_asset_type(const std::string& type) override;
+ std::int32_t type_to_int(std::string type) override;
+ std::string type_to_string(std::int32_t type) override;
+ bool supports_building() override;
+ bool supports_version(const zone_target_version version) override;
+
+ void dump_zone(const std::string& name) override;
+ void verify_zone(const std::string& name) override;
+
+ static void* Dedicated_RegisterDvarBool(const char* name, bool defaultValue, unsigned int flags,
+ const char* description);
+ static void* DB_AddXAsset(XAsset* asset, int unk);
+ static const char* GetAssetName(XAsset* asset);
+ static void HandleAsset(XAsset* asset);
+ };
+ }
+}
diff --git a/src/IW3/Structs.hpp b/src/IW3/Structs.hpp
new file mode 100644
index 0000000..4296063
--- /dev/null
+++ b/src/IW3/Structs.hpp
@@ -0,0 +1,1930 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW3
+ {
+ enum XAssetType : std::int32_t
+ {
+ xmodelpieces,
+ physpreset,
+ xanim,
+ xmodel,
+ material,
+ techset,
+ image,
+ sound,
+ sndcurve,
+ loaded_sound,
+ col_map_sp,
+ col_map_mp,
+ com_map,
+ game_map_sp,
+ game_map_mp,
+ map_ents,
+ gfx_map,
+ lightdef,
+ ui_map,
+ // not used
+ font,
+ menufile,
+ menu,
+ localize,
+ weapon,
+ snddriverglobals,
+ // not used
+ fx,
+ impactfx,
+ aitype,
+ // not used
+ mptype,
+ // not used
+ character,
+ // not used
+ xmodelalias,
+ // not used
+ rawfile,
+ stringtable,
+ max,
+ };
+
+ typedef float vec4_t[4];
+ typedef float vec3_t[3];
+ typedef float vec2_t[2];
+
+ template
+ struct VecInternal
+ {
+ float data[N];
+ };
+
+ enum MapType
+ {
+ MAPTYPE_NONE = 0x0,
+ MAPTYPE_INVALID1 = 0x1,
+ MAPTYPE_INVALID2 = 0x2,
+ MAPTYPE_2D = 0x3,
+ MAPTYPE_3D = 0x4,
+ MAPTYPE_CUBE = 0x5,
+ MAPTYPE_COUNT = 0x6,
+ };
+
+ struct Picmip
+ {
+ char platform[2];
+ };
+
+ struct CardMemory
+ {
+ int platform[2];
+ };
+
+ struct GfxImageLoadDef
+ {
+ char levelCount;
+ char flags;
+ __int16 dimensions[3];
+ int format;
+ int resourceSize;
+ char data[1];
+ };
+
+ union GfxTexture
+ {
+ /*IDirect3DBaseTexture9 *basemap;
+ IDirect3DTexture9 *map;
+ IDirect3DVolumeTexture9 *volmap;
+ IDirect3DCubeTexture9 *cubemap;*/
+ GfxImageLoadDef* loadDef;
+ void* data;
+ };
+
+ struct GfxImage
+ {
+ MapType mapType;
+ GfxTexture texture;
+ Picmip picmip;
+ bool noPicmip;
+ char semantic;
+ char track;
+ CardMemory cardMemory;
+ unsigned __int16 width;
+ unsigned __int16 height;
+ unsigned __int16 depth;
+ char category;
+ bool delayLoadPixels;
+ const char* name;
+ };
+
+ enum file_image_flags_t
+ {
+ IMG_FLAG_NOPICMIP = 0x1,
+ IMG_FLAG_NOMIPMAPS = 0x2,
+ IMG_FLAG_CUBEMAP = 0x4,
+ IMG_FLAG_VOLMAP = 0x8,
+ IMG_FLAG_STREAMING = 0x10,
+ IMG_FLAG_LEGACY_NORMALS = 0x20,
+ IMG_FLAG_CLAMP_U = 0x40,
+ IMG_FLAG_CLAMP_V = 0x80,
+ IMG_FLAG_DYNAMIC = 0x10000,
+ IMG_FLAG_RENDER_TARGET = 0x20000,
+ IMG_FLAG_SYSTEMMEM = 0x40000,
+ };
+
+ struct GfxImageFileHeader
+ {
+ char tag[3];
+ char version;
+ char format;
+ char flags;
+ short dimensions[3];
+ int fileSizeForPicmip[4];
+ };
+
+ struct MaterialConstantDef
+ {
+ unsigned int nameHash;
+ char name[12];
+ vec4_t literal;
+ };
+
+ struct GfxStateBits
+ {
+ unsigned int loadBits[2];
+ };
+
+ struct WaterWritable
+ {
+ float floatTime;
+ };
+
+ struct complex_s
+ {
+ float real;
+ float imag;
+ };
+
+ struct water_t
+ {
+ WaterWritable writable;
+ complex_s* H0;
+ float* wTerm;
+ int M;
+ int N;
+ float Lx;
+ float Lz;
+ float gravity;
+ float windvel;
+ float winddir[2];
+ float amplitude;
+ float codeConstant[4];
+ GfxImage* image;
+ };
+
+ /* MaterialTextureDef->semantic */
+#define TS_2D 0x0
+#define TS_FUNCTION 0x1
+#define TS_COLOR_MAP 0x2
+#define TS_UNUSED_1 0x3
+#define TS_UNUSED_2 0x4
+#define TS_NORMAL_MAP 0x5
+#define TS_UNUSED_3 0x6
+#define TS_UNUSED_4 0x7
+#define TS_SPECULAR_MAP 0x8
+#define TS_UNUSED_5 0x9
+#define TS_UNUSED_6 0xA
+#define TS_WATER_MAP 0xB
+
+ union MaterialTextureDefInfo
+ {
+ GfxImage* image; // MaterialTextureDef->semantic != TS_WATER_MAP
+ water_t* water; // MaterialTextureDef->semantic == TS_WATER_MAP
+ };
+
+ struct MaterialTextureDef
+ {
+ unsigned int typeHash;
+ char firstCharacter;
+ char secondLastCharacter;
+ char sampleState;
+ char semantic;
+ GfxImage* image;
+ };
+
+ struct GfxDrawSurfFields
+ {
+ unsigned __int64 objectId : 16;
+ unsigned __int64 reflectionProbeIndex : 8;
+ unsigned __int64 customIndex : 5;
+ unsigned __int64 materialSortedIndex : 11;
+ unsigned __int64 prepass : 2;
+ unsigned __int64 primaryLightIndex : 8;
+ unsigned __int64 surfType : 4;
+ unsigned __int64 primarySortKey : 6;
+ unsigned __int64 unused : 4;
+ };
+
+ union GfxDrawSurf
+ {
+ GfxDrawSurfFields fields;
+ unsigned long long packed;
+ };
+
+ struct GfxVertexShaderLoadDef
+ {
+ unsigned int* program;
+ unsigned __int16 programSize;
+ unsigned __int16 loadForRenderer;
+ };
+
+ struct MaterialVertexShaderProgram
+ {
+ void* vs;
+ GfxVertexShaderLoadDef loadDef;
+ };
+
+ struct MaterialVertexShader
+ {
+ const char* name;
+ MaterialVertexShaderProgram prog;
+ };
+
+ struct GfxPixelShaderLoadDef
+ {
+ unsigned int* program;
+ unsigned __int16 programSize;
+ unsigned __int16 loadForRenderer;
+ };
+
+ struct MaterialPixelShaderProgram
+ {
+ void* ps;
+ GfxPixelShaderLoadDef loadDef;
+ };
+
+ struct MaterialPixelShader
+ {
+ const char* name;
+ MaterialPixelShaderProgram prog;
+ };
+
+ struct MaterialArgumentCodeConst
+ {
+ unsigned __int16 index;
+ char firstRow;
+ char rowCount;
+ };
+
+ union MaterialArgumentDef
+ {
+ const float* literalConst;
+ MaterialArgumentCodeConst codeConst;
+ unsigned int codeSampler;
+ unsigned int nameHash;
+ };
+
+ struct MaterialShaderArgument
+ {
+ unsigned __int16 type;
+ unsigned __int16 dest;
+ MaterialArgumentDef u;
+ };
+
+ struct MaterialStreamRouting
+ {
+ char source;
+ char dest;
+ };
+
+ struct MaterialVertexStreamRouting
+ {
+ MaterialStreamRouting data[16];
+ void* decl[16];
+ };
+
+ struct MaterialVertexDeclaration
+ {
+ char streamCount;
+ bool hasOptionalSource;
+ bool isLoaded;
+ char pad[1];
+ MaterialVertexStreamRouting routing;
+ };
+
+ struct MaterialPass
+ {
+ MaterialVertexDeclaration* vertexDecl;
+ MaterialVertexShader* vertexShader;
+ MaterialPixelShader* pixelShader;
+ char perPrimArgCount;
+ char perObjArgCount;
+ char stableArgCount;
+ char customSamplerFlags;
+ MaterialShaderArgument* args;
+ };
+
+ struct MaterialTechniqueHdr
+ {
+ const char* name;
+ unsigned __int16 flags;
+ unsigned __int16 numPasses;
+ };
+
+ struct MaterialTechnique
+ {
+ MaterialTechniqueHdr hdr;
+ MaterialPass pass[1];
+ };
+
+ struct MaterialTechniqueSet
+ {
+ const char* name;
+
+ union
+ {
+ int pad;
+
+ struct
+ {
+ char worldVertFormat;
+ bool hasBeenUploaded;
+ char unused[1];
+ };
+ };
+
+ MaterialTechniqueSet* remappedTechniqueSet;
+ MaterialTechnique* techniques[34];
+ };
+
+#pragma pack(push, 4)
+ struct MaterialInfo
+ {
+ const char* name;
+ char gameFlags;
+ char sortKey;
+ char textureAtlasRowCount;
+ char textureAtlasColumnCount;
+ GfxDrawSurf drawSurf;
+ unsigned int surfaceTypeBits;
+ unsigned __int16 hashIndex;
+ };
+#pragma pack(pop)
+
+ //enum MaterialTechniqueTypeMeme
+ //{
+ // TECHNIQUE_DEPTH_PREPASS = 0x0,
+ // TECHNIQUE_BUILD_FLOAT_Z = 0x1,
+ // TECHNIQUE_BUILD_SHADOWMAP_DEPTH = 0x2,
+ // TECHNIQUE_BUILD_SHADOWMAP_COLOR = 0x3,
+ // TECHNIQUE_UNLIT = 0x4,
+ // TECHNIQUE_EMISSIVE = 0x5,
+ // TECHNIQUE_EMISSIVE_SHADOW = 0x6,
+ // TECHNIQUE_LIT_BEGIN = 0x7,
+ // TECHNIQUE_LIT = 0x7,
+ // TECHNIQUE_LIT_SUN = 0x8,
+ // TECHNIQUE_LIT_SUN_SHADOW = 0x9,
+ // TECHNIQUE_LIT_SPOT = 0xA,
+ // TECHNIQUE_LIT_SPOT_SHADOW = 0xB,
+ // TECHNIQUE_LIT_OMNI = 0xC,
+ // TECHNIQUE_LIT_OMNI_SHADOW = 0xD,
+ // TECHNIQUE_LIT_INSTANCED = 0xE,
+ // TECHNIQUE_LIT_INSTANCED_SUN = 0xF,
+ // TECHNIQUE_LIT_INSTANCED_SUN_SHADOW = 0x10,
+ // TECHNIQUE_LIT_INSTANCED_SPOT = 0x11,
+ // TECHNIQUE_LIT_INSTANCED_SPOT_SHADOW = 0x12,
+ // TECHNIQUE_LIT_INSTANCED_OMNI = 0x13,
+ // TECHNIQUE_LIT_INSTANCED_OMNI_SHADOW = 0x14,
+ // TECHNIQUE_LIT_END = 0x15,
+ // TECHNIQUE_LIGHT_SPOT = 0x15,
+ // TECHNIQUE_LIGHT_OMNI = 0x16,
+ // TECHNIQUE_LIGHT_SPOT_SHADOW = 0x17,
+ // TECHNIQUE_FAKELIGHT_NORMAL = 0x18,
+ // TECHNIQUE_FAKELIGHT_VIEW = 0x19,
+ // TECHNIQUE_SUNLIGHT_PREVIEW = 0x1A,
+ // TECHNIQUE_CASE_TEXTURE = 0x1B,
+ // TECHNIQUE_WIREFRAME_SOLID = 0x1C,
+ // TECHNIQUE_WIREFRAME_SHADED = 0x1D,
+ // TECHNIQUE_SHADOWCOOKIE_CASTER = 0x1E,
+ // TECHNIQUE_SHADOWCOOKIE_RECEIVER = 0x1F,
+ // TECHNIQUE_DEBUG_BUMPMAP = 0x20,
+ // TECHNIQUE_DEBUG_BUMPMAP_INSTANCED = 0x21,
+ // //TECHNIQUE_COUNT = 0x22
+ //};
+
+ struct infoParm_t
+ {
+ const char* name;
+ int clearSolid;
+ int surfaceFlags;
+ int contents;
+ int toolFlags;
+ };
+
+ struct Material
+ {
+ const char* name;
+ char gameFlags;
+ char sortKey;
+ char textureAtlasRowCount;
+ char textureAtlasColumnCount;
+ GfxDrawSurf drawSurf;
+ unsigned int surfaceTypeBits;
+ unsigned __int16 hashIndex;
+ unsigned char animationX;
+ unsigned char animationY;
+ // MaterialInfo info;
+ char stateBitsEntry[34];
+ char numMaps;
+ char constantCount;
+ char stateBitsCount;
+ char stateFlags;
+ char cameraRegion;
+ MaterialTechniqueSet* techniqueSet;
+ MaterialTextureDef* maps;
+ MaterialConstantDef* constantTable;
+ GfxStateBits* stateMap;
+ };
+
+ struct cplane_s
+ {
+ float normal[3];
+ float dist;
+ char type;
+ char signbits;
+ char pad[2];
+ };
+
+#pragma pack(push, 2)
+ struct cbrushside_t
+ {
+ cplane_s* plane;
+ unsigned int materialNum;
+ __int16 firstAdjacentSideOffset;
+ char edgeCount;
+ };
+#pragma pack(pop)
+
+ struct DObjAnimMat
+ {
+ float quat[4];
+ float trans[3];
+ float transWeight;
+ };
+
+ struct XSurfaceVertexInfo
+ {
+ short vertCount[4];
+ unsigned short* vertsBlend;
+ };
+
+ union GfxColor
+ {
+ unsigned int packed;
+ char array[4];
+ };
+
+ union PackedTexCoords
+ {
+ unsigned int packed;
+ };
+
+ union PackedUnitVec
+ {
+ unsigned int packed;
+ char array[4];
+ };
+
+ struct GfxPackedVertex
+ {
+ float xyz[3];
+ float binormalSign;
+ GfxColor color;
+ PackedTexCoords texCoord;
+ PackedUnitVec normal;
+ PackedUnitVec tangent;
+ };
+
+ struct XSurfaceCollisionAabb
+ {
+ unsigned short mins[3];
+ unsigned short maxs[3];
+ };
+
+ struct XSurfaceCollisionNode
+ {
+ XSurfaceCollisionAabb aabb;
+ unsigned short childBeginIndex;
+ unsigned short childCount;
+ };
+
+ struct XSurfaceCollisionLeaf
+ {
+ unsigned short triangleBeginIndex;
+ };
+
+ struct XSurfaceCollisionTree
+ {
+ float trans[3];
+ float scale[3];
+ unsigned int nodeCount;
+ XSurfaceCollisionNode* nodes;
+ unsigned int leafCount;
+ XSurfaceCollisionLeaf* leafs;
+ };
+
+ struct XRigidVertList
+ {
+ unsigned short boneOffset;
+ unsigned short vertCount;
+ unsigned short triOffset;
+ unsigned short triCount;
+ XSurfaceCollisionTree* collisionTree;
+ };
+
+ struct XSurface
+ {
+ char tileMode;
+ bool deformed;
+ unsigned __int16 vertCount;
+ unsigned __int16 triCount;
+ char zoneHandle;
+ unsigned __int16 baseTriIndex;
+ unsigned __int16 baseVertIndex;
+ unsigned __int16* triIndices;
+ XSurfaceVertexInfo vertInfo;
+ GfxPackedVertex* verts0;
+ unsigned int vertListCount;
+ XRigidVertList* vertList;
+ int partBits[4];
+ };
+
+ struct BrushWrapper
+ {
+ float mins[3];
+ int contents;
+ float maxs[3];
+ unsigned int numsides;
+ cbrushside_t* sides;
+ __int16 axialMaterialNum[2][3];
+ char* baseAdjacentSide;
+ __int16 firstAdjacentSideOffsets[2][3];
+ char edgeCount[2][3];
+ int totalEdgeCount;
+ cplane_s* planes;
+ };
+
+ struct PhysMass
+ {
+ float centerOfMass[3];
+ float momentsOfInertia[3];
+ float productsOfInertia[3];
+ };
+
+ struct PhysGeomInfo
+ {
+ BrushWrapper* brush;
+ int type;
+ float orientation[3][3];
+ float offset[3];
+ float halfLengths[3];
+ };
+
+ struct PhysGeomList
+ {
+ unsigned int count;
+ PhysGeomInfo* geoms;
+ PhysMass mass;
+ };
+
+ struct XBoneInfo
+ {
+ float bounds[2][3];
+ float offset[3];
+ float radiusSquared;
+ };
+
+ struct XModelHighMipBounds
+ {
+ float mins[3];
+ float maxs[3];
+ };
+
+ struct XModelStreamInfo
+ {
+ XModelHighMipBounds* highMipBounds;
+ };
+
+ struct XModelCollTri_s
+ {
+ float plane[4];
+ float svec[4];
+ float tvec[4];
+ };
+
+ struct XModelCollSurf_s
+ {
+ XModelCollTri_s* collTris;
+ int numCollTris;
+ float mins[3];
+ float maxs[3];
+ int boneIdx;
+ int contents;
+ int surfFlags;
+ };
+
+ struct XModelLodInfo
+ {
+ float dist;
+ unsigned __int16 numsurfs;
+ unsigned __int16 surfIndex;
+ int partBits[4];
+ char lod;
+ char smcIndexPlusOne;
+ char smcAllocBits;
+ char unused;
+ };
+
+#pragma pack(push, 4)
+ struct PhysPreset
+ {
+ const char* name;
+ int type;
+ float mass;
+ float bounce;
+ float friction;
+ float bulletForceScale;
+ float explosiveForceScale;
+ const char* sndAliasPrefix;
+ float piecesSpreadFraction;
+ float piecesUpwardVelocity;
+ char tempDefaultToCylinder;
+ };
+#pragma pack(pop)
+
+ struct XModel
+ {
+ const char* name;
+ char numBones;
+ char numRootBones;
+ unsigned char numsurfs;
+ char lodRampType;
+ unsigned __int16* boneNames;
+ char* parentList;
+ __int16* quats;
+ float* trans;
+ char* partClassification;
+ DObjAnimMat* baseMat;
+ XSurface* surfs;
+ Material** materialHandles;
+ XModelLodInfo lodInfo[4];
+ XModelCollSurf_s* collSurfs;
+ int numCollSurfs;
+ int contents;
+ XBoneInfo* boneInfo;
+ float radius;
+ float mins[3];
+ float maxs[3];
+ __int16 numLods;
+ __int16 collLod;
+ XModelStreamInfo streamInfo;
+ int memUsage;
+ char flags;
+ bool bad;
+ PhysPreset* physPreset;
+ PhysGeomList* physGeoms;
+ };
+
+ union XAnimIndices
+ {
+ char* _1;
+ unsigned __int16* _2;
+ void* data;
+ };
+
+ union XAnimDynamicFrames
+ {
+ char (*_1)[3];
+ unsigned __int16 (*_2)[3];
+ };
+
+ union XAnimDynamicIndices
+ {
+ char _1[1];
+ unsigned __int16 _2[1];
+ };
+
+#pragma pack(push, 4)
+ struct XAnimPartTransFrames
+ {
+ float mins[3];
+ float size[3];
+ XAnimDynamicFrames frames;
+ XAnimDynamicIndices indices;
+ };
+
+ union XAnimPartTransData
+ {
+ XAnimPartTransFrames frames;
+ float frame0[3];
+ };
+
+ struct XAnimPartTrans
+ {
+ unsigned __int16 size;
+ char smallTrans;
+ __declspec(align(2)) XAnimPartTransData u;
+ };
+
+ struct XAnimDeltaPartQuatDataFrames
+ {
+ __int16 (*frames)[2];
+ XAnimDynamicIndices indices;
+ };
+
+ union XAnimDeltaPartQuatData
+ {
+ XAnimDeltaPartQuatDataFrames frames;
+ __int16 frame0[2];
+ };
+
+ struct XAnimDeltaPartQuat
+ {
+ unsigned __int16 size;
+ __declspec(align(4)) XAnimDeltaPartQuatData u;
+ };
+
+ struct XAnimDeltaPart
+ {
+ XAnimPartTrans* trans;
+ XAnimDeltaPartQuat* quat;
+ };
+
+ struct XAnimNotifyInfo
+ {
+ short name;
+ float time;
+ };
+
+#ifdef __cplusplus
+ enum XAnimPartType
+ {
+ PART_TYPE_NO_QUAT = 0x0,
+ PART_TYPE_SIMPLE_QUAT = 0x1,
+ PART_TYPE_NORMAL_QUAT = 0x2,
+ PART_TYPE_PRECISION_QUAT = 0x3,
+ PART_TYPE_SIMPLE_QUAT_NO_SIZE = 0x4,
+ PART_TYPE_NORMAL_QUAT_NO_SIZE = 0x5,
+ PART_TYPE_PRECISION_QUAT_NO_SIZE = 0x6,
+ PART_TYPE_SMALL_TRANS = 0x7,
+ PART_TYPE_TRANS = 0x8,
+ PART_TYPE_TRANS_NO_SIZE = 0x9,
+ PART_TYPE_NO_TRANS = 0xA,
+ PART_TYPE_ALL = 0xB,
+ PART_TYPE_COUNT = 0xC,
+ };
+#endif
+
+#pragma pack(pop)
+
+ struct XAnimParts
+ {
+ char* name; // 0
+ unsigned short dataByteCount; // 4
+ unsigned short dataShortCount; // 6
+ unsigned short dataIntCount; // 8
+ unsigned short randomDataByteCount; // 10 - 0xA
+ unsigned short randomDataIntCount; // 12 - 0xC
+ unsigned short framecount; // 14 - 0xE
+ char bLoop; // 16
+ char bDelta; // 31
+ unsigned char boneCount[10]; // 17
+ char notifyCount; // 27
+ char assetType; // 30
+ bool isDefault;
+ unsigned int randomDataShortCount; // 32 - 0x20
+ unsigned int indexcount; // 36 - 0x24
+ float framerate; // 40 - 0x28
+ float frequency; // 44 - 0x2C
+ unsigned short* tagnames; // 48 - 0x30
+ char* dataByte; // 52 - 0x34
+ short* dataShort; // 56 - 0x38
+ int* dataInt; // 60 - 0x3C
+ short* randomDataShort; // 64 - 0x40
+ char* randomDataByte; // 68 - 0x44
+ int* randomDataInt; // 72 - 0x48
+ XAnimIndices indices; // 76 - 0x4C
+ XAnimNotifyInfo* notify; // 80 - 0x50
+ XAnimDeltaPart* delta; // 84 - 0x54
+ };
+
+ struct GfxStreamingAabbTree
+ {
+ unsigned __int16 firstItem;
+ unsigned __int16 itemCount;
+ unsigned __int16 firstChild;
+ unsigned __int16 childCount;
+ float mins[3];
+ float maxs[3];
+ };
+
+ struct GfxWorldStreamInfo
+ {
+ int aabbTreeCount;
+ // GfxStreamingAabbTree *aabbTrees;
+ // int leafRefCount;
+ // int *leafRefs;
+ };
+
+ struct GfxWorldVertex
+ {
+ float xyz[3];
+ float binormalSign;
+ GfxColor color;
+ float texCoord[2];
+ float lmapCoord[2];
+ PackedUnitVec normal;
+ PackedUnitVec tangent;
+ };
+
+ struct GfxWorldVertexData
+ {
+ GfxWorldVertex* vertices;
+ void/*IDirect3DVertexBuffer9*/ * worldVb;
+ };
+
+ struct GfxWorldVertexLayerData
+ {
+ char* data;
+ void/*IDirect3DVertexBuffer9*/ * layerVb;
+ };
+
+ struct SunLightParseParams
+ {
+ char name[64];
+ float ambientScale;
+ float ambientColor[3];
+ float diffuseFraction;
+ float sunLight;
+ float sunColor[3];
+ float diffuseColor[3];
+ char diffuseColorHasBeenSet;
+ float angles[3];
+ };
+
+ struct __declspec(align(4)) GfxLightImage
+ {
+ GfxImage* image;
+ char samplerState;
+ };
+
+ struct GfxLightDef
+ {
+ const char* name;
+ GfxLightImage attenuation;
+ int lmapLookupStart;
+ };
+
+ struct GfxLight
+ {
+ char type;
+ char canUseShadowMap;
+ char unused[2];
+ float color[3];
+ float dir[3];
+ float origin[3];
+ float radius;
+ float cosHalfFovOuter;
+ float cosHalfFovInner;
+ int exponent;
+ unsigned int spotShadowIndex;
+ GfxLightDef* def;
+ };
+
+ struct GfxReflectionProbe
+ {
+ float origin[3];
+ GfxImage* reflectionImage;
+ };
+
+ struct GfxWorldDpvsPlanes
+ {
+ int cellCount;
+ cplane_s* planes;
+ unsigned __int16* nodes;
+ unsigned int* sceneEntCellBits;
+ };
+
+ struct GfxAabbTree
+ {
+ float mins[3];
+ float maxs[3];
+ unsigned __int16 childCount;
+ unsigned __int16 surfaceCount;
+ unsigned __int16 startSurfIndex;
+ unsigned __int16 surfaceCountNoDecal;
+ unsigned __int16 startSurfIndexNoDecal;
+ unsigned __int16 smodelIndexCount;
+ unsigned __int16* smodelIndexes;
+ int childrenOffset;
+ };
+
+ struct GfxPortal;
+
+ struct GfxPortalWritable
+ {
+ char isQueued;
+ char isAncestor;
+ char recursionDepth;
+ char hullPointCount;
+ float (*hullPoints)[2];
+ GfxPortal* queuedParent;
+ };
+
+ struct DpvsPlane
+ {
+ float coeffs[4];
+ char side[3];
+ char pad;
+ };
+
+ struct GfxCell;
+
+ struct GfxPortal
+ {
+ GfxPortalWritable writable;
+ DpvsPlane plane;
+ GfxCell* cell;
+ float (*vertices)[3];
+ char vertexCount;
+ float hullAxis[2][3];
+ };
+
+ struct GfxCell
+ {
+ float mins[3];
+ float maxs[3];
+ int aabbTreeCount;
+ GfxAabbTree* aabbTree;
+ int portalCount;
+ GfxPortal* portals;
+ int cullGroupCount;
+ int* cullGroups;
+ char reflectionProbeCount;
+ char* reflectionProbes;
+ };
+
+ struct GfxLightmapArray
+ {
+ GfxImage* primary;
+ GfxImage* secondary;
+ };
+
+ struct GfxLightGridEntry
+ {
+ unsigned __int16 colorsIndex;
+ char primaryLightIndex;
+ char needsTrace;
+ };
+
+ struct GfxLightGridColors
+ {
+ char rgb[56][3];
+ };
+
+ struct GfxLightGrid
+ {
+ char hasLightRegions;
+ unsigned int sunPrimaryLightIndex;
+ unsigned __int16 mins[3];
+ unsigned __int16 maxs[3];
+ unsigned int rowAxis;
+ unsigned int colAxis;
+ unsigned __int16* rowDataStart;
+ unsigned int rawRowDataSize;
+ char* rawRowData;
+ unsigned int entryCount;
+ GfxLightGridEntry* entries;
+ unsigned int colorCount;
+ GfxLightGridColors* colors;
+ };
+
+ struct GfxBrushModelWritable
+ {
+ float mins[3];
+ float maxs[3];
+ };
+
+ struct __declspec(align(4)) GfxBrushModel
+ {
+ GfxBrushModelWritable writable;
+ float bounds[2][3];
+ unsigned __int16 surfaceCount;
+ unsigned __int16 startSurfIndex;
+ unsigned __int16 surfaceCountNoDecal;
+ };
+
+ struct MaterialMemory
+ {
+ Material* material;
+ int memory;
+ };
+
+ struct sunflare_t
+ {
+ char hasValidData;
+ Material* spriteMaterial;
+ Material* flareMaterial;
+ float spriteSize;
+ float flareMinSize;
+ float flareMinDot;
+ float flareMaxSize;
+ float flareMaxDot;
+ float flareMaxAlpha;
+ int flareFadeInTime;
+ int flareFadeOutTime;
+ float blindMinDot;
+ float blindMaxDot;
+ float blindMaxDarken;
+ int blindFadeInTime;
+ int blindFadeOutTime;
+ float glareMinDot;
+ float glareMaxDot;
+ float glareMaxLighten;
+ int glareFadeInTime;
+ int glareFadeOutTime;
+ float sunFxPosition[3];
+ };
+
+ struct XModelDrawInfo
+ {
+ unsigned __int16 lod;
+ unsigned __int16 surfId;
+ };
+
+ struct GfxSceneDynModel
+ {
+ XModelDrawInfo info;
+ unsigned __int16 dynEntId;
+ };
+
+ struct BModelDrawInfo
+ {
+ unsigned __int16 surfId;
+ };
+
+ struct GfxSceneDynBrush
+ {
+ BModelDrawInfo info;
+ unsigned __int16 dynEntId;
+ };
+
+ struct GfxShadowGeometry
+ {
+ unsigned __int16 surfaceCount;
+ unsigned __int16 smodelCount;
+ unsigned __int16* sortedSurfIndex;
+ unsigned __int16* smodelIndex;
+ };
+
+ struct GfxLightRegionAxis
+ {
+ float dir[3];
+ float midPoint;
+ float halfSize;
+ };
+
+ struct GfxLightRegionHull
+ {
+ float kdopMidPoint[9];
+ float kdopHalfSize[9];
+ unsigned int axisCount;
+ GfxLightRegionAxis* axis;
+ };
+
+ struct GfxLightRegion
+ {
+ unsigned int hullCount;
+ GfxLightRegionHull* hulls;
+ };
+
+ struct GfxStaticModelInst
+ {
+ float mins[3];
+ float maxs[3];
+ GfxColor groundLighting;
+ };
+
+ struct srfTriangles_t
+ {
+ int vertexLayerData;
+ int firstVertex;
+ unsigned __int16 vertexCount;
+ unsigned __int16 triCount;
+ int baseIndex;
+ };
+
+ struct GfxSurface
+ {
+ srfTriangles_t tris;
+ Material* material;
+ char lightmapIndex;
+ char reflectionProbeIndex;
+ char primaryLightIndex;
+ char flags;
+ float bounds[2][3];
+ };
+
+ struct GfxCullGroup
+ {
+ float mins[3];
+ float maxs[3];
+ int surfaceCount;
+ int startSurfIndex;
+ };
+
+ struct GfxPackedPlacement
+ {
+ float origin[3];
+ vec3_t axis[3];
+ float scale;
+ };
+
+ struct __declspec(align(4)) GfxStaticModelDrawInst
+ {
+ float cullDist;
+ GfxPackedPlacement placement;
+ XModel* model;
+ unsigned __int16 smodelCacheIndex[4];
+ char reflectionProbeIndex;
+ char primaryLightIndex;
+ unsigned __int16 lightingHandle;
+ char flags;
+ };
+
+ struct GfxWorldDpvsStatic
+ {
+ unsigned int smodelCount;
+ unsigned int staticSurfaceCount;
+ unsigned int staticSurfaceCountNoDecal;
+ unsigned int litSurfsBegin;
+ unsigned int litSurfsEnd;
+ unsigned int decalSurfsBegin;
+ unsigned int decalSurfsEnd;
+ unsigned int emissiveSurfsBegin;
+ unsigned int emissiveSurfsEnd;
+ unsigned int smodelVisDataCount;
+ unsigned int surfaceVisDataCount;
+ char* smodelVisData[3];
+ char* surfaceVisData[3];
+ unsigned int* lodData;
+ unsigned __int16* sortedSurfIndex;
+ GfxStaticModelInst* smodelInsts;
+ GfxSurface* surfaces;
+ GfxCullGroup* cullGroups;
+ GfxStaticModelDrawInst* smodelDrawInsts;
+ GfxDrawSurf* surfaceMaterials;
+ unsigned int* surfaceCastsSunShadow;
+ volatile int usageCount;
+ };
+
+ struct GfxWorldDpvsDynamic
+ {
+ unsigned int dynEntClientWordCount[2];
+ unsigned int dynEntClientCount[2];
+ unsigned int* dynEntCellBits[2];
+ char* dynEntVisData[2][3];
+ };
+
+ struct GfxWorld
+ {
+ const char* name;
+ const char* baseName;
+ int planeCount;
+ int nodeCount;
+ int indexCount;
+ unsigned __int16* indices;
+ int surfaceCount;
+ GfxWorldStreamInfo streamInfo;
+ int skySurfCount;
+ int* skyStartSurfs;
+ GfxImage* skyImage;
+ char skySamplerState;
+ unsigned int vertexCount;
+ GfxWorldVertexData vd;
+ unsigned int vertexLayerDataSize;
+ GfxWorldVertexLayerData vld;
+ SunLightParseParams sunParse;
+ GfxLight* sunLight;
+ float sunColorFromBsp[3];
+ unsigned int sunPrimaryLightIndex;
+ unsigned int primaryLightCount;
+ int cullGroupCount;
+ unsigned int reflectionProbeCount;
+ GfxReflectionProbe* reflectionProbes;
+ GfxTexture* reflectionProbeTextures;
+ GfxWorldDpvsPlanes dpvsPlanes;
+ int cellBitsCount;
+ GfxCell* cells;
+ int lightmapCount;
+ GfxLightmapArray* lightmaps;
+ GfxLightGrid lightGrid;
+ GfxTexture* lightmapPrimaryTextures;
+ GfxTexture* lightmapSecondaryTextures;
+ int modelCount;
+ GfxBrushModel* models;
+ float mins[3];
+ float maxs[3];
+ unsigned int checksum;
+ int materialMemoryCount;
+ MaterialMemory* materialMemory;
+ sunflare_t sun;
+ float outdoorLookupMatrix[4][4];
+ GfxImage* outdoorImage;
+ unsigned int* cellCasterBits;
+ GfxSceneDynModel* sceneDynModel;
+ GfxSceneDynBrush* sceneDynBrush;
+ unsigned int* primaryLightEntityShadowVis;
+ unsigned int* primaryLightDynEntShadowVis[2];
+ char* nonSunPrimaryLightForModelDynEnt;
+ GfxShadowGeometry* shadowGeom;
+ GfxLightRegion* lightRegion;
+ GfxWorldDpvsStatic dpvs;
+ GfxWorldDpvsDynamic dpvsDyn;
+ };
+
+ struct cStaticModelWritable
+ {
+ unsigned __int16 nextModelInWorldSector;
+ };
+
+ struct cStaticModel_s
+ {
+ cStaticModelWritable writable;
+ XModel* xmodel;
+ float origin[3];
+ float invScaledAxis[3][3];
+ float absmin[3];
+ float absmax[3];
+ };
+
+ struct dmaterial_t
+ {
+ char material[64];
+ int surfaceFlags;
+ int contentFlags;
+ };
+
+ struct cNode_t
+ {
+ cplane_s* plane;
+ __int16 children[2];
+ };
+
+#pragma pack(push, 4)
+ struct cLeaf_t
+ {
+ unsigned __int16 firstCollAabbIndex;
+ unsigned __int16 collAabbCount;
+ int brushContents;
+ int terrainContents;
+ float mins[3];
+ float maxs[3];
+ int leafBrushNode;
+ __int16 cluster;
+ };
+#pragma pack(pop)
+
+ struct cLeafBrushNodeLeaf_t
+ {
+ unsigned __int16* brushes;
+ };
+
+ struct cLeafBrushNodeChildren_t
+ {
+ float dist;
+ float range;
+ unsigned __int16 childOffset[2];
+ };
+
+ union cLeafBrushNodeData_t
+ {
+ cLeafBrushNodeLeaf_t leaf;
+ cLeafBrushNodeChildren_t children;
+ };
+
+ struct cLeafBrushNode_s
+ {
+ char axis;
+ __int16 leafBrushCount;
+ int contents;
+ cLeafBrushNodeData_t data;
+ };
+
+ struct CollisionBorder
+ {
+ float distEq[3];
+ float zBase;
+ float zSlope;
+ float start;
+ float length;
+ };
+
+ struct CollisionPartition
+ {
+ char triCount;
+ char borderCount;
+ int firstTri;
+ CollisionBorder* borders;
+ };
+
+ union CollisionAabbTreeIndex
+ {
+ int firstChildIndex;
+ int partitionIndex;
+ };
+
+ struct CollisionAabbTree
+ {
+ float origin[3];
+ float halfSize[3];
+ unsigned __int16 materialIndex;
+ unsigned __int16 childCount;
+ CollisionAabbTreeIndex u;
+ };
+
+ /* 860 */
+ struct cmodel_t
+ {
+ float mins[3];
+ float maxs[3];
+ float radius;
+ cLeaf_t leaf;
+ };
+
+ /* 861 */
+#pragma pack(push, 16)
+ struct cbrush_t
+ {
+ float mins[3];
+ int contents;
+ float maxs[3];
+ unsigned int numsides;
+ cbrushside_t* sides;
+ __int16 axialMaterialNum[2][3];
+ char* baseAdjacentSide;
+ __int16 firstAdjacentSideOffsets[2][3];
+ char edgeCount[2][3];
+ char pad[8];
+ };
+#pragma pack(pop)
+
+ struct Bounds
+ {
+ vec3_t midPoint;
+ vec3_t halfSize;
+ };
+
+ struct TriggerModel
+ {
+ int contents;
+ unsigned __int16 hullCount;
+ unsigned __int16 firstHull;
+ };
+
+ /* 2376 */
+ struct TriggerHull
+ {
+ Bounds bounds;
+ int contents;
+ unsigned __int16 slabCount;
+ unsigned __int16 firstSlab;
+ };
+
+ /* 2377 */
+ struct TriggerSlab
+ {
+ float dir[3];
+ float midPoint;
+ float halfSize;
+ };
+
+ /* 2378 */
+ struct MapTriggers
+ {
+ unsigned int count;
+ TriggerModel* models;
+ unsigned int hullCount;
+ TriggerHull* hulls;
+ unsigned int slabCount;
+ TriggerSlab* slabs;
+ };
+
+ struct MapEnts
+ {
+ const char* name;
+ char* entityString;
+ int numEntityChars; // The structure actually ends here...
+ MapTriggers trigger; // Pretty sure that's not correct.
+ // this goes on for a while but we don't need any of it
+ };
+
+ struct GfxPlacement
+ {
+ float quat[4];
+ float origin[3];
+ };
+
+ struct FxEffectDef_Placeholder
+ {
+ const char* name;
+ };
+
+ struct DynEntityDef
+ {
+ int type;
+ GfxPlacement pose;
+ XModel* xModel;
+ unsigned __int16 brushModel;
+ unsigned __int16 physicsBrushModel;
+ FxEffectDef_Placeholder* destroyFx;
+ /*XModelPieces*/
+ void* destroyPieces;
+ PhysPreset* physPreset;
+ int health;
+ PhysMass mass;
+ int contents;
+ };
+
+ struct clipMap_t
+ {
+ const char* name;
+ int isInUse;
+ int planeCount;
+ cplane_s* planes;
+ unsigned int numStaticModels;
+ cStaticModel_s* staticModelList;
+ unsigned int numMaterials;
+ dmaterial_t* materials;
+ unsigned int numBrushSides;
+ cbrushside_t* brushsides;
+ unsigned int numBrushEdges;
+ char* brushEdges;
+ unsigned int numNodes;
+ cNode_t* nodes;
+ unsigned int numLeafs;
+ cLeaf_t* leafs;
+ unsigned int leafbrushNodesCount;
+ cLeafBrushNode_s* leafbrushNodes;
+ unsigned int numLeafBrushes;
+ unsigned __int16* leafbrushes;
+ unsigned int numLeafSurfaces;
+ unsigned int* leafsurfaces;
+ unsigned int vertCount;
+ float (*verts)[3];
+ int triCount;
+ unsigned __int16* triIndices;
+ char* triEdgeIsWalkable;
+ int borderCount;
+ CollisionBorder* borders;
+ int partitionCount;
+ CollisionPartition* partitions;
+ int aabbTreeCount;
+ CollisionAabbTree* aabbTrees;
+ unsigned int numSubModels;
+ cmodel_t* cmodels;
+ unsigned __int16 numBrushes;
+ cbrush_t* brushes;
+ int numClusters;
+ int clusterBytes;
+ char* visibility;
+ int vised;
+ MapEnts* mapEnts;
+ cbrush_t* box_brush;
+ cmodel_t box_model;
+ unsigned __int16 dynEntCount[2];
+ DynEntityDef* dynEntDefList[2];
+ /*DynEntityPose*/
+ void* dynEntPoseList[2];
+ /*DynEntityClient*/
+ void* dynEntClientList[2];
+ /*DynEntityColl*/
+ void* dynEntCollList[2];
+ unsigned int checksum;
+ };
+
+ struct RawFile
+ {
+ const char* name;
+ int len;
+ const char* buffer;
+ };
+
+ struct ComPrimaryLight
+ {
+ char type;
+ char canUseShadowMap;
+ char exponent;
+ char unused;
+ float color[3];
+ float dir[3];
+ float origin[3];
+ float radius;
+ float cosHalfFovOuter;
+ float cosHalfFovInner;
+ float cosHalfFovExpanded;
+ float rotationLimit;
+ float translationLimit;
+ const char* defName;
+ };
+
+ struct ComWorld
+ {
+ const char* name;
+ int isInUse;
+ unsigned int primaryLightCount;
+ ComPrimaryLight* primaryLights;
+ };
+
+ struct FxSpawnDefLooping
+ {
+ int intervalMsec;
+ int count;
+ };
+
+ struct FxIntRange
+ {
+ int base;
+ int amplitude;
+ };
+
+ struct FxSpawnDefOneShot
+ {
+ FxIntRange count;
+ };
+
+ union FxSpawnDef
+ {
+ FxSpawnDefLooping looping;
+ FxSpawnDefOneShot oneShot;
+ };
+
+ struct FxFloatRange
+ {
+ float base;
+ float amplitude;
+ };
+
+ struct FxElemAtlas
+ {
+ char behavior;
+ char index;
+ char fps;
+ char loopCount;
+ char colIndexBits;
+ char rowIndexBits;
+ __int16 entryCount;
+ };
+
+ struct FxElemVec3Range
+ {
+ float base[3];
+ float amplitude[3];
+ };
+
+ struct FxElemVelStateInFrame
+ {
+ FxElemVec3Range velocity;
+ FxElemVec3Range totalDelta;
+ };
+
+ const struct FxElemVelStateSample
+ {
+ FxElemVelStateInFrame local;
+ FxElemVelStateInFrame world;
+ };
+
+ struct FxElemVisualState
+ {
+ char color[4];
+ float rotationDelta;
+ float rotationTotal;
+ float size[2];
+ float scale;
+ };
+
+ const struct FxElemVisStateSample
+ {
+ FxElemVisualState base;
+ FxElemVisualState amplitude;
+ };
+
+ struct FxEffectDef;
+
+ union FxEffectDefRef
+ {
+ FxEffectDef* handle;
+ const char* name;
+ };
+
+ union FxElemVisuals
+ {
+ const void* anonymous;
+ Material* material;
+ XModel* model;
+ FxEffectDefRef effectDef;
+ const char* soundName;
+ };
+
+ struct FxElemMarkVisuals
+ {
+ Material* materials[2];
+ };
+
+ union FxElemDefVisuals
+ {
+ FxElemMarkVisuals* markArray;
+ FxElemVisuals* array;
+ FxElemVisuals instance;
+ };
+
+ struct FxTrailVertex
+ {
+ float pos[2];
+ float normal[2];
+ float texCoord;
+ };
+
+ struct FxTrailDef
+ {
+ int scrollTimeMsec;
+ int repeatDist;
+ int splitDist;
+ int vertCount;
+ FxTrailVertex* verts;
+ int indCount;
+ unsigned __int16* inds;
+ };
+
+ const struct FxElemDef
+ {
+ int flags;
+ FxSpawnDef spawn;
+ FxFloatRange spawnRange;
+ FxFloatRange fadeInRange;
+ FxFloatRange fadeOutRange;
+ float spawnFrustumCullRadius;
+ FxIntRange spawnDelayMsec;
+ FxIntRange lifeSpanMsec;
+ FxFloatRange spawnOrigin[3];
+ FxFloatRange spawnOffsetRadius;
+ FxFloatRange spawnOffsetHeight;
+ FxFloatRange spawnAngles[3];
+ FxFloatRange angularVelocity[3];
+ FxFloatRange initialRotation;
+ FxFloatRange gravity;
+ FxFloatRange reflectionFactor;
+ FxElemAtlas atlas;
+ char elemType;
+ char visualCount;
+ char velIntervalCount;
+ char visStateIntervalCount;
+ FxElemVelStateSample* velSamples;
+ FxElemVisStateSample* visSamples;
+ FxElemDefVisuals visuals;
+ Bounds collBounds;
+ FxEffectDefRef effectOnImpact;
+ FxEffectDefRef effectOnDeath;
+ FxEffectDefRef effectEmitted;
+ FxFloatRange emitDist;
+ FxFloatRange emitDistVariance;
+ FxTrailDef* trailDef;
+ char sortOrder;
+ char lightingFrac;
+ char useItemClip;
+ char unused[1];
+ };
+
+ struct FxEffectDef
+ {
+ const char* name;
+ int flags;
+ int totalSize;
+ int msecLoopingLife;
+ int elemDefCountLooping;
+ int elemDefCountOneShot;
+ int elemDefCountEmission;
+ FxElemDef* elemDefs;
+ };
+
+ enum FxElemType : char
+ {
+ FX_ELEM_TYPE_SPRITE_BILLBOARD = 0x0,
+ FX_ELEM_TYPE_SPRITE_ORIENTED = 0x1,
+ FX_ELEM_TYPE_TAIL = 0x2,
+ FX_ELEM_TYPE_TRAIL = 0x3,
+ FX_ELEM_TYPE_CLOUD = 0x4,
+ FX_ELEM_TYPE_MODEL = 0x5,
+ FX_ELEM_TYPE_OMNI_LIGHT = 0x6,
+ FX_ELEM_TYPE_SPOT_LIGHT = 0x7,
+ FX_ELEM_TYPE_SOUND = 0x8,
+ FX_ELEM_TYPE_DECAL = 0x9,
+ FX_ELEM_TYPE_RUNNER = 0xA,
+ FX_ELEM_TYPE_COUNT = 0xB,
+ FX_ELEM_TYPE_LAST_SPRITE = 0x3,
+ FX_ELEM_TYPE_LAST_DRAWN = 0x7,
+ };
+
+ struct GameWorldMp
+ {
+ const char* name;
+ };
+
+ // Loaded sound
+#pragma pack(push, 4)
+ struct LoadedSoundStruct
+ {
+ int waveFormat;
+ int unknown1;
+ int dataLength;
+ int sampleRate;
+ int bitPerChannel;
+ int channelCount;
+ int unknown3;
+ int blockAlign;
+ int unknown5;
+ char* soundData;
+ };
+#pragma pack(pop)
+
+ struct LoadedSound
+ {
+ const char* name;
+ LoadedSoundStruct struct1;
+ };
+
+ // Sounds
+ struct SpeakerLevels
+ {
+ int speaker;
+ int numLevels;
+ float levels[2];
+ };
+ struct ChannelMap
+ {
+ int entryCount; // how many entries are used
+ SpeakerLevels speakers[6];
+ };
+ struct SpeakerMap
+ {
+ bool isDefault;
+ char _pad[3];
+ const char* name;
+ ChannelMap channelMaps[2][2];
+ };
+ enum snd_alias_type_t : char
+ {
+ SAT_UNKNOWN = 0x0,
+ SAT_LOADED = 0x1,
+ SAT_STREAMED = 0x2,
+ SAT_PRIMED = 0x3,
+ SAT_COUNT = 0x4,
+ };
+ struct StreamFileNamePacked
+ {
+ unsigned __int64 offset;
+ unsigned __int64 length;
+ };
+ struct StreamFileNameRaw
+ {
+ const char* dir;
+ const char* name;
+ };
+ union StreamFileInfo
+ {
+ StreamFileNameRaw raw;
+ StreamFileNamePacked packed;
+ };
+ struct StreamFileName
+ {
+ unsigned __int16 isLocalized;
+ unsigned __int16 fileIndex;
+ StreamFileInfo info;
+ };
+ /*struct StreamedSound
+ {
+ StreamFileName filename;
+ unsigned int totalMsec;
+ };*/
+ struct StreamedSound
+ {
+ const char* dir;
+ const char* name;
+ };
+ struct PrimedSound
+ {
+ StreamFileName filename;
+ LoadedSound* loadedPart;
+ int dataOffset;
+ int totalSize;
+ unsigned int primedCrc;
+ };
+ union SoundData
+ {
+ LoadedSound* loadSnd; // SoundFile->type == SAT_LOADED
+ StreamedSound streamSnd; // SoundFile->type == SAT_STREAMED
+ //PrimedSound primedSnd; // SoundFile->type == SAT_PRIMED
+ };
+ struct SoundFile // 0x10
+ {
+ char type;
+ char _pad[2];
+ bool exists;
+ SoundData sound;
+ };
+#pragma pack(push, 4)
+ struct SndCurve
+ {
+ const char* filename;
+ unsigned __int16 knotCount;
+ vec2_t knots[16];
+ };
+ const struct snd_alias_t
+ {
+ const char* aliasName;
+ const char* subtitle;
+ const char* secondaryAliasName;
+ const char* chainAliasName;
+ SoundFile* soundFile;
+ int sequence;
+ float volMin;
+ float volMax;
+ float pitchMin;
+ float pitchMax;
+ float distMin;
+ float distMax;
+ int flags;
+ float slavePercentage;
+ float probability;
+ float lfePercentage;
+ float centerPercentage;
+ int startDelay;
+ SndCurve* volumeFalloffCurve;
+ float envelopMin;
+ float envelopMax;
+ float envelopPercentage;
+ SpeakerMap* speakerMap;
+ };
+#pragma push(pop)
+ struct snd_alias_list_t
+ {
+ const char* aliasName;
+ snd_alias_t* head;
+ int count;
+ };
+
+ union XAssetHeader
+ {
+ void* data;
+ // XModelPieces *xmodelPieces;
+ PhysPreset* physPreset;
+ XAnimParts* xanim;
+ XModel* xmodel;
+ Material* material;
+ // MaterialPixelShader *pixelShader;
+ // MaterialVertexShader *vertexShader;
+ MaterialTechniqueSet* techset;
+ GfxImage* image;
+ snd_alias_list_t *sound;
+ // SndCurve *sndCurve;
+ clipMap_t* clipMap;
+ clipMap_t* col_map_mp;
+ ComWorld* com_map;
+ // GameWorldSp *gameWorldSp;
+ GameWorldMp* gameWorldMp;
+ MapEnts* mapEnts;
+ MapEnts* map_ents;
+ GfxWorld* gfxWorld;
+ GfxWorld* gfx_map;
+ GfxLightDef* lightDef;
+ LoadedSound* loaded_sound;
+ // Font_s *font;
+ // MenuList *menuList;
+ // menuDef_t *menu;
+ // LocalizeEntry *localize;
+ // WeaponDef *weapon;
+ // SndDriverGlobals *sndDriverGlobals;
+ FxEffectDef* fx;
+ // FxImpactTable *impactFx;
+ RawFile* rawfile;
+ // StringTable *stringTable;
+ };
+ }
+}
diff --git a/src/IW3/stdafx.cpp b/src/IW3/stdafx.cpp
new file mode 100644
index 0000000..34ba508
--- /dev/null
+++ b/src/IW3/stdafx.cpp
@@ -0,0 +1,10 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
\ No newline at end of file
diff --git a/src/IW3/stdafx.hpp b/src/IW3/stdafx.hpp
new file mode 100644
index 0000000..bbef6a1
--- /dev/null
+++ b/src/IW3/stdafx.hpp
@@ -0,0 +1,21 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+#define _CRT_SECURE_NO_WARNINGS
+#define WIN32_LEAN_AND_MEAN
+
+#include
+#include
+#include
+
+using namespace std::string_literals;
+
+#include "IW3.hpp"
+#include "IW4/Structs.hpp"
\ No newline at end of file
diff --git a/src/IW4.lua b/src/IW4.lua
new file mode 100644
index 0000000..2085e65
--- /dev/null
+++ b/src/IW4.lua
@@ -0,0 +1,36 @@
+IW4 = {}
+
+function IW4:include()
+ includedirs {
+ path.join(ProjectFolder(), "IW4")
+ }
+end
+
+function IW4:link()
+ self:include()
+ links {
+ "IW4"
+ }
+end
+
+function IW4:project()
+ local folder = ProjectFolder();
+
+ project "IW4"
+ kind "StaticLib"
+ language "C++"
+
+ pchheader "stdafx.hpp"
+ pchsource(path.join(folder, "IW4/stdafx.cpp"))
+
+ files {
+ path.join(folder, "IW4/**.h"),
+ path.join(folder, "IW4/**.hpp"),
+ path.join(folder, "IW4/**.cpp")
+ }
+
+ self:include()
+ ZoneUtils:include()
+ IW5:include()
+ zlib:include()
+end
\ No newline at end of file
diff --git a/src/IW4/Assets/AddonMapEnts.cpp b/src/IW4/Assets/AddonMapEnts.cpp
new file mode 100644
index 0000000..a23a0db
--- /dev/null
+++ b/src/IW4/Assets/AddonMapEnts.cpp
@@ -0,0 +1,147 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "ZoneUtils/Utils/BinaryDumper.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ AddonMapEnts* IAddonMapEnts::parse(std::string name, ZoneMemory* mem)
+ {
+ // check if we can open a filepointer
+ if (!FileSystem::FileExists(name))
+ {
+ return nullptr;
+ }
+
+ auto file = FileSystem::FileOpen(name, "rb");
+
+ // let them know that we're parsing a custom mapents file
+ ZONETOOL_INFO("Parsing addon mapents \"%s\"...", name.c_str());
+
+ // alloc mapents
+ auto ents = mem->Alloc();
+
+ ents->name = mem->StrDup(name);
+ ents->numEntityChars = FileSystem::FileSize(file) + 1;
+
+ ents->entityString = mem->Alloc(ents->numEntityChars);
+ memset((char*)ents->entityString, 0, ents->numEntityChars);
+ fread((char*)ents->entityString, ents->numEntityChars - 1, 1, file);
+
+#ifdef CONVERT_IW5_MAPENTS
+ // convert the mapents!
+ IMapEnts::convert_ents(reinterpret_cast(ents), mem);
+#endif
+
+ // close filepointer
+ FileSystem::FileClose(file);
+
+ AssetReader triggerReader(mem);
+ AssetReader stageReader(mem);
+
+ if (triggerReader.open(name + ".triggers"))
+ {
+ ents->trigger.modelCount = triggerReader.read_int();
+ ents->trigger.models = triggerReader.read_array();
+
+ ents->trigger.hullCount = triggerReader.read_int();
+ ents->trigger.hulls = triggerReader.read_array();
+
+ ents->trigger.slabCount = triggerReader.read_int();
+ ents->trigger.slabs = triggerReader.read_array();
+ }
+
+ triggerReader.close();
+
+ // return mapents
+ return ents;
+ }
+
+ void IAddonMapEnts::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = "maps/"s + (currentzone.substr(0, 3) == "mp_" ? "mp/" : "") + currentzone + ".mapents"; // name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), name.data()).addon_map_ents;
+ }
+ }
+
+ void IAddonMapEnts::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IAddonMapEnts::load_depending(IZone* zone)
+ {
+
+ }
+
+ std::string IAddonMapEnts::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IAddonMapEnts::type()
+ {
+ return addon_map_ents;
+ }
+
+ void IAddonMapEnts::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto data = this->asset_;
+ auto dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->entityString)
+ {
+ buf->align(0);
+ buf->write(data->entityString, data->numEntityChars);
+ ZoneBuffer::clear_pointer(&dest->entityString);
+ }
+
+ IMapEnts::write_triggers(zone, buf, &dest->trigger);
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ void IAddonMapEnts::dump(AddonMapEnts* asset)
+ {
+ auto* file = FileSystem::FileOpen(asset->name, "wb");
+
+ if (file)
+ {
+ fwrite(asset->entityString, asset->numEntityChars, 1, file);
+ FileSystem::FileClose(file);
+ }
+
+ AssetDumper trigger_dumper;
+ if (trigger_dumper.open(asset->name + ".triggers"s))
+ {
+ trigger_dumper.dump_int(asset->trigger.modelCount);
+ trigger_dumper.dump_array(asset->trigger.models, asset->trigger.modelCount);
+
+ trigger_dumper.dump_int(asset->trigger.hullCount);
+ trigger_dumper.dump_array(asset->trigger.hulls, asset->trigger.hullCount);
+
+ trigger_dumper.dump_int(asset->trigger.slabCount);
+ trigger_dumper.dump_array(asset->trigger.slabs, asset->trigger.slabCount);
+
+ trigger_dumper.close();
+ }
+ }
+ }
+}
diff --git a/src/IW4/Assets/AddonMapEnts.hpp b/src/IW4/Assets/AddonMapEnts.hpp
new file mode 100644
index 0000000..81b56ff
--- /dev/null
+++ b/src/IW4/Assets/AddonMapEnts.hpp
@@ -0,0 +1,35 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IAddonMapEnts : public IAsset
+ {
+ private:
+ std::string name_;
+ AddonMapEnts* asset_ = nullptr;
+
+ public:
+ AddonMapEnts* parse(std::string name, ZoneMemory* mem);
+
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(AddonMapEnts* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/ClipMap.cpp b/src/IW4/Assets/ClipMap.cpp
new file mode 100644
index 0000000..5841f24
--- /dev/null
+++ b/src/IW4/Assets/ClipMap.cpp
@@ -0,0 +1,631 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../iw5/Assets/ClipMap.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ clipMap_t* IClipMap::parse(const std::string& name, ZoneMemory* mem)
+ {
+ auto* iw5_colmap = IW5::IClipMap::parse(name, mem);
+
+ if (!iw5_colmap)
+ {
+ return nullptr;
+ }
+
+ // allocate collision map
+ auto* colmap = mem->Alloc();
+
+ // copy data from IW5 to IW4
+ colmap->name = iw5_colmap->name;
+ colmap->isInUse = iw5_colmap->isInUse;
+
+ colmap->numCPlanes = iw5_colmap->info.numCPlanes;
+ colmap->cPlanes = (cplane_s*)iw5_colmap->info.cPlanes;
+
+ colmap->numStaticModels = iw5_colmap->numStaticModels;
+ colmap->staticModelList = (cStaticModel_s*)iw5_colmap->staticModelList;
+
+ colmap->numMaterials = iw5_colmap->info.numMaterials;
+ colmap->materials = (dmaterial_t*)iw5_colmap->info.materials;
+
+ colmap->numCBrushSides = iw5_colmap->info.numCBrushSides;
+ colmap->cBrushSides = (cbrushside_t*)iw5_colmap->info.cBrushSides;
+
+ colmap->numCBrushEdges = iw5_colmap->info.numCBrushEdges;
+ colmap->cBrushEdges = (cbrushedge_t*)iw5_colmap->info.cBrushEdges;
+
+ colmap->numCNodes = iw5_colmap->numCNodes;
+ colmap->cNodes = (cNode_t*)iw5_colmap->cNodes;
+
+ colmap->numCLeaf = iw5_colmap->numCLeaf;
+ colmap->cLeaf = (cLeaf_t*)iw5_colmap->cLeaf;
+
+ colmap->numCLeafBrushNodes = iw5_colmap->info.numCLeafBrushNodes;
+ colmap->cLeafBrushNodes = (cLeafBrushNode_s*)iw5_colmap->info.cLeafBrushNodes;
+
+ colmap->numLeafBrushes = iw5_colmap->info.numLeafBrushes;
+ colmap->leafBrushes = iw5_colmap->info.leafBrushes;
+
+ // leafSurfaces todo!
+
+ colmap->numVerts = iw5_colmap->numVerts;
+ colmap->verts = (VecInternal<3>*)iw5_colmap->verts;
+
+ colmap->numTriIndices = iw5_colmap->numTriIndices;
+ colmap->triIndices = iw5_colmap->triIndices;
+ colmap->triEdgeIsWalkable = iw5_colmap->triEdgeIsWalkable;
+
+ colmap->numCollisionBorders = iw5_colmap->numCollisionBorders;
+ colmap->collisionBorders = (CollisionBorder*)iw5_colmap->collisionBorders;
+
+ colmap->numCollisionPartitions = iw5_colmap->numCollisionPartitions;
+ colmap->collisionPartitions = (CollisionPartition*)iw5_colmap->collisionPartitions;
+
+ colmap->numCollisionAABBTrees = iw5_colmap->numCollisionAABBTrees;
+ colmap->collisionAABBTrees = (CollisionAabbTree*)iw5_colmap->collisionAABBTrees;
+
+ // cmodels!
+ colmap->numCModels = iw5_colmap->numCModels;
+ colmap->cModels = new cmodel_t[colmap->numCModels];
+ memset(colmap->cModels, 0, sizeof(cmodel_t) * colmap->numCModels);
+
+ for (int i = 0; i < colmap->numCModels; i++)
+ {
+ memcpy(colmap->cModels[i]._portpad0, iw5_colmap->cModels[i]._portpad0, 28);
+ memcpy(colmap->cModels[i]._portpad1, iw5_colmap->cModels[i]._portpad1, 40);
+ }
+
+ colmap->numBrushes = iw5_colmap->info.numBrushes;
+ colmap->brushes = (cbrush_t*)iw5_colmap->info.brushes;
+ colmap->brushBounds = (Bounds*)iw5_colmap->info.brushBounds;
+ colmap->brushContents = iw5_colmap->info.brushContents;
+
+ colmap->mapEnts = (MapEnts*)iw5_colmap->mapEnts;
+
+ colmap->smodelNodeCount = iw5_colmap->smodelNodeCount;
+ colmap->smodelNodes = (SModelAabbNode*)iw5_colmap->smodelNodes;
+
+ // return converted colmap
+ return colmap;
+ }
+
+ void IClipMap::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = "maps/"s + (currentzone.substr(0, 3) == "mp_" ? "mp/" : "") + currentzone + ".d3dbsp"; // name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), name.data()).clipmap;
+ }
+ }
+
+ void IClipMap::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IClipMap::load_depending(IZone* zone)
+ {
+ auto* data = this->asset_;
+
+ if (data->staticModelList)
+ {
+ for (auto i = 0u; i < data->numStaticModels; i++)
+ {
+ if (data->staticModelList[i].xmodel)
+ {
+ zone->add_asset_of_type(xmodel, data->staticModelList[i].xmodel->name);
+ }
+ }
+ }
+
+ if (data->dynEntDefList[0])
+ {
+ for (auto i = 0u; i < data->dynEntCount[0]; i++)
+ {
+ if (data->dynEntDefList[0][i].xModel)
+ {
+ zone->add_asset_of_type(xmodel, data->dynEntDefList[0][i].xModel->name);
+ }
+ if (data->dynEntDefList[0][i].destroyFx)
+ {
+ // zone->AddAssetOfType(fx, data->dynEntDefList[0][i].destroyFx->name);
+ }
+ if (data->dynEntDefList[0][i].physPreset)
+ {
+ zone->add_asset_of_type(physpreset, data->dynEntDefList[0][i].physPreset->name);
+ }
+ }
+ }
+
+ if (data->dynEntDefList[1])
+ {
+ for (auto i = 0u; i < data->dynEntCount[1]; i++)
+ {
+ if (data->dynEntDefList[1][i].xModel)
+ {
+ zone->add_asset_of_type(xmodel, data->dynEntDefList[1][i].xModel->name);
+ }
+ if (data->dynEntDefList[1][i].destroyFx)
+ {
+ // zone->AddAssetOfType(fx, data->dynEntDefList[1][i].destroyFx->name);
+ }
+ if (data->dynEntDefList[1][i].physPreset)
+ {
+ zone->add_asset_of_type(physpreset, data->dynEntDefList[1][i].physPreset->name);
+ }
+ }
+ }
+
+ if (data->mapEnts)
+ {
+ zone->add_asset_of_type(map_ents, this->asset_->mapEnts->name);
+ }
+ }
+
+ std::string IClipMap::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IClipMap::type()
+ {
+ return col_map_sp;
+ }
+
+ void IClipMap::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->cPlanes)
+ {
+ cplane_s* dest_cplanes = nullptr;
+ dest->cPlanes = buf->write_s(3, data->cPlanes, data->numCPlanes, sizeof cplane_s, &dest_cplanes);
+ }
+
+ if (data->staticModelList)
+ {
+ buf->align(3);
+ auto* static_model = buf->write(data->staticModelList, data->numStaticModels);
+
+ for (auto i = 0; i < data->numStaticModels; i++)
+ {
+ if (data->staticModelList[i].xmodel)
+ {
+ static_model[i].xmodel = reinterpret_cast(zone->get_asset_pointer(
+ xmodel, data->staticModelList[i].xmodel->name));
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&data->staticModelList);
+ }
+
+ if (data->materials)
+ {
+ dmaterial_t* dmaterial;
+ dest->materials = buf->write_s(3, data->materials, data->numMaterials, sizeof dmaterial_t, &dmaterial);
+
+ if (dest->materials == reinterpret_cast(-1))
+ {
+ for (auto i = 0; i < data->numMaterials; i++)
+ {
+ if (data->materials[i].material)
+ {
+ dmaterial[i].material = buf->write_str(data->materials[i].material);
+ }
+ }
+ }
+ }
+
+ if (data->cBrushSides)
+ {
+ cbrushside_t* brush_side;
+ dest->cBrushSides = buf->write_s(3, data->cBrushSides, data->numCBrushSides, sizeof cbrushside_t,
+ &brush_side);
+
+ if (dest->cBrushSides == reinterpret_cast(-1))
+ {
+ for (auto i = 0; i < data->numCBrushSides; i++)
+ {
+ if (data->cBrushSides[i].plane)
+ {
+ // should use zone pointer, no need to convert
+ brush_side[i].plane = buf->write_s(3, data->cBrushSides[i].plane);
+ }
+
+ if (zone->get_target() != zone_target::pc)
+ {
+ endian_convert(&brush_side[i].plane);
+ endian_convert(&brush_side[i].materialNum);
+ }
+ }
+ }
+ }
+
+ if (data->cBrushEdges)
+ {
+ dest->cBrushEdges = buf->write_s(0, data->cBrushEdges, data->numCBrushEdges);
+ }
+
+ if (data->cNodes)
+ {
+ buf->align(3);
+ auto* node = buf->write(data->cNodes, data->numCNodes);
+
+ for (auto i = 0; i < data->numCNodes; i++)
+ {
+ if (data->cNodes[i].plane)
+ {
+ // should use zone pointer, no need to convert
+ node[i].plane = buf->write_s(3, data->cNodes[i].plane);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->cNodes);
+ }
+
+ if (data->cLeaf)
+ {
+ buf->align(3);
+ auto* dest_leaf = buf->write(data->cLeaf, data->numCLeaf);
+ ZoneBuffer::clear_pointer(&dest->cLeaf);
+ }
+
+ if (data->leafBrushes)
+ {
+ short* dest_leaf_brushes = nullptr;
+ dest->leafBrushes = buf->write_s(1, data->leafBrushes, data->numLeafBrushes, sizeof (short), &dest_leaf_brushes);
+ }
+
+ if (data->cLeafBrushNodes)
+ {
+ cLeafBrushNode_s* leaf_brush_node = nullptr;
+ dest->cLeafBrushNodes = buf->write_s(3, data->cLeafBrushNodes, data->numCLeafBrushNodes,
+ sizeof cLeafBrushNode_s, &leaf_brush_node);
+
+ if (dest->cLeafBrushNodes == reinterpret_cast(-1))
+ {
+ for (auto i = 0; i < data->numCLeafBrushNodes; i++)
+ {
+ if (data->cLeafBrushNodes[i].leafBrushCount > 0 && data->cLeafBrushNodes[i].data.leaf.brushes)
+ {
+ unsigned short* dest_leaf_brushes = nullptr;
+ leaf_brush_node[i].data.leaf.brushes = buf->write_s(
+ 1, data->cLeafBrushNodes[i].data.leaf.brushes, data->cLeafBrushNodes[i].leafBrushCount, sizeof (unsigned short), &dest_leaf_brushes);
+ }
+ }
+ }
+ }
+
+ if (data->verts)
+ {
+ buf->align(3);
+ auto* dest_verts = buf->write(data->verts, data->numVerts);
+ ZoneBuffer::clear_pointer(&dest->verts);
+ }
+
+ if (data->triIndices)
+ {
+ buf->align(1);
+ auto* dest_tri_indices = buf->write(data->triIndices, data->numTriIndices * 3);
+ ZoneBuffer::clear_pointer(&dest->triIndices);
+ }
+
+ if (data->triEdgeIsWalkable)
+ {
+ buf->align(0);
+ buf->write(data->triEdgeIsWalkable, 4 * ((3 * data->numTriIndices + 31) >> 5));
+ ZoneBuffer::clear_pointer(&dest->triEdgeIsWalkable);
+ }
+
+ if (data->collisionBorders)
+ {
+ buf->align(3);
+ auto* dest_borders = buf->write_p(data->collisionBorders, data->numCollisionBorders);
+ ZoneBuffer::clear_pointer(&dest->collisionBorders);
+ }
+
+ if (data->collisionPartitions)
+ {
+ buf->align(3);
+ auto* collision_partition = buf->write(data->collisionPartitions, data->numCollisionPartitions);
+
+ for (auto i = 0; i < data->numCollisionPartitions; i++)
+ {
+ if (data->collisionPartitions[i].borders)
+ {
+ collision_partition[i].borders = buf->write_s(3, data->collisionPartitions[i].borders);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->collisionPartitions);
+ }
+
+ if (data->collisionAABBTrees)
+ {
+ buf->align(15);
+ auto* dest_aabb_trees = buf->write(data->collisionAABBTrees, data->numCollisionAABBTrees);
+ ZoneBuffer::clear_pointer(&dest->collisionAABBTrees);
+ }
+
+ if (data->cModels)
+ {
+ buf->align(3);
+ auto* dest_c_models = buf->write(data->cModels, data->numCModels);
+ ZoneBuffer::clear_pointer(&dest->cModels);
+ }
+
+ // brushes
+ if (data->brushes)
+ {
+ cbrush_t* brush = nullptr;
+ dest->brushes = buf->write_s(127, data->brushes, data->numBrushes, sizeof cbrush_t, &brush);
+
+ if (dest->brushes == reinterpret_cast(-1))
+ {
+ for (auto i = 0; i < data->numBrushes; i++)
+ {
+ if (data->brushes[i].sides)
+ {
+ cbrushside_t* side = nullptr;
+ brush[i].sides = buf->write_s(3, data->brushes[i].sides, 1, sizeof cbrushside_t, &side);
+
+ if (brush[i].sides == reinterpret_cast(-1) && side)
+ {
+ if (side->plane)
+ {
+ // should use zone pointer
+ side->plane = buf->write_s(3, side->plane);
+ }
+ }
+ }
+
+ if (data->brushes[i].edge)
+ {
+ // should use zone pointer
+ brush[i].edge = buf->write_s(0, data->brushes[i].edge);
+ }
+ }
+ }
+ }
+
+ // brushBounds
+ if (data->brushBounds)
+ {
+ Bounds* dest_bounds = nullptr;
+ dest->brushBounds = buf->write_s(127, data->brushBounds, data->numBrushes, sizeof Bounds, &dest_bounds);
+ }
+
+ // brushContents
+ if (data->brushContents)
+ {
+ int* destBrushContents = nullptr;
+ dest->brushContents = buf->write_s(3, data->brushContents, data->numBrushes, sizeof (int), &destBrushContents);
+ }
+
+ if (data->smodelNodes)
+ {
+ buf->align(3);
+ auto* dest_smodels = buf->write(data->smodelNodes, data->smodelNodeCount);
+ ZoneBuffer::clear_pointer(&dest->smodelNodes);
+ }
+
+ if (data->mapEnts)
+ {
+ dest->mapEnts = reinterpret_cast(zone->get_asset_pointer(map_ents, this->name()));
+ }
+
+ if (data->dynEntDefList[0])
+ {
+ buf->align(3);
+ auto* dyn_entity_def = buf->write(data->dynEntDefList[0], data->dynEntCount[0]);
+
+ for (std::uint16_t i = 0; i < data->dynEntCount[0]; i++)
+ {
+ if (data->dynEntDefList[0][i].xModel)
+ {
+ dyn_entity_def[i].xModel = reinterpret_cast(zone->get_asset_pointer(
+ xmodel, data->dynEntDefList[0][i].xModel->name));
+ }
+ if (data->dynEntDefList[0][i].destroyFx)
+ {
+ // dyn_entity_def[i].destroyFx = reinterpret_cast(zone->GetAssetPointer(fx, data->dynEntDefList[0][i].destroyFx->name));
+ }
+ if (data->dynEntDefList[0][i].physPreset)
+ {
+ dyn_entity_def[i].physPreset = reinterpret_cast(zone->get_asset_pointer(
+ physpreset, data->dynEntDefList[0][i].physPreset->name));
+ }
+
+ /*if (data->dynEntDefList[0][i].hinge)
+ {
+ dyn_entity_def[i].hinge = buf->write_s(3, dyn_entity_def[i].hinge, 1);
+ }*/
+ }
+
+ ZoneBuffer::clear_pointer(&dest->dynEntDefList[0]);
+ }
+
+ if (data->dynEntDefList[1])
+ {
+ buf->align(3);
+ auto* dyn_entity_def = buf->write(data->dynEntDefList[1], data->dynEntCount[1]);
+
+ for (std::uint16_t i = 0; i < data->dynEntCount[1]; i++)
+ {
+ if (data->dynEntDefList[1][i].xModel)
+ {
+ dyn_entity_def[i].xModel = reinterpret_cast(zone->get_asset_pointer(
+ xmodel, data->dynEntDefList[1][i].xModel->name));
+ }
+ if (data->dynEntDefList[1][i].destroyFx)
+ {
+ // dyn_entity_def[i].destroyFx = reinterpret_cast(zone->GetAssetPointer(fx, data->dynEntDefList[1][i].destroyFx->name));
+ }
+ if (data->dynEntDefList[1][i].physPreset)
+ {
+ dyn_entity_def[i].physPreset = reinterpret_cast(zone->get_asset_pointer(
+ physpreset, data->dynEntDefList[1][i].physPreset->name));
+ }
+
+ /*if (data->dynEntDefList[1][i].hinge)
+ {
+ dyn_entity_def[i].hinge = buf->write_s(3, dyn_entity_def[i].hinge, 1);
+ }*/
+ }
+
+ ZoneBuffer::clear_pointer(&dest->dynEntDefList[1]);
+ }
+
+ buf->push_stream(2);
+
+ if (data->dynEntPoseList[0])
+ {
+ buf->align(3);
+ buf->write(data->dynEntPoseList[0], data->dynEntCount[0]);
+ ZoneBuffer::clear_pointer(&dest->dynEntPoseList[0]);
+ }
+
+ if (data->dynEntPoseList[1])
+ {
+ buf->align(3);
+ buf->write(data->dynEntPoseList[1], data->dynEntCount[1]);
+ ZoneBuffer::clear_pointer(&dest->dynEntPoseList[1]);
+ }
+
+ if (data->dynEntClientList[0])
+ {
+ buf->align(3);
+ buf->write(data->dynEntClientList[0], data->dynEntCount[0]);
+ ZoneBuffer::clear_pointer(&dest->dynEntClientList[0]);
+ }
+
+ if (data->dynEntClientList[1])
+ {
+ buf->align(3);
+ buf->write(data->dynEntClientList[1], data->dynEntCount[1]);
+ ZoneBuffer::clear_pointer(&dest->dynEntClientList[1]);
+ }
+
+ if (data->dynEntCollList[0])
+ {
+ buf->align(3);
+ buf->write(data->dynEntCollList[0], data->dynEntCount[0]);
+ ZoneBuffer::clear_pointer(&dest->dynEntCollList[0]);
+ }
+
+ if (data->dynEntCollList[1])
+ {
+ buf->align(3);
+ buf->write(data->dynEntCollList[1], data->dynEntCount[1]);
+ ZoneBuffer::clear_pointer(&dest->dynEntCollList[1]);
+ }
+
+ buf->pop_stream();
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ void IClipMap::dump(clipMap_t* asset)
+ {
+ auto* iw5_clipmap = new IW5::clipMap_t;
+ memset(iw5_clipmap, 0, sizeof IW5::clipMap_t);
+
+ // convert clipmap to IW5 format
+ iw5_clipmap->name = asset->name;
+ iw5_clipmap->isInUse = asset->isInUse;
+
+ iw5_clipmap->info.numCPlanes = asset->numCPlanes;
+ iw5_clipmap->info.cPlanes = (IW5::cplane_s*)asset->cPlanes;
+
+ iw5_clipmap->numStaticModels = asset->numStaticModels;
+ iw5_clipmap->staticModelList = (IW5::cStaticModel_s*)asset->staticModelList;
+
+ iw5_clipmap->info.numMaterials = asset->numMaterials;
+ iw5_clipmap->info.materials = (IW5::dmaterial_t*)asset->materials;
+
+ iw5_clipmap->info.numCBrushSides = asset->numCBrushSides;
+ iw5_clipmap->info.cBrushSides = (IW5::cbrushside_t*)asset->cBrushSides;
+
+ iw5_clipmap->info.numCBrushEdges = asset->numCBrushEdges;
+ iw5_clipmap->info.cBrushEdges = (IW5::cbrushedge_t*)asset->cBrushEdges;
+
+ iw5_clipmap->numCNodes = asset->numCNodes;
+ iw5_clipmap->cNodes = (IW5::cNode_t*)asset->cNodes;
+
+ iw5_clipmap->numCLeaf = asset->numCLeaf;
+ iw5_clipmap->cLeaf = (IW5::cLeaf_t*)asset->cLeaf;
+
+ iw5_clipmap->info.numCLeafBrushNodes = asset->numCLeafBrushNodes;
+ iw5_clipmap->info.cLeafBrushNodes = (IW5::cLeafBrushNode_s*)asset->cLeafBrushNodes;
+
+ iw5_clipmap->info.numLeafBrushes = asset->numLeafBrushes;
+ iw5_clipmap->info.leafBrushes = asset->leafBrushes;
+
+ // leafSurfaces todo!
+
+ iw5_clipmap->numVerts = asset->numVerts;
+ iw5_clipmap->verts = (IW5::VecInternal<3>*)asset->verts;
+
+ iw5_clipmap->numTriIndices = asset->numTriIndices;
+ iw5_clipmap->triIndices = asset->triIndices;
+ iw5_clipmap->triEdgeIsWalkable = asset->triEdgeIsWalkable;
+
+ iw5_clipmap->numCollisionBorders = asset->numCollisionBorders;
+ iw5_clipmap->collisionBorders = (IW5::CollisionBorder*)asset->collisionBorders;
+
+ iw5_clipmap->numCollisionPartitions = asset->numCollisionPartitions;
+ iw5_clipmap->collisionPartitions = (IW5::CollisionPartition*)asset->collisionPartitions;
+
+ iw5_clipmap->numCollisionAABBTrees = asset->numCollisionAABBTrees;
+ iw5_clipmap->collisionAABBTrees = (IW5::CollisionAabbTree*)asset->collisionAABBTrees;
+
+ // cmodels!
+ iw5_clipmap->numCModels = asset->numCModels;
+ iw5_clipmap->cModels = new IW5::cmodel_t[iw5_clipmap->numCModels];
+ memset(iw5_clipmap->cModels, 0, sizeof(IW5::cmodel_t) * iw5_clipmap->numCModels);
+
+ for (int i = 0; i < iw5_clipmap->numCModels; i++)
+ {
+ memcpy(iw5_clipmap->cModels[i]._portpad0, asset->cModels[i]._portpad0, 28);
+ memcpy(iw5_clipmap->cModels[i]._portpad1, asset->cModels[i]._portpad1, 40);
+ }
+
+ iw5_clipmap->info.numBrushes = asset->numBrushes;
+ iw5_clipmap->info.brushes = (IW5::cbrush_t*)asset->brushes;
+ iw5_clipmap->info.brushBounds = (IW5::Bounds*)asset->brushBounds;
+ iw5_clipmap->info.brushContents = asset->brushContents;
+
+ iw5_clipmap->mapEnts = (IW5::MapEnts*)asset->mapEnts;
+ iw5_clipmap->stageCount = asset->mapEnts->stageCount;
+ iw5_clipmap->stages = (IW5::Stage*)asset->mapEnts->stageNames;
+
+ iw5_clipmap->smodelNodeCount = asset->smodelNodeCount;
+ iw5_clipmap->smodelNodes = (IW5::SModelAabbNode*)asset->smodelNodes;
+
+ // dump clipmap
+ IW5::IClipMap::dump(iw5_clipmap);
+
+ // free memory_
+ delete[] iw5_clipmap->cModels;
+ delete iw5_clipmap;
+ }
+ }
+}
diff --git a/src/IW4/Assets/ClipMap.hpp b/src/IW4/Assets/ClipMap.hpp
new file mode 100644
index 0000000..2ec0907
--- /dev/null
+++ b/src/IW4/Assets/ClipMap.hpp
@@ -0,0 +1,35 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IClipMap : public IAsset
+ {
+ private:
+ std::string name_;
+ clipMap_t* asset_ = nullptr;
+
+ public:
+ clipMap_t* parse(const std::string& name, ZoneMemory* mem);
+
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(clipMap_t* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/ComWorld.cpp b/src/IW4/Assets/ComWorld.cpp
new file mode 100644
index 0000000..88b224b
--- /dev/null
+++ b/src/IW4/Assets/ComWorld.cpp
@@ -0,0 +1,131 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../iw5/Assets/ComWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ ComWorld* IComWorld::parse(const std::string& name, ZoneMemory* mem)
+ {
+ auto* iw5_comworld = IW5::IComWorld::parse(name, mem);
+
+ if (!iw5_comworld)
+ {
+ return nullptr;
+ }
+
+ // fixup data
+ auto* light_array = mem->Alloc(iw5_comworld->primaryLightCount);
+
+ // convert structure
+ for (auto i = 0u; i < iw5_comworld->primaryLightCount; i++)
+ {
+ memcpy(light_array[i]._portpad0, iw5_comworld->primaryLights[i]._portpad0, 28);
+ memcpy(light_array[i]._portpad1, iw5_comworld->primaryLights[i]._portpad1, 40);
+ }
+
+ // set pointer
+ iw5_comworld->primaryLights = (IW5::ComPrimaryLight*)light_array;
+
+ // asset is the exact same so just cast to the correct type here
+ return (ComWorld*)iw5_comworld;
+ }
+
+ void IComWorld::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = "maps/"s + (currentzone.substr(0, 3) == "mp_" ? "mp/" : "") + currentzone + ".d3dbsp"; // name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), name.data()).comworld;
+ }
+ }
+
+ void IComWorld::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IComWorld::load_depending(IZone* zone)
+ {
+ auto* asset = this->asset_;
+
+ for (auto i = 0u; i < asset->primaryLightCount; i++)
+ {
+ if (asset->primaryLights[i].defName)
+ {
+ zone->add_asset_of_type(lightdef, asset->primaryLights[i].defName);
+ }
+ }
+ }
+
+ std::string IComWorld::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IComWorld::type()
+ {
+ return com_map;
+ }
+
+ void IComWorld::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ buf->push_stream(3);
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->primaryLights)
+ {
+ buf->align(3);
+ auto* primary_light = buf->write(data->primaryLights, data->primaryLightCount);
+
+ for (auto i = 0u; i < data->primaryLightCount; i++)
+ {
+ if (data->primaryLights[i].defName)
+ {
+ primary_light[i].defName = buf->write_str(data->primaryLights[i].defName);
+ }
+ }
+ }
+
+ buf->pop_stream();
+ }
+
+ void IComWorld::dump(ComWorld* asset)
+ {
+ // alloc comworld
+ auto* iw5_comworld = new IW5::ComWorld;
+ memcpy(iw5_comworld, asset, sizeof ComWorld);
+
+ // alloc lights
+ iw5_comworld->primaryLights = new IW5::ComPrimaryLight[iw5_comworld->primaryLightCount];
+ memset(iw5_comworld->primaryLights, 0, sizeof(IW5::ComPrimaryLight) * iw5_comworld->primaryLightCount);
+
+ // copy data
+ for (unsigned int i = 0; i < iw5_comworld->primaryLightCount; i++)
+ {
+ memcpy(iw5_comworld->primaryLights[i]._portpad0, asset->primaryLights[i]._portpad0, 28);
+ memcpy(iw5_comworld->primaryLights[i]._portpad1, asset->primaryLights[i]._portpad1, 40);
+ }
+
+ // dump comworld
+ IW5::IComWorld::dump(iw5_comworld);
+
+ // free memory_
+ delete[] iw5_comworld->primaryLights;
+ delete[] iw5_comworld;
+ }
+ }
+}
diff --git a/src/IW4/Assets/ComWorld.hpp b/src/IW4/Assets/ComWorld.hpp
new file mode 100644
index 0000000..802d698
--- /dev/null
+++ b/src/IW4/Assets/ComWorld.hpp
@@ -0,0 +1,35 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IComWorld : public IAsset
+ {
+ private:
+ std::string name_;
+ ComWorld* asset_ = nullptr;
+
+ public:
+ ComWorld* parse(const std::string& name, ZoneMemory* mem);
+
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(ComWorld* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/FontDef.cpp b/src/IW4/Assets/FontDef.cpp
new file mode 100644
index 0000000..cc4b277
--- /dev/null
+++ b/src/IW4/Assets/FontDef.cpp
@@ -0,0 +1,101 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "IW5/Assets/FontDef.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ void IFontDef::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), this->name_.data()).font;
+ }
+ }
+
+ void IFontDef::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IFontDef::load_depending(IZone* zone)
+ {
+ auto* data = this->asset_;
+
+ if (data->material)
+ {
+ zone->add_asset_of_type(material, data->material->name);
+ }
+
+ if (data->glowMaterial)
+ {
+ zone->add_asset_of_type(material, data->glowMaterial->name);
+ }
+ }
+
+ std::string IFontDef::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IFontDef::type()
+ {
+ return font;
+ }
+
+ void IFontDef::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->fontName = buf->write_str(this->name());
+
+ if (data->material)
+ {
+ dest->material = reinterpret_cast(
+ zone->get_asset_pointer(material, data->material->name)
+ );
+ }
+
+ if (data->glowMaterial)
+ {
+ dest->glowMaterial = reinterpret_cast(
+ zone->get_asset_pointer(material, data->glowMaterial->name)
+ );
+ }
+
+ if (data->glyphs)
+ {
+ buf->align(3);
+ auto* dest_glyphs = buf->write(data->glyphs, data->glyphCount);
+ ZoneBuffer::clear_pointer(&dest->glyphs);
+ }
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ Font_s* IFontDef::parse(const std::string& name, ZoneMemory* mem)
+ {
+ return reinterpret_cast(IW5::IFontDef::parse(name, mem));
+ }
+
+ void IFontDef::dump(Font_s* asset)
+ {
+ IW5::IFontDef::dump(reinterpret_cast(asset));
+ }
+ }
+}
diff --git a/src/IW4/Assets/FontDef.hpp b/src/IW4/Assets/FontDef.hpp
new file mode 100644
index 0000000..c70c1aa
--- /dev/null
+++ b/src/IW4/Assets/FontDef.hpp
@@ -0,0 +1,34 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IFontDef : public IAsset
+ {
+ private:
+ std::string name_;
+ Font_s* asset_ = nullptr;
+
+ public:
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(Font_s* asset);
+ static Font_s* parse(const std::string& name, ZoneMemory* mem);
+ };
+ }
+}
diff --git a/src/IW4/Assets/FxEffectDef.cpp b/src/IW4/Assets/FxEffectDef.cpp
new file mode 100644
index 0000000..06700b5
--- /dev/null
+++ b/src/IW4/Assets/FxEffectDef.cpp
@@ -0,0 +1,403 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "IW5/Assets/FxEffectDef.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ void IFxEffectDef::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), this->name().data()).fx;
+ }
+ }
+
+ void IFxEffectDef::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ FxEffectDef* IFxEffectDef::parse(const std::string& name, ZoneMemory* mem)
+ {
+ const auto iw5_fx = IW5::IFxEffectDef::parse(name, mem);
+
+ if (!iw5_fx)
+ {
+ return nullptr;
+ }
+
+ const auto fx = mem->Alloc();
+
+ memcpy(fx, iw5_fx, sizeof FxEffectDef);
+
+ // transform elem defs
+ const auto elem_count = fx->elemDefCountLooping + fx->elemDefCountEmission + fx->elemDefCountOneShot;
+ fx->elemDefs = mem->Alloc(elem_count);
+ for (auto i = 0; i < elem_count; i++)
+ {
+ memcpy(&fx->elemDefs[i], &iw5_fx->elemDefs[i], sizeof FxElemDef);
+
+ if (fx->elemDefs[i].extended.trailDef)
+ {
+ // iw5 feature, unsupported on iw4
+ if (fx->elemDefs[i].elemType == 9)
+ {
+ fx->elemDefs[i].extended.trailDef = nullptr;
+ }
+ }
+ }
+
+ return fx;
+ }
+
+ void IFxEffectDef::load_depending(IZone* zone)
+ {
+ auto* data = this->asset_;
+
+ auto load_fx_elem_visuals = [zone](FxElemDef* def, FxElemDefVisuals* vis)
+ {
+ if (def->elemType == 11)
+ {
+ for (auto i = 0; i < def->visualCount; i++)
+ {
+ if (vis->markArray[i])
+ {
+ if (vis->markArray[i][0])
+ {
+ zone->add_asset_of_type(material, vis->markArray[i][0]->name);
+ }
+ if (vis->markArray[i][1])
+ {
+ zone->add_asset_of_type(material, vis->markArray[i][1]->name);
+ }
+ }
+ }
+ }
+ else if (def->visualCount > 1)
+ {
+ for (auto i = 0; i < def->visualCount; i++)
+ {
+ if (def->elemType == 12 && vis->array[i].effectDef)
+ {
+ zone->add_asset_of_type(fx, vis->array[i].effectDef->name);
+ }
+ else if (def->elemType == 10 && vis->array[i].soundName)
+ {
+ zone->add_asset_of_type(sound, vis->array[i].soundName);
+ }
+ else if (def->elemType == 7 && vis->array[i].xmodel)
+ {
+ zone->add_asset_of_type(xmodel, vis->array[i].xmodel->name);
+ }
+ else
+ {
+ if (def->elemType != 8 && vis->array[i].material)
+ {
+ zone->add_asset_of_type(material, vis->array[i].material->name);
+ }
+ }
+ }
+ }
+ else
+ {
+ if (def->elemType == 12 && vis->instance.effectDef)
+ {
+ zone->add_asset_of_type(fx, vis->instance.effectDef->name);
+ }
+ else if (def->elemType == 10 && vis->instance.soundName)
+ {
+ zone->add_asset_of_type(sound, vis->instance.soundName);
+ }
+ else if (def->elemType == 7 && vis->instance.xmodel)
+ {
+ zone->add_asset_of_type(xmodel, vis->instance.xmodel->name);
+ }
+ else
+ {
+ if (def->elemType != 8 && vis->instance.material)
+ {
+ zone->add_asset_of_type(material, vis->instance.material->name);
+ }
+ }
+ }
+ };
+
+ // Loop through frames
+ for (auto i = 0; i < data->elemDefCountEmission + data->elemDefCountLooping + data->elemDefCountOneShot; i++)
+ {
+ auto* def = &data->elemDefs[i];
+
+ // Sub-FX effects
+ if (def->effectEmitted)
+ {
+ zone->add_asset_of_type(fx, def->effectEmitted->name);
+ }
+ if (def->effectOnDeath)
+ {
+ zone->add_asset_of_type(fx, def->effectOnDeath->name);
+ }
+ if (def->effectOnImpact)
+ {
+ zone->add_asset_of_type(fx, def->effectOnImpact->name);
+ }
+
+ // Visuals
+ load_fx_elem_visuals(def, &def->visuals);
+ }
+ }
+
+ std::string IFxEffectDef::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IFxEffectDef::type()
+ {
+ return fx;
+ }
+
+ void IFxEffectDef::write_fx_elem_visuals(IZone* zone, ZoneBuffer* buf, FxElemDef* def,
+ FxElemVisuals* dest)
+ {
+ auto* data = dest;
+
+ switch (def->elemType)
+ {
+ case FX_ELEM_TYPE_RUNNER:
+ {
+ buf->write_str(data->effectDef->name);
+ ZoneBuffer::clear_pointer(&dest->effectDef);
+ break;
+ }
+ case FX_ELEM_TYPE_SOUND:
+ {
+ if (data->soundName)
+ {
+ buf->write_str(data->soundName);
+ ZoneBuffer::clear_pointer(&dest->soundName);
+ }
+ break;
+ }
+ case FX_ELEM_TYPE_SPOT_LIGHT:
+ {
+ dest->anonymous = (data->anonymous)
+ ? zone->get_asset_pointer(lightdef, ((GfxLightDef*)data->anonymous)->name)
+ : nullptr;
+ break;
+ }
+ case FX_ELEM_TYPE_MODEL:
+ {
+ dest->xmodel = (data->xmodel)
+ ? reinterpret_cast(zone->get_asset_pointer(xmodel, data->xmodel->name))
+ : nullptr;
+ break;
+ }
+ default:
+ {
+ if (def->elemType != FX_ELEM_TYPE_OMNI_LIGHT)
+ {
+ dest->material = (data->material)
+ ? reinterpret_cast(zone->get_asset_pointer(
+ material, data->material->name))
+ : nullptr;
+ }
+ }
+ }
+ }
+
+ void IFxEffectDef::write_fx_elem_def_visuals(IZone* zone, ZoneBuffer* buf, FxElemDef* def,
+ FxElemDefVisuals* dest)
+ {
+ auto* data = dest;
+
+ if (def->elemType == FX_ELEM_TYPE_DECAL)
+ {
+ if (data->markArray)
+ {
+ auto destvisuals = buf->write(data->markArray, def->visualCount);
+
+ for (int i = 0; i < def->visualCount; i++)
+ {
+ destvisuals[i][0] = (data->markArray[i][0])
+ ? reinterpret_cast(zone->get_asset_pointer(
+ material, data->markArray[i][0]->name))
+ : nullptr;
+ destvisuals[i][1] = (data->markArray[i][1])
+ ? reinterpret_cast(zone->get_asset_pointer(
+ material, data->markArray[i][1]->name))
+ : nullptr;
+ }
+ }
+ }
+ else if (def->visualCount > 1)
+ {
+ auto* vis = buf->write(data->array, def->visualCount);
+
+ for (auto i = 0; i < def->visualCount; i++)
+ {
+ write_fx_elem_visuals(zone, buf, def, &vis[i]);
+ }
+ }
+ else
+ {
+ write_fx_elem_visuals(zone, buf, def, &dest->instance);
+ }
+ }
+
+ void IFxEffectDef::write_fx_elem_def(IZone* zone, ZoneBuffer* buf, FxElemDef* dest)
+ {
+ auto* data = dest;
+
+ if (data->velSamples)
+ {
+ buf->align(3);
+ buf->write(data->velSamples, data->velIntervalCount + 1);
+ ZoneBuffer::clear_pointer(&dest->velSamples);
+ }
+
+ if (data->visSamples)
+ {
+ buf->align(3);
+ buf->write(data->visSamples, data->visStateIntervalCount + 1);
+ ZoneBuffer::clear_pointer(&dest->visSamples);
+ }
+
+ write_fx_elem_def_visuals(zone, buf, data, &dest->visuals);
+
+ if (data->effectOnImpact)
+ {
+ buf->write_str_raw(data->effectOnImpact->name);
+ ZoneBuffer::clear_pointer(&dest->effectOnImpact);
+ }
+
+ if (data->effectOnDeath)
+ {
+ buf->write_str_raw(data->effectOnDeath->name);
+ ZoneBuffer::clear_pointer(&dest->effectOnDeath);
+ }
+
+ if (data->effectEmitted)
+ {
+ buf->write_str_raw(data->effectEmitted->name);
+ ZoneBuffer::clear_pointer(&dest->effectEmitted);
+ }
+
+ if (data->extended.trailDef)
+ {
+ if (data->elemType == FX_ELEM_TYPE_TRAIL)
+ {
+ if (data->extended.trailDef)
+ {
+ buf->align(3);
+ buf->write(data->extended.trailDef, sizeof(FxTrailDef));
+
+ if (data->extended.trailDef->verts)
+ {
+ buf->align(3);
+ buf->write(data->extended.trailDef->verts, data->extended.trailDef->vertCount);
+ }
+
+ if (data->extended.trailDef->inds)
+ {
+ buf->align(1);
+ buf->write(data->extended.trailDef->inds, data->extended.trailDef->indCount);
+ }
+
+ ZoneBuffer::clear_pointer(&dest->extended.trailDef);
+ }
+ }
+ else if (data->elemType == FX_ELEM_TYPE_SPARKFOUNTAIN)
+ {
+ if (data->extended.sparkFountain)
+ {
+ buf->align(3);
+ buf->write(data->extended.sparkFountain);
+ ZoneBuffer::clear_pointer(&dest->extended.sparkFountain);
+ }
+ }
+ else if (data->elemType == FX_ELEM_TYPE_SPOT_LIGHT)
+ {
+ if (data->extended.unknownDef)
+ {
+ buf->align(3);
+ buf->write_stream(data->extended.unknownDef, 24);
+ ZoneBuffer::clear_pointer(&dest->extended.unknownDef);
+ }
+ }
+ else
+ {
+ if (data->extended.unknownDef)
+ {
+ buf->align(1);
+ buf->write_stream(data->extended.unknownDef, sizeof(BYTE));
+ ZoneBuffer::clear_pointer(&dest->extended.unknownDef);
+ }
+ }
+ }
+ }
+
+ void IFxEffectDef::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->elemDefs)
+ {
+ buf->align(3);
+ auto* fx_elem_def = buf->write(data->elemDefs,
+ data->elemDefCountEmission + data->elemDefCountLooping + data->
+ elemDefCountOneShot);
+
+ for (std::int32_t i = 0; i < (data->elemDefCountEmission + data->elemDefCountLooping + data->
+ elemDefCountOneShot); i++)
+ {
+ write_fx_elem_def(zone, buf, &fx_elem_def[i]);
+ }
+
+ ZoneBuffer::clear_pointer(&dest->elemDefs);
+ }
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ void IFxEffectDef::dump(FxEffectDef* asset)
+ {
+ auto* iw5_fx = new IW5::FxEffectDef;
+ memcpy(iw5_fx, asset, sizeof FxEffectDef);
+ memset(iw5_fx->pad, 0, sizeof iw5_fx->pad);
+
+ // alloc elemdefs
+ const auto elem_def_count = iw5_fx->elemDefCountEmission + iw5_fx->elemDefCountLooping + iw5_fx->elemDefCountOneShot;
+ iw5_fx->elemDefs = new IW5::FxElemDef[elem_def_count];
+
+ // transform elemdefs to iw5 format
+ for (auto i = 0; i < elem_def_count; i++)
+ {
+ memcpy(&iw5_fx->elemDefs[i], &asset->elemDefs[i], sizeof IW4::FxElemDef);
+ iw5_fx->elemDefs[i].pad = 0;
+ }
+
+ IW5::IFxEffectDef::dump(iw5_fx);
+
+ delete[] iw5_fx->elemDefs;
+ delete iw5_fx;
+ }
+ }
+}
diff --git a/src/IW4/Assets/FxEffectDef.hpp b/src/IW4/Assets/FxEffectDef.hpp
new file mode 100644
index 0000000..a8b32e2
--- /dev/null
+++ b/src/IW4/Assets/FxEffectDef.hpp
@@ -0,0 +1,41 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IFxEffectDef : public IAsset
+ {
+ private:
+ std::string name_;
+ FxEffectDef* asset_ = nullptr;
+
+ static void write_fx_elem_def_visuals(IZone* zone, ZoneBuffer* buf, FxElemDef* def,
+ FxElemDefVisuals* dest);
+ static void write_fx_elem_def(IZone* zone, ZoneBuffer* buf, FxElemDef* dest);
+ static void write_fx_elem_visuals(IZone* zone, ZoneBuffer* buf, FxElemDef* def,
+ FxElemVisuals* dest);
+
+ FxEffectDef* parse(const std::string& name, ZoneMemory* mem);
+
+ public:
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(FxEffectDef* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/FxWorld.cpp b/src/IW4/Assets/FxWorld.cpp
new file mode 100644
index 0000000..a89fff0
--- /dev/null
+++ b/src/IW4/Assets/FxWorld.cpp
@@ -0,0 +1,209 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW5/Assets/FxWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ FxWorld* IFxWorld::parse(const std::string& name, ZoneMemory* mem)
+ {
+ auto* iw5_fxworld = IW5::IFxWorld::parse(name, mem);
+
+ if (!iw5_fxworld)
+ {
+ return nullptr;
+ }
+
+ // asset is actually the same so just cast
+ return reinterpret_cast(iw5_fxworld);
+ }
+
+ void IFxWorld::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = "maps/"s + (currentzone.substr(0, 3) == "mp_" ? "mp/" : "") + currentzone + ".d3dbsp"; // name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), name.data()).fxworld;
+ }
+ }
+
+ void IFxWorld::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IFxWorld::load_depending(IZone* zone)
+ {
+ auto* data = this->asset_;
+ if (data->glassSys.defs)
+ {
+ for (unsigned int i = 0; i < data->glassSys.defCount; i++)
+ {
+ if (data->glassSys.defs[i].physPreset)
+ {
+ zone->add_asset_of_type(physpreset, data->glassSys.defs[i].physPreset->name);
+ }
+ if (data->glassSys.defs[i].material)
+ {
+ zone->add_asset_of_type(material, data->glassSys.defs[i].material->name);
+ }
+ if (data->glassSys.defs[i].materialShattered)
+ {
+ zone->add_asset_of_type(material, data->glassSys.defs[i].materialShattered->name);
+ }
+ }
+ }
+ }
+
+ std::string IFxWorld::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IFxWorld::type()
+ {
+ return fx_map;
+ }
+
+ void IFxWorld::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->glassSys.defs)
+ {
+ buf->align(3);
+ auto* glass_def = buf->write(data->glassSys.defs, data->glassSys.defCount);
+
+ for (std::uint32_t i = 0; i < data->glassSys.defCount; i++)
+ {
+ if (data->glassSys.defs[i].physPreset)
+ {
+ glass_def[i].physPreset = reinterpret_cast(zone->get_asset_pointer(
+ physpreset, data->glassSys.defs[i].physPreset->name));
+ }
+ if (data->glassSys.defs[i].material)
+ {
+ glass_def[i].material = reinterpret_cast(zone->get_asset_pointer(
+ material, data->glassSys.defs[i].material->name));
+ }
+ if (data->glassSys.defs[i].materialShattered)
+ {
+ glass_def[i].materialShattered = reinterpret_cast(zone->get_asset_pointer(
+ material, data->glassSys.defs[i].materialShattered->name));
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->glassSys.defs);
+ }
+
+ buf->push_stream(2);
+ if (data->glassSys.piecePlaces)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.piecePlaces, data->glassSys.pieceLimit);
+ ZoneBuffer::clear_pointer(&dest->glassSys.piecePlaces);
+ }
+
+ if (data->glassSys.pieceStates)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.pieceStates, data->glassSys.pieceLimit);
+ ZoneBuffer::clear_pointer(&dest->glassSys.pieceStates);
+ }
+
+ if (data->glassSys.pieceDynamics)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.pieceDynamics, data->glassSys.pieceLimit);
+ ZoneBuffer::clear_pointer(&dest->glassSys.pieceDynamics);
+ }
+
+ if (data->glassSys.geoData)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.geoData, data->glassSys.geoDataLimit);
+ ZoneBuffer::clear_pointer(&dest->glassSys.geoData);
+ }
+
+ if (data->glassSys.isInUse)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.isInUse, data->glassSys.pieceWordCount);
+ ZoneBuffer::clear_pointer(&dest->glassSys.isInUse);
+ }
+
+ if (data->glassSys.cellBits)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.cellBits, data->glassSys.pieceWordCount * data->glassSys.cellCount);
+ ZoneBuffer::clear_pointer(&dest->glassSys.cellBits);
+ }
+
+ if (data->glassSys.visData)
+ {
+ buf->align(15);
+ buf->write(data->glassSys.visData, (data->glassSys.pieceLimit + 15) & 0xFFFFFFF0);
+ ZoneBuffer::clear_pointer(&dest->glassSys.visData);
+ }
+
+ if (data->glassSys.linkOrg)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.linkOrg, data->glassSys.pieceLimit);
+ ZoneBuffer::clear_pointer(&dest->glassSys.linkOrg);
+ }
+
+ if (data->glassSys.halfThickness)
+ {
+ buf->align(15);
+ buf->write(data->glassSys.halfThickness, (data->glassSys.pieceLimit + 3) & 0xFFFFFFFC);
+ ZoneBuffer::clear_pointer(&dest->glassSys.halfThickness);
+ }
+ buf->pop_stream();
+
+ if (data->glassSys.lightingHandles)
+ {
+ buf->align(1);
+ buf->write(data->glassSys.lightingHandles, data->glassSys.initPieceCount);
+ ZoneBuffer::clear_pointer(&dest->glassSys.lightingHandles);
+ }
+
+ if (data->glassSys.initPieceStates)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.initPieceStates, data->glassSys.initPieceCount);
+ ZoneBuffer::clear_pointer(&dest->glassSys.initPieceStates);
+ }
+
+ if (data->glassSys.initGeoData)
+ {
+ buf->align(3);
+ buf->write(data->glassSys.initGeoData, data->glassSys.initGeoDataCount);
+ ZoneBuffer::clear_pointer(&dest->glassSys.initGeoData);
+ }
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ void IFxWorld::dump(FxWorld* asset)
+ {
+ IW5::IFxWorld::dump((IW5::FxWorld*)asset);
+ }
+ }
+}
diff --git a/src/IW4/Assets/FxWorld.hpp b/src/IW4/Assets/FxWorld.hpp
new file mode 100644
index 0000000..344c389
--- /dev/null
+++ b/src/IW4/Assets/FxWorld.hpp
@@ -0,0 +1,35 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IFxWorld : public IAsset
+ {
+ private:
+ std::string name_;
+ FxWorld* asset_ = nullptr;
+
+ FxWorld* parse(const std::string& name, ZoneMemory* mem);
+
+ public:
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(FxWorld* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/GameWorldMp.cpp b/src/IW4/Assets/GameWorldMp.cpp
new file mode 100644
index 0000000..91046bd
--- /dev/null
+++ b/src/IW4/Assets/GameWorldMp.cpp
@@ -0,0 +1,26 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW5/Assets/GlassWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ std::int32_t IGameWorldMp::type()
+ {
+ return game_map_mp;
+ }
+
+ void IGameWorldMp::dump(GameWorldMp* asset)
+ {
+ IGlassWorld::dump(reinterpret_cast(asset));
+ }
+ }
+}
diff --git a/src/IW4/Assets/GameWorldMp.hpp b/src/IW4/Assets/GameWorldMp.hpp
new file mode 100644
index 0000000..89b5346
--- /dev/null
+++ b/src/IW4/Assets/GameWorldMp.hpp
@@ -0,0 +1,24 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+#include "../IW5/Assets/GlassWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IGameWorldMp : public IW5::IGlassWorld
+ {
+ public:
+ std::int32_t type() override;
+ static void dump(GameWorldMp* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/GameWorldSp.cpp b/src/IW4/Assets/GameWorldSp.cpp
new file mode 100644
index 0000000..a6bb458
--- /dev/null
+++ b/src/IW4/Assets/GameWorldSp.cpp
@@ -0,0 +1,119 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ void IGameWorldSp::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = "maps/"s + (currentzone.substr(0, 3) == "mp_" ? "mp/" : "") + currentzone + ".d3dbsp";
+ auto* mp_asset = IGameWorldMp::parse(name, mem);
+
+ if (!mp_asset)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), this->name().data()).game_map_sp;
+ }
+ else
+ {
+ // generate sp asset based on mp one
+ this->asset_ = mem->Alloc();
+ this->asset_->name = mp_asset->name;
+ this->asset_->g_glassData = reinterpret_cast(mp_asset->g_glassData);
+ }
+ }
+
+ void IGameWorldSp::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IGameWorldSp::load_depending(IZone* zone)
+ {
+ }
+
+ std::string IGameWorldSp::name()
+ {
+ return this->name_;
+ }
+
+ void IGameWorldSp::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ assert(sizeof GameWorldSp, 56);
+ assert(sizeof G_GlassData, 128);
+ assert(sizeof G_GlassPiece, 12);
+ assert(sizeof G_GlassName, 12);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->name = buf->write_str(this->name());
+
+ if (data->g_glassData)
+ {
+ buf->align(3);
+
+ auto* glass_data = data->g_glassData;
+ auto* dest_glass_data = buf->write(glass_data);
+
+ if (glass_data->glassPieces)
+ {
+ buf->align(3);
+ buf->write(glass_data->glassPieces, glass_data->pieceCount);
+ ZoneBuffer::clear_pointer(&dest_glass_data->glassPieces);
+ }
+ if (glass_data->glassNames)
+ {
+ buf->align(3);
+ const auto namedest = buf->write(glass_data->glassNames, glass_data->glassNameCount);
+
+ for (unsigned int i = 0; i < glass_data->glassNameCount; i++)
+ {
+ namedest[i].nameStr = buf->write_str(glass_data->glassNames[i].nameStr);
+
+ if (glass_data->glassNames[i].pieceCount)
+ {
+ buf->align(1);
+ buf->write(glass_data->glassNames[i].pieceIndices, glass_data->glassNames[i].pieceCount);
+ ZoneBuffer::clear_pointer(&glass_data->glassNames[i].pieceIndices);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest_glass_data->glassNames);
+ }
+
+ ZoneBuffer::clear_pointer(&dest->g_glassData);
+ }
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+
+ std::int32_t IGameWorldSp::type()
+ {
+ return game_map_sp;
+ }
+
+ void IGameWorldSp::dump(GameWorldSp* asset)
+ {
+ auto* mp_asset = new GameWorldMp;
+ memset(mp_asset, 0, sizeof GameWorldMp);
+
+ mp_asset->name = asset->name;
+ mp_asset->g_glassData = asset->g_glassData;
+
+ IGameWorldMp::dump(mp_asset);
+
+ delete mp_asset;
+ }
+ }
+}
diff --git a/src/IW4/Assets/GameWorldSp.hpp b/src/IW4/Assets/GameWorldSp.hpp
new file mode 100644
index 0000000..8facec4
--- /dev/null
+++ b/src/IW4/Assets/GameWorldSp.hpp
@@ -0,0 +1,35 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+#include "../IW5/Assets/GlassWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IGameWorldSp : public IAsset
+ {
+ private:
+ std::string name_;
+ GameWorldSp* asset_ = nullptr;
+
+ public:
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(GameWorldSp* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/GfxImage.cpp b/src/IW4/Assets/GfxImage.cpp
new file mode 100644
index 0000000..5ab655a
--- /dev/null
+++ b/src/IW4/Assets/GfxImage.cpp
@@ -0,0 +1,423 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "IW5/Assets/GfxImage.hpp"
+
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ std::string IGfxImage::clean_name(const std::string& name)
+ {
+ auto newName = name;
+
+ for (auto i = 0u; i < name.size(); i++)
+ {
+ switch (newName[i])
+ {
+ case '*':
+ newName[i] = '_';
+ break;
+ }
+ }
+
+ return newName;
+ }
+
+ GfxImage* IGfxImage::parse(const std::string& name, ZoneMemory* mem)
+ {
+ auto path = "images\\" + this->clean_name(name) + ".ffimg";
+
+ if (!FileSystem::FileExists(path))
+ {
+ return nullptr;
+ }
+
+ auto fp = FileSystem::FileOpen(path, "rb");
+ if (!fp)
+ {
+ return nullptr;
+ }
+
+ ZONETOOL_INFO("Parsing GfxImage \"%s\"...", name.data());
+
+ auto reader = FileSystem::ToReader(fp);
+
+ auto img = mem->Alloc();
+ img->mapType = reader->Read();
+ img->semantic = reader->Read();
+ img->category = reader->Read();
+ img->flags = reader->Read();
+ img->cardMemory = reader->Read();
+ img->dataLen1 = reader->Read();
+ img->dataLen2 = reader->Read();
+ img->height = reader->Read();
+ img->width = reader->Read();
+ img->depth = reader->Read();
+ img->loaded = reader->Read();
+ img->name = mem->StrDup(reader->ReadString());
+
+ auto loaddef = mem->Alloc();
+ loaddef->mipLevels = reader->Read();
+ loaddef->flags = reader->Read();
+ loaddef->dimensions[0] = reader->Read();
+ loaddef->dimensions[1] = reader->Read();
+ loaddef->dimensions[2] = reader->Read();
+ loaddef->format = reader->Read();
+ loaddef->dataSize = reader->Read();
+
+ GfxImageLoadDef* finalLoaddef = nullptr;
+
+ if (loaddef->dataSize > 4)
+ {
+ finalLoaddef = mem->ManualAlloc(
+ sizeof GfxImageLoadDef +
+ (loaddef->dataSize - 4));
+ memcpy(finalLoaddef, loaddef, sizeof GfxImageLoadDef);
+ reader->ReadManual(&finalLoaddef->texture, loaddef->dataSize, 1);
+ }
+ else
+ {
+ finalLoaddef = loaddef;
+ }
+
+
+ img->texture = finalLoaddef;
+
+ FileSystem::FileClose(fp);
+
+ return img;
+ }
+
+ void IGfxImage::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = name;
+ this->asset_ = this->parse(name, mem);
+ this->isMapImage = (this->name_.size() >= 6)
+ ? ((this->name_.substr(0, 6) == "*light" || this->name_.substr(0, 6) == "*refle" ||
+ this->name_ == "$outdoor")
+ ? true
+ : false)
+ : false;
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), this->name_.data()).gfximage;
+ }
+ }
+
+ void IGfxImage::init(void* asset, ZoneMemory* mem)
+ {
+ this->asset_ = reinterpret_cast(asset);
+ this->name_ = this->asset_->name;
+ this->isMapImage = (this->name_.size() >= 6)
+ ? ((this->name_.substr(0, 6) == "*light" || this->name_.substr(0, 6) == "*refle" ||
+ this->name_ == "$outdoor")
+ ? true
+ : false)
+ : false;
+
+ auto parsed = this->parse(this->name_, mem);
+ if (parsed)
+ {
+ this->asset_ = parsed;
+ }
+ }
+
+ void IGfxImage::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IGfxImage::load_depending(IZone* zone)
+ {
+ }
+
+ std::string IGfxImage::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IGfxImage::type()
+ {
+ return image;
+ }
+
+ void IGfxImage::write(IZone* zone, ZoneBuffer* buf)
+ {
+ if (zone->get_target() == zone_target::pc)
+ {
+ IW5::IGfxImage::dump_iwi(this->name());
+
+ auto data = this->asset_;
+ auto dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ dest->name = buf->write_str(this->name());
+
+ // set loaded to false
+ dest->loaded = false;
+
+ buf->push_stream(0);
+ if (data->texture)
+ {
+ buf->align(3);
+
+ auto desttext = buf->at();
+ buf->write_stream(data->texture, sizeof GfxImageLoadDef - sizeof std::uintptr_t);
+
+ if (isMapImage && desttext->dataSize)
+ {
+ buf->write_stream(&data->texture->texture, data->texture->dataSize);
+ }
+ else
+ {
+ desttext->dataSize = 0;
+ }
+
+ ZoneBuffer::clear_pointer(&dest->texture);
+ }
+ buf->pop_stream();
+
+ END_LOG_STREAM;
+ buf->pop_stream();
+ }
+ else
+ {
+ alpha::GfxImage alpha_image = {};
+
+ // transform iwi
+ if (!FileSystem::FileExists(va("images/%s.iwi", this->name().data())) && !this->isMapImage)
+ {
+ ZONETOOL_FATAL("Image %s is missing!", this->name().data());
+ }
+
+ std::vector pixels;
+ auto fp = FileSystem::FileOpen(va("images/%s.iwi", this->name().data()), "rb");
+ if (fp || this->isMapImage)
+ {
+ if (!this->isMapImage)
+ {
+ auto file_size = FileSystem::FileSize(fp);
+ auto img_data = FileSystem::ReadBytes(fp, file_size);
+
+ auto iwi_header = (GfxImageFileHeader*)img_data.data();
+
+ sizeof GfxImageFileHeader;
+
+ auto pixel_data = img_data.data() + 32;
+ auto pixel_data_size = img_data.size() - 32;
+
+ pixels.resize(pixel_data_size);
+ memcpy(&pixels[0], pixel_data, pixel_data_size);
+
+ // add image to imagepak
+
+
+ // zone images
+ alpha_image.cached = false;
+ alpha_image.cardMemory.platform[0] = pixels.size();
+
+ // pakfile images
+ //alpha_image.cached = true;
+ //alpha_image.cardMemory.platform[0] = 0;
+ //alpha_image.streams[0].width = iwi_header->dimensions[0];
+ //alpha_image.streams[0].height = iwi_header->dimensions[1];
+ //alpha_image.streams[0].pixelSize = 1;
+ //buf->add_image(pixels);
+
+ alpha_image.format = 0x1A200154;
+ alpha_image.width = iwi_header->dimensions[0];
+ alpha_image.height = iwi_header->dimensions[1];
+ alpha_image.depth = iwi_header->dimensions[2];
+ alpha_image.levelCount = 1;
+ alpha_image.mapType = 3;
+ alpha_image.category = 3;
+ }
+ else
+ {
+ pixels.resize(this->asset_->texture->dataSize);
+ memcpy(&pixels[0], &this->asset_->texture->texture, pixels.size());
+
+ alpha_image.cached = false;
+ alpha_image.cardMemory.platform[0] = pixels.size();
+ if (this->name().starts_with("*refle"))
+ {
+ alpha_image.format = 0x18280186;
+ alpha_image.mapType = 5;
+ alpha_image.semantic = 1;
+ alpha_image.category = 1;
+ }
+ else if (this->name().starts_with("*light"))
+ {
+ alpha_image.format = 0x2800017A;
+ alpha_image.mapType = 3;
+ alpha_image.semantic = 1;
+ alpha_image.category = 2;
+ }
+ else if (this->name() == "$outdoor")
+ {
+ alpha_image.format = 0x28000102;
+ alpha_image.mapType = 3;
+ alpha_image.semantic = 1;
+ alpha_image.category = 1;
+ }
+ else
+ {
+ ZONETOOL_FATAL("you goofed");
+ }
+ alpha_image.width = this->asset_->width;
+ alpha_image.height = this->asset_->height;
+ alpha_image.depth = this->asset_->depth;
+ alpha_image.levelCount = 1;
+ }
+
+ }
+ else
+ {
+ ZONETOOL_FATAL("Cannot open image %s!", this->name().data());
+ }
+
+
+ auto data = &alpha_image;
+ auto dest = buf->write(data);
+
+ buf->push_stream(3);
+
+ dest->name = buf->write_str(this->name());
+
+ buf->push_stream(1);
+ if (data->cardMemory.platform[0])
+ {
+ buf->align(4095);
+ buf->write(pixels.data(), pixels.size());
+ ZoneBuffer::clear_pointer(&dest->pixels);
+ }
+ else
+ {
+ dest->pixels = nullptr;
+ }
+ buf->pop_stream();
+
+ buf->pop_stream();
+
+ endian_convert(&dest->name);
+ endian_convert(&dest->format);
+ endian_convert(&dest->width);
+ endian_convert(&dest->height);
+ endian_convert(&dest->depth);
+ endian_convert(&dest->pixels);
+ endian_convert(&dest->cardMemory.platform[0]);
+ for (auto i = 0; i < 4; i++)
+ {
+ endian_convert(&dest->streams[i].width);
+ endian_convert(&dest->streams[i].height);
+ endian_convert(&dest->streams[i].pixelSize);
+ }
+ }
+ }
+
+ // Legacy cancer code
+ void fwritestr(FILE* file, const char* str)
+ {
+ if (!str)
+ return;
+ while (*str)
+ {
+ fwrite(str, 1, 1, file);
+ str++;
+ }
+ fwrite(str, 1, 1, file);
+ }
+
+ void fwriteint(FILE* file, int value)
+ {
+ int _val = value;
+ fwrite(&_val, 4, 1, file);
+ }
+
+ void fwriteuint(FILE* file, unsigned int value)
+ {
+ unsigned int _val = value;
+ fwrite(&_val, 4, 1, file);
+ }
+
+ void fwritechar(FILE* file, char c)
+ {
+ char _val = c;
+ fwrite(&_val, 1, 1, file);
+ }
+
+ char cleanAssetName[50];
+
+ char* ClearAssetName(char* name, int maxSize = 50)
+ {
+ int size = strnlen(name, maxSize);
+ char* newName = cleanAssetName;
+ memset(newName, 0, size + 1);
+ strncpy(newName, name, maxSize);
+ for (int i = 0; i < size; i++)
+ {
+ switch (newName[i])
+ {
+ case '*':
+ newName[i] = '_';
+ break;
+ }
+ }
+ return newName;
+ }
+
+ void IGfxImage::dump(GfxImage* asset)
+ {
+ if (asset->texture && asset->texture->dataSize)
+ {
+ char* newName = ClearAssetName((char*)asset->name);
+ auto fp = FileSystem::FileOpen("images/"s + newName + ".ffImg"s, "wb");
+
+ if (!fp) return;
+
+#define fwstr(_str) fwritestr(fp, _str)
+#define fwint(_int) fwriteint(fp, _int)
+#define fwchr(_chr) fwritechar(fp, _chr)
+#define frstr() freadstr(fp)
+#define frint() freadint(fp)
+#define frchr() freadchar(fp)
+
+ // Header
+ fwchr(asset->mapType);
+ fwchr(asset->semantic);
+ fwchr(asset->category);
+ fwchr(asset->flags);
+ fwint((int)asset->cardMemory);
+ fwint(asset->dataLen1);
+ fwint(asset->dataLen2);
+ fwint(asset->height);
+ fwint(asset->width);
+ fwint(asset->depth);
+ fwstr(asset->name);
+
+ // LoadDef
+ fwchr(asset->texture->mipLevels);
+ fwchr(asset->texture->flags);
+ fwint(asset->texture->dimensions[0]);
+ fwint(asset->texture->dimensions[1]);
+ fwint(asset->texture->dimensions[2]);
+ fwint(asset->texture->format);
+ fwint(asset->texture->dataSize);
+
+ fwrite(&asset->texture->texture, 1, asset->texture->dataSize, fp);
+
+ FileSystem::FileClose(fp);
+ }
+ }
+ }
+}
diff --git a/src/IW4/Assets/GfxImage.hpp b/src/IW4/Assets/GfxImage.hpp
new file mode 100644
index 0000000..7618d75
--- /dev/null
+++ b/src/IW4/Assets/GfxImage.hpp
@@ -0,0 +1,40 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#pragma once
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ class IGfxImage : public IAsset
+ {
+ private:
+ std::string name_;
+ GfxImage* asset_ = nullptr;
+ bool isMapImage;
+
+ std::string clean_name(const std::string& name);
+ GfxImage* parse(const std::string& name, ZoneMemory* mem);
+
+ public:
+ void init(const std::string& name, ZoneMemory* mem) override;
+ void init(void* asset, ZoneMemory* mem) override;
+
+ void prepare(ZoneBuffer* buf, ZoneMemory* mem) override;
+ void load_depending(IZone* zone) override;
+
+ void* pointer() override { return asset_; }
+ std::string name() override;
+ std::int32_t type() override;
+ void write(IZone* zone, ZoneBuffer* buffer) override;
+
+ static void dump(GfxImage* asset);
+ };
+ }
+}
diff --git a/src/IW4/Assets/GfxWorld.cpp b/src/IW4/Assets/GfxWorld.cpp
new file mode 100644
index 0000000..891e486
--- /dev/null
+++ b/src/IW4/Assets/GfxWorld.cpp
@@ -0,0 +1,850 @@
+// ======================= ZoneTool =======================
+// zonetool, a fastfile linker for various
+// Call of Duty titles.
+//
+// Project: https://github.com/ZoneTool/zonetool
+// Author: RektInator (https://github.com/RektInator)
+// License: GNU GPL v3.0
+// ========================================================
+#include "stdafx.hpp"
+#include "../IW5/Assets/GfxWorld.hpp"
+
+namespace ZoneTool
+{
+ namespace IW4
+ {
+ /*legacy zonetool code, refactor me!*/
+ GfxWorld* IGfxWorld::parse(const std::string& name, ZoneMemory* mem)
+ {
+ auto iw5_gfxmap = IW5::IGfxWorld::parse(name, mem);
+
+ if (!iw5_gfxmap)
+ {
+ return nullptr;
+ }
+
+ // convert to IW4 format
+ auto gfxmap = mem->Alloc();
+
+ // copy struct data
+ memcpy(&gfxmap->name, &iw5_gfxmap->name, Difference(&gfxmap->cells, &gfxmap->name));
+
+ // allocate cells
+ gfxmap->cells = new GfxCell[gfxmap->dpvsPlanes.cellCount];
+ memset(gfxmap->cells, 0, sizeof(GfxCell) * gfxmap->dpvsPlanes.cellCount);
+
+ // copy cell data
+ for (int i = 0; i < gfxmap->dpvsPlanes.cellCount; i++)
+ {
+ memcpy(&gfxmap->cells[i], &iw5_gfxmap->cells[i], sizeof GfxCell);
+ }
+
+ // copy draw data
+ memcpy(gfxmap->draw._portpad0, iw5_gfxmap->worldDraw._portpad0, 16);
+ memcpy(gfxmap->draw._portpad1, iw5_gfxmap->worldDraw._portpad1, 56);
+
+ // copy remaining GfxWorld data
+ memcpy(&gfxmap->lightGrid, &iw5_gfxmap->lightGrid,
+ Difference(&gfxmap->fogTypesAllowed + 1, &gfxmap->lightGrid));
+
+ // return converted gfxmap
+ return gfxmap;
+ }
+
+ IGfxWorld::IGfxWorld()
+ {
+ }
+
+ IGfxWorld::~IGfxWorld()
+ {
+ }
+
+ void IGfxWorld::init(const std::string& name, ZoneMemory* mem)
+ {
+ this->name_ = "maps/"s + (currentzone.substr(0, 3) == "mp_" ? "mp/" : "") + currentzone + ".d3dbsp"; // name;
+ this->asset_ = this->parse(name, mem);
+
+ if (!this->asset_)
+ {
+ this->asset_ = DB_FindXAssetHeader(this->type(), name.data()).gfxworld;
+ }
+ }
+
+ void IGfxWorld::prepare(ZoneBuffer* buf, ZoneMemory* mem)
+ {
+ }
+
+ void IGfxWorld::load_depending(IZone* zone)
+ {
+ auto* data = this->asset_;
+
+ // Skies
+ if (data->skyCount)
+ {
+ for (unsigned int i = 0; i < data->skyCount; i++)
+ {
+ if (data->skies[i].skyImage)
+ {
+ zone->add_asset_of_type(image, data->skies[i].skyImage->name);
+ }
+ }
+ }
+
+ // ReflectionImages
+ if (data->draw.reflectionImages)
+ {
+ for (unsigned int i = 0; i < data->draw.reflectionProbeCount; i++)
+ {
+ if (data->draw.reflectionImages[i])
+ {
+ zone->add_asset_of_type(image, data->draw.reflectionImages[i]->name);
+ }
+ }
+ }
+
+ // Lightmaps
+ if (data->draw.lightmaps)
+ {
+ for (int i = 0; i < data->draw.lightmapCount; i++)
+ {
+ if (data->draw.lightmaps[i].primary)
+ {
+ zone->add_asset_of_type(image, data->draw.lightmaps[i].primary->name);
+ }
+
+ if (data->draw.lightmaps[i].secondary)
+ {
+ zone->add_asset_of_type(image, data->draw.lightmaps[i].secondary->name);
+ }
+ }
+ }
+
+ // SkyImage (Unused?)
+ if (data->draw.skyImage)
+ {
+ zone->add_asset_of_type(image, data->draw.skyImage->name);
+ }
+
+ // OutdoorImage (Unused?)
+ if (data->draw.outdoorImage)
+ {
+ zone->add_asset_of_type(image, data->draw.outdoorImage->name);
+ }
+
+ if (zone->get_target() != zone_target::pc)
+ {
+ return;
+ }
+
+ // MaterialMemory
+ if (data->materialMemory)
+ {
+ for (int i = 0; i < data->materialMemoryCount; i++)
+ {
+ if (data->materialMemory[i].material)
+ {
+ zone->add_asset_of_type(material, data->materialMemory[i].material->name);
+ }
+ }
+ }
+
+ // Sunflare_t
+ if (data->sun.spriteMaterial)
+ {
+ zone->add_asset_of_type(material, data->sun.spriteMaterial->name);
+ }
+
+ if (data->sun.flareMaterial)
+ {
+ zone->add_asset_of_type(material, data->sun.flareMaterial->name);
+ }
+
+ // OutdoorImage
+ if (data->outdoorImage)
+ {
+ zone->add_asset_of_type(image, data->outdoorImage->name);
+ }
+
+ // Dpvs.Surfaces
+ if (data->dpvs.surfaces)
+ {
+ for (int i = 0; i < data->surfaceCount; i++)
+ {
+ if (data->dpvs.surfaces[i].material)
+ {
+ zone->add_asset_of_type(material, data->dpvs.surfaces[i].material->name);
+ }
+ }
+ }
+
+ if (data->dpvs.smodelDrawInsts)
+ {
+ for (unsigned int i = 0; i < data->dpvs.smodelCount; i++)
+ {
+ if (data->dpvs.smodelDrawInsts[i].model)
+ {
+ zone->add_asset_of_type(xmodel, data->dpvs.smodelDrawInsts[i].model->name);
+ }
+ }
+ }
+ }
+
+ std::string IGfxWorld::name()
+ {
+ return this->name_;
+ }
+
+ std::int32_t IGfxWorld::type()
+ {
+ return gfx_map;
+ }
+
+ void IGfxWorld::write(IZone* zone, ZoneBuffer* buf)
+ {
+ auto* data = this->asset_;
+ auto* dest = buf->write(data);
+
+ buf->push_stream(3);
+ START_LOG_STREAM;
+
+ if (data->name)
+ {
+ dest->name = buf->write_str(this->name());
+ }
+ if (data->baseName)
+ {
+ dest->baseName = buf->write_str(this->name());
+ }
+
+ if (data->skies)
+ {
+ buf->align(3);
+ auto skiesArray = buf->write(data->skies, data->skyCount);
+
+ for (std::uint32_t i = 0; i < data->skyCount; i++)
+ {
+ if (data->skies[i].skyStartSurfs)
+ {
+ buf->align(3);
+ buf->write_p(data->skies[i].skyStartSurfs, data->skies[i].skySurfCount);
+ ZoneBuffer::clear_pointer(&skiesArray[i].skyStartSurfs);
+ }
+
+ if (data->skies[i].skyImage)
+ {
+ skiesArray[i].skyImage = reinterpret_cast(zone->get_asset_pointer(
+ image, data->skies[i].skyImage->name));
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->skies);
+ }
+
+ if (dest->dpvsPlanes.planes)
+ {
+ dest->dpvsPlanes.planes = buf->write_s(3, data->dpvsPlanes.planes, data->planeCount);
+ }
+
+ if (dest->dpvsPlanes.nodes)
+ {
+ buf->align(1);
+ buf->write_p(data->dpvsPlanes.nodes, data->nodeCount);
+ ZoneBuffer::clear_pointer(&dest->dpvsPlanes.nodes);
+ }
+
+ buf->push_stream(2);
+ if (dest->dpvsPlanes.sceneEntCellBits)
+ {
+ buf->align(3);
+ buf->write(data->dpvsPlanes.sceneEntCellBits, data->dpvsPlanes.cellCount << 11);
+ ZoneBuffer::clear_pointer(&dest->dpvsPlanes.sceneEntCellBits);
+ }
+ buf->pop_stream();
+
+ if (data->aabbTreeCounts)
+ {
+ buf->align(3);
+ buf->write_p(data->aabbTreeCounts, data->dpvsPlanes.cellCount);
+ ZoneBuffer::clear_pointer(&dest->aabbTreeCounts);
+ }
+
+ if (data->aabbTree)
+ {
+ buf->align(127);
+ auto cell_tree = buf->write_p(data->aabbTree, data->dpvsPlanes.cellCount);
+
+ for (std::int32_t i = 0; i < data->dpvsPlanes.cellCount; i++)
+ {
+ if (data->aabbTree[i].aabbtree)
+ {
+ buf->align(3);
+ auto gfx_aabb_tree = buf->write_p(data->aabbTree[i].aabbtree,
+ data->aabbTreeCounts[i].aabbTreeCount);
+
+ for (std::int32_t i2 = 0; i2 < data->aabbTreeCounts[i].aabbTreeCount; i2++)
+ {
+ if (data->aabbTree[i].aabbtree[i2].smodelIndexes)
+ {
+ gfx_aabb_tree[i2].smodelIndexes = buf->write_s(
+ 1, data->aabbTree[i].aabbtree[i2].smodelIndexes,
+ data->aabbTree[i].aabbtree[i2].smodelIndexCount);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&cell_tree[i].aabbtree);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->aabbTree);
+ }
+
+ if (data->cells)
+ {
+ buf->align(3);
+ auto gfx_cell = buf->write(data->cells, data->dpvsPlanes.cellCount);
+
+ for (std::int32_t i = 0; i < data->dpvsPlanes.cellCount; i++)
+ {
+ if (data->cells[i].portals)
+ {
+ buf->align(3);
+ auto gfx_portal = buf->write(data->cells[i].portals, data->cells[i].portalCount);
+
+ for (std::int32_t i2 = 0; i2 < data->cells[i].portalCount; i2++)
+ {
+ if (data->cells[i].portals[i2].vertices)
+ {
+ buf->align(3);
+ buf->write(data->cells[i].portals[i2].vertices, data->cells[i].portals[i2].vertexCount);
+ ZoneBuffer::clear_pointer(&gfx_portal[i2].vertices);
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&gfx_cell[i].portals);
+ }
+
+ if (data->cells[i].reflectionProbes)
+ {
+ buf->align(0);
+ buf->write(data->cells[i].reflectionProbes, data->cells[i].reflectionProbeCount);
+ ZoneBuffer::clear_pointer(&gfx_cell[i].reflectionProbes);
+ }
+
+ ZoneBuffer::clear_pointer(&dest->cells);
+ }
+ }
+
+ if (data->draw.reflectionImages)
+ {
+ buf->align(3);
+ auto reflectionProbes = buf->write(data->draw.reflectionImages,
+ data->draw.reflectionProbeCount);
+
+ for (std::uint64_t i = 0; i < data->draw.reflectionProbeCount; i++)
+ {
+ if (reflectionProbes[i])
+ {
+ reflectionProbes[i] = reinterpret_cast(zone->get_asset_pointer(
+ image, data->draw.reflectionImages[i]->name));
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->draw.reflectionImages);
+ }
+
+ if (data->draw.reflectionProbes)
+ {
+ buf->align(3);
+ buf->write(data->draw.reflectionProbes, data->draw.reflectionProbeCount);
+ ZoneBuffer::clear_pointer(&dest->draw.reflectionProbes);
+ }
+
+ buf->push_stream(2);
+ if (data->draw.reflectionProbeTextures)
+ {
+ buf->align(3);
+ buf->write(data->draw.reflectionProbeTextures, data->draw.reflectionProbeCount);
+ ZoneBuffer::clear_pointer(&dest->draw.reflectionProbeTextures);
+ }
+ buf->pop_stream();
+
+ if (data->draw.lightmaps)
+ {
+ buf->align(3);
+ auto gfx_lightmap_array = buf->write(data->draw.lightmaps, data->draw.lightmapCount);
+
+ for (std::int32_t i = 0; i < data->draw.lightmapCount; i++)
+ {
+ if (data->draw.lightmaps[i].primary)
+ {
+ gfx_lightmap_array[i].primary = reinterpret_cast(zone->get_asset_pointer(
+ image, data->draw.lightmaps[i].primary->name));
+ }
+
+ if (data->draw.lightmaps[i].secondary)
+ {
+ gfx_lightmap_array[i].secondary = reinterpret_cast(zone->get_asset_pointer(
+ image, data->draw.lightmaps[i].secondary->name));
+ }
+ }
+
+ ZoneBuffer::clear_pointer(&dest->draw.lightmaps);
+ }
+
+ buf->push_stream(2);
+ if (data->draw.lightmapPrimaryTextures)
+ {
+ buf->align(3);
+ buf->write_p(data->draw.lightmapPrimaryTextures, data->draw.lightmapCount);
+ ZoneBuffer::clear_pointer(&dest->draw.lightmapPrimaryTextures);
+ }
+
+ if (data->draw.lightmapSecondaryTextures)
+ {
+ buf->align(3);
+ buf->write_p(data->draw.lightmapSecondaryTextures, data->draw.lightmapCount);
+ ZoneBuffer::clear_pointer(&dest->draw.lightmapSecondaryTextures);
+ }
+ buf->pop_stream();
+
+ if (data->draw.skyImage)
+ {
+ dest->draw.skyImage = reinterpret_cast(zone->get_asset_pointer(
+ image, data->draw.skyImage->name));
+ }
+
+ if (data->draw.outdoorImage)
+ {
+ dest->draw.outdoorImage = reinterpret_cast