Skip to content

Commit

Permalink
feat(extra-natives/rdr3): add GET_WORLD_COORD_FROM_SCREEN_COORD
Browse files Browse the repository at this point in the history
  • Loading branch information
Disquse committed Feb 1, 2024
1 parent 66d0529 commit 4ef633c
Show file tree
Hide file tree
Showing 2 changed files with 69 additions and 0 deletions.
40 changes: 40 additions & 0 deletions code/components/extra-natives-rdr3/include/GamePrimitives.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,4 +51,44 @@ struct spdRay
Vec3V start;
Vec3V end;
};

struct grcViewport
{
float m_mat1[16];
float m_mat2[16];
float m_viewProjection[16];
float m_inverseView[16];
char m_pad[64];
float m_projection[16];
};
}

struct CViewportGame
{
public:
virtual ~CViewportGame() = 0;

private:
char m_pad[8];

public:
rage::grcViewport viewport;
};

extern CViewportGame** g_viewportGame;

inline rage::Vec3V Unproject(const rage::grcViewport& viewport, const rage::Vec3V& viewPos)
{
using namespace DirectX;

auto composite = XMMatrixMultiply(XMLoadFloat4x4((const XMFLOAT4X4*)&viewport.m_projection), XMLoadFloat4x4((const XMFLOAT4X4*)&viewport.m_viewProjection));
auto invVP = XMMatrixInverse(NULL, composite);
auto inVec = XMVectorSet((viewPos.x * 2.0f) - 1.0f, ((1.0 - viewPos.y) * 2.0f) - 1.0f, viewPos.z, 1.0f);
auto outCoord = XMVector3TransformCoord(inVec, invVP);

return {
XMVectorGetX(outCoord),
XMVectorGetY(outCoord),
XMVectorGetZ(outCoord)
};
}
29 changes: 29 additions & 0 deletions code/components/extra-natives-rdr3/src/GraphicsNatives.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#include "CfxRGBA.h"
#include "Hooking.Stubs.h"
#include "GamePrimitives.h"
#include "scrEngine.h"

enum ScriptImDrawType : uint32_t
{
Expand Down Expand Up @@ -104,13 +105,16 @@ struct WorldhorizonManager

static WorldhorizonManager* g_worldhorizonMgr;

CViewportGame** g_viewportGame;

static HookFunction hookFunction([]()
{
static_assert(sizeof(ScriptImRequest) == 64);
static_assert(sizeof(DrawOriginData) == 32);
static_assert(sizeof(DrawOriginStore) == 1040);

{
g_viewportGame = hook::get_address<CViewportGame**>(hook::get_pattern("0F 2F F0 76 ? 4C 8B 35", 8));
g_worldhorizonMgr = hook::get_address<WorldhorizonManager*>(hook::get_pattern("89 44 24 40 48 8D 0D ? ? ? ? 8B 84 24 90 00", 7));
}

Expand Down Expand Up @@ -286,4 +290,29 @@ static HookFunction hookFunction([]()
g_worldhorizonMgr->m_disableRendering = flag;
}
});

fx::ScriptEngine::RegisterNativeHandler("GET_WORLD_COORD_FROM_SCREEN_COORD", [](fx::ScriptContext& context)
{
float screenX = context.GetArgument<float>(0);
float screenY = context.GetArgument<float>(1);

using namespace DirectX;
rage::Vec3V start = Unproject((*g_viewportGame)->viewport, rage::Vec3V{ screenX, screenY, 0.0f });
rage::Vec3V end = Unproject((*g_viewportGame)->viewport, rage::Vec3V{ screenX, screenY, 1.0f });

auto startVector = XMLoadFloat3((XMFLOAT3*)&start);
auto endVector = XMLoadFloat3((XMFLOAT3*)&end);
auto normalVector = XMVector3Normalize(XMVectorSubtract(endVector, startVector));

scrVector* worldOut = context.GetArgument<scrVector*>(2);
scrVector* normalOut = context.GetArgument<scrVector*>(3);

worldOut->x = start.x;
worldOut->y = start.y;
worldOut->z = start.z;

normalOut->x = XMVectorGetX(normalVector);
normalOut->y = XMVectorGetY(normalVector);
normalOut->z = XMVectorGetZ(normalVector);
});
});

0 comments on commit 4ef633c

Please sign in to comment.