You are not logged in.
Привет, народ! Сколько лет тут не был, но как симэн взялся за санник, решил заглянуть снова
.
К делу. Пытаюсь своими силами через c++ вывести текстуру на экран из определённого TXD файла.
За основу взял небезызвестный gta_dll, к процессу игры подключаюсь путём подмены vorbisFile. Всё стандартно, вобщем.
Чудеса начинаются, когда я пытаюсь загрузить текстуру и попытаться отрисовать её по нажатию кнопки.
В самом верху:
CTexture* achievementGetTexture;
Далее, три процедуры отвечающие за загрузку, освобождение и отрисовку текстуры:
void LoadTextures()
{
int slot = txdStore.AddTxdSlot("achiv");
txdStore.LoadTxd(slot, "MODELS\\ACHIEV.TXD");
txdStore.AddRef(slot);
txdStore.PushCurrentTxd();
txdStore.SetCurrentTxd(slot);
achievementGetTexture->Load("ac_box", NULL);
txdStore.PopCurrentTxd();
debug("TEXTURE: %x", achievementGetTexture);
debug("Textures loaded");
}
void ReleaseTextures()
{
if ( achievementGetTexture ) {
achievementGetTexture->Clean();
achievementGetTexture = NULL;
}
int achievementGetTextureSlotIndex = CTxdStore::FindTxdSlot("achiv");
txdStore.RemoveTxdSlot(achievementGetTextureSlotIndex);
debug("Textures released");
}
void Update_Hook()
{
// Draw texture on demand.
while ( GetAsyncKeyState(0x09) )
achievementGetTexture->DrawTexturedRect(&RwRect2D(_width(0), _height(448), _width(280), _height(188)), &RwRGBA(255, 255, 255, 255));
}Где-то в DllMain:
call(0x5BD765, &LoadTextures, PATCH_CALL); call(0x53BBCB, &ReleaseTextures, PATCH_CALL); call(0x53BFAE, &Update_Hook, PATCH_CALL);
Собственно, проблема: при нажатии 0x09 (Tab) игра вылетает. Вылетает из-за того, что почему-то текстура не грузится в мой achievementGetTexture. Вот лог:
20:27:17.680 CTXDSTORE::ADDTXDSLOT([achiv])
20:27:17.681 CTXDSTORE::LOADTXD([4], [MODELS\ACHIEV.TXD])
20:27:17.697 CTXDSTORE::ADDREF([4])
20:27:17.697 CTXDSTORE::PUSHCURRENTTXD
20:27:17.697 CTXDSTORE::SETCURRENTTXD([4])
20:27:17.697 CTEXTURE::LOAD([ac_box], [(null)])
20:27:17.697 CTXDSTORE::POPCURRENTTXD
20:27:17.697 TEXTURE: 0 <-- sic!
20:27:17.697 Textures loaded
20:27:25.692 CTXDSTORE::FINDTXDSLOT([achiv])
20:27:25.692 CTXDSTORE::REMOVETXDSLOT([4])
20:27:25.692 Textures released
20:27:26.092 Log closed
Теперь самое главное: CTexture.h/.cpp, CTxdStore.h.cpp и RW.h/.cpp с определениями текстур и TxdStore.
#define FUNC_CTexture__DrawTexturedRect 0x728350
#define FUNC_CTexture__Load 0x7272B0
#define FUNC_CTexture__Reload 0x727270
#define FUNC_CTexture__Clean 0x727240
class CTexture
{
private:
RwTexture* texture;
public:
CTexture()
: texture(NULL)
{
};
void DrawTexturedRect(RwRect2D* pos, RwRGBA* color);
void Load(const char* name, const char* maskName);
void Clean();
void Reload(const char* name);
void Reload(const char* name, const char* maskName);
RwTexture* GetTexture() { return texture; };
};#include "StdAfx.h"
void CTexture::DrawTexturedRect(RwRect2D* pos, RwRGBA* color)
{
debug("CTEXTURE::DRAWTEXTUREDRECT([%.3f %.3f %.3f %.3f], [%i %i %i %i])", pos->x1, pos->y1, pos->x2, pos->y2, color->r, color->g, color->b, color->a);
DWORD dwFunc = FUNC_CTexture__DrawTexturedRect;
RwTexture* tex = GetTexture();
_asm
{
push color
push pos
mov ecx, tex
call dwFunc
}
}
void CTexture::Load(const char* name, const char* maskName)
{
debug("CTEXTURE::LOAD([%s], [%s])", name, maskName);
DWORD dwFunc = FUNC_CTexture__Load;
_asm
{
push maskName
push name
mov ecx, this
call dwFunc
mov [this], eax
add esp, 8
}
}
void CTexture::Clean()
{
debug("CTEXTURE::CLEAN()");
DWORD dwFunc = FUNC_CTexture__Clean;
_asm
{
mov ecx, this
call dwFunc
}
}
void CTexture::Reload(const char* name)
{
debug("CTEXTURE::RELOAD([%s])", name);
if ( name ) {
if ( texture ) {
RwTexture::Destroy(texture);
texture = NULL;
}
texture = RwTexture::Read(name, NULL);
}
}
void CTexture::Reload(const char* name, const char* maskName)
{
debug("CTEXTURE::RELOAD([%s], [%s])", name, maskName);
if ( name && maskName ) {
if ( texture ) {
RwTexture::Destroy(texture);
texture = NULL;
}
texture = RwTexture::Read(name, maskName);
}
}#define FUNC_CTxdStore__PushCurrentTxd 0x7316A0
#define FUNC_CTxdStore__PopCurrentTxd 0x7316B0
#define FUNC_CTxdStore__FindTxdSlot 0x731850
#define FUNC_CTxdStore__SetCurrentTxd 0x7319C0
#define FUNC_CTxdStore__AddTxdRef 0x731A00
#define FUNC_CTxdStore__AddTxdSlot 0x731C80
#define FUNC_CTxdStore__RemoveTxdSlot 0x731CD0
#define FUNC_CTxdStore__LoadTxd 0x7320B0
class CTxdStore
{
public:
static void PushCurrentTxd();
static void PopCurrentTxd();
static int FindTxdSlot(const char *name);
static void SetCurrentTxd(int slot);
static void AddRef(int index);
static int AddTxdSlot(const char* slotName);
static void RemoveTxdSlot(int slot);
static void LoadTxd(int slot, const char* fp);
};
static CTxdStore txdStore;#include "stdafx.h"
void CTxdStore::PushCurrentTxd()
{
debug("CTXDSTORE::PUSHCURRENTTXD");
DWORD dwFunc = FUNC_CTxdStore__PushCurrentTxd;
_asm call dwFunc
}
void CTxdStore::PopCurrentTxd()
{
debug("CTXDSTORE::POPCURRENTTXD");
DWORD dwFunc = FUNC_CTxdStore__PopCurrentTxd;
_asm call dwFunc
}
int CTxdStore::FindTxdSlot(const char *name)
{
debug("CTXDSTORE::FINDTXDSLOT([%s])", name);
DWORD dwFunc = FUNC_CTxdStore__FindTxdSlot;
int result = 0;
_asm
{
push name
call dwFunc
mov result, eax
add esp, 4
}
}
void CTxdStore::SetCurrentTxd(int slot)
{
debug("CTXDSTORE::SETCURRENTTXD([%i])", slot);
DWORD dwFunc = FUNC_CTxdStore__SetCurrentTxd;
_asm
{
push slot
call dwFunc
}
}
void CTxdStore::AddRef(int index)
{
debug("CTXDSTORE::ADDREF([%i])", index);
DWORD dwFunc = FUNC_CTxdStore__AddTxdRef;
_asm
{
push index
call dwFunc
}
}
int CTxdStore::AddTxdSlot(const char* slotName)
{
debug("CTXDSTORE::ADDTXDSLOT([%s])", slotName);
DWORD dwFunc = FUNC_CTxdStore__AddTxdSlot;
int result = 0;
_asm
{
push slotName
call dwFunc
mov result, eax
add esp, 4
}
}
void CTxdStore::RemoveTxdSlot(int slot)
{
debug("CTXDSTORE::REMOVETXDSLOT([%i])", slot);
DWORD dwFunc = FUNC_CTxdStore__RemoveTxdSlot;
_asm
{
push slot
call dwFunc
}
}
void CTxdStore::LoadTxd(int slot, const char* fp)
{
debug("CTXDSTORE::LOADTXD([%i], [%s])", slot, fp);
DWORD dwFunc = FUNC_CTxdStore__LoadTxd;
_asm
{
push fp
push slot
call dwFunc
}
}...
#define FUNC_RwTexture__Destroy 0x7F3820
#define FUNC_RwTexture__Read 0x7F3AC0
struct RwTexture
{
RwRaster *raster;
RwTexDictionary *txd;
RwListEntry TXDList;
char name[RW_TEXTURE_NAME_LENGTH];
char mask[RW_TEXTURE_NAME_LENGTH];
unsigned int flags;
int refs;
static void Destroy(RwTexture* texture);
static RwTexture* Read(const char* name, const char* maskName);
RwRaster* GetRaster() { return this->raster; };
};
......
void RwTexture::Destroy(RwTexture* texture)
{
DWORD dwFunc = FUNC_RwTexture__Destroy;
_asm
{
push texture
call dwFunc
add esp, 4
}
}
RwTexture* RwTexture::Read(const char* name, const char* maskName)
{
DWORD dwFunc = FUNC_RwTexture__Read;
RwTexture* result;
_asm
{
push maskName
push name
call dwFunc
add esp, 8
mov result, eax
}
return result;
}
...
Offline
Может стоит попробовать это:
http://ru-script.3dn.ru/publ/sozdanie_d … 18-1-0-206
http://ru-script.3dn.ru/forum/30-105-1
Просто предложение)
Вообще, жаль, что не так много времени нахожу на эту разработку. Но работа с текстурами - это святое, и было сделано в первую очередь. 
Last edited by DK22Pac (20-11-2013 00:44)
Plugin-SDK https://github.com/DK22Pac/plugin-sdk
Discord-сервер по plugin-sdk и программированию в GTA
RU https://discord.gg/QEesDGb
ENG https://discord.gg/zaVqFQv
Offline
http://ru-script.3dn.ru/publ/sozdanie_d … 18-1-0-206
А у меня как-то по-другому это сделано? Где у меня ошибка подскажите.
Last edited by Sw[ee]t (20-11-2013 15:13)
Offline
ну это, например:
while ( GetAsyncKeyState(0x09) )
Так нельзя писать. Замени на
if ( GetAsyncKeyState(0x09) )
К предыдущему посту: я просто привел альтернативный вариант gta_dll. Это некая платформа для создания собственных плагинов для игры, которая позволяет абстрагироваться от хуков и замен вызовов дефолтных функций. Представь, что тебе понадобиться ещё в каком-то плагине делать те же хуки (инициализация, отрисовка, удаление), а потом ещё в каком-то. Будешь искать новые адреса для патчинга? Эта платформа позволяет не думать создателю плагина о таких проблемах.
Last edited by DK22Pac (20-11-2013 20:47)
Plugin-SDK https://github.com/DK22Pac/plugin-sdk
Discord-сервер по plugin-sdk и программированию в GTA
RU https://discord.gg/QEesDGb
ENG https://discord.gg/zaVqFQv
Offline
Заменил. Вылет остался. В чём у меня проблема, кто-нибудь может ответить?
Место вылета:
Last edited by Sw[ee]t (21-11-2013 14:45)
Offline