Код:
#include "CreateAndLinkDLLProj.h"
#include "CreateAndLinkDLLTutBFL.h"
// MessageId: ERROR_SUCCESS
//
// MessageText:
//
// The operation completed successfully.
//
#define ERROR_SUCCESS 0L
typedef unsigned short WORD;
typedef unsigned long DWORD;
typedef float FLOAT;
typedef unsigned char BYTE;
typedef short SHORT;
#define XINPUT_GAMEPAD_DPAD_UP 0x0001
#define XINPUT_GAMEPAD_DPAD_DOWN 0x0002
#define XINPUT_GAMEPAD_DPAD_LEFT 0x0004
#define XINPUT_GAMEPAD_DPAD_RIGHT 0x0008
#define XINPUT_GAMEPAD_START 0x0010
#define XINPUT_GAMEPAD_BACK 0x0020
#define XINPUT_GAMEPAD_LEFT_THUMB 0x0040
#define XINPUT_GAMEPAD_RIGHT_THUMB 0x0080
#define XINPUT_GAMEPAD_LEFT_SHOULDER 0x0100
#define XINPUT_GAMEPAD_RIGHT_SHOULDER 0x0200
#define XINPUT_GAMEPAD_A 0x1000
#define XINPUT_GAMEPAD_B 0x2000
#define XINPUT_GAMEPAD_X 0x4000
#define XINPUT_GAMEPAD_Y 0x8000
// Structures used by XInput APIs
//
typedef struct _XINPUT_GAMEPAD
{
WORD wButtons;
BYTE bLeftTrigger;
BYTE bRightTrigger;
SHORT sThumbLX;
SHORT sThumbLY;
SHORT sThumbRX;
SHORT sThumbRY;
} XINPUT_GAMEPAD, *PXINPUT_GAMEPAD;
typedef struct _XINPUT_STATE
{
DWORD dwPacketNumber;
XINPUT_GAMEPAD Gamepad;
} XINPUT_STATE, *PXINPUT_STATE;
typedef void(*_XInputGamePadSetState)(int32 DeviceIndex, float leftMotor, float rightMotor);
typedef DWORD(*_XInputGamePadGetState)(int32 DeviceIndex, XINPUT_STATE* pState);
_XInputGamePadSetState m_XInputVibration;
_XInputGamePadGetState m_XInputGetStateDll;
void *v_dllHandle;
#pragma region Load DLL
// Method to import a DLL.
bool UCreateAndLinkDLLTutBFL::importDLL(FString folder, FString name)
{
FString filePath = *FPaths::GamePluginsDir() + folder + "/" + name;
if (FPaths::FileExists(filePath))
{
v_dllHandle = FPlatformProcess::GetDllHandle(*filePath); // Retrieve the DLL.
if (v_dllHandle != NULL)
{
return true;
}
}
return false; // Return an error.
}
#pragma endregion Load DLL
#pragma region Import Methods
// Imports the method XInputSetDLL from the DLL.
bool UCreateAndLinkDLLTutBFL::XInputSetDLL()
{
if (v_dllHandle != NULL)
{
m_XInputVibration = NULL;
FString procName = "XInputGamePadSetState"; // Needs to be the exact name of the DLL method.
m_XInputVibration = (_XInputGamePadSetState)FPlatformProcess::GetDllExport(v_dllHandle, *procName);
if (m_XInputVibration != NULL)
{
return true;
}
}
return false; // Return an error.
}
#pragma endregion Import Methods
#pragma region Import Methods
// Imports the method XInputGetDLL from the DLL.
bool UCreateAndLinkDLLTutBFL::XInputGetDLL()
{
if (v_dllHandle != NULL)
{
m_XInputGetStateDll = NULL;
FString procName = "XInputGamePadGetState"; // Needs to be the exact name of the DLL method.
m_XInputGetStateDll = (_XInputGamePadGetState)FPlatformProcess::GetDllExport(v_dllHandle, *procName);
if (m_XInputGetStateDll != NULL)
{
return true;
}
}
return false; // Return an error.
}
#pragma endregion Import Methods
#pragma region Method Calls
// Calls the method XInputVibration that was imported from the DLL.
void UCreateAndLinkDLLTutBFL::XInputVibration(int32 DeviceIndex, float leftMotor, float rightMotor)
{
if (m_XInputVibration != NULL)
{
m_XInputVibration( DeviceIndex, leftMotor, rightMotor);
}
}
#pragma endregion Method Calls
#pragma region Method Calls
// Calls the method XInputState that was imported from the DLL.
bool UCreateAndLinkDLLTutBFL::XInputGetState(int32 DeviceIndex, bool& DPAD_UP, bool& DPAD_DOWN, bool& DPAD_LEFT, bool& DPAD_RIGHT, TArray<bool>& BUTTONS, float& RTrigger, float& LTrigger, TArray<float>& RStick, TArray<float>& LStick)
{
if (m_XInputGetStateDll != NULL)
{
XINPUT_STATE state;
DWORD Result = m_XInputGetStateDll(DeviceIndex, &state);
if (Result == ERROR_SUCCESS)
{
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_DPAD_UP) DPAD_UP = true;
else DPAD_UP = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_DPAD_DOWN) DPAD_DOWN = true;
else DPAD_DOWN = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_DPAD_LEFT) DPAD_LEFT = true;
else DPAD_LEFT = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_DPAD_RIGHT) DPAD_RIGHT = true;
else DPAD_RIGHT = false;
BUTTONS.SetNum(10);
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_A) BUTTONS[0] = true;
else BUTTONS[0] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_B) BUTTONS[1] = true;
else BUTTONS[1] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_X) BUTTONS[2] = true;
else BUTTONS[2] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_Y) BUTTONS[3] = true;
else BUTTONS[3] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_LEFT_SHOULDER) BUTTONS[4] = true;
else BUTTONS[4] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_RIGHT_SHOULDER) BUTTONS[5] = true;
else BUTTONS[5] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_BACK) BUTTONS[6] = true;
else BUTTONS[6] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_START) BUTTONS[7] = true;
else BUTTONS[7] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_LEFT_THUMB) BUTTONS[8] = true;
else BUTTONS[8] = false;
if (state.Gamepad.wButtons & XINPUT_GAMEPAD_RIGHT_THUMB) BUTTONS[9] = true;
else BUTTONS[9] = false;
RTrigger = state.Gamepad.bRightTrigger / 255.0f;
LTrigger = state.Gamepad.bLeftTrigger / 255.0f;
RStick.SetNum(2);
LStick.SetNum(2);
RStick[0] = state.Gamepad.sThumbRX / 32767.0f;
RStick[1] = state.Gamepad.sThumbRY / 32767.0f;
LStick[0] = state.Gamepad.sThumbLX / 32767.0f;
LStick[1] = state.Gamepad.sThumbLY / 32767.0f;
return true;
}
}
return false; // Return an error.
}
#pragma endregion Method Calls
#pragma region Unload DLL
// If you love something set it free.
void UCreateAndLinkDLLTutBFL::freeDLL()
{
if (v_dllHandle != NULL)
{
m_XInputVibration = NULL;
m_XInputGetStateDll = NULL;
FPlatformProcess::FreeDllHandle(v_dllHandle);
v_dllHandle = NULL;
}
}
#pragma endregion Unload DLL