fixed bug with texture allocation

This commit is contained in:
aap 2015-09-19 19:28:23 +02:00
parent ee96da332f
commit 3c0df895f1
19 changed files with 380 additions and 273 deletions

View File

@ -77,6 +77,7 @@
<Optimization>Disabled</Optimization> <Optimization>Disabled</Optimization>
<SDLCheck>true</SDLCheck> <SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>_USING_V110_SDK71_;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions> <PreprocessorDefinitions>_USING_V110_SDK71_;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
</ClCompile> </ClCompile>
<Link> <Link>
<GenerateDebugInformation>true</GenerateDebugInformation> <GenerateDebugInformation>true</GenerateDebugInformation>

View File

@ -524,7 +524,7 @@ Atomic::getPipeline(void)
{ {
return this->pipeline ? return this->pipeline ?
this->pipeline : this->pipeline :
defaultPipelines[platformIdx[platform]]; defaultPipelines[platform];
} }
void void
@ -533,15 +533,15 @@ Atomic::init(void)
ObjPipeline *defpipe = new ObjPipeline(PLATFORM_NULL); ObjPipeline *defpipe = new ObjPipeline(PLATFORM_NULL);
for(uint i = 0; i < nelem(matFXGlobals.pipelines); i++) for(uint i = 0; i < nelem(matFXGlobals.pipelines); i++)
defaultPipelines[i] = defpipe; defaultPipelines[i] = defpipe;
defaultPipelines[platformIdx[PLATFORM_PS2]] = defaultPipelines[PLATFORM_PS2] =
ps2::makeDefaultPipeline(); ps2::makeDefaultPipeline();
defaultPipelines[platformIdx[PLATFORM_OGL]] = defaultPipelines[PLATFORM_OGL] =
gl::makeDefaultPipeline(); gl::makeDefaultPipeline();
defaultPipelines[platformIdx[PLATFORM_XBOX]] = defaultPipelines[PLATFORM_XBOX] =
xbox::makeDefaultPipeline(); xbox::makeDefaultPipeline();
defaultPipelines[platformIdx[PLATFORM_D3D8]] = defaultPipelines[PLATFORM_D3D8] =
d3d8::makeDefaultPipeline(); d3d8::makeDefaultPipeline();
defaultPipelines[platformIdx[PLATFORM_D3D9]] = defaultPipelines[PLATFORM_D3D9] =
d3d9::makeDefaultPipeline(); d3d9::makeDefaultPipeline();
} }

View File

@ -340,7 +340,7 @@ deleteObject(void *object)
int32 nativeRasterOffset; int32 nativeRasterOffset;
void void
makeNativeRaster(Raster *raster) D3dRaster::create(Raster *raster)
{ {
static uint32 formatMap[] = { static uint32 formatMap[] = {
0, 0,
@ -366,46 +366,42 @@ makeNativeRaster(Raster *raster)
0, 0,
0, 0, 0, 0, 0 0, 0, 0, 0, 0
}; };
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
if(raster->flags & 0x80) if(raster->flags & 0x80)
return; return;
uint32 format; uint32 format;
if(raster->format & (Raster::PAL4 | Raster::PAL8)){ if(raster->format & (Raster::PAL4 | Raster::PAL8)){
format = D3DFMT_P8; format = D3DFMT_P8;
ras->palette = new uint8[4*256]; this->palette = new uint8[4*256];
}else }else
format = formatMap[(raster->format >> 8) & 0xF]; format = formatMap[(raster->format >> 8) & 0xF];
ras->format = 0; this->format = 0;
ras->hasAlpha = alphaMap[(raster->format >> 8) & 0xF]; this->hasAlpha = alphaMap[(raster->format >> 8) & 0xF];
int32 levels = Raster::calculateNumLevels(raster->width, raster->height); int32 levels = Raster::calculateNumLevels(raster->width, raster->height);
ras->texture = createTexture(raster->width, raster->width, this->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? levels : 1, raster->format & Raster::MIPMAP ? levels : 1,
format); format);
} }
uint8* uint8*
lockRaster(Raster *raster, int32 level) D3dRaster::lock(Raster *raster, int32 level)
{ {
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); return lockTexture(this->texture, level);
return lockTexture(ras->texture, level);
} }
void void
unlockRaster(Raster *raster, int32 level) D3dRaster::unlock(Raster *raster, int32 level)
{ {
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); unlockTexture(this->texture, level);
unlockTexture(ras->texture, level);
} }
int32 int32
getNumLevels(Raster *raster) D3dRaster::getNumLevels(Raster *raster)
{ {
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
#ifdef RW_D3D9 #ifdef RW_D3D9
IDirect3DTexture9 *tex = (IDirect3DTexture9*)ras->texture; IDirect3DTexture9 *tex = (IDirect3DTexture9*)this->texture;
return tex->GetLevelCount(); return tex->GetLevelCount();
#else #else
RasterLevels *levels = (RasterLevels*)ras->texture; RasterLevels *levels = (RasterLevels*)this->texture;
return levels->numlevels; return levels->numlevels;
#endif #endif
} }
@ -425,11 +421,46 @@ getLevelSize(Raster *raster, int32 level)
#endif #endif
} }
void
allocateDXT(Raster *raster, int32 dxt, int32 numLevels, bool32 hasAlpha)
{
static uint32 dxtMap[] = {
0x31545844, // DXT1
0x32545844, // DXT2
0x33545844, // DXT3
0x34545844, // DXT4
0x35545844, // DXT5
};
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
ras->format = dxtMap[dxt-1];
ras->hasAlpha = hasAlpha;
ras->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? numLevels : 1,
ras->format);
raster->flags &= ~0x80;
}
void
setPalette(Raster *raster, void *palette, int32 size)
{
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
memcpy(ras->palette, palette, 4*size);
}
void
setTexels(Raster *raster, void *texels, int32 level)
{
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
uint8 *dst = raster->lock(level);
memcpy(dst, texels, getLevelSize(raster, level));
raster->unlock(level);
}
static void* static void*
createNativeRaster(void *object, int32 offset, int32) createNativeRaster(void *object, int32 offset, int32)
{ {
D3dRaster *raster = PLUGINOFFSET(D3dRaster, object, offset); D3dRaster *raster = PLUGINOFFSET(D3dRaster, object, offset);
new (raster) D3dRaster;
raster->texture = NULL; raster->texture = NULL;
raster->palette = NULL; raster->palette = NULL;
raster->format = 0; raster->format = 0;
@ -463,6 +494,8 @@ registerNativeRaster(void)
createNativeRaster, createNativeRaster,
destroyNativeRaster, destroyNativeRaster,
copyNativeRaster); copyNativeRaster);
Raster::nativeOffsets[PLATFORM_D3D8] = nativeRasterOffset;
Raster::nativeOffsets[PLATFORM_D3D9] = nativeRasterOffset;
} }
} }

View File

@ -385,13 +385,6 @@ makeMatFXPipeline(void)
Texture* Texture*
readNativeTexture(Stream *stream) readNativeTexture(Stream *stream)
{ {
static uint32 dxtMap[] = {
0x31545844, // DXT1
0x32545844, // DXT2
0x33545844, // DXT3
0x34545844, // DXT4
0x35545844, // DXT5
};
assert(findChunk(stream, ID_STRUCT, NULL, NULL)); assert(findChunk(stream, ID_STRUCT, NULL, NULL));
assert(stream->readU32() == PLATFORM_D3D8); assert(stream->readU32() == PLATFORM_D3D8);
Texture *tex = new Texture; Texture *tex = new Texture;
@ -415,13 +408,7 @@ readNativeTexture(Stream *stream)
D3dRaster *ras; D3dRaster *ras;
if(compression){ if(compression){
raster = new Raster(width, height, depth, format | type | 0x80, PLATFORM_D3D8); raster = new Raster(width, height, depth, format | type | 0x80, PLATFORM_D3D8);
ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); allocateDXT(raster, compression, numLevels, hasAlpha);
ras->format = dxtMap[compression-1];
ras->hasAlpha = hasAlpha;
ras->texture = createTexture(raster->width, raster->width,
raster->format & Raster::MIPMAP ? numLevels : 1,
ras->format);
raster->flags &= ~0x80;
}else }else
raster = new Raster(width, height, depth, format | type, PLATFORM_D3D8); raster = new Raster(width, height, depth, format | type, PLATFORM_D3D8);

View File

@ -304,6 +304,11 @@ Geometry::generateTriangles(void)
this->numTriangles = 0; this->numTriangles = 0;
Mesh *m = header->mesh; Mesh *m = header->mesh;
for(uint32 i = 0; i < header->numMeshes; i++){ for(uint32 i = 0; i < header->numMeshes; i++){
if(m->numIndices < 3){
// shouldn't happen but it does
m++;
continue;
}
if(header->flags == 1){ // tristrip if(header->flags == 1){ // tristrip
for(uint32 j = 0; j < m->numIndices-2; j++){ for(uint32 j = 0; j < m->numIndices-2; j++){
if(!isDegenerate(&m->indices[j])) if(!isDegenerate(&m->indices[j]))
@ -320,6 +325,10 @@ Geometry::generateTriangles(void)
uint16 *f = this->triangles; uint16 *f = this->triangles;
m = header->mesh; m = header->mesh;
for(uint32 i = 0; i < header->numMeshes; i++){ for(uint32 i = 0; i < header->numMeshes; i++){
if(m->numIndices < 3){
m++;
continue;
}
int32 matid = findPointer((void*)m->material, int32 matid = findPointer((void*)m->material,
(void**)this->materialList, (void**)this->materialList,
this->numMaterials); this->numMaterials);

View File

@ -10,6 +10,7 @@
#include "rwpipeline.h" #include "rwpipeline.h"
#include "rwobjects.h" #include "rwobjects.h"
#include "rwps2.h" #include "rwps2.h"
#include "rwd3d.h"
#include "rwxbox.h" #include "rwxbox.h"
#include "gtaplg.h" #include "gtaplg.h"
@ -21,7 +22,11 @@ void
attachPlugins(void) attachPlugins(void)
{ {
rw::ps2::registerPDSPlugin(); rw::ps2::registerPDSPlugin();
rw::ps2::registerNativeRaster(); rw::ps2::registerNativeRaster();
rw::xbox::registerNativeRaster();
rw::d3d::registerNativeRaster();
rw::registerMeshPlugin(); rw::registerMeshPlugin();
rw::registerNativeDataPlugin(); rw::registerNativeDataPlugin();
rw::registerAtomicRightsPlugin(); rw::registerAtomicRightsPlugin();
@ -36,7 +41,7 @@ attachPlugins(void)
gta::registerExtraNormalsPlugin(); gta::registerExtraNormalsPlugin();
gta::registerExtraVertColorPlugin(); gta::registerExtraVertColorPlugin();
gta::registerEnvSpecPlugin(); gta::registerEnvSpecPlugin();
gta::registerBreakableModelPlugin(); // gta::registerBreakableModelPlugin();
gta::registerCollisionPlugin(); gta::registerCollisionPlugin();
gta::register2dEffectPlugin(); gta::register2dEffectPlugin();
gta::registerPipelinePlugin(); gta::registerPipelinePlugin();

View File

@ -532,6 +532,8 @@ writeTGA(Image *image, const char *filename)
// Raster // Raster
// //
int32 Raster::nativeOffsets[NUM_PLATFORMS];
Raster::Raster(int32 width, int32 height, int32 depth, int32 format, int32 platform) Raster::Raster(int32 width, int32 height, int32 depth, int32 format, int32 platform)
{ {
this->platform = platform ? platform : rw::platform; this->platform = platform ? platform : rw::platform;
@ -543,11 +545,11 @@ Raster::Raster(int32 width, int32 height, int32 depth, int32 format, int32 platf
this->depth = depth; this->depth = depth;
this->texels = this->palette = NULL; this->texels = this->palette = NULL;
this->constructPlugins(); this->constructPlugins();
if(this->platform == PLATFORM_D3D8 ||
this->platform == PLATFORM_D3D9) int32 offset = nativeOffsets[this->platform];
d3d::makeNativeRaster(this); assert(offset != 0 && "unimplemented raster platform");
if(this->platform == PLATFORM_XBOX) NativeRaster *nr = PLUGINOFFSET(NativeRaster, this, offset);
xbox::makeNativeRaster(this); nr->create(this);
} }
Raster::~Raster(void) Raster::~Raster(void)
@ -560,37 +562,28 @@ Raster::~Raster(void)
uint8* uint8*
Raster::lock(int32 level) Raster::lock(int32 level)
{ {
if(this->platform == PLATFORM_D3D8 || int32 offset = nativeOffsets[this->platform];
this->platform == PLATFORM_D3D9) assert(offset != 0 && "unimplemented raster platform");
return d3d::lockRaster(this, level); NativeRaster *nr = PLUGINOFFSET(NativeRaster, this, offset);
if(this->platform == PLATFORM_XBOX) return nr->lock(this, level);
return xbox::lockRaster(this, level);
assert(0 && "unsupported raster platform");
return NULL;
} }
void void
Raster::unlock(int32 level) Raster::unlock(int32 level)
{ {
if(this->platform == PLATFORM_D3D8 || int32 offset = nativeOffsets[this->platform];
this->platform == PLATFORM_D3D9) assert(offset != 0 && "unimplemented raster platform");
d3d::unlockRaster(this, level); NativeRaster *nr = PLUGINOFFSET(NativeRaster, this, offset);
else if(this->platform == PLATFORM_XBOX) nr->unlock(this, level);
xbox::unlockRaster(this, level);
else
assert(0 && "unsupported raster platform");
} }
int32 int32
Raster::getNumLevels(void) Raster::getNumLevels(void)
{ {
if(this->platform == PLATFORM_D3D8 || int32 offset = nativeOffsets[this->platform];
this->platform == PLATFORM_D3D9) assert(offset != 0 && "unimplemented raster platform");
return d3d::getNumLevels(this); NativeRaster *nr = PLUGINOFFSET(NativeRaster, this, offset);
if(this->platform == PLATFORM_XBOX) return nr->getNumLevels(this);
return xbox::getNumLevels(this);
assert(0 && "unsupported raster platform");
return 1;
} }
int32 int32

View File

@ -303,6 +303,7 @@ MeshHeader::allocateIndices(void)
for(uint32 i = 0; i < this->numMeshes; i++){ for(uint32 i = 0; i < this->numMeshes; i++){
mesh->indices = p; mesh->indices = p;
p += mesh->numIndices; p += mesh->numIndices;
mesh++;
} }
} }
@ -597,7 +598,7 @@ getSizeSkin(void *object, int32 offset, int32)
static void static void
skinRights(void *object, int32, int32, uint32) skinRights(void *object, int32, int32, uint32)
{ {
((Atomic*)object)->pipeline = skinGlobals.pipelines[platformIdx[rw::platform]]; ((Atomic*)object)->pipeline = skinGlobals.pipelines[rw::platform];
} }
void void
@ -608,15 +609,15 @@ registerSkinPlugin(void)
defpipe->pluginData = 1; defpipe->pluginData = 1;
for(uint i = 0; i < nelem(matFXGlobals.pipelines); i++) for(uint i = 0; i < nelem(matFXGlobals.pipelines); i++)
skinGlobals.pipelines[i] = defpipe; skinGlobals.pipelines[i] = defpipe;
skinGlobals.pipelines[platformIdx[PLATFORM_PS2]] = skinGlobals.pipelines[PLATFORM_PS2] =
ps2::makeSkinPipeline(); ps2::makeSkinPipeline();
skinGlobals.pipelines[platformIdx[PLATFORM_OGL]] = skinGlobals.pipelines[PLATFORM_OGL] =
gl::makeSkinPipeline(); gl::makeSkinPipeline();
skinGlobals.pipelines[platformIdx[PLATFORM_XBOX]] = skinGlobals.pipelines[PLATFORM_XBOX] =
xbox::makeSkinPipeline(); xbox::makeSkinPipeline();
skinGlobals.pipelines[platformIdx[PLATFORM_D3D8]] = skinGlobals.pipelines[PLATFORM_D3D8] =
d3d8::makeSkinPipeline(); d3d8::makeSkinPipeline();
skinGlobals.pipelines[platformIdx[PLATFORM_D3D9]] = skinGlobals.pipelines[PLATFORM_D3D9] =
d3d9::makeSkinPipeline(); d3d9::makeSkinPipeline();
skinGlobals.offset = Geometry::registerPlugin(sizeof(Skin*), ID_SKIN, skinGlobals.offset = Geometry::registerPlugin(sizeof(Skin*), ID_SKIN,
@ -733,7 +734,7 @@ readAtomicMatFX(Stream *stream, int32, void *object, int32 offset, int32)
*PLUGINOFFSET(int32, object, offset) = flag; *PLUGINOFFSET(int32, object, offset) = flag;
if(flag) if(flag)
((Atomic*)object)->pipeline = ((Atomic*)object)->pipeline =
matFXGlobals.pipelines[platformIdx[rw::platform]]; matFXGlobals.pipelines[rw::platform];
} }
static void static void
@ -1022,15 +1023,15 @@ registerMatFXPlugin(void)
defpipe->pluginData = 0; defpipe->pluginData = 0;
for(uint i = 0; i < nelem(matFXGlobals.pipelines); i++) for(uint i = 0; i < nelem(matFXGlobals.pipelines); i++)
matFXGlobals.pipelines[i] = defpipe; matFXGlobals.pipelines[i] = defpipe;
matFXGlobals.pipelines[platformIdx[PLATFORM_PS2]] = matFXGlobals.pipelines[PLATFORM_PS2] =
ps2::makeMatFXPipeline(); ps2::makeMatFXPipeline();
matFXGlobals.pipelines[platformIdx[PLATFORM_OGL]] = matFXGlobals.pipelines[PLATFORM_OGL] =
gl::makeMatFXPipeline(); gl::makeMatFXPipeline();
matFXGlobals.pipelines[platformIdx[PLATFORM_XBOX]] = matFXGlobals.pipelines[PLATFORM_XBOX] =
xbox::makeMatFXPipeline(); xbox::makeMatFXPipeline();
matFXGlobals.pipelines[platformIdx[PLATFORM_D3D8]] = matFXGlobals.pipelines[PLATFORM_D3D8] =
d3d8::makeMatFXPipeline(); d3d8::makeMatFXPipeline();
matFXGlobals.pipelines[platformIdx[PLATFORM_D3D9]] = matFXGlobals.pipelines[PLATFORM_D3D9] =
d3d9::makeMatFXPipeline(); d3d9::makeMatFXPipeline();
matFXGlobals.atomicOffset = matFXGlobals.atomicOffset =

View File

@ -1114,15 +1114,11 @@ sizedebug(InstanceData *inst)
int32 nativeRasterOffset; int32 nativeRasterOffset;
struct Ps2Raster
{
int32 mipmap;
};
static void* static void*
createNativeRaster(void *object, int32 offset, int32) createNativeRaster(void *object, int32 offset, int32)
{ {
Ps2Raster *raster = PLUGINOFFSET(Ps2Raster, object, offset); Ps2Raster *raster = PLUGINOFFSET(Ps2Raster, object, offset);
new (raster) Ps2Raster;
raster->mipmap = 0xFC0; raster->mipmap = 0xFC0;
return object; return object;
} }
@ -1176,6 +1172,7 @@ registerNativeRaster(void)
createNativeRaster, createNativeRaster,
destroyNativeRaster, destroyNativeRaster,
copyNativeRaster); copyNativeRaster);
Raster::nativeOffsets[PLATFORM_PS2] = nativeRasterOffset;
Texture::registerPlugin(0, ID_SKYMIPMAP, NULL, NULL, NULL); Texture::registerPlugin(0, ID_SKYMIPMAP, NULL, NULL, NULL);
Texture::registerPluginStream(ID_SKYMIPMAP, readMipmap, writeMipmap, getSizeMipmap); Texture::registerPluginStream(ID_SKYMIPMAP, readMipmap, writeMipmap, getSizeMipmap);
} }

View File

@ -12,8 +12,6 @@ using namespace std;
namespace rw { namespace rw {
int platformIdx[10] = { 0, -1, 1, -1, 2, 3, -1, -1, 4, 5 };
int version = 0x36003; int version = 0x36003;
int build = 0xFFFF; int build = 0xFFFF;
#ifdef RW_PS2 #ifdef RW_PS2

View File

@ -105,11 +105,9 @@ enum Platform
// SOFTRAS // SOFTRAS
PLATFORM_D3D8 = 8, PLATFORM_D3D8 = 8,
PLATFORM_D3D9 = 9, PLATFORM_D3D9 = 9,
NUM_PLATFORMS = 6 NUM_PLATFORMS
}; };
extern int platformIdx[10];
enum PluginID enum PluginID
{ {
// Core // Core

View File

@ -70,22 +70,26 @@ uint8 *lockTexture(void *texture, int32 level);
void unlockTexture(void *texture, int32 level); void unlockTexture(void *texture, int32 level);
void deleteObject(void *object); void deleteObject(void *object);
// Native Raster // Native Texture and Raster
void makeNativeRaster(Raster *raster); struct D3dRaster : NativeRaster
uint8 *lockRaster(Raster *raster, int32 level);
void unlockRaster(Raster *raster, int32 level);
int32 getNumLevels(Raster *raster);
int32 getLevelSize(Raster *raster, int32 level);
struct D3dRaster
{ {
void *texture; void *texture;
void *palette; void *palette;
uint32 format; uint32 format;
bool32 hasAlpha; bool32 hasAlpha;
virtual void create(Raster *raster);
virtual uint8 *lock(Raster *raster, int32 level);
virtual void unlock(Raster *raster, int32 level);
virtual int32 getNumLevels(Raster *raster);
}; };
int32 getLevelSize(Raster *raster, int32 level);
void allocateDXT(Raster *raster, int32 dxt, int32 numLevels, bool32 hasAlpha);
void setPalette(Raster *raster, void *palette, int32 size);
void setTexels(Raster *raster, void *texels, int32 level);
extern int32 nativeRasterOffset; extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);

View File

@ -118,6 +118,8 @@ struct Raster : PluginBase<Raster>
uint8 *texels; uint8 *texels;
uint8 *palette; uint8 *palette;
static int32 nativeOffsets[NUM_PLATFORMS];
Raster(int32 width, int32 height, int32 depth, int32 format, int32 platform = 0); Raster(int32 width, int32 height, int32 depth, int32 format, int32 platform = 0);
~Raster(void); ~Raster(void);
@ -146,6 +148,14 @@ struct Raster : PluginBase<Raster>
}; };
}; };
struct NativeRaster
{
virtual void create(Raster *raster) { assert (0 && "unimplemented"); };
virtual uint8 *lock(Raster *raster, int32 level) { assert (0 && "unimplemented"); return NULL; };
virtual void unlock(Raster *raster, int32 level) { assert (0 && "unimplemented"); };
virtual int32 getNumLevels(Raster *raster) { assert (0 && "unimplemented"); return 0; };
};
// TODO: link into texdict // TODO: link into texdict
struct Texture : PluginBase<Texture> struct Texture : PluginBase<Texture>
{ {

View File

@ -116,7 +116,12 @@ void registerADCPlugin(void);
void registerPDSPlugin(void); void registerPDSPlugin(void);
// Raster // Native Texture and Raster
struct Ps2Raster : NativeRaster
{
int32 mipmap;
};
extern int32 nativeRasterOffset; extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);

View File

@ -68,28 +68,119 @@ void registerVertexFormatPlugin(void);
// Native Texture and Raster // Native Texture and Raster
void makeNativeRaster(Raster *raster); struct XboxRaster : NativeRaster
uint8 *lockRaster(Raster *raster, int32 level);
void unlockRaster(Raster *raster, int32 level);
int32 getNumLevels(Raster *raster);
int32 getLevelSize(Raster *raster, int32 level);
Texture *readNativeTexture(Stream *stream);
void writeNativeTexture(Texture *tex, Stream *stream);
uint32 getSizeNativeTexture(Texture *tex);
struct XboxRaster
{ {
void *texture; void *texture;
void *palette; void *palette;
uint32 format; uint32 format;
bool32 hasAlpha; bool32 hasAlpha;
bool32 unknownFlag; bool32 unknownFlag;
// int32 compression;
virtual void create(Raster *raster);
virtual uint8 *lock(Raster *raster, int32 level);
virtual void unlock(Raster *raster, int32 level);
virtual int32 getNumLevels(Raster *raster);
}; };
int32 getLevelSize(Raster *raster, int32 level);
extern int32 nativeRasterOffset; extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);
Texture *readNativeTexture(Stream *stream);
void writeNativeTexture(Texture *tex, Stream *stream);
uint32 getSizeNativeTexture(Texture *tex);
enum {
D3DFMT_UNKNOWN = 0xFFFFFFFF,
/* Swizzled formats */
D3DFMT_A8R8G8B8 = 0x00000006,
D3DFMT_X8R8G8B8 = 0x00000007,
D3DFMT_R5G6B5 = 0x00000005,
D3DFMT_R6G5B5 = 0x00000027,
D3DFMT_X1R5G5B5 = 0x00000003,
D3DFMT_A1R5G5B5 = 0x00000002,
D3DFMT_A4R4G4B4 = 0x00000004,
D3DFMT_A8 = 0x00000019,
D3DFMT_A8B8G8R8 = 0x0000003A,
D3DFMT_B8G8R8A8 = 0x0000003B,
D3DFMT_R4G4B4A4 = 0x00000039,
D3DFMT_R5G5B5A1 = 0x00000038,
D3DFMT_R8G8B8A8 = 0x0000003C,
D3DFMT_R8B8 = 0x00000029,
D3DFMT_G8B8 = 0x00000028,
D3DFMT_P8 = 0x0000000B,
D3DFMT_L8 = 0x00000000,
D3DFMT_A8L8 = 0x0000001A,
D3DFMT_AL8 = 0x00000001,
D3DFMT_L16 = 0x00000032,
D3DFMT_V8U8 = 0x00000028,
D3DFMT_L6V5U5 = 0x00000027,
D3DFMT_X8L8V8U8 = 0x00000007,
D3DFMT_Q8W8V8U8 = 0x0000003A,
D3DFMT_V16U16 = 0x00000033,
D3DFMT_D16_LOCKABLE = 0x0000002C,
D3DFMT_D16 = 0x0000002C,
D3DFMT_D24S8 = 0x0000002A,
D3DFMT_F16 = 0x0000002D,
D3DFMT_F24S8 = 0x0000002B,
/* YUV formats */
D3DFMT_YUY2 = 0x00000024,
D3DFMT_UYVY = 0x00000025,
/* Compressed formats */
D3DFMT_DXT1 = 0x0000000C,
D3DFMT_DXT2 = 0x0000000E,
D3DFMT_DXT3 = 0x0000000E,
D3DFMT_DXT4 = 0x0000000F,
D3DFMT_DXT5 = 0x0000000F,
/* Linear formats */
D3DFMT_LIN_A1R5G5B5 = 0x00000010,
D3DFMT_LIN_A4R4G4B4 = 0x0000001D,
D3DFMT_LIN_A8 = 0x0000001F,
D3DFMT_LIN_A8B8G8R8 = 0x0000003F,
D3DFMT_LIN_A8R8G8B8 = 0x00000012,
D3DFMT_LIN_B8G8R8A8 = 0x00000040,
D3DFMT_LIN_G8B8 = 0x00000017,
D3DFMT_LIN_R4G4B4A4 = 0x0000003E,
D3DFMT_LIN_R5G5B5A1 = 0x0000003D,
D3DFMT_LIN_R5G6B5 = 0x00000011,
D3DFMT_LIN_R6G5B5 = 0x00000037,
D3DFMT_LIN_R8B8 = 0x00000016,
D3DFMT_LIN_R8G8B8A8 = 0x00000041,
D3DFMT_LIN_X1R5G5B5 = 0x0000001C,
D3DFMT_LIN_X8R8G8B8 = 0x0000001E,
D3DFMT_LIN_A8L8 = 0x00000020,
D3DFMT_LIN_AL8 = 0x0000001B,
D3DFMT_LIN_L16 = 0x00000035,
D3DFMT_LIN_L8 = 0x00000013,
D3DFMT_LIN_V16U16 = 0x00000036,
D3DFMT_LIN_V8U8 = 0x00000017,
D3DFMT_LIN_L6V5U5 = 0x00000037,
D3DFMT_LIN_X8L8V8U8 = 0x0000001E,
D3DFMT_LIN_Q8W8V8U8 = 0x00000012,
D3DFMT_LIN_D24S8 = 0x0000002E,
D3DFMT_LIN_F24S8 = 0x0000002F,
D3DFMT_LIN_D16 = 0x00000030,
D3DFMT_LIN_F16 = 0x00000031,
D3DFMT_VERTEXDATA = 100,
D3DFMT_INDEX16 = 101,
};
} }
} }

View File

@ -16,97 +16,6 @@ using namespace std;
namespace rw { namespace rw {
namespace xbox { namespace xbox {
enum {
D3DFMT_UNKNOWN = 0xFFFFFFFF,
/* Swizzled formats */
D3DFMT_A8R8G8B8 = 0x00000006,
D3DFMT_X8R8G8B8 = 0x00000007,
D3DFMT_R5G6B5 = 0x00000005,
D3DFMT_R6G5B5 = 0x00000027,
D3DFMT_X1R5G5B5 = 0x00000003,
D3DFMT_A1R5G5B5 = 0x00000002,
D3DFMT_A4R4G4B4 = 0x00000004,
D3DFMT_A8 = 0x00000019,
D3DFMT_A8B8G8R8 = 0x0000003A,
D3DFMT_B8G8R8A8 = 0x0000003B,
D3DFMT_R4G4B4A4 = 0x00000039,
D3DFMT_R5G5B5A1 = 0x00000038,
D3DFMT_R8G8B8A8 = 0x0000003C,
D3DFMT_R8B8 = 0x00000029,
D3DFMT_G8B8 = 0x00000028,
D3DFMT_P8 = 0x0000000B,
D3DFMT_L8 = 0x00000000,
D3DFMT_A8L8 = 0x0000001A,
D3DFMT_AL8 = 0x00000001,
D3DFMT_L16 = 0x00000032,
D3DFMT_V8U8 = 0x00000028,
D3DFMT_L6V5U5 = 0x00000027,
D3DFMT_X8L8V8U8 = 0x00000007,
D3DFMT_Q8W8V8U8 = 0x0000003A,
D3DFMT_V16U16 = 0x00000033,
D3DFMT_D16_LOCKABLE = 0x0000002C,
D3DFMT_D16 = 0x0000002C,
D3DFMT_D24S8 = 0x0000002A,
D3DFMT_F16 = 0x0000002D,
D3DFMT_F24S8 = 0x0000002B,
/* YUV formats */
D3DFMT_YUY2 = 0x00000024,
D3DFMT_UYVY = 0x00000025,
/* Compressed formats */
D3DFMT_DXT1 = 0x0000000C,
D3DFMT_DXT2 = 0x0000000E,
D3DFMT_DXT3 = 0x0000000E,
D3DFMT_DXT4 = 0x0000000F,
D3DFMT_DXT5 = 0x0000000F,
/* Linear formats */
D3DFMT_LIN_A1R5G5B5 = 0x00000010,
D3DFMT_LIN_A4R4G4B4 = 0x0000001D,
D3DFMT_LIN_A8 = 0x0000001F,
D3DFMT_LIN_A8B8G8R8 = 0x0000003F,
D3DFMT_LIN_A8R8G8B8 = 0x00000012,
D3DFMT_LIN_B8G8R8A8 = 0x00000040,
D3DFMT_LIN_G8B8 = 0x00000017,
D3DFMT_LIN_R4G4B4A4 = 0x0000003E,
D3DFMT_LIN_R5G5B5A1 = 0x0000003D,
D3DFMT_LIN_R5G6B5 = 0x00000011,
D3DFMT_LIN_R6G5B5 = 0x00000037,
D3DFMT_LIN_R8B8 = 0x00000016,
D3DFMT_LIN_R8G8B8A8 = 0x00000041,
D3DFMT_LIN_X1R5G5B5 = 0x0000001C,
D3DFMT_LIN_X8R8G8B8 = 0x0000001E,
D3DFMT_LIN_A8L8 = 0x00000020,
D3DFMT_LIN_AL8 = 0x0000001B,
D3DFMT_LIN_L16 = 0x00000035,
D3DFMT_LIN_L8 = 0x00000013,
D3DFMT_LIN_V16U16 = 0x00000036,
D3DFMT_LIN_V8U8 = 0x00000017,
D3DFMT_LIN_L6V5U5 = 0x00000037,
D3DFMT_LIN_X8L8V8U8 = 0x0000001E,
D3DFMT_LIN_Q8W8V8U8 = 0x00000012,
D3DFMT_LIN_D24S8 = 0x0000002E,
D3DFMT_LIN_F24S8 = 0x0000002F,
D3DFMT_LIN_D16 = 0x00000030,
D3DFMT_LIN_F16 = 0x00000031,
D3DFMT_VERTEXDATA = 100,
D3DFMT_INDEX16 = 101,
};
void* void*
destroyNativeData(void *object, int32, int32) destroyNativeData(void *object, int32, int32)
{ {
@ -716,6 +625,8 @@ registerVertexFormatPlugin(void)
// Native Texture and Raster // Native Texture and Raster
int32 nativeRasterOffset;
static uint32 static uint32
calculateTextureSize(uint32 width, uint32 height, uint32 depth, uint32 format) calculateTextureSize(uint32 width, uint32 height, uint32 depth, uint32 format)
{ {
@ -799,10 +710,7 @@ calculateTextureSize(uint32 width, uint32 height, uint32 depth, uint32 format)
} }
} }
static void*
int32 nativeRasterOffset;
void*
createTexture(int32 width, int32 height, int32 numlevels, uint32 format) createTexture(int32 width, int32 height, int32 numlevels, uint32 format)
{ {
int32 w = width; int32 w = width;
@ -838,7 +746,7 @@ createTexture(int32 width, int32 height, int32 numlevels, uint32 format)
} }
void void
makeNativeRaster(Raster *raster) XboxRaster::create(Raster *raster)
{ {
static uint32 formatMap[] = { static uint32 formatMap[] = {
D3DFMT_UNKNOWN, D3DFMT_UNKNOWN,
@ -870,41 +778,38 @@ makeNativeRaster(Raster *raster)
0, 0,
0, 0, 0, 0, 0 0, 0, 0, 0, 0
}; };
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset);
if(raster->flags & 0x80) if(raster->flags & 0x80)
return; return;
uint32 format; uint32 format;
if(raster->format & (Raster::PAL4 | Raster::PAL8)){ if(raster->format & (Raster::PAL4 | Raster::PAL8)){
format = D3DFMT_P8; format = D3DFMT_P8;
ras->palette = new uint8[4*256]; this->palette = new uint8[4*256];
}else }else
format = formatMap[(raster->format >> 8) & 0xF]; format = formatMap[(raster->format >> 8) & 0xF];
ras->format = 0; this->format = 0;
ras->hasAlpha = alphaMap[(raster->format >> 8) & 0xF]; this->hasAlpha = alphaMap[(raster->format >> 8) & 0xF];
int32 levels = Raster::calculateNumLevels(raster->width, raster->height); int32 levels = Raster::calculateNumLevels(raster->width, raster->height);
ras->texture = createTexture(raster->width, raster->width, this->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? levels : 1, raster->format & Raster::MIPMAP ? levels : 1,
format); format);
} }
uint8* uint8*
lockRaster(Raster *raster, int32 level) XboxRaster::lock(Raster *raster, int32 level)
{ {
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); RasterLevels *levels = (RasterLevels*)this->texture;
RasterLevels *levels = (RasterLevels*)ras->texture;
return levels->levels[level].data; return levels->levels[level].data;
} }
void void
unlockRaster(Raster *raster, int32 level) XboxRaster::unlock(Raster *raster, int32 level)
{ {
} }
int32 int32
getNumLevels(Raster *raster) XboxRaster::getNumLevels(Raster *raster)
{ {
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); RasterLevels *levels = (RasterLevels*)this->texture;
RasterLevels *levels = (RasterLevels*)ras->texture;
return levels->numlevels; return levels->numlevels;
} }
@ -916,6 +821,49 @@ getLevelSize(Raster *raster, int32 level)
return levels->levels[level].size; return levels->levels[level].size;
} }
static void*
createNativeRaster(void *object, int32 offset, int32)
{
XboxRaster *raster = PLUGINOFFSET(XboxRaster, object, offset);
new (raster) XboxRaster;
raster->texture = NULL;
raster->palette = NULL;
raster->format = 0;
raster->hasAlpha = 0;
raster->unknownFlag = 0;
return object;
}
static void*
destroyNativeRaster(void *object, int32 offset, int32)
{
// TODO:
return object;
}
static void*
copyNativeRaster(void *dst, void *, int32 offset, int32)
{
XboxRaster *raster = PLUGINOFFSET(XboxRaster, dst, offset);
raster->texture = NULL;
raster->palette = NULL;
raster->format = 0;
raster->hasAlpha = 0;
raster->unknownFlag = 0;
return dst;
}
void
registerNativeRaster(void)
{
nativeRasterOffset = Raster::registerPlugin(sizeof(XboxRaster),
0x12340000 | PLATFORM_XBOX,
createNativeRaster,
destroyNativeRaster,
copyNativeRaster);
Raster::nativeOffsets[PLATFORM_XBOX] = nativeRasterOffset;
}
Texture* Texture*
readNativeTexture(Stream *stream) readNativeTexture(Stream *stream)
{ {
@ -949,7 +897,7 @@ readNativeTexture(Stream *stream)
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset);
ras->format = compression; ras->format = compression;
ras->hasAlpha = hasAlpha; ras->hasAlpha = hasAlpha;
ras->texture = createTexture(raster->width, raster->width, ras->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? numLevels : 1, raster->format & Raster::MIPMAP ? numLevels : 1,
ras->format); ras->format);
raster->flags &= ~0x80; raster->flags &= ~0x80;
@ -1035,49 +983,5 @@ getSizeNativeTexture(Texture *tex)
return size; return size;
} }
static void*
createNativeRaster(void *object, int32 offset, int32)
{
XboxRaster *raster = PLUGINOFFSET(XboxRaster, object, offset);
raster->texture = NULL;
raster->palette = NULL;
raster->format = 0;
raster->hasAlpha = 0;
raster->unknownFlag = 0;
// raster->compression = 0;
return object;
}
static void*
destroyNativeRaster(void *object, int32 offset, int32)
{
// TODO:
return object;
}
static void*
copyNativeRaster(void *dst, void *, int32 offset, int32)
{
XboxRaster *raster = PLUGINOFFSET(XboxRaster, dst, offset);
raster->texture = NULL;
raster->palette = NULL;
raster->format = 0;
raster->hasAlpha = 0;
raster->unknownFlag = 0;
// raster->compression = 0;
return dst;
}
void
registerNativeRaster(void)
{
nativeRasterOffset = Raster::registerPlugin(sizeof(XboxRaster),
0x12340000 | PLATFORM_XBOX,
createNativeRaster,
destroyNativeRaster,
copyNativeRaster);
}
} }
} }

View File

@ -15,10 +15,10 @@ main(int argc, char *argv[])
{ {
gta::attachPlugins(); gta::attachPlugins();
// rw::version = 0x33002; rw::version = 0x34003;
rw::platform = rw::PLATFORM_PS2; // rw::platform = rw::PLATFORM_PS2;
// rw::platform = rw::PLATFORM_OGL; // rw::platform = rw::PLATFORM_OGL;
// rw::platform = rw::PLATFORM_XBOX; rw::platform = rw::PLATFORM_XBOX;
// rw::platform = rw::PLATFORM_D3D8; // rw::platform = rw::PLATFORM_D3D8;
// rw::platform = rw::PLATFORM_D3D9; // rw::platform = rw::PLATFORM_D3D9;
@ -32,7 +32,7 @@ main(int argc, char *argv[])
if(strcmp(argv[arg], "-u") == 0){ if(strcmp(argv[arg], "-u") == 0){
uninstance++; uninstance++;
arg++; arg++;
if(argc < 3){ if(argc < 3){
printf("usage: %s [-u] in.dff\n", argv[0]); printf("usage: %s [-u] in.dff\n", argv[0]);
return 0; return 0;
@ -82,6 +82,9 @@ main(int argc, char *argv[])
p->instance(a); p->instance(a);
} }
if(uninstance)
rw::platform = rw::PLATFORM_D3D8;
data = new rw::uint8[1024*1024]; data = new rw::uint8[1024*1024];
rw::StreamMemory out; rw::StreamMemory out;
out.open(data, 0, 1024*1024); out.open(data, 0, 1024*1024);
@ -89,7 +92,11 @@ main(int argc, char *argv[])
currentUVAnimDictionary->streamWrite(&out); currentUVAnimDictionary->streamWrite(&out);
c->streamWrite(&out); c->streamWrite(&out);
FILE *cf = fopen("out.dff", "wb"); FILE *cf;
if(arg+1 < argc)
cf = fopen(argv[arg+1], "wb");
else
cf = fopen("out.dff", "wb");
assert(cf != NULL); assert(cf != NULL);
fwrite(data, out.getLength(), 1, cf); fwrite(data, out.getLength(), 1, cf);
fclose(cf); fclose(cf);

View File

@ -81,11 +81,15 @@
<Optimization>Disabled</Optimization> <Optimization>Disabled</Optimization>
<SDLCheck>true</SDLCheck> <SDLCheck>true</SDLCheck>
<PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions> <PreprocessorDefinitions>_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
</ClCompile> </ClCompile>
<Link> <Link>
<GenerateDebugInformation>true</GenerateDebugInformation> <GenerateDebugInformation>true</GenerateDebugInformation>
<AdditionalDependencies>librw.lib;%(AdditionalDependencies)</AdditionalDependencies> <AdditionalDependencies>librw.lib;%(AdditionalDependencies)</AdditionalDependencies>
</Link> </Link>
<PostBuildEvent>
<Command>copy /y "$(TargetPath)" "C:\Users\aap\bin\"</Command>
</PostBuildEvent>
</ItemDefinitionGroup> </ItemDefinitionGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<ClCompile> <ClCompile>

View File

@ -10,15 +10,67 @@
using namespace std; using namespace std;
using namespace rw; using namespace rw;
Raster*
xboxToD3d8(Raster *raster)
{
using namespace xbox;
Raster *newras;
if(raster->platform != PLATFORM_XBOX)
return raster;
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset);
int32 numLevels = raster->getNumLevels();
int32 format = raster->format;
// format &= ~Raster::MIPMAP;
if(ras->format){
newras = new Raster(raster->width, raster->height, raster->depth,
format | raster->type | 0x80, PLATFORM_D3D8);
int32 dxt = 0;
switch(ras->format){
case D3DFMT_DXT1:
dxt = 1;
break;
case D3DFMT_DXT3:
dxt = 3;
break;
case D3DFMT_DXT5:
dxt = 5;
break;
}
d3d::allocateDXT(newras, dxt, numLevels, ras->hasAlpha);
}else{
printf("swizzled!\n");
newras = new Raster(raster->width, raster->height, raster->depth,
format | raster->type, PLATFORM_D3D8);
}
if(raster->format & Raster::PAL4)
d3d::setPalette(newras, ras->palette, 32);
else if(raster->format & Raster::PAL8)
d3d::setPalette(newras, ras->palette, 256);
uint8 *data;
for(int32 i = 0; i < numLevels; i++){
if(i >= newras->getNumLevels())
break;
data = raster->lock(i);
d3d::setTexels(newras, data, i);
raster->unlock(i);
}
delete raster;
return newras;
}
int int
main(int argc, char *argv[]) main(int argc, char *argv[])
{ {
gta::attachPlugins(); gta::attachPlugins();
rw::ps2::registerNativeRaster();
rw::xbox::registerNativeRaster();
rw::d3d::registerNativeRaster();
// rw::version = 0x33002; // rw::version = 0x33002;
rw::version = 0x32000;
// rw::platform = rw::PLATFORM_PS2; // rw::platform = rw::PLATFORM_PS2;
// rw::platform = rw::PLATFORM_OGL; // rw::platform = rw::PLATFORM_OGL;
// rw::platform = rw::PLATFORM_XBOX; // rw::platform = rw::PLATFORM_XBOX;
@ -32,7 +84,7 @@ main(int argc, char *argv[])
rw::StreamFile in; rw::StreamFile in;
if(in.open(argv[1], "rb") == NULL){ if(in.open(argv[1], "rb") == NULL){
printf("couldn't open file\n"); printf("couldn't open file %s\n", argv[1]);
return 1; return 1;
} }
rw::findChunk(&in, rw::ID_TEXDICTIONARY, NULL, NULL); rw::findChunk(&in, rw::ID_TEXDICTIONARY, NULL, NULL);
@ -42,8 +94,16 @@ main(int argc, char *argv[])
in.close(); in.close();
rw::currentTexDictionary = txd; rw::currentTexDictionary = txd;
// for(Texture *tex = txd->first; tex; tex = tex->next)
// tex->raster = xboxToD3d8(tex->raster);
for(Texture *tex = txd->first; tex; tex = tex->next)
tex->filterAddressing = (tex->filterAddressing&~0xF) | 0x2;
rw::StreamFile out; rw::StreamFile out;
out.open("out.txd", "wb"); if(argc > 2)
out.open(argv[2], "wb");
else
out.open("out.txd", "wb");
txd->streamWrite(&out); txd->streamWrite(&out);
out.close(); out.close();