Port PSP2/Vita backend to modern librw

This commit is contained in:
Dima353
2026-07-26 13:33:19 +03:00
parent 7d73222f14
commit 008049b8bd
95 changed files with 9889 additions and 2113 deletions
+1 -1
View File
@@ -11,7 +11,7 @@ CC = $(PREFIX)-gcc
CXX = $(PREFIX)-g++ CXX = $(PREFIX)-g++
AR = $(PREFIX)-gcc-ar AR = $(PREFIX)-gcc-ar
CFLAGS = -g -Wl,-q,--no-enum-size-warning -fno-short-enums -fno-optimize-sibling-calls -O3 -fsingle-precision-constant -mfloat-abi=hard -ffast-math \ CFLAGS = -g -Wl,-q,--no-enum-size-warning -fno-short-enums -fno-optimize-sibling-calls -O3 -fsingle-precision-constant -mfloat-abi=hard -ffast-math \
-DPSP2 -DNDEBUG -DRW_GL3 -DLIBRW_GLAD -DPSP2_USE_SHADER_COMPILER -Dmemcpy_neon=sceClibMemcpy -DPSP2 -DRW_GL3 -DLIBRW_GLAD -DPSP2_USE_SHADER_COMPILER -Dmemcpy_neon=sceClibMemcpy
CXXFLAGS = $(CFLAGS) CXXFLAGS = $(CFLAGS)
ASFLAGS = $(CFLAGS) ASFLAGS = $(CFLAGS)
+8 -17
View File
@@ -19,12 +19,6 @@
#include "rwobjects.h" #include "rwobjects.h"
#include "rwengine.h" #include "rwengine.h"
#include <vitasdk.h>
#include <vitaGL.h>
extern "C"{
#include <math_neon.h>
};
namespace rw { namespace rw {
#define PLUGIN_ID 0 #define PLUGIN_ID 0
@@ -194,9 +188,6 @@ V3d::transformVectors(V3d *out, const V3d *in, int32 n, const Matrix *m)
void void
RawMatrix::mult(RawMatrix *dst, RawMatrix *src1, RawMatrix *src2) RawMatrix::mult(RawMatrix *dst, RawMatrix *src1, RawMatrix *src2)
{ {
#ifdef PSP2
matmul4_neon((float*)&src1->right.x, (float*)&src2->right.x, (float*)&dst->right.x);
#else
dst->right.x = src1->right.x*src2->right.x + src1->right.y*src2->up.x + src1->right.z*src2->at.x + src1->rightw*src2->pos.x; dst->right.x = src1->right.x*src2->right.x + src1->right.y*src2->up.x + src1->right.z*src2->at.x + src1->rightw*src2->pos.x;
dst->right.y = src1->right.x*src2->right.y + src1->right.y*src2->up.y + src1->right.z*src2->at.y + src1->rightw*src2->pos.y; dst->right.y = src1->right.x*src2->right.y + src1->right.y*src2->up.y + src1->right.z*src2->at.y + src1->rightw*src2->pos.y;
dst->right.z = src1->right.x*src2->right.z + src1->right.y*src2->up.z + src1->right.z*src2->at.z + src1->rightw*src2->pos.z; dst->right.z = src1->right.x*src2->right.z + src1->right.y*src2->up.z + src1->right.z*src2->at.z + src1->rightw*src2->pos.z;
@@ -213,7 +204,6 @@ RawMatrix::mult(RawMatrix *dst, RawMatrix *src1, RawMatrix *src2)
dst->pos.y = src1->pos.x*src2->right.y + src1->pos.y*src2->up.y + src1->pos.z*src2->at.y + src1->posw*src2->pos.y; dst->pos.y = src1->pos.x*src2->right.y + src1->pos.y*src2->up.y + src1->pos.z*src2->at.y + src1->posw*src2->pos.y;
dst->pos.z = src1->pos.x*src2->right.z + src1->pos.y*src2->up.z + src1->pos.z*src2->at.z + src1->posw*src2->pos.z; dst->pos.z = src1->pos.x*src2->right.z + src1->pos.y*src2->up.z + src1->pos.z*src2->at.z + src1->posw*src2->pos.z;
dst->posw = src1->pos.x*src2->rightw + src1->pos.y*src2->upw + src1->pos.z*src2->atw + src1->posw*src2->posw; dst->posw = src1->pos.x*src2->rightw + src1->pos.y*src2->upw + src1->pos.z*src2->atw + src1->posw*src2->posw;
#endif
} }
void void
@@ -675,7 +665,7 @@ correctPathCase(char *filename)
sofar[2] = '\0'; sofar[2] = '\0';
arg++; arg++;
} }
while(dir = strtok(arg, PSEP_S)){ while((dir = strtok(arg, PSEP_S))){
arg = nil; arg = nil;
if(direct = opendir(sofar), dir == nil) if(direct = opendir(sofar), dir == nil)
return; return;
@@ -769,8 +759,8 @@ Stream::write32(const void *data, uint32 length)
int32 n, len; int32 n, len;
for(len = length >>= 2; len > 0; len -= 256){ for(len = length >>= 2; len > 0; len -= 256){
n = len < 256 ? len : 256; n = len < 256 ? len : 256;
memcpy_neon(buf, src, n*4); memcpy(buf, src, n*4);
memLittle16(buf, n*4); memLittle32(buf, n*4);
write8(buf, n*4); write8(buf, n*4);
src += n*4; src += n*4;
} }
@@ -789,7 +779,7 @@ Stream::write16(const void *data, uint32 length)
int32 n, len; int32 n, len;
for(len = length >>= 1; len > 0; len -= 256){ for(len = length >>= 1; len > 0; len -= 256){
n = len < 256 ? len : 256; n = len < 256 ? len : 256;
memcpy_neon(buf, src, n*2); memcpy(buf, src, n*2);
memLittle16(buf, n*2); memLittle16(buf, n*2);
write8(buf, n*2); write8(buf, n*2);
src += n*2; src += n*2;
@@ -934,7 +924,7 @@ StreamMemory::write8(const void *data, uint32 len)
l = this->capacity-this->position; l = this->capacity-this->position;
this->length = this->position+l; this->length = this->position+l;
} }
memcpy_neon(&this->data[this->position], data, l); memcpy(&this->data[this->position], data, l);
this->position += l; this->position += l;
if(len != l) if(len != l)
this->position = S_EOF; this->position = S_EOF;
@@ -949,7 +939,7 @@ StreamMemory::read8(void *data, uint32 len)
uint32 l = len; uint32 l = len;
if(this->position+l > this->length) if(this->position+l > this->length)
l = this->length-this->position; l = this->length-this->position;
memcpy_neon(data, &this->data[this->position], l); memcpy(data, &this->data[this->position], l);
this->position += l; this->position += l;
if(len != l) if(len != l)
this->position = S_EOF; this->position = S_EOF;
@@ -1117,7 +1107,8 @@ uint8*
getFileContents(const char *name, uint32 *len) getFileContents(const char *name, uint32 *len)
{ {
FILE *cf = fopen(name, "rb"); FILE *cf = fopen(name, "rb");
assert(cf != nil); if(cf == nil)
return nil;
fseek(cf, 0, SEEK_END); fseek(cf, 0, SEEK_END);
*len = ftell(cf); *len = ftell(cf);
fseek(cf, 0, SEEK_SET); fseek(cf, 0, SEEK_SET);
+3 -1
View File
@@ -19,4 +19,6 @@ ECODE(ERR_ENGINESTART,
ECODE(ERR_INVRASTER, ECODE(ERR_INVRASTER,
"Invalid raster format"), "Invalid raster format"),
ECODE(ERR_NOTEXTURE, ECODE(ERR_NOTEXTURE,
"Could not create texture") "Could not create texture"),
ECODE(ERR_FORMAT_UNSUPPORTED,
"Unsupported raster format")
+1 -1
View File
@@ -247,7 +247,7 @@ writeBMP(Image *image, const char *filename)
for(int x = 0; x < image->width; x++){ for(int x = 0; x < image->width; x++){
switch(image->depth){ switch(image->depth){
case 4: case 4:
file.writeU8((p[0]&0xF)<<4 | p[1]&0xF); file.writeU8((p[0]&0xF)<<4 | (p[1]&0xF));
p += 2; p += 2;
x++; x++;
break; break;
+8
View File
@@ -128,8 +128,16 @@ Charset::flushBuffer(void)
rw::SetRenderState(rw::TEXTUREADDRESS, rw::Texture::WRAP); rw::SetRenderState(rw::TEXTUREADDRESS, rw::Texture::WRAP);
rw::SetRenderState(rw::TEXTUREFILTER, rw::Texture::NEAREST); rw::SetRenderState(rw::TEXTUREFILTER, rw::Texture::NEAREST);
uint32 cull = rw::GetRenderState(rw::CULLMODE);
uint32 ztest = rw::GetRenderState(rw::ZTESTENABLE);
rw::SetRenderState(rw::CULLMODE, rw::CULLNONE);
rw::SetRenderState(rw::ZTESTENABLE, 0);
im2d::RenderIndexedPrimitive(rw::PRIMTYPETRILIST, im2d::RenderIndexedPrimitive(rw::PRIMTYPETRILIST,
vertices, numChars*4, indices, numChars*6); vertices, numChars*4, indices, numChars*6);
rw::SetRenderState(rw::CULLMODE, cull);
rw::SetRenderState(rw::ZTESTENABLE, ztest);
} }
numChars = 0; numChars = 0;
+144 -165
View File
@@ -18,106 +18,7 @@
namespace rw { namespace rw {
namespace d3d { namespace d3d {
bool32 isP8supported = 1; bool32 isP8supported = 1; // set to 0 when actual d3d device is used
#ifndef RW_D3D9
#define MAKEFOURCC(ch0, ch1, ch2, ch3) \
((uint32)(uint8)(ch0) | ((uint32)(uint8)(ch1) << 8) | \
((uint32)(uint8)(ch2) << 16) | ((uint32)(uint8)(ch3) << 24 ))
enum {
D3DFMT_UNKNOWN = 0,
D3DFMT_R8G8B8 = 20,
D3DFMT_A8R8G8B8 = 21,
D3DFMT_X8R8G8B8 = 22,
D3DFMT_R5G6B5 = 23,
D3DFMT_X1R5G5B5 = 24,
D3DFMT_A1R5G5B5 = 25,
D3DFMT_A4R4G4B4 = 26,
D3DFMT_R3G3B2 = 27,
D3DFMT_A8 = 28,
D3DFMT_A8R3G3B2 = 29,
D3DFMT_X4R4G4B4 = 30,
D3DFMT_A2B10G10R10 = 31,
D3DFMT_A8B8G8R8 = 32,
D3DFMT_X8B8G8R8 = 33,
D3DFMT_G16R16 = 34,
D3DFMT_A2R10G10B10 = 35,
D3DFMT_A16B16G16R16 = 36,
D3DFMT_A8P8 = 40,
D3DFMT_P8 = 41,
D3DFMT_L8 = 50,
D3DFMT_A8L8 = 51,
D3DFMT_A4L4 = 52,
D3DFMT_V8U8 = 60,
D3DFMT_L6V5U5 = 61,
D3DFMT_X8L8V8U8 = 62,
D3DFMT_Q8W8V8U8 = 63,
D3DFMT_V16U16 = 64,
D3DFMT_A2W10V10U10 = 67,
D3DFMT_UYVY = MAKEFOURCC('U', 'Y', 'V', 'Y'),
D3DFMT_R8G8_B8G8 = MAKEFOURCC('R', 'G', 'B', 'G'),
D3DFMT_YUY2 = MAKEFOURCC('Y', 'U', 'Y', '2'),
D3DFMT_G8R8_G8B8 = MAKEFOURCC('G', 'R', 'G', 'B'),
D3DFMT_DXT1 = MAKEFOURCC('D', 'X', 'T', '1'),
D3DFMT_DXT2 = MAKEFOURCC('D', 'X', 'T', '2'),
D3DFMT_DXT3 = MAKEFOURCC('D', 'X', 'T', '3'),
D3DFMT_DXT4 = MAKEFOURCC('D', 'X', 'T', '4'),
D3DFMT_DXT5 = MAKEFOURCC('D', 'X', 'T', '5'),
D3DFMT_D16_LOCKABLE = 70,
D3DFMT_D32 = 71,
D3DFMT_D15S1 = 73,
D3DFMT_D24S8 = 75,
D3DFMT_D24X8 = 77,
D3DFMT_D24X4S4 = 79,
D3DFMT_D16 = 80,
D3DFMT_D32F_LOCKABLE = 82,
D3DFMT_D24FS8 = 83,
// d3d9ex only
/* Z-Stencil formats valid for CPU access */
D3DFMT_D32_LOCKABLE = 84,
D3DFMT_S8_LOCKABLE = 85,
D3DFMT_L16 = 81,
D3DFMT_VERTEXDATA =100,
D3DFMT_INDEX16 =101,
D3DFMT_INDEX32 =102,
D3DFMT_Q16W16V16U16 =110,
D3DFMT_MULTI2_ARGB8 = MAKEFOURCC('M','E','T','1'),
// Floating point surface formats
// s10e5 formats (16-bits per channel)
D3DFMT_R16F = 111,
D3DFMT_G16R16F = 112,
D3DFMT_A16B16G16R16F = 113,
// IEEE s23e8 formats (32-bits per channel)
D3DFMT_R32F = 114,
D3DFMT_G32R32F = 115,
D3DFMT_A32B32G32R32F = 116,
D3DFMT_CxV8U8 = 117,
// d3d9ex only
// Monochrome 1 bit per pixel format
D3DFMT_A1 = 118,
// 2.8 biased fixed point
D3DFMT_A2B10G10R10_XR_BIAS = 119,
// Binary format indicating that the data has no inherent type
D3DFMT_BINARYBUFFER = 199
};
#endif
// stolen from d3d8to9 // stolen from d3d8to9
static uint32 static uint32
@@ -306,11 +207,11 @@ unlockVertices(void *vertexBuffer)
} }
void* void*
createTexture(int32 width, int32 height, int32 numlevels, uint32 format) createTexture(int32 width, int32 height, int32 numlevels, uint32 usage, uint32 format)
{ {
#ifdef RW_D3D9 #ifdef RW_D3D9
IDirect3DTexture9 *tex; IDirect3DTexture9 *tex;
d3ddevice->CreateTexture(width, height, numlevels, 0, d3ddevice->CreateTexture(width, height, numlevels, usage,
(D3DFORMAT)format, D3DPOOL_MANAGED, &tex, nil); (D3DFORMAT)format, D3DPOOL_MANAGED, &tex, nil);
if(tex) if(tex)
d3d9Globals.numTextures++; d3d9Globals.numTextures++;
@@ -377,7 +278,7 @@ struct RasterFormatInfo
// indexed directly by RW format // indexed directly by RW format
static RasterFormatInfo formatInfoRW[16] = { static RasterFormatInfo formatInfoRW[16] = {
{ 0, 0, 0}, { 0, 0, 0, 0},
{ D3DFMT_A1R5G5B5, 16, 1, Raster::C1555 }, { D3DFMT_A1R5G5B5, 16, 1, Raster::C1555 },
{ D3DFMT_R5G6B5, 16, 0, Raster::C565 }, { D3DFMT_R5G6B5, 16, 0, Raster::C565 },
{ D3DFMT_A4R4G4B4, 16, 1, Raster::C4444 }, { D3DFMT_A4R4G4B4, 16, 1, Raster::C4444 },
@@ -444,7 +345,7 @@ findFormatInfoD3D(uint32 d3dformat)
{ {
static RasterFormatInfo fake = { 0, 0, 0, 0 }; static RasterFormatInfo fake = { 0, 0, 0, 0 };
int i; int i;
for(i = 0; i < nelem(formatInfoFull); i++) for(i = 0; i < (int)nelem(formatInfoFull); i++)
if(formatInfoFull[i].d3dformat == d3dformat) if(formatInfoFull[i].d3dformat == d3dformat)
return &formatInfoFull[i]; return &formatInfoFull[i];
return &fake; return &fake;
@@ -492,7 +393,7 @@ rasterSetFormat(Raster *raster)
} }
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
if(raster->format & (Raster::PAL4 | Raster::PAL8)){ if(raster->format & (Raster::PAL4 | Raster::PAL8)){
// TODO: do we even allow PAL4? // TODO: do we even allow PAL4?
natras->format = D3DFMT_P8; natras->format = D3DFMT_P8;
@@ -505,25 +406,28 @@ rasterSetFormat(Raster *raster)
natras->hasAlpha = formatInfoRW[(raster->format >> 8) & 0xF].hasAlpha; natras->hasAlpha = formatInfoRW[(raster->format >> 8) & 0xF].hasAlpha;
raster->stride = raster->width*natras->bpp; raster->stride = raster->width*natras->bpp;
raster->pixels = nil; natras->autogenMipmap = (raster->format & (Raster::MIPMAP|Raster::AUTOMIPMAP)) == (Raster::MIPMAP|Raster::AUTOMIPMAP);
raster->originalWidth = raster->width;
raster->originalHeight = raster->height;
raster->originalStride = raster->stride;
raster->originalPixels = raster->pixels;
} }
static Raster* static Raster*
rasterCreateTexture(Raster *raster) rasterCreateTexture(Raster *raster)
{ {
int32 levels; int32 levels;
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
if(natras->format == D3DFMT_P8) if(natras->format == D3DFMT_P8)
natras->palette = (uint8*)rwNew(4*256, MEMDUR_EVENT | ID_DRIVER); natras->palette = (uint8*)rwNew(4*256, MEMDUR_EVENT | ID_DRIVER);
if(natras->autogenMipmap)
levels = 0;
else if(raster->format & Raster::MIPMAP)
levels = Raster::calculateNumLevels(raster->width, raster->height); levels = Raster::calculateNumLevels(raster->width, raster->height);
else
levels = 1;
assert(natras->texture == nil); assert(natras->texture == nil);
natras->texture = createTexture(raster->width, raster->height, natras->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? levels : 1, levels,
natras->autogenMipmap ? D3DUSAGE_AUTOGENMIPMAP : 0,
natras->format); natras->format);
if(natras->texture == nil){ if(natras->texture == nil){
RWERROR((ERR_NOTEXTURE)); RWERROR((ERR_NOTEXTURE));
@@ -543,13 +447,18 @@ rasterCreateCameraTexture(Raster *raster)
} }
int32 levels; int32 levels;
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
if(natras->autogenMipmap)
levels = 0;
else if(raster->format & Raster::MIPMAP)
levels = Raster::calculateNumLevels(raster->width, raster->height); levels = Raster::calculateNumLevels(raster->width, raster->height);
else
levels = 1;
IDirect3DTexture9 *tex; IDirect3DTexture9 *tex;
d3ddevice->CreateTexture(raster->width, raster->height, d3ddevice->CreateTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? levels : 1, levels,
D3DUSAGE_RENDERTARGET, (natras->autogenMipmap ? D3DUSAGE_AUTOGENMIPMAP : 0) | D3DUSAGE_RENDERTARGET,
(D3DFORMAT)natras->format, D3DPOOL_DEFAULT, &tex, nil); (D3DFORMAT)natras->format, D3DPOOL_DEFAULT, &tex, nil);
assert(natras->texture == nil); assert(natras->texture == nil);
natras->texture = tex; natras->texture = tex;
@@ -565,11 +474,9 @@ rasterCreateCameraTexture(Raster *raster)
static Raster* static Raster*
rasterCreateCamera(Raster *raster) rasterCreateCamera(Raster *raster)
{ {
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
raster->originalWidth = raster->width;
raster->originalHeight = raster->height; natras->autogenMipmap = 0;
raster->originalStride = raster->stride = 0;
raster->originalPixels = raster->pixels = nil;
natras->format = d3d9Globals.present.BackBufferFormat; natras->format = d3d9Globals.present.BackBufferFormat;
raster->depth = findFormatDepth(natras->format); raster->depth = findFormatDepth(natras->format);
@@ -581,11 +488,9 @@ rasterCreateCamera(Raster *raster)
static Raster* static Raster*
rasterCreateZbuffer(Raster *raster) rasterCreateZbuffer(Raster *raster)
{ {
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
raster->originalWidth = raster->width;
raster->originalHeight = raster->height; natras->autogenMipmap = 0;
raster->originalStride = raster->stride = 0;
raster->originalPixels = raster->pixels = nil;
// TODO: allow other formats // TODO: allow other formats
natras->format = d3d9Globals.present.AutoDepthStencilFormat; natras->format = d3d9Globals.present.AutoDepthStencilFormat;
@@ -617,39 +522,53 @@ rasterCreateZbuffer(Raster *raster)
Raster* Raster*
rasterCreate(Raster *raster) rasterCreate(Raster *raster)
{ {
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
rasterSetFormat(raster); rasterSetFormat(raster);
Raster *ret = raster;
if(raster->width == 0 || raster->height == 0){ if(raster->width == 0 || raster->height == 0){
raster->flags |= Raster::DONTALLOCATE; raster->flags |= Raster::DONTALLOCATE;
raster->stride = 0; raster->stride = 0;
return raster; goto ret;
} }
if(raster->flags & Raster::DONTALLOCATE) if(raster->flags & Raster::DONTALLOCATE)
return raster; goto ret;
switch(raster->type){ switch(raster->type){
case Raster::NORMAL: case Raster::NORMAL:
case Raster::TEXTURE: case Raster::TEXTURE:
return rasterCreateTexture(raster); ret = rasterCreateTexture(raster);
break;
#ifdef RW_D3D9 #ifdef RW_D3D9
case Raster::CAMERATEXTURE: case Raster::CAMERATEXTURE:
return rasterCreateCameraTexture(raster); ret = rasterCreateCameraTexture(raster);
break;
case Raster::ZBUFFER: case Raster::ZBUFFER:
return rasterCreateZbuffer(raster); ret = rasterCreateZbuffer(raster);
break;
case Raster::CAMERA: case Raster::CAMERA:
return rasterCreateCamera(raster); ret = rasterCreateCamera(raster);
break;
#endif #endif
}
default:
RWERROR((ERR_INVRASTER));
return nil; return nil;
}
ret:
raster->originalWidth = raster->width;
raster->originalHeight = raster->height;
raster->originalStride = raster->stride;
raster->originalPixels = raster->pixels;
return ret;
} }
uint8* uint8*
rasterLock(Raster *raster, int32 level, int32 lockMode) rasterLock(Raster *raster, int32 level, int32 lockMode)
{ {
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
// check if already locked // check if already locked
if(raster->privateFlags & (Raster::PRIVATELOCK_READ|Raster::PRIVATELOCK_WRITE)) if(raster->privateFlags & (Raster::PRIVATELOCK_READ|Raster::PRIVATELOCK_WRITE))
@@ -660,7 +579,7 @@ rasterLock(Raster *raster, int32 level, int32 lockMode)
if(lockMode & Raster::LOCKREAD) if(lockMode & Raster::LOCKREAD)
flags |= D3DLOCK_READONLY | D3DLOCK_NO_DIRTY_UPDATE; flags |= D3DLOCK_READONLY | D3DLOCK_NO_DIRTY_UPDATE;
IDirect3DTexture9 *tex = (IDirect3DTexture9*)natras->texture; IDirect3DTexture9 *tex = (IDirect3DTexture9*)natras->texture;
IDirect3DSurface9 *surf; IDirect3DSurface9 *surf, *rt;
D3DLOCKED_RECT lr; D3DLOCKED_RECT lr;
switch(raster->type){ switch(raster->type){
@@ -668,7 +587,28 @@ rasterLock(Raster *raster, int32 level, int32 lockMode)
case Raster::TEXTURE: { case Raster::TEXTURE: {
tex->GetSurfaceLevel(level, &surf); tex->GetSurfaceLevel(level, &surf);
natras->lockedSurf = surf; natras->lockedSurf = surf;
surf->LockRect(&lr, 0, flags); HRESULT res = surf->LockRect(&lr, 0, flags);
assert(res == D3D_OK);
break;
}
case Raster::CAMERATEXTURE:
case Raster::CAMERA: {
if(lockMode & Raster::PRIVATELOCK_WRITE)
assert(0 && "can't lock framebuffer for writing");
if(raster->type == Raster::CAMERA)
rt = d3d9Globals.defaultRenderTarget;
else
tex->GetSurfaceLevel(level, &rt);
D3DSURFACE_DESC desc;
rt->GetDesc(&desc);
HRESULT res = d3ddevice->CreateOffscreenPlainSurface(desc.Width, desc.Height, desc.Format, D3DPOOL_SYSTEMMEM, &surf, nil);
if(res != D3D_OK)
return nil;
d3ddevice->GetRenderTargetData(rt, surf);
natras->lockedSurf = surf;
res = surf->LockRect(&lr, 0, flags);
assert(res == D3D_OK);
break; break;
} }
@@ -682,22 +622,24 @@ rasterLock(Raster *raster, int32 level, int32 lockMode)
raster->stride = lr.Pitch; raster->stride = lr.Pitch;
if(raster->width == 0) raster->width = 1; if(raster->width == 0) raster->width = 1;
if(raster->height == 0) raster->height = 1; if(raster->height == 0) raster->height = 1;
#else
RasterLevels *levels = (RasterLevels*)natras->texture;
raster->pixels = levels->levels[level].data;
raster->width = levels->levels[level].width;
raster->height = levels->levels[level].height;
raster->stride = raster->width*natras->bpp;
#endif
if(lockMode & Raster::LOCKREAD) raster->privateFlags |= Raster::PRIVATELOCK_READ; if(lockMode & Raster::LOCKREAD) raster->privateFlags |= Raster::PRIVATELOCK_READ;
if(lockMode & Raster::LOCKWRITE) raster->privateFlags |= Raster::PRIVATELOCK_WRITE; if(lockMode & Raster::LOCKWRITE) raster->privateFlags |= Raster::PRIVATELOCK_WRITE;
return raster->pixels; return raster->pixels;
#else
RasterLevels *levels = (RasterLevels*)natras->texture;
return levels->levels[level].data;
#endif
} }
void void
rasterUnlock(Raster *raster, int32 level) rasterUnlock(Raster *raster, int32 level)
{ {
#if RW_D3D9 #if RW_D3D9
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
IDirect3DSurface9 *surf = (IDirect3DSurface9*)natras->lockedSurf; IDirect3DSurface9 *surf = (IDirect3DSurface9*)natras->lockedSurf;
surf->UnlockRect(); surf->UnlockRect();
surf->Release(); surf->Release();
@@ -714,7 +656,7 @@ rasterUnlock(Raster *raster, int32 level)
int32 int32
rasterNumLevels(Raster *raster) rasterNumLevels(Raster *raster)
{ {
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
#ifdef RW_D3D9 #ifdef RW_D3D9
IDirect3DTexture9 *tex = (IDirect3DTexture9*)natras->texture; IDirect3DTexture9 *tex = (IDirect3DTexture9*)natras->texture;
return tex->GetLevelCount(); return tex->GetLevelCount();
@@ -799,44 +741,47 @@ rasterFromImage(Raster *raster, Image *image)
image = truecolimg; image = truecolimg;
} }
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
int32 format = raster->format&(Raster::PAL8 | Raster::PAL4 | 0xF00);
switch(image->depth){ switch(image->depth){
case 32: case 32:
if(raster->format == Raster::C8888) if(format == Raster::C8888)
conv = conv_BGRA8888_from_RGBA8888; conv = conv_BGRA8888_from_RGBA8888;
else if(raster->format == Raster::C888) else if(format == Raster::C888)
conv = conv_BGR888_from_RGB888; conv = conv_BGR888_from_RGB888;
else else
goto err; goto err;
break; break;
case 24: case 24:
if(raster->format == Raster::C8888) if(format == Raster::C8888)
conv = conv_BGRA8888_from_RGB888; conv = conv_BGRA8888_from_RGB888;
else if(raster->format == Raster::C888) else if(format == Raster::C888)
conv = conv_BGR888_from_RGB888; conv = conv_BGR888_from_RGB888;
else else
goto err; goto err;
break; break;
case 16: case 16:
if(raster->format == Raster::C1555) if(format == Raster::C1555)
conv = conv_ARGB1555_from_ARGB1555; conv = conv_ARGB1555_from_ARGB1555;
else else
goto err; goto err;
break; break;
case 8: case 8:
if(raster->format == (Raster::PAL8 | Raster::C8888)) if(format == (Raster::PAL8 | Raster::C8888))
conv = conv_8_from_8; conv = conv_8_from_8;
else else
goto err; goto err;
break; break;
case 4: case 4:
if(raster->format == (Raster::PAL4 | Raster::C8888) || if(format == (Raster::PAL4 | Raster::C8888) ||
raster->format == (Raster::PAL8 | Raster::C8888)) format == (Raster::PAL8 | Raster::C8888))
conv = conv_8_from_8; conv = conv_8_from_8;
else else
goto err; goto err;
break;
default: default:
err: err:
fprintf(stderr, "%d %x\n", image->depth, format); fflush(stdout);
RWERROR((ERR_INVRASTER)); RWERROR((ERR_INVRASTER));
return 0; return 0;
} }
@@ -857,7 +802,13 @@ rasterFromImage(Raster *raster, Image *image)
} }
} }
uint8 *pixels = raster->lock(0, Raster::LOCKWRITE|Raster::LOCKNOFETCH); bool unlock = false;
if(raster->pixels == nil){
raster->lock(0, Raster::LOCKWRITE|Raster::LOCKNOFETCH);
unlock = true;
}
uint8 *pixels = raster->pixels;
assert(pixels); assert(pixels);
uint8 *imgpixels = image->pixels; uint8 *imgpixels = image->pixels;
@@ -875,6 +826,7 @@ rasterFromImage(Raster *raster, Image *image)
imgpixels += image->stride; imgpixels += image->stride;
pixels += raster->stride; pixels += raster->stride;
} }
if(unlock)
raster->unlock(0); raster->unlock(0);
if(truecolimg) if(truecolimg)
@@ -888,11 +840,23 @@ rasterToImage(Raster *raster)
{ {
int32 depth; int32 depth;
Image *image; Image *image;
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset);
bool unlock = false;
if(raster->pixels == nil){
raster->lock(0, Raster::LOCKREAD);
unlock = true;
}
D3dRaster *natras = GETD3DRASTEREXT(raster);
if(natras->customFormat){ if(natras->customFormat){
image = Image::create(raster->width, raster->height, 32); int w = raster->width;
int h = raster->height;
// pixels are in the upper right corner
if(w < 4) w = 4;
if(h < 4) h = 4;
image = Image::create(w, h, 32);
image->allocate(); image->allocate();
uint8 *pix = raster->lock(0, Raster::LOCKREAD); uint8 *pix = raster->pixels;
switch(natras->format){ switch(natras->format){
case D3DFMT_DXT1: case D3DFMT_DXT1:
image->setPixelsDXT(1, pix); image->setPixelsDXT(1, pix);
@@ -906,10 +870,16 @@ rasterToImage(Raster *raster)
image->setPixelsDXT(5, pix); image->setPixelsDXT(5, pix);
break; break;
default: default:
raster->unlock(0);
image->destroy(); image->destroy();
if(unlock)
raster->unlock(0);
return nil; return nil;
} }
// fix it up again
image->width = raster->width;
image->height = raster->height;
if(unlock)
raster->unlock(0); raster->unlock(0);
return image; return image;
} }
@@ -964,7 +934,7 @@ rasterToImage(Raster *raster)
} }
uint8 *imgpixels = image->pixels; uint8 *imgpixels = image->pixels;
uint8 *pixels = raster->lock(0, Raster::LOCKREAD); uint8 *pixels = raster->pixels;
int x, y; int x, y;
assert(image->width == raster->width); assert(image->width == raster->width);
@@ -980,17 +950,18 @@ rasterToImage(Raster *raster)
imgpixels += image->stride; imgpixels += image->stride;
pixels += raster->stride; pixels += raster->stride;
} }
raster->unlock(0);
image->compressPalette(); image->compressPalette();
if(unlock)
raster->unlock(0);
return image; return image;
} }
int32 int32
getLevelSize(Raster *raster, int32 level) getLevelSize(Raster *raster, int32 level)
{ {
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *ras = GETD3DRASTEREXT(raster);
#ifdef RW_D3D9 #ifdef RW_D3D9
IDirect3DTexture9 *tex = (IDirect3DTexture9*)ras->texture; IDirect3DTexture9 *tex = (IDirect3DTexture9*)ras->texture;
D3DSURFACE_DESC desc; D3DSURFACE_DESC desc;
@@ -1012,11 +983,19 @@ allocateDXT(Raster *raster, int32 dxt, int32 numLevels, bool32 hasAlpha)
0x34545844, // DXT4 0x34545844, // DXT4
0x35545844, // DXT5 0x35545844, // DXT5
}; };
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *ras = GETD3DRASTEREXT(raster);
ras->format = dxtMap[dxt-1]; ras->format = dxtMap[dxt-1];
ras->hasAlpha = hasAlpha; ras->hasAlpha = hasAlpha;
ras->customFormat = 1;
if(ras->autogenMipmap)
numLevels = 0;
else if(raster->format & Raster::MIPMAP)
{}
else
numLevels = 1;
ras->texture = createTexture(raster->width, raster->height, ras->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? numLevels : 1, numLevels,
ras->autogenMipmap ? D3DUSAGE_AUTOGENMIPMAP : 0,
ras->format); ras->format);
raster->flags &= ~Raster::DONTALLOCATE; raster->flags &= ~Raster::DONTALLOCATE;
} }
@@ -1024,7 +1003,7 @@ allocateDXT(Raster *raster, int32 dxt, int32 numLevels, bool32 hasAlpha)
void void
setPalette(Raster *raster, void *palette, int32 size) setPalette(Raster *raster, void *palette, int32 size)
{ {
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *ras = GETD3DRASTEREXT(raster);
memcpy(ras->palette, palette, 4*size); memcpy(ras->palette, palette, 4*size);
} }
+37 -11
View File
@@ -468,14 +468,27 @@ readAsImage(Stream *stream, int32 width, int32 height, int32 depth, int32 format
for(int32 i = 0; i < pallen; i++) for(int32 i = 0; i < pallen; i++)
palette[i*4+3] = 0xFF; palette[i*4+3] = 0xFF;
// Only read one mipmap Raster *ras = nil;
for(int32 i = 0; i < numLevels; i++){
for(int i = 0; i < numLevels; i++){
uint32 size = stream->readU32(); uint32 size = stream->readU32();
if(i == 0){
// don't read levels that don't exist
if(ras && i >= ras->getNumLevels()){
stream->seek(size);
continue;
}
// one allocation is enough, first level is largest
if(data == nil)
data = rwNewT(uint8, size, MEMDUR_FUNCTION | ID_IMAGE); data = rwNewT(uint8, size, MEMDUR_FUNCTION | ID_IMAGE);
stream->read8(data, size); stream->read8(data, size);
}else
stream->seek(size); if(ras){
ras->lock(i, Raster::LOCKWRITE|Raster::LOCKNOFETCH);
img->width = ras->width;
img->height = ras->height;
img->stride = img->width*img->bpp;
} }
if(format & (Raster::PAL4 | Raster::PAL8)){ if(format & (Raster::PAL4 | Raster::PAL8)){
@@ -487,16 +500,29 @@ readAsImage(Stream *stream, int32 width, int32 height, int32 depth, int32 format
line[0] = palette[*idx*4+0]; line[0] = palette[*idx*4+0];
line[1] = palette[*idx*4+1]; line[1] = palette[*idx*4+1];
line[2] = palette[*idx*4+2]; line[2] = palette[*idx*4+2];
if(img->bpp > 3)
line[3] = palette[*idx*4+3]; line[3] = palette[*idx*4+3];
line += 4; line += img->bpp;
idx++; idx++;
} }
pixels += img->stride; pixels += img->stride;
} }
} }
if(ras == nil){
// Important to have filled the image with data
int32 newformat;
Raster::imageFindRasterFormat(img, format&7, &width, &height, &depth, &newformat);
newformat |= format & (Raster::MIPMAP | Raster::AUTOMIPMAP);
ras = Raster::create(width, height, depth, newformat);
ras->lock(i, Raster::LOCKWRITE|Raster::LOCKNOFETCH);
}
ras->setFromImage(img);
ras->unlock(i);
}
rwFree(data); rwFree(data);
Raster *ras = Raster::createFromImage(img, PLATFORM_D3D8);
img->destroy(); img->destroy();
return ras; return ras;
} }
@@ -545,13 +571,13 @@ readNativeTexture(Stream *stream)
Raster *raster; Raster *raster;
D3dRaster *ras; D3dRaster *ras;
if(compression){ if(compression){
raster = Raster::create(width, height, depth, format | type | 0x80, PLATFORM_D3D8); raster = Raster::create(width, height, depth, format | type | Raster::DONTALLOCATE, PLATFORM_D3D8);
ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); ras = GETD3DRASTEREXT(raster);
allocateDXT(raster, compression, numLevels, hasAlpha); allocateDXT(raster, compression, numLevels, hasAlpha);
ras->customFormat = 1; ras->customFormat = 1;
}else{ }else{
raster = Raster::create(width, height, depth, format | type, PLATFORM_D3D8); raster = Raster::create(width, height, depth, format | type, PLATFORM_D3D8);
ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); ras = GETD3DRASTEREXT(raster);
} }
tex->raster = raster; tex->raster = raster;
@@ -588,7 +614,7 @@ writeNativeTexture(Texture *tex, Stream *stream)
// Raster // Raster
Raster *raster = tex->raster; Raster *raster = tex->raster;
D3dRaster *ras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *ras = GETD3DRASTEREXT(raster);
int32 numLevels = raster->getNumLevels(); int32 numLevels = raster->getNumLevels();
stream->writeI32(raster->format); stream->writeI32(raster->format);
stream->writeI32(ras->hasAlpha); stream->writeI32(ras->hasAlpha);
+4 -4
View File
@@ -29,8 +29,8 @@ defaultRenderCB(Atomic *atomic, InstanceDataHeader *header)
d3d::lightingCB_Fix(atomic); d3d::lightingCB_Fix(atomic);
Geometry *geo = atomic->geometry; uint32 flags = atomic->geometry->flags;
d3d::setRenderState(D3DRS_LIGHTING, !!(geo->flags & rw::Geometry::LIGHT)); d3d::setRenderState(D3DRS_LIGHTING, !!(flags & rw::Geometry::LIGHT));
Frame *f = atomic->getFrame(); Frame *f = atomic->getFrame();
convMatrix(&world, f->getLTM()); convMatrix(&world, f->getLTM());
@@ -39,12 +39,12 @@ defaultRenderCB(Atomic *atomic, InstanceDataHeader *header)
InstanceData *inst = header->inst; InstanceData *inst = header->inst;
for(uint32 i = 0; i < header->numMeshes; i++){ for(uint32 i = 0; i < header->numMeshes; i++){
d3d::setTexture(0, inst->material->texture); d3d::setTexture(0, inst->material->texture);
d3d::setMaterial(inst->material->color, inst->material->surfaceProps); d3d::setMaterial(flags, inst->material->color, inst->material->surfaceProps);
d3d::setRenderState(D3DRS_AMBIENTMATERIALSOURCE, D3DMCS_MATERIAL); d3d::setRenderState(D3DRS_AMBIENTMATERIALSOURCE, D3DMCS_MATERIAL);
d3d::setRenderState(D3DRS_DIFFUSEMATERIALSOURCE, D3DMCS_MATERIAL); d3d::setRenderState(D3DRS_DIFFUSEMATERIALSOURCE, D3DMCS_MATERIAL);
if(geo->flags & Geometry::PRELIT) if(flags & Geometry::PRELIT)
d3d::setRenderState(D3DRS_EMISSIVEMATERIALSOURCE, D3DMCS_COLOR1); d3d::setRenderState(D3DRS_EMISSIVEMATERIALSOURCE, D3DMCS_COLOR1);
else else
d3d::setRenderState(D3DRS_EMISSIVEMATERIALSOURCE, D3DMCS_MATERIAL); d3d::setRenderState(D3DRS_EMISSIVEMATERIALSOURCE, D3DMCS_MATERIAL);
+7 -4
View File
@@ -746,11 +746,12 @@ readNativeTexture(Stream *stream)
assert((flags & 2) == 0 && "Can't have cube maps yet"); assert((flags & 2) == 0 && "Can't have cube maps yet");
raster = Raster::create(width, height, depth, format | type | Raster::DONTALLOCATE, PLATFORM_D3D9); raster = Raster::create(width, height, depth, format | type | Raster::DONTALLOCATE, PLATFORM_D3D9);
assert(raster); assert(raster);
ext = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); ext = GETD3DRASTEREXT(raster);
ext->format = d3dformat; ext->format = d3dformat;
ext->hasAlpha = flags & 1; ext->hasAlpha = flags & 1;
ext->texture = createTexture(raster->width, raster->height, ext->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? numLevels : 1, raster->format & Raster::MIPMAP ? numLevels : 1,
0,
ext->format); ext->format);
assert(ext->texture); assert(ext->texture);
raster->flags &= ~Raster::DONTALLOCATE; raster->flags &= ~Raster::DONTALLOCATE;
@@ -760,7 +761,7 @@ readNativeTexture(Stream *stream)
}else{ }else{
raster = Raster::create(width, height, depth, format | type, PLATFORM_D3D9); raster = Raster::create(width, height, depth, format | type, PLATFORM_D3D9);
assert(raster); assert(raster);
ext = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); ext = GETD3DRASTEREXT(raster);
} }
tex->raster = raster; tex->raster = raster;
@@ -799,7 +800,7 @@ writeNativeTexture(Texture *tex, Stream *stream)
// Raster // Raster
Raster *raster = tex->raster; Raster *raster = tex->raster;
D3dRaster *ext = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *ext = GETD3DRASTEREXT(raster);
int32 numLevels = raster->getNumLevels(); int32 numLevels = raster->getNumLevels();
stream->writeI32(raster->format); stream->writeI32(raster->format);
stream->writeU32(ext->format); stream->writeU32(ext->format);
@@ -811,7 +812,9 @@ writeNativeTexture(Texture *tex, Stream *stream)
uint8 flags = 0; uint8 flags = 0;
if(ext->hasAlpha) if(ext->hasAlpha)
flags |= 1; flags |= 1;
// no automipmapgen and cube supported yet // no cube supported yet
if(ext->autogenMipmap)
flags |= 4;
if(ext->customFormat) if(ext->customFormat)
flags |= 8; flags |= 8;
stream->writeU8(flags); stream->writeU8(flags);
+20 -9
View File
@@ -33,9 +33,10 @@ static void *matfx_env_tex_PS;
enum enum
{ {
VSLOC_texMat = VSLOC_afterLights, VSLOC_texMat = VSLOC_afterLights,
VSLOC_colorClamp = VSLOC_texMat + 4,
VSLOC_envColor,
PSLOC_shininess = 1, PSLOC_shininess = 1,
PSLOC_colorClamp = 2
}; };
void void
@@ -79,14 +80,17 @@ uploadEnvMatrix(Frame *frame)
frame = engine->currentCamera->getFrame(); frame = engine->currentCamera->getFrame();
// cache the matrix across multiple meshes // cache the matrix across multiple meshes
if(frame == lastEnvFrame) // can't do it, frame matrix may change
return; // if(frame == lastEnvFrame)
lastEnvFrame = frame; // return;
// lastEnvFrame = frame;
RawMatrix envMtx, invMtx; RawMatrix envMtx, invMtx;
Matrix::invert(&invMat, frame->getLTM()); Matrix::invert(&invMat, frame->getLTM());
convMatrix(&invMtx, &invMat); convMatrix(&invMtx, &invMat);
invMtx.pos.set(0.0f, 0.0f, 0.0f); invMtx.pos.set(0.0f, 0.0f, 0.0f);
float uscale = fabs(normal2texcoord.right.x);
normal2texcoord.right.x = MatFX::envMapFlipU ? -uscale : uscale;
RawMatrix::mult(&envMtx, &invMtx, &normal2texcoord); RawMatrix::mult(&envMtx, &invMtx, &normal2texcoord);
d3ddevice->SetVertexShaderConstantF(VSLOC_texMat, (float*)&envMtx, 4); d3ddevice->SetVertexShaderConstantF(VSLOC_texMat, (float*)&envMtx, 4);
} }
@@ -117,10 +121,16 @@ matfxRender_EnvMap(InstanceDataHeader *header, InstanceData *inst, int32 lightBi
fxparams.disableFBA = env->fbAlpha ? 0.0f : 1.0f; fxparams.disableFBA = env->fbAlpha ? 0.0f : 1.0f;
d3ddevice->SetPixelShaderConstantF(PSLOC_shininess, (float*)&fxparams, 1); d3ddevice->SetPixelShaderConstantF(PSLOC_shininess, (float*)&fxparams, 1);
// This clamps the vertex color below. With it we can achieve both PC and PS2 style matfx // This clamps the vertex color below. With it we can achieve both PC and PS2 style matfx
if(MatFX::modulateEnvMap) if(MatFX::envMapApplyLight)
d3ddevice->SetPixelShaderConstantF(PSLOC_colorClamp, zero, 1); d3ddevice->SetVertexShaderConstantF(VSLOC_colorClamp, zero, 1);
else else
d3ddevice->SetPixelShaderConstantF(PSLOC_colorClamp, one, 1); d3ddevice->SetVertexShaderConstantF(VSLOC_colorClamp, one, 1);
RGBAf envcol[4];
if(MatFX::envMapUseMatColor)
convColor(envcol, &m->color);
else
convColor(envcol, &MatFX::envMapColor);
d3ddevice->SetVertexShaderConstantF(VSLOC_envColor, (float*)&envcol, 1);
// Pick a shader // Pick a shader
if((lightBits & VSLIGHT_MASK) == 0) if((lightBits & VSLIGHT_MASK) == 0)
@@ -130,7 +140,7 @@ matfxRender_EnvMap(InstanceDataHeader *header, InstanceData *inst, int32 lightBi
else else
setVertexShader(matfx_env_all_VS); setVertexShader(matfx_env_all_VS);
bool32 texAlpha = PLUGINOFFSET(D3dRaster, env->tex->raster, nativeRasterOffset)->hasAlpha; bool32 texAlpha = GETD3DRASTEREXT(env->tex->raster)->hasAlpha;
if(inst->material->texture){ if(inst->material->texture){
d3d::setTexture(0, m->texture); d3d::setTexture(0, m->texture);
@@ -149,6 +159,7 @@ void
matfxRenderCB_Shader(Atomic *atomic, InstanceDataHeader *header) matfxRenderCB_Shader(Atomic *atomic, InstanceDataHeader *header)
{ {
int vsBits; int vsBits;
uint32 flags = atomic->geometry->flags;
setStreamSource(0, (IDirect3DVertexBuffer9*)header->vertexStream[0].vertexBuffer, setStreamSource(0, (IDirect3DVertexBuffer9*)header->vertexStream[0].vertexBuffer,
0, header->vertexStream[0].stride); 0, header->vertexStream[0].stride);
setIndices((IDirect3DIndexBuffer9*)header->indexBuffer); setIndices((IDirect3DIndexBuffer9*)header->indexBuffer);
@@ -165,7 +176,7 @@ matfxRenderCB_Shader(Atomic *atomic, InstanceDataHeader *header)
for(uint32 i = 0; i < header->numMeshes; i++){ for(uint32 i = 0; i < header->numMeshes; i++){
Material *m = inst->material; Material *m = inst->material;
setMaterial(m->color, m->surfaceProps); setMaterial(flags, m->color, m->surfaceProps);
MatFX *matfx = MatFX::get(m); MatFX *matfx = MatFX::get(m);
if(matfx == nil) if(matfx == nil)
+2 -1
View File
@@ -145,6 +145,7 @@ void
defaultRenderCB_Shader(Atomic *atomic, InstanceDataHeader *header) defaultRenderCB_Shader(Atomic *atomic, InstanceDataHeader *header)
{ {
int vsBits; int vsBits;
uint32 flags = atomic->geometry->flags;
setStreamSource(0, header->vertexStream[0].vertexBuffer, 0, header->vertexStream[0].stride); setStreamSource(0, header->vertexStream[0].vertexBuffer, 0, header->vertexStream[0].stride);
setIndices(header->indexBuffer); setIndices(header->indexBuffer);
setVertexDeclaration(header->vertexDeclaration); setVertexDeclaration(header->vertexDeclaration);
@@ -166,7 +167,7 @@ defaultRenderCB_Shader(Atomic *atomic, InstanceDataHeader *header)
SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 255); SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 255);
setMaterial(m->color, m->surfaceProps); setMaterial(flags, m->color, m->surfaceProps);
if(m->texture){ if(m->texture){
d3d::setTexture(0, m->texture); d3d::setTexture(0, m->texture);
+2 -2
View File
@@ -289,7 +289,7 @@ void
skinRenderCB(Atomic *atomic, InstanceDataHeader *header) skinRenderCB(Atomic *atomic, InstanceDataHeader *header)
{ {
int vsBits; int vsBits;
uint32 flags = atomic->geometry->flags;
setStreamSource(0, (IDirect3DVertexBuffer9*)header->vertexStream[0].vertexBuffer, setStreamSource(0, (IDirect3DVertexBuffer9*)header->vertexStream[0].vertexBuffer,
0, header->vertexStream[0].stride); 0, header->vertexStream[0].stride);
setIndices((IDirect3DIndexBuffer9*)header->indexBuffer); setIndices((IDirect3DIndexBuffer9*)header->indexBuffer);
@@ -314,7 +314,7 @@ skinRenderCB(Atomic *atomic, InstanceDataHeader *header)
SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 255); SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 255);
setMaterial(m->color, m->surfaceProps); setMaterial(flags, m->color, m->surfaceProps);
if(inst->material->texture){ if(inst->material->texture){
d3d::setTexture(0, m->texture); d3d::setTexture(0, m->texture);
+252 -36
View File
@@ -63,6 +63,7 @@ struct RwRasterStateCache {
Texture::Addressing addressingU; Texture::Addressing addressingU;
Texture::Addressing addressingV; Texture::Addressing addressingV;
Texture::FilterMode filter; Texture::FilterMode filter;
int32 maxAniso;
}; };
#define MAXNUMSTAGES 8 #define MAXNUMSTAGES 8
@@ -77,6 +78,14 @@ struct RwStateCache {
uint32 fogenable; uint32 fogenable;
RGBA fogcolor; RGBA fogcolor;
uint32 cullmode; uint32 cullmode;
uint32 stencilenable;
uint32 stencilpass;
uint32 stencilfail;
uint32 stencilzfail;
uint32 stencilfunc;
uint32 stencilref;
uint32 stencilmask;
uint32 stencilwritemask;
uint32 alphafunc; uint32 alphafunc;
uint32 alpharef; uint32 alpharef;
@@ -89,6 +98,7 @@ struct RwStateCache {
static RwStateCache rwStateCache; static RwStateCache rwStateCache;
void *constantVertexStream; void *constantVertexStream;
static IDirect3DTexture9 *whiteTex;
D3dShaderState d3dShaderState; D3dShaderState d3dShaderState;
@@ -157,6 +167,30 @@ static uint32 blendMap[] = {
D3DBLEND_SRCALPHASAT D3DBLEND_SRCALPHASAT
}; };
static uint32 stencilOpMap[] = {
D3DSTENCILOP_KEEP, // actually invalid
D3DSTENCILOP_KEEP,
D3DSTENCILOP_ZERO,
D3DSTENCILOP_REPLACE,
D3DSTENCILOP_INCRSAT,
D3DSTENCILOP_DECRSAT,
D3DSTENCILOP_INVERT,
D3DSTENCILOP_INCR,
D3DSTENCILOP_DECR
};
static uint32 stencilFuncMap[] = {
D3DCMP_NEVER, // actually invalid
D3DCMP_NEVER,
D3DCMP_LESS,
D3DCMP_EQUAL,
D3DCMP_LESSEQUAL,
D3DCMP_GREATER,
D3DCMP_NOTEQUAL,
D3DCMP_GREATEREQUAL,
D3DCMP_ALWAYS
};
static uint32 alphafuncMap[] = { static uint32 alphafuncMap[] = {
D3DCMP_ALWAYS, D3DCMP_ALWAYS,
D3DCMP_GREATEREQUAL, D3DCMP_GREATEREQUAL,
@@ -170,12 +204,16 @@ static uint32 cullmodeMap[] = {
D3DCULL_CCW D3DCULL_CCW
}; };
// TODO: support mipmaps static uint32 filterConvMap[] = {
static uint32 filterConvMap_NoMIP[] = {
0, D3DTEXF_POINT, D3DTEXF_LINEAR, 0, D3DTEXF_POINT, D3DTEXF_LINEAR,
D3DTEXF_POINT, D3DTEXF_LINEAR, D3DTEXF_POINT, D3DTEXF_LINEAR,
D3DTEXF_POINT, D3DTEXF_LINEAR D3DTEXF_POINT, D3DTEXF_LINEAR
}; };
static uint32 filterConvMap_MIP[] = {
0, D3DTEXF_NONE, D3DTEXF_NONE,
D3DTEXF_POINT, D3DTEXF_POINT,
D3DTEXF_LINEAR, D3DTEXF_LINEAR
};
static uint32 addressConvMap[] = { static uint32 addressConvMap[] = {
0, D3DTADDRESS_WRAP, D3DTADDRESS_MIRROR, 0, D3DTADDRESS_WRAP, D3DTADDRESS_MIRROR,
D3DTADDRESS_CLAMP, D3DTADDRESS_BORDER D3DTADDRESS_CLAMP, D3DTADDRESS_BORDER
@@ -298,14 +336,18 @@ restoreD3d9Device(void)
for(i = 0; i < MAXNUMSTAGES; i++){ for(i = 0; i < MAXNUMSTAGES; i++){
Raster *raster = rwStateCache.texstage[i].raster; Raster *raster = rwStateCache.texstage[i].raster;
if(raster){ if(raster){
D3dRaster *d3draster = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *d3draster = GETD3DRASTEREXT(raster);
d3ddevice->SetTexture(i, (IDirect3DTexture9*)d3draster->texture); d3ddevice->SetTexture(i, (IDirect3DTexture9*)d3draster->texture);
}else }else
d3ddevice->SetTexture(i, nil); d3ddevice->SetTexture(i, nil);
setSamplerState(i, D3DSAMP_ADDRESSU, addressConvMap[rwStateCache.texstage[i].addressingU]); setSamplerState(i, D3DSAMP_ADDRESSU, addressConvMap[rwStateCache.texstage[i].addressingU]);
setSamplerState(i, D3DSAMP_ADDRESSV, addressConvMap[rwStateCache.texstage[i].addressingV]); setSamplerState(i, D3DSAMP_ADDRESSV, addressConvMap[rwStateCache.texstage[i].addressingV]);
setSamplerState(i, D3DSAMP_MAGFILTER, filterConvMap_NoMIP[rwStateCache.texstage[i].filter]); setSamplerState(i, D3DSAMP_MAGFILTER, filterConvMap[rwStateCache.texstage[i].filter]);
setSamplerState(i, D3DSAMP_MINFILTER, filterConvMap_NoMIP[rwStateCache.texstage[i].filter]); if(rwStateCache.texstage[i].maxAniso == 1)
setSamplerState(i, D3DSAMP_MINFILTER, filterConvMap[rwStateCache.texstage[i].filter]);
else
setSamplerState(i, D3DSAMP_MINFILTER, D3DTEXF_ANISOTROPIC);
setSamplerState(i, D3DSAMP_MIPFILTER, filterConvMap_MIP[rwStateCache.texstage[i].filter]);
} }
for(s = 0; s < MAXNUMSTATES; s++) for(s = 0; s < MAXNUMSTATES; s++)
if(validStates[s]) if(validStates[s])
@@ -325,6 +367,24 @@ restoreD3d9Device(void)
d3ddevice->SetIndices(deviceCache.indices); d3ddevice->SetIndices(deviceCache.indices);
for(i = 0; i < MAXNUMSTREAMS; i++) for(i = 0; i < MAXNUMSTREAMS; i++)
d3ddevice->SetStreamSource(i, deviceCache.vertexStreams[i].buffer, deviceCache.vertexStreams[i].offset, deviceCache.vertexStreams[i].stride); d3ddevice->SetStreamSource(i, deviceCache.vertexStreams[i].buffer, deviceCache.vertexStreams[i].offset, deviceCache.vertexStreams[i].stride);
// shader constants are zero now
d3dShaderState.fogDirty = true;
d3dShaderState.matColor.red = 0;
d3dShaderState.matColor.green = 0;
d3dShaderState.matColor.blue = 0;
d3dShaderState.matColor.alpha = 0;
d3dShaderState.surfProps.ambient = 0.0f;
d3dShaderState.surfProps.specular = 0.0f;
d3dShaderState.surfProps.diffuse = 0.0f;
d3dShaderState.extraSurfProp = 0.0f;
d3dShaderState.numDir = 0;
d3dShaderState.numPoint = 0;
d3dShaderState.numSpot = 0;
d3dShaderState.ambient.red = 0.0f;
d3dShaderState.ambient.green = 0.0f;
d3dShaderState.ambient.blue = 0.0f;
d3dShaderState.ambient.alpha = 0.0f;
} }
void void
@@ -332,7 +392,7 @@ evictD3D9Raster(Raster *raster)
{ {
int i; int i;
// Make sure we're not still referencing this raster // Make sure we're not still referencing this raster
D3dRaster *natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); D3dRaster *natras = GETD3DRASTEREXT(raster);
switch(raster->type){ switch(raster->type){
case Raster::CAMERATEXTURE: case Raster::CAMERATEXTURE:
for(i = 0; i < MAXNUMRENDERTARGETS; i++) for(i = 0; i < MAXNUMRENDERTARGETS; i++)
@@ -406,11 +466,11 @@ setRasterStage(uint32 stage, Raster *raster)
if(raster){ if(raster){
assert(raster->platform == PLATFORM_D3D8 || assert(raster->platform == PLATFORM_D3D8 ||
raster->platform == PLATFORM_D3D9); raster->platform == PLATFORM_D3D9);
d3draster = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); d3draster = GETD3DRASTEREXT(raster);
d3ddevice->SetTexture(stage, (IDirect3DTexture9*)d3draster->texture); d3ddevice->SetTexture(stage, (IDirect3DTexture9*)d3draster->texture);
alpha = d3draster->hasAlpha; alpha = d3draster->hasAlpha;
}else{ }else{
d3ddevice->SetTexture(stage, nil); d3ddevice->SetTexture(stage, whiteTex);
alpha = 0; alpha = 0;
} }
if(stage == 0){ if(stage == 0){
@@ -426,13 +486,24 @@ setRasterStage(uint32 stage, Raster *raster)
} }
static void static void
setFilterMode(uint32 stage, int32 filter) setFilterMode(uint32 stage, int32 filter, int32 maxAniso = 1)
{ {
// TODO: mip mapping
if(rwStateCache.texstage[stage].filter != (Texture::FilterMode)filter){ if(rwStateCache.texstage[stage].filter != (Texture::FilterMode)filter){
rwStateCache.texstage[stage].filter = (Texture::FilterMode)filter; rwStateCache.texstage[stage].filter = (Texture::FilterMode)filter;
setSamplerState(stage, D3DSAMP_MAGFILTER, filterConvMap_NoMIP[filter]); setSamplerState(stage, D3DSAMP_MAGFILTER, filterConvMap[filter]);
setSamplerState(stage, D3DSAMP_MINFILTER, filterConvMap_NoMIP[filter]); if(maxAniso == 1)
setSamplerState(stage, D3DSAMP_MINFILTER, filterConvMap[filter]);
else
setSamplerState(stage, D3DSAMP_MINFILTER, D3DTEXF_ANISOTROPIC);
setSamplerState(stage, D3DSAMP_MIPFILTER, filterConvMap_MIP[filter]);
}
if(rwStateCache.texstage[stage].maxAniso != maxAniso){
rwStateCache.texstage[stage].maxAniso = maxAniso;
if(maxAniso == 1)
setSamplerState(stage, D3DSAMP_MINFILTER, filterConvMap[filter]);
else
setSamplerState(stage, D3DSAMP_MINFILTER, D3DTEXF_ANISOTROPIC);
setSamplerState(stage, D3DSAMP_MAXANISOTROPY, maxAniso);
} }
} }
@@ -462,7 +533,7 @@ setTexture(uint32 stage, Texture *tex)
return; return;
} }
if(tex->raster){ if(tex->raster){
setFilterMode(stage, tex->getFilter()); setFilterMode(stage, tex->getFilter(), tex->getMaxAnisotropy());
setAddressU(stage, tex->getAddressU()); setAddressU(stage, tex->getAddressU());
setAddressV(stage, tex->getAddressV()); setAddressV(stage, tex->getAddressV());
} }
@@ -517,7 +588,7 @@ setMaterial_fix(const RGBA &color, const SurfaceProperties &surfProps)
void void
setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops) setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops, float extraSurfProp)
{ {
if(!equal(d3dShaderState.matColor, color)){ if(!equal(d3dShaderState.matColor, color)){
rw::RGBAf col; rw::RGBAf col;
@@ -528,14 +599,16 @@ setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops)
if(d3dShaderState.surfProps.ambient != surfaceprops.ambient || if(d3dShaderState.surfProps.ambient != surfaceprops.ambient ||
d3dShaderState.surfProps.specular != surfaceprops.specular || d3dShaderState.surfProps.specular != surfaceprops.specular ||
d3dShaderState.surfProps.diffuse != surfaceprops.diffuse){ d3dShaderState.surfProps.diffuse != surfaceprops.diffuse ||
d3dShaderState.extraSurfProp != extraSurfProp){
float surfProps[4]; float surfProps[4];
surfProps[0] = surfaceprops.ambient; surfProps[0] = surfaceprops.ambient;
surfProps[1] = surfaceprops.specular; surfProps[1] = surfaceprops.specular;
surfProps[2] = surfaceprops.diffuse; surfProps[2] = surfaceprops.diffuse;
surfProps[3] = 0.0f; surfProps[3] = extraSurfProp;
d3ddevice->SetVertexShaderConstantF(VSLOC_surfProps, surfProps, 1); d3ddevice->SetVertexShaderConstantF(VSLOC_surfProps, surfProps, 1);
d3dShaderState.surfProps = surfaceprops; d3dShaderState.surfProps = surfaceprops;
d3dShaderState.extraSurfProp = extraSurfProp;
} }
} }
@@ -608,6 +681,56 @@ setRwRenderState(int32 state, void *pvalue)
setRenderState(D3DRS_CULLMODE, cullmodeMap[value]); setRenderState(D3DRS_CULLMODE, cullmodeMap[value]);
} }
break; break;
case STENCILENABLE:
if(rwStateCache.stencilenable != bval){
rwStateCache.stencilenable = bval;
setRenderState(D3DRS_STENCILENABLE, bval);
}
break;
case STENCILFAIL:
if(rwStateCache.stencilfail != value){
rwStateCache.stencilfail = value;
setRenderState(D3DRS_STENCILFAIL, stencilOpMap[value]);
}
break;
case STENCILZFAIL:
if(rwStateCache.stencilzfail != value){
rwStateCache.stencilzfail = value;
setRenderState(D3DRS_STENCILZFAIL, stencilOpMap[value]);
}
break;
case STENCILPASS:
if(rwStateCache.stencilpass != value){
rwStateCache.stencilpass = value;
setRenderState(D3DRS_STENCILPASS, stencilOpMap[value]);
}
break;
case STENCILFUNCTION:
if(rwStateCache.stencilfunc != value){
rwStateCache.stencilfunc = value;
setRenderState(D3DRS_STENCILFUNC, stencilFuncMap[value]);
}
break;
case STENCILFUNCTIONREF:
if(rwStateCache.stencilref != value){
rwStateCache.stencilref = value;
setRenderState(D3DRS_STENCILREF, value);
}
break;
case STENCILFUNCTIONMASK:
if(rwStateCache.stencilmask != value){
rwStateCache.stencilmask = value;
setRenderState(D3DRS_STENCILMASK, value);
}
break;
case STENCILFUNCTIONWRITEMASK:
if(rwStateCache.stencilwritemask != value){
rwStateCache.stencilwritemask = value;
setRenderState(D3DRS_STENCILWRITEMASK, value);
}
break;
case ALPHATESTFUNC: case ALPHATESTFUNC:
if(rwStateCache.alphafunc != value){ if(rwStateCache.alphafunc != value){
rwStateCache.alphafunc = value; rwStateCache.alphafunc = value;
@@ -677,6 +800,32 @@ getRwRenderState(int32 state)
case CULLMODE: case CULLMODE:
val = rwStateCache.cullmode; val = rwStateCache.cullmode;
break; break;
case STENCILENABLE:
val = rwStateCache.stencilenable;
break;
case STENCILFAIL:
val = rwStateCache.stencilfail;
break;
case STENCILZFAIL:
val = rwStateCache.stencilzfail;
break;
case STENCILPASS:
val = rwStateCache.stencilpass;
break;
case STENCILFUNCTION:
val = rwStateCache.stencilfunc;
break;
case STENCILFUNCTIONREF:
val = rwStateCache.stencilref;
break;
case STENCILFUNCTIONMASK:
val = rwStateCache.stencilmask;
break;
case STENCILFUNCTIONWRITEMASK:
val = rwStateCache.stencilwritemask;
break;
case ALPHATESTFUNC: case ALPHATESTFUNC:
val = rwStateCache.alphafunc; val = rwStateCache.alphafunc;
break; break;
@@ -795,7 +944,10 @@ setRenderSurfaces(Camera *cam)
Raster *fbuf = cam->frameBuffer; Raster *fbuf = cam->frameBuffer;
assert(fbuf); assert(fbuf);
{ {
D3dRaster *natras = PLUGINOFFSET(D3dRaster, fbuf, nativeRasterOffset); if(fbuf->parent)
fbuf = fbuf->parent;
D3dRaster *natras = GETD3DRASTEREXT(fbuf);
assert(fbuf->type == Raster::CAMERA || fbuf->type == Raster::CAMERATEXTURE); assert(fbuf->type == Raster::CAMERA || fbuf->type == Raster::CAMERATEXTURE);
if(natras->texture == nil) if(natras->texture == nil)
setRenderTarget(0, d3d9Globals.defaultRenderTarget); setRenderTarget(0, d3d9Globals.defaultRenderTarget);
@@ -810,7 +962,10 @@ setRenderSurfaces(Camera *cam)
Raster *zbuf = cam->zBuffer; Raster *zbuf = cam->zBuffer;
if(zbuf){ if(zbuf){
D3dRaster *natras = PLUGINOFFSET(D3dRaster, zbuf, nativeRasterOffset); if(zbuf->parent)
zbuf = zbuf->parent;
D3dRaster *natras = GETD3DRASTEREXT(zbuf);
assert(zbuf->type == Raster::ZBUFFER); assert(zbuf->type == Raster::ZBUFFER);
setDepthSurface(natras->texture); setDepthSurface(natras->texture);
}else }else
@@ -818,6 +973,19 @@ setRenderSurfaces(Camera *cam)
} }
static void
setViewport(Raster *fb)
{
D3DVIEWPORT9 vp;
vp.MinZ = 0.0f;
vp.MaxZ = 1.0f;
vp.X = fb->offsetX;
vp.Y = fb->offsetY;
vp.Width = fb->width;
vp.Height = fb->height;
d3ddevice->SetViewport(&vp);
}
static void static void
beginUpdate(Camera *cam) beginUpdate(Camera *cam)
{ {
@@ -897,23 +1065,14 @@ beginUpdate(Camera *cam)
setRenderSurfaces(cam); setRenderSurfaces(cam);
D3DVIEWPORT9 vp; setViewport(cam->frameBuffer);
vp.MinZ = 0.0f;
vp.MaxZ = 1.0f;
vp.X = cam->frameBuffer->offsetX;
vp.Y = cam->frameBuffer->offsetY;
vp.Width = cam->frameBuffer->width;
vp.Height = cam->frameBuffer->height;
d3ddevice->SetViewport(&vp);
// TODO: figure out when to call this
d3ddevice->BeginScene(); d3ddevice->BeginScene();
} }
static void static void
endUpdate(Camera *cam) endUpdate(Camera *cam)
{ {
// TODO: figure out when to call this
d3ddevice->EndScene(); d3ddevice->EndScene();
} }
@@ -950,7 +1109,7 @@ releaseVidmemRasters(void)
D3dRaster *natras; D3dRaster *natras;
for(vmr = vidmemRasters; vmr; vmr = vmr->next){ for(vmr = vidmemRasters; vmr; vmr = vmr->next){
raster = vmr->raster; raster = vmr->raster;
natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); natras = GETD3DRASTEREXT(raster);
switch(raster->type){ switch(raster->type){
case Raster::CAMERATEXTURE: case Raster::CAMERATEXTURE:
destroyTexture(natras->texture); destroyTexture(natras->texture);
@@ -976,11 +1135,11 @@ recreateVidmemRasters(void)
D3dRaster *natras; D3dRaster *natras;
for(vmr = vidmemRasters; vmr; vmr = vmr->next){ for(vmr = vidmemRasters; vmr; vmr = vmr->next){
raster = vmr->raster; raster = vmr->raster;
natras = PLUGINOFFSET(D3dRaster, raster, nativeRasterOffset); natras = GETD3DRASTEREXT(raster);
switch(raster->type){ switch(raster->type){
case Raster::CAMERATEXTURE: { case Raster::CAMERATEXTURE: {
int32 levels = Raster::calculateNumLevels(raster->width, raster->height); int32 levels = Raster::calculateNumLevels(raster->width, raster->height);
IDirect3DTexture9 *tex; IDirect3DTexture9 *tex = nil;
d3ddevice->CreateTexture(raster->width, raster->height, d3ddevice->CreateTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? levels : 1, raster->format & Raster::MIPMAP ? levels : 1,
D3DUSAGE_RENDERTARGET, D3DUSAGE_RENDERTARGET,
@@ -1158,12 +1317,13 @@ clearCamera(Camera *cam, RGBA *col, uint32 mode)
mode |= D3DCLEAR_TARGET; mode |= D3DCLEAR_TARGET;
if(mode & Camera::CLEARZ) if(mode & Camera::CLEARZ)
mode |= D3DCLEAR_ZBUFFER; mode |= D3DCLEAR_ZBUFFER;
if(mode & Camera::CLEARSTENCIL)
mode |= D3DCLEAR_STENCIL;
D3DCOLOR c = D3DCOLOR_RGBA(col->red, col->green, col->blue, col->alpha); D3DCOLOR c = D3DCOLOR_RGBA(col->red, col->green, col->blue, col->alpha);
RECT r; RECT r;
GetClientRect(d3d9Globals.window, &r); GetClientRect(d3d9Globals.window, &r);
BOOL icon = IsIconic(d3d9Globals.window); BOOL icon = IsIconic(d3d9Globals.window);
Raster *ras = cam->frameBuffer;
if(!icon && if(!icon &&
(r.right != d3d9Globals.present.BackBufferWidth || r.bottom != d3d9Globals.present.BackBufferHeight)){ (r.right != d3d9Globals.present.BackBufferWidth || r.bottom != d3d9Globals.present.BackBufferHeight)){
@@ -1177,7 +1337,8 @@ clearCamera(Camera *cam, RGBA *col, uint32 mode)
setRenderSurfaces(cam); setRenderSurfaces(cam);
d3ddevice->Clear(0, 0, mode, c, 1.0f, 0); setViewport(cam->frameBuffer); // need to set this for the clear to work correctly
d3ddevice->Clear(0, nil, mode, c, 1.0f, 0);
} }
static void static void
@@ -1216,8 +1377,8 @@ rasterRenderFast(Raster *raster, int32 x, int32 y)
Raster *src = raster; Raster *src = raster;
Raster *dst = Raster::getCurrentContext(); Raster *dst = Raster::getCurrentContext();
D3dRaster *natdst = PLUGINOFFSET(D3dRaster, dst, nativeRasterOffset); D3dRaster *natdst = GETD3DRASTEREXT(dst);
D3dRaster *natsrc = PLUGINOFFSET(D3dRaster, src, nativeRasterOffset); D3dRaster *natsrc = GETD3DRASTEREXT(src);
switch(dst->type){ switch(dst->type){
case Raster::CAMERATEXTURE: case Raster::CAMERATEXTURE:
@@ -1440,7 +1601,8 @@ startD3D(void)
d3d9Globals.present.BackBufferHeight = height; d3d9Globals.present.BackBufferHeight = height;
d3d9Globals.present.BackBufferFormat = format; d3d9Globals.present.BackBufferFormat = format;
d3d9Globals.present.BackBufferCount = 1; d3d9Globals.present.BackBufferCount = 1;
d3d9Globals.present.MultiSampleType = D3DMULTISAMPLE_NONE; d3d9Globals.present.MultiSampleType = d3d9Globals.msLevel == 1 ?
D3DMULTISAMPLE_NONE : (D3DMULTISAMPLE_TYPE)d3d9Globals.msLevel;
d3d9Globals.present.MultiSampleQuality = 0; d3d9Globals.present.MultiSampleQuality = 0;
d3d9Globals.present.SwapEffect = D3DSWAPEFFECT_DISCARD; d3d9Globals.present.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3d9Globals.present.hDeviceWindow = d3d9Globals.window; d3d9Globals.present.hDeviceWindow = d3d9Globals.window;
@@ -1452,6 +1614,8 @@ startD3D(void)
// d3d9Globals.present.PresentationInterval = D3DPRESENT_INTERVAL_ONE; // d3d9Globals.present.PresentationInterval = D3DPRESENT_INTERVAL_ONE;
d3d9Globals.present.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE; d3d9Globals.present.PresentationInterval = D3DPRESENT_INTERVAL_IMMEDIATE;
rw::d3d::isP8supported = 0;
assert(d3d::d3ddevice == nil); assert(d3d::d3ddevice == nil);
BOOL icon = IsIconic(d3d9Globals.window); BOOL icon = IsIconic(d3d9Globals.window);
@@ -1471,6 +1635,7 @@ initD3D(void)
{ {
int32 s, t; int32 s, t;
memset(&deviceCache, 0, sizeof(deviceCache));
d3ddevice->GetRenderTarget(0, &d3d9Globals.defaultRenderTarget); d3ddevice->GetRenderTarget(0, &d3d9Globals.defaultRenderTarget);
d3d9Globals.defaultRenderTarget->Release(); // refcount increased by Get d3d9Globals.defaultRenderTarget->Release(); // refcount increased by Get
deviceCache.renderTargets[0] = d3d9Globals.defaultRenderTarget; deviceCache.renderTargets[0] = d3d9Globals.defaultRenderTarget;
@@ -1530,6 +1695,23 @@ initD3D(void)
rwStateCache.vertexAlpha = 0; rwStateCache.vertexAlpha = 0;
rwStateCache.textureAlpha = 0; rwStateCache.textureAlpha = 0;
rwStateCache.stencilenable = 0;
d3ddevice->SetRenderState(D3DRS_STENCILENABLE, FALSE);
rwStateCache.stencilfail = STENCILKEEP;
d3ddevice->SetRenderState(D3DRS_STENCILFAIL, D3DSTENCILOP_KEEP);
rwStateCache.stencilzfail = STENCILKEEP;
d3ddevice->SetRenderState(D3DRS_STENCILZFAIL, D3DSTENCILOP_KEEP);
rwStateCache.stencilpass = STENCILKEEP;
d3ddevice->SetRenderState(D3DRS_STENCILPASS, D3DSTENCILOP_KEEP);
rwStateCache.stencilfunc = STENCILALWAYS;
d3ddevice->SetRenderState(D3DRS_STENCILFUNC, D3DCMP_ALWAYS);
rwStateCache.stencilref = 0;
d3ddevice->SetRenderState(D3DRS_STENCILREF, 0);
rwStateCache.stencilmask = 0xFFFFFFFF;
d3ddevice->SetRenderState(D3DRS_STENCILMASK, 0xFFFFFFFF);
rwStateCache.stencilwritemask = 0xFFFFFFFF;
d3ddevice->SetRenderState(D3DRS_STENCILWRITEMASK, 0xFFFFFFFF);
setTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE); setTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE);
// setTextureStageState(0, D3DTSS_CONSTANT, 0xFFFFFFFF); // setTextureStageState(0, D3DTSS_CONSTANT, 0xFFFFFFFF);
// setTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1); // setTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1);
@@ -1684,6 +1866,17 @@ initD3D(void)
setAddressV(t, Texture::WRAP); setAddressV(t, Texture::WRAP);
} }
IDirect3DSurface9 *surf;
D3DLOCKED_RECT lr;
uint8 whitepixel[4] = {0xFF, 0xFF, 0xFF, 0xFF};
whiteTex = (IDirect3DTexture9*)createTexture(1, 1, 1, 0, D3DFMT_X8R8G8B8);
whiteTex->GetSurfaceLevel(0, &surf);
HRESULT res = surf->LockRect(&lr, 0, D3DLOCK_NOSYSLOCK);
assert(res == D3D_OK);
memcpy(lr.pBits, whitepixel, 4);
surf->UnlockRect();
surf->Release();
openIm2D(); openIm2D();
openIm3D(); openIm3D();
@@ -1696,6 +1889,9 @@ termD3D(void)
destroyVertexBuffer(constantVertexStream); destroyVertexBuffer(constantVertexStream);
constantVertexStream = nil; constantVertexStream = nil;
destroyTexture(whiteTex);
whiteTex = nil;
closeIm3D(); closeIm3D();
closeIm2D(); closeIm2D();
@@ -1778,6 +1974,26 @@ deviceSystem(DeviceReq req, void *arg, int32 n)
rwmode->depth = findFormatDepth(d3d9Globals.modes[n].mode.Format); rwmode->depth = findFormatDepth(d3d9Globals.modes[n].mode.Format);
rwmode->flags = d3d9Globals.modes[n].flags; rwmode->flags = d3d9Globals.modes[n].flags;
return 1; return 1;
case DEVICEGETMAXMULTISAMPLINGLEVELS:
{
assert(d3d9Globals.d3d9 != nil);
uint32 level;
DWORD quality;
for (level = D3DMULTISAMPLE_16_SAMPLES; level > D3DMULTISAMPLE_NONMASKABLE; level--) {
if (SUCCEEDED(d3d9Globals.d3d9->CheckDeviceMultiSampleType(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, d3d9Globals.startMode.mode.Format,
!(d3d9Globals.startMode.flags & VIDEOMODEEXCLUSIVE), (D3DMULTISAMPLE_TYPE)level,
&quality)))
return level;
}
}
return 1;
case DEVICEGETMULTISAMPLINGLEVELS:
if(d3d9Globals.msLevel == 0)
return 1;
return d3d9Globals.msLevel;
case DEVICESETMULTISAMPLINGLEVELS:
d3d9Globals.msLevel = (uint32)n;
return 1;
} }
return 1; return 1;
} }
+23 -1
View File
@@ -43,7 +43,9 @@ void
openIm2D(void) openIm2D(void)
{ {
D3DVERTEXELEMENT9 elements[4] = { D3DVERTEXELEMENT9 elements[4] = {
{ 0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITIONT, 0 }, // can't get proper fog with this :(
// { 0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITIONT, 0 },
{ 0, 0, D3DDECLTYPE_FLOAT4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0 },
{ 0, offsetof(Im2DVertex, color), D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0 }, { 0, offsetof(Im2DVertex, color), D3DDECLTYPE_D3DCOLOR, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR, 0 },
{ 0, offsetof(Im2DVertex, u), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0 }, { 0, offsetof(Im2DVertex, u), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0 },
D3DDECL_END() D3DDECL_END()
@@ -99,6 +101,20 @@ im2DRenderTriangle(void *vertices, int32 numVertices, int32 vert1, int32 vert2,
im2DRenderPrimitive(PRIMTYPETRILIST, tmpprimbuf, 3); im2DRenderPrimitive(PRIMTYPETRILIST, tmpprimbuf, 3);
} }
void
im2DSetXform(void)
{
float xform[4];
Camera *cam;
cam = (Camera*)engine->currentCamera;
xform[0] = 2.0f/cam->frameBuffer->width;
xform[1] = -2.0f/cam->frameBuffer->height;
xform[2] = -1.0f;
xform[3] = 1.0f;
// TODO: should cache this...
d3ddevice->SetVertexShaderConstantF(VSLOC_afterLights, xform, 1);
}
void void
im2DRenderPrimitive(PrimitiveType primType, void *vertices, int32 numVertices) im2DRenderPrimitive(PrimitiveType primType, void *vertices, int32 numVertices)
{ {
@@ -113,6 +129,9 @@ im2DRenderPrimitive(PrimitiveType primType, void *vertices, int32 numVertices)
setStreamSource(0, im2dvertbuf, 0, sizeof(Im2DVertex)); setStreamSource(0, im2dvertbuf, 0, sizeof(Im2DVertex));
setVertexDeclaration(im2ddecl); setVertexDeclaration(im2ddecl);
im2DSetXform();
setVertexShader(im2d_VS);
if(im2dOverridePS) if(im2dOverridePS)
setPixelShader(im2dOverridePS); setPixelShader(im2dOverridePS);
else if(engine->device.getRenderState(TEXTURERASTER)) else if(engine->device.getRenderState(TEXTURERASTER))
@@ -167,6 +186,9 @@ im2DRenderIndexedPrimitive(PrimitiveType primType,
setIndices(im2dindbuf); setIndices(im2dindbuf);
setVertexDeclaration(im2ddecl); setVertexDeclaration(im2ddecl);
im2DSetXform();
setVertexShader(im2d_VS);
if(im2dOverridePS) if(im2dOverridePS)
setPixelShader(im2dOverridePS); setPixelShader(im2dOverridePS);
else if(engine->device.getRenderState(TEXTURERASTER)) else if(engine->device.getRenderState(TEXTURERASTER))
+9
View File
@@ -27,6 +27,7 @@ void *default_amb_dir_VS;
void *default_all_VS; void *default_all_VS;
void *default_PS; void *default_PS;
void *default_tex_PS; void *default_tex_PS;
void *im2d_VS;
void *im2d_PS; void *im2d_PS;
void *im2d_tex_PS; void *im2d_tex_PS;
@@ -66,6 +67,12 @@ createDefaultShaders(void)
assert(default_tex_PS); assert(default_tex_PS);
} }
{
static
#include "shaders/im2d_VS.h"
im2d_VS = createVertexShader((void*)VS_NAME);
assert(im2d_VS);
}
{ {
static static
#include "shaders/im2d_PS.h" #include "shaders/im2d_PS.h"
@@ -95,6 +102,8 @@ destroyDefaultShaders(void)
destroyPixelShader(default_tex_PS); destroyPixelShader(default_tex_PS);
default_tex_PS = nil; default_tex_PS = nil;
destroyVertexShader(im2d_VS);
im2d_VS = nil;
destroyPixelShader(im2d_PS); destroyPixelShader(im2d_PS);
im2d_PS = nil; im2d_PS = nil;
destroyPixelShader(im2d_tex_PS); destroyPixelShader(im2d_tex_PS);
+129 -9
View File
@@ -64,15 +64,17 @@ struct Im3DVertex
struct Im2DVertex struct Im2DVertex
{ {
float32 x, y, z; float32 x, y, z;
float32 q; //float32 q; // recipz no longer used because we have a vertex stage now
float32 w;
uint32 color; uint32 color;
float32 u, v; float32 u, v;
void setScreenX(float32 x) { this->x = x; } void setScreenX(float32 x) { this->x = x; }
void setScreenY(float32 y) { this->y = y; } void setScreenY(float32 y) { this->y = y; }
void setScreenZ(float32 z) { this->z = z; } void setScreenZ(float32 z) { this->z = z; }
void setCameraZ(float32 z) { } void setCameraZ(float32 z) { this->w = z; }
void setRecipCameraZ(float32 recipz) { this->q = recipz; } // void setRecipCameraZ(float32 recipz) { this->q = recipz; }
void setRecipCameraZ(float32 recipz) { this->w = 1.0f/recipz; }
void setColor(uint8 r, uint8 g, uint8 b, uint8 a) { this->color = COLOR_ARGB(a, r, g, b); } void setColor(uint8 r, uint8 g, uint8 b, uint8 a) { this->color = COLOR_ARGB(a, r, g, b); }
void setU(float32 u, float recipZ) { this->u = u; } void setU(float32 u, float recipZ) { this->u = u; }
void setV(float32 v, float recipZ) { this->v = v; } void setV(float32 v, float recipZ) { this->v = v; }
@@ -80,8 +82,10 @@ struct Im2DVertex
float getScreenX(void) { return this->x; } float getScreenX(void) { return this->x; }
float getScreenY(void) { return this->y; } float getScreenY(void) { return this->y; }
float getScreenZ(void) { return this->z; } float getScreenZ(void) { return this->z; }
float getCameraZ(void) { return 1.0f/this->q; } // float getCameraZ(void) { return 1.0f/this->q; }
float getRecipCameraZ(void) { return this->q; } // float getRecipCameraZ(void) { return this->q; }
float getCameraZ(void) { return this->w; }
float getRecipCameraZ(void) { return 1.0f/this->w; }
RGBA getColor(void) { return makeRGBA(this->color>>16 & 0xFF, this->color>>8 & 0xFF, RGBA getColor(void) { return makeRGBA(this->color>>16 & 0xFF, this->color>>8 & 0xFF,
this->color & 0xFF, this->color>>24 & 0xFF); } this->color & 0xFF, this->color>>24 & 0xFF); }
float getU(void) { return this->u; } float getU(void) { return this->u; }
@@ -89,6 +93,105 @@ struct Im2DVertex
}; };
#else #else
#ifndef MAKEFOURCC
#define MAKEFOURCC(ch0, ch1, ch2, ch3) \
((uint32)(uint8)(ch0) | ((uint32)(uint8)(ch1) << 8) | \
((uint32)(uint8)(ch2) << 16) | ((uint32)(uint8)(ch3) << 24 ))
#endif
enum {
D3DFMT_UNKNOWN = 0,
D3DFMT_R8G8B8 = 20,
D3DFMT_A8R8G8B8 = 21,
D3DFMT_X8R8G8B8 = 22,
D3DFMT_R5G6B5 = 23,
D3DFMT_X1R5G5B5 = 24,
D3DFMT_A1R5G5B5 = 25,
D3DFMT_A4R4G4B4 = 26,
D3DFMT_R3G3B2 = 27,
D3DFMT_A8 = 28,
D3DFMT_A8R3G3B2 = 29,
D3DFMT_X4R4G4B4 = 30,
D3DFMT_A2B10G10R10 = 31,
D3DFMT_A8B8G8R8 = 32,
D3DFMT_X8B8G8R8 = 33,
D3DFMT_G16R16 = 34,
D3DFMT_A2R10G10B10 = 35,
D3DFMT_A16B16G16R16 = 36,
D3DFMT_A8P8 = 40,
D3DFMT_P8 = 41,
D3DFMT_L8 = 50,
D3DFMT_A8L8 = 51,
D3DFMT_A4L4 = 52,
D3DFMT_V8U8 = 60,
D3DFMT_L6V5U5 = 61,
D3DFMT_X8L8V8U8 = 62,
D3DFMT_Q8W8V8U8 = 63,
D3DFMT_V16U16 = 64,
D3DFMT_A2W10V10U10 = 67,
D3DFMT_UYVY = MAKEFOURCC('U', 'Y', 'V', 'Y'),
D3DFMT_R8G8_B8G8 = MAKEFOURCC('R', 'G', 'B', 'G'),
D3DFMT_YUY2 = MAKEFOURCC('Y', 'U', 'Y', '2'),
D3DFMT_G8R8_G8B8 = MAKEFOURCC('G', 'R', 'G', 'B'),
D3DFMT_DXT1 = MAKEFOURCC('D', 'X', 'T', '1'),
D3DFMT_DXT2 = MAKEFOURCC('D', 'X', 'T', '2'),
D3DFMT_DXT3 = MAKEFOURCC('D', 'X', 'T', '3'),
D3DFMT_DXT4 = MAKEFOURCC('D', 'X', 'T', '4'),
D3DFMT_DXT5 = MAKEFOURCC('D', 'X', 'T', '5'),
D3DFMT_D16_LOCKABLE = 70,
D3DFMT_D32 = 71,
D3DFMT_D15S1 = 73,
D3DFMT_D24S8 = 75,
D3DFMT_D24X8 = 77,
D3DFMT_D24X4S4 = 79,
D3DFMT_D16 = 80,
D3DFMT_D32F_LOCKABLE = 82,
D3DFMT_D24FS8 = 83,
// d3d9ex only
/* Z-Stencil formats valid for CPU access */
D3DFMT_D32_LOCKABLE = 84,
D3DFMT_S8_LOCKABLE = 85,
D3DFMT_L16 = 81,
D3DFMT_VERTEXDATA =100,
D3DFMT_INDEX16 =101,
D3DFMT_INDEX32 =102,
D3DFMT_Q16W16V16U16 =110,
D3DFMT_MULTI2_ARGB8 = MAKEFOURCC('M','E','T','1'),
// Floating point surface formats
// s10e5 formats (16-bits per channel)
D3DFMT_R16F = 111,
D3DFMT_G16R16F = 112,
D3DFMT_A16B16G16R16F = 113,
// IEEE s23e8 formats (32-bits per channel)
D3DFMT_R32F = 114,
D3DFMT_G32R32F = 115,
D3DFMT_A32B32G32R32F = 116,
D3DFMT_CxV8U8 = 117,
// d3d9ex only
// Monochrome 1 bit per pixel format
D3DFMT_A1 = 118,
// 2.8 biased fixed point
D3DFMT_A2B10G10R10_XR_BIAS = 119,
// Binary format indicating that the data has no inherent type
D3DFMT_BINARYBUFFER = 199
};
enum { enum {
D3DLOCK_NOSYSLOCK = 0, // ignored D3DLOCK_NOSYSLOCK = 0, // ignored
D3DPOOL_MANAGED = 0, // ignored D3DPOOL_MANAGED = 0, // ignored
@@ -135,6 +238,9 @@ enum {
D3DDECLUSAGE_FOG, // 11 D3DDECLUSAGE_FOG, // 11
D3DDECLUSAGE_DEPTH, // 12 D3DDECLUSAGE_DEPTH, // 12
D3DDECLUSAGE_SAMPLE // 13 D3DDECLUSAGE_SAMPLE // 13
,
D3DUSAGE_AUTOGENMIPMAP = 0x400
}; };
#endif #endif
@@ -150,7 +256,7 @@ void destroyVertexBuffer(void *vertexBuffer);
uint8 *lockVertices(void *vertexBuffer, uint32 offset, uint32 size, uint32 flags); uint8 *lockVertices(void *vertexBuffer, uint32 offset, uint32 size, uint32 flags);
void unlockVertices(void *vertexBuffer); void unlockVertices(void *vertexBuffer);
void *createTexture(int32 width, int32 height, int32 levels, uint32 format); void *createTexture(int32 width, int32 height, int32 levels, uint32 usage, uint32 format);
void destroyTexture(void *texture); void destroyTexture(void *texture);
uint8 *lockTexture(void *texture, int32 level); uint8 *lockTexture(void *texture, int32 level);
void unlockTexture(void *texture, int32 level); void unlockTexture(void *texture, int32 level);
@@ -164,8 +270,9 @@ struct D3dRaster
void *lockedSurf; void *lockedSurf;
uint32 format; uint32 format;
uint32 bpp; // bytes per pixel uint32 bpp; // bytes per pixel
bool32 hasAlpha; bool hasAlpha;
bool32 customFormat; bool customFormat;
bool autogenMipmap;
}; };
int32 getLevelSize(Raster *raster, int32 level); int32 getLevelSize(Raster *raster, int32 level);
@@ -175,6 +282,7 @@ void setTexels(Raster *raster, void *texels, int32 level);
extern int32 nativeRasterOffset; extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);
#define GETD3DRASTEREXT(raster) PLUGINOFFSET(rw::d3d::D3dRaster, raster, rw::d3d::nativeRasterOffset)
// Rendering // Rendering
@@ -187,7 +295,15 @@ void getSamplerState(uint32 stage, uint32 type, uint32 *value);
void flushCache(void); void flushCache(void);
void setTexture(uint32 stage, Texture *tex); void setTexture(uint32 stage, Texture *tex);
void setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops); void setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops, float extraSurfProp = 0.0f);
inline void setMaterial(uint32 flags, const RGBA &color, const SurfaceProperties &surfaceprops, float extraSurfProp = 0.0f)
{
static RGBA white = { 255, 255, 255, 255 };
if(flags & Geometry::MODULATE)
setMaterial(color, surfaceprops, extraSurfProp);
else
setMaterial(white, surfaceprops, extraSurfProp);
}
void setVertexShader(void *vs); void setVertexShader(void *vs);
void setPixelShader(void *ps); void setPixelShader(void *ps);
@@ -226,6 +342,7 @@ struct D3dShaderState
} fogData, fogDisable; } fogData, fogDisable;
RGBA matColor; RGBA matColor;
SurfaceProperties surfProps; SurfaceProperties surfProps;
float extraSurfProp;
float lightOffset[3]; float lightOffset[3];
int32 numDir, numPoint, numSpot; int32 numDir, numPoint, numSpot;
RGBAf ambient; RGBAf ambient;
@@ -272,6 +389,8 @@ int32 lightingCB_Shader(Atomic *atomic);
// for VS // for VS
void uploadMatrices(void); // no world transform void uploadMatrices(void); // no world transform
void uploadMatrices(Matrix *worldMat); void uploadMatrices(Matrix *worldMat);
void setAmbient(const RGBAf &color);
void setNumLights(int numDir, int numPoint, int numSpot);
int32 uploadLights(WorldLights *lightData); // called by lightingCB_Shader int32 uploadLights(WorldLights *lightData); // called by lightingCB_Shader
extern void *im2dOverridePS; extern void *im2dOverridePS;
@@ -281,6 +400,7 @@ extern void *default_amb_dir_VS;
extern void *default_all_VS; extern void *default_all_VS;
extern void *default_PS; extern void *default_PS;
extern void *default_tex_PS; extern void *default_tex_PS;
extern void *im2d_VS;
extern void *im2d_PS; extern void *im2d_PS;
extern void *im2d_tex_PS; extern void *im2d_tex_PS;
void createDefaultShaders(void); void createDefaultShaders(void);
+1
View File
@@ -94,6 +94,7 @@ ObjPipeline *makeDefaultPipeline(void);
void initSkin(void); void initSkin(void);
void uploadSkinMatrices(Atomic *atomic); void uploadSkinMatrices(Atomic *atomic);
void skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance); void skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance);
void skinRenderCB(Atomic *atomic, InstanceDataHeader *header);
ObjPipeline *makeSkinPipeline(void); ObjPipeline *makeSkinPipeline(void);
// MatFX plugin // MatFX plugin
+2
View File
@@ -36,6 +36,8 @@ struct D3d9Globals
int currentMode; int currentMode;
DisplayMode startMode; DisplayMode startMode;
uint32 msLevel;
D3DPRESENT_PARAMETERS present; D3DPRESENT_PARAMETERS present;
IDirect3DSurface9 *defaultRenderTarget; IDirect3DSurface9 *defaultRenderTarget;
+4 -1
View File
@@ -84,7 +84,9 @@ struct XboxRaster
void *texture; void *texture;
void *palette; void *palette;
uint32 format; uint32 format;
bool32 hasAlpha; uint32 bpp; // bytes per pixel
bool hasAlpha;
bool customFormat;
bool32 unknownFlag; bool32 unknownFlag;
}; };
@@ -92,6 +94,7 @@ int32 getLevelSize(Raster *raster, int32 level);
extern int32 nativeRasterOffset; extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);
#define GETXBOXRASTEREXT(raster) PLUGINOFFSET(rw::xbox::XboxRaster, raster, rw::xbox::nativeRasterOffset)
Texture *readNativeTexture(Stream *stream); Texture *readNativeTexture(Stream *stream);
void writeNativeTexture(Texture *tex, Stream *stream); void writeNativeTexture(Texture *tex, Stream *stream);
+44 -9
View File
@@ -4,22 +4,47 @@
// //
// fxc /nologo /T ps_2_0 /Fh im2d_PS.h im2d_PS.hlsl // fxc /nologo /T ps_2_0 /Fh im2d_PS.h im2d_PS.hlsl
// //
ps_2_0 //
dcl v0 // Parameters:
mov oC0, v0 //
// float4 fogColor;
//
//
// Registers:
//
// Name Reg Size
// ------------ ----- ----
// fogColor c0 1
//
// approximately 1 instruction slot used ps_2_0
dcl t0.xyz
dcl v0
add r0.xyz, v0, -c0
mad r0.xyz, t0.z, r0, c0
mov r0.w, v0.w
mov oC0, r0
// approximately 4 instruction slots used
#endif #endif
const BYTE g_ps20_main[] = const BYTE g_ps20_main[] =
{ {
0, 2, 255, 255, 254, 255, 0, 2, 255, 255, 254, 255,
22, 0, 67, 84, 65, 66, 34, 0, 67, 84, 65, 66,
28, 0, 0, 0, 35, 0, 28, 0, 0, 0, 83, 0,
0, 0, 0, 2, 255, 255, 0, 0, 0, 2, 255, 255,
0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
28, 0, 0, 0, 112, 115, 76, 0, 0, 0, 48, 0,
0, 0, 2, 0, 0, 0,
1, 0, 2, 0, 60, 0,
0, 0, 0, 0, 0, 0,
102, 111, 103, 67, 111, 108,
111, 114, 0, 171, 171, 171,
1, 0, 3, 0, 1, 0,
4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 112, 115,
95, 50, 95, 48, 0, 77, 95, 50, 95, 48, 0, 77,
105, 99, 114, 111, 115, 111, 105, 99, 114, 111, 115, 111,
102, 116, 32, 40, 82, 41, 102, 116, 32, 40, 82, 41,
@@ -29,9 +54,19 @@ const BYTE g_ps20_main[] =
108, 101, 114, 32, 57, 46, 108, 101, 114, 32, 57, 46,
50, 57, 46, 57, 53, 50, 50, 57, 46, 57, 53, 50,
46, 51, 49, 49, 49, 0, 46, 51, 49, 49, 49, 0,
31, 0, 0, 2, 0, 0,
0, 128, 0, 0, 7, 176,
31, 0, 0, 2, 0, 0, 31, 0, 0, 2, 0, 0,
0, 128, 0, 0, 15, 144, 0, 128, 0, 0, 15, 144,
2, 0, 0, 3, 0, 0,
7, 128, 0, 0, 228, 144,
0, 0, 228, 161, 4, 0,
0, 4, 0, 0, 7, 128,
0, 0, 170, 176, 0, 0,
228, 128, 0, 0, 228, 160,
1, 0, 0, 2, 0, 0,
8, 128, 0, 0, 255, 144,
1, 0, 0, 2, 0, 8, 1, 0, 0, 2, 0, 8,
15, 128, 0, 0, 228, 144, 15, 128, 0, 0, 228, 128,
255, 255, 0, 0 255, 255, 0, 0
}; };
+3 -1
View File
@@ -1,11 +1,12 @@
struct VS_out { struct VS_out {
float4 Position : POSITION; float4 Position : POSITION;
float2 TexCoord0 : TEXCOORD0; float3 TexCoord0 : TEXCOORD0;
float4 Color : COLOR0; float4 Color : COLOR0;
}; };
sampler2D tex0 : register(s0); sampler2D tex0 : register(s0);
float4 fogColor : register(c0);
float4 main(VS_out input) : COLOR float4 main(VS_out input) : COLOR
{ {
@@ -13,5 +14,6 @@ float4 main(VS_out input) : COLOR
#ifdef TEX #ifdef TEX
color *= tex2D(tex0, input.TexCoord0.xy); color *= tex2D(tex0, input.TexCoord0.xy);
#endif #endif
color.rgb = lerp(fogColor.rgb, color.rgb, input.TexCoord0.z);
return color; return color;
} }
+107
View File
@@ -0,0 +1,107 @@
#if 0
//
// Generated by Microsoft (R) HLSL Shader Compiler 9.29.952.3111
//
// fxc /nologo /T vs_2_0 /Fh im2d_VS.h im2d_VS.hlsl
//
//
// Parameters:
//
// float4 fogData;
// float4 xform;
//
//
// Registers:
//
// Name Reg Size
// ------------ ----- ----
// fogData c14 1
// xform c41 1
//
vs_2_0
def c0, 1, 0, 0, 0
dcl_position v0
dcl_texcoord v1
dcl_color v2
add r0.x, v0.w, -c14.y
mul r0.x, r0.x, c14.z
max r0.x, r0.x, c14.w
min oT0.z, r0.x, c0.x
mad r0.xy, v0, c41, c41.zwzw
mov r0.z, v0.z
mul oPos.xyz, r0, v0.w
mov oPos.w, v0.w
mov oT0.xy, v1
mov oD0, v2
// approximately 10 instruction slots used
#endif
const BYTE g_vs20_main[] =
{
0, 2, 254, 255, 254, 255,
40, 0, 67, 84, 65, 66,
28, 0, 0, 0, 105, 0,
0, 0, 0, 2, 254, 255,
2, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0,
98, 0, 0, 0, 68, 0,
0, 0, 2, 0, 14, 0,
1, 0, 58, 0, 76, 0,
0, 0, 0, 0, 0, 0,
92, 0, 0, 0, 2, 0,
41, 0, 1, 0, 166, 0,
76, 0, 0, 0, 0, 0,
0, 0, 102, 111, 103, 68,
97, 116, 97, 0, 1, 0,
3, 0, 1, 0, 4, 0,
1, 0, 0, 0, 0, 0,
0, 0, 120, 102, 111, 114,
109, 0, 118, 115, 95, 50,
95, 48, 0, 77, 105, 99,
114, 111, 115, 111, 102, 116,
32, 40, 82, 41, 32, 72,
76, 83, 76, 32, 83, 104,
97, 100, 101, 114, 32, 67,
111, 109, 112, 105, 108, 101,
114, 32, 57, 46, 50, 57,
46, 57, 53, 50, 46, 51,
49, 49, 49, 0, 171, 171,
81, 0, 0, 5, 0, 0,
15, 160, 0, 0, 128, 63,
0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0,
31, 0, 0, 2, 0, 0,
0, 128, 0, 0, 15, 144,
31, 0, 0, 2, 5, 0,
0, 128, 1, 0, 15, 144,
31, 0, 0, 2, 10, 0,
0, 128, 2, 0, 15, 144,
2, 0, 0, 3, 0, 0,
1, 128, 0, 0, 255, 144,
14, 0, 85, 161, 5, 0,
0, 3, 0, 0, 1, 128,
0, 0, 0, 128, 14, 0,
170, 160, 11, 0, 0, 3,
0, 0, 1, 128, 0, 0,
0, 128, 14, 0, 255, 160,
10, 0, 0, 3, 0, 0,
4, 224, 0, 0, 0, 128,
0, 0, 0, 160, 4, 0,
0, 4, 0, 0, 3, 128,
0, 0, 228, 144, 41, 0,
228, 160, 41, 0, 238, 160,
1, 0, 0, 2, 0, 0,
4, 128, 0, 0, 170, 144,
5, 0, 0, 3, 0, 0,
7, 192, 0, 0, 228, 128,
0, 0, 255, 144, 1, 0,
0, 2, 0, 0, 8, 192,
0, 0, 255, 144, 1, 0,
0, 2, 0, 0, 3, 224,
1, 0, 228, 144, 1, 0,
0, 2, 0, 0, 15, 208,
2, 0, 228, 144, 255, 255,
0, 0
};
+30
View File
@@ -0,0 +1,30 @@
#include "standardConstants.h"
struct VS_in
{
float4 Position : POSITION;
float2 TexCoord : TEXCOORD0;
float4 Color : COLOR0;
};
struct VS_out {
float4 Position : POSITION;
float3 TexCoord0 : TEXCOORD0;
float4 Color : COLOR0;
};
float4 xform : register(c41);
VS_out main(in VS_in input)
{
VS_out output;
output.Position = input.Position;
output.Position.xy = output.Position.xy * xform.xy + xform.zw;
output.TexCoord0.z = clamp((output.Position.w - fogEnd)*fogRange, fogDisable, 1.0);
output.Position.xyz *= output.Position.w;
output.Color = input.Color;
output.TexCoord0.xy = input.TexCoord;
return output;
}
+35 -17
View File
@@ -7,6 +7,7 @@
// //
// Parameters: // Parameters:
// //
// float4 fogColor;
// sampler2D tex0; // sampler2D tex0;
// //
// //
@@ -14,31 +15,42 @@
// //
// Name Reg Size // Name Reg Size
// ------------ ----- ---- // ------------ ----- ----
// fogColor c0 1
// tex0 s0 1 // tex0 s0 1
// //
ps_2_0 ps_2_0
dcl t0.xy dcl t0.xyz
dcl v0 dcl v0
dcl_2d s0 dcl_2d s0
texld r0, t0, s0 texld r0, t0, s0
mul r0, r0, v0 mad r0.xyz, v0, r0, -c0
mov oC0, r0 mul r1.w, r0.w, v0.w
mad r1.xyz, t0.z, r0, c0
mov oC0, r1
// approximately 3 instruction slots used (1 texture, 2 arithmetic) // approximately 5 instruction slots used (1 texture, 4 arithmetic)
#endif #endif
const BYTE g_ps20_main[] = const BYTE g_ps20_main[] =
{ {
0, 2, 255, 255, 254, 255, 0, 2, 255, 255, 254, 255,
33, 0, 67, 84, 65, 66, 45, 0, 67, 84, 65, 66,
28, 0, 0, 0, 79, 0, 28, 0, 0, 0, 127, 0,
0, 0, 0, 2, 255, 255, 0, 0, 0, 2, 255, 255,
1, 0, 0, 0, 28, 0, 2, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
72, 0, 0, 0, 48, 0, 120, 0, 0, 0, 68, 0,
0, 0, 3, 0, 0, 0, 0, 0, 2, 0, 0, 0,
1, 0, 2, 0, 56, 0, 1, 0, 2, 0, 80, 0,
0, 0, 0, 0, 0, 0,
96, 0, 0, 0, 3, 0,
0, 0, 1, 0, 2, 0,
104, 0, 0, 0, 0, 0,
0, 0, 102, 111, 103, 67,
111, 108, 111, 114, 0, 171,
171, 171, 1, 0, 3, 0,
1, 0, 4, 0, 1, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
116, 101, 120, 48, 0, 171, 116, 101, 120, 48, 0, 171,
171, 171, 4, 0, 12, 0, 171, 171, 4, 0, 12, 0,
@@ -55,17 +67,23 @@ const BYTE g_ps20_main[] =
53, 50, 46, 51, 49, 49, 53, 50, 46, 51, 49, 49,
49, 0, 31, 0, 0, 2, 49, 0, 31, 0, 0, 2,
0, 0, 0, 128, 0, 0, 0, 0, 0, 128, 0, 0,
3, 176, 31, 0, 0, 2, 7, 176, 31, 0, 0, 2,
0, 0, 0, 128, 0, 0, 0, 0, 0, 128, 0, 0,
15, 144, 31, 0, 0, 2, 15, 144, 31, 0, 0, 2,
0, 0, 0, 144, 0, 8, 0, 0, 0, 144, 0, 8,
15, 160, 66, 0, 0, 3, 15, 160, 66, 0, 0, 3,
0, 0, 15, 128, 0, 0, 0, 0, 15, 128, 0, 0,
228, 176, 0, 8, 228, 160, 228, 176, 0, 8, 228, 160,
5, 0, 0, 3, 0, 0, 4, 0, 0, 4, 0, 0,
15, 128, 0, 0, 228, 128, 7, 128, 0, 0, 228, 144,
0, 0, 228, 144, 1, 0, 0, 0, 228, 128, 0, 0,
0, 2, 0, 8, 15, 128, 228, 161, 5, 0, 0, 3,
0, 0, 228, 128, 255, 255, 1, 0, 8, 128, 0, 0,
0, 0 255, 128, 0, 0, 255, 144,
4, 0, 0, 4, 1, 0,
7, 128, 0, 0, 170, 176,
0, 0, 228, 128, 0, 0,
228, 160, 1, 0, 0, 2,
0, 8, 15, 128, 1, 0,
228, 128, 255, 255, 0, 0
}; };
+1 -1
View File
@@ -11,7 +11,7 @@ float3 DoDirLight(Light L, float3 N)
return l*L.color.xyz; return l*L.color.xyz;
} }
float3 DoDirLightSpec(Light L, float3 N, float3 V, float power)) float3 DoDirLightSpec(Light L, float3 N, float3 V, float power)
{ {
return pow(saturate(dot(N, normalize(V + -L.direction.xyz))), power)*L.color.xyz; return pow(saturate(dot(N, normalize(V + -L.direction.xyz))), power)*L.color.xyz;
} }
+1
View File
@@ -6,5 +6,6 @@
"%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /Fh default_PS.h default_PS.hlsl "%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /Fh default_PS.h default_PS.hlsl
"%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /DTEX /Fh default_tex_PS.h default_PS.hlsl "%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /DTEX /Fh default_tex_PS.h default_PS.hlsl
"%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T vs_2_0 /Fh im2d_VS.h im2d_VS.hlsl
"%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /Fh im2d_PS.h im2d_PS.hlsl "%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /Fh im2d_PS.h im2d_PS.hlsl
"%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /DTEX /Fh im2d_tex_PS.h im2d_PS.hlsl "%DXSDK_DIR%\utilities\bin\x86\fxc.exe" /nologo /T ps_2_0 /DTEX /Fh im2d_tex_PS.h im2d_PS.hlsl
+67 -74
View File
@@ -7,7 +7,6 @@
// //
// Parameters: // Parameters:
// //
// float4 colorClamp;
// sampler2D envTex; // sampler2D envTex;
// float4 fogColor; // float4 fogColor;
// float4 fxparams; // float4 fxparams;
@@ -19,7 +18,6 @@
// ------------ ----- ---- // ------------ ----- ----
// fogColor c0 1 // fogColor c0 1
// fxparams c1 1 // fxparams c1 1
// colorClamp c2 1
// envTex s1 1 // envTex s1 1
// //
@@ -27,10 +25,10 @@
dcl t0.xyz dcl t0.xyz
dcl t1.xy dcl t1.xy
dcl v0 dcl v0
dcl v1.xyz
dcl_2d s1 dcl_2d s1
texld r0, t1, s1 texld r0, t1, s1
max r1.xyz, v0, c2 mul r1.xyz, v1, c1.x
mul r1.xyz, r1, c1.x
mul r0.xyz, r0, r1 mul r0.xyz, r0, r1
mul r0.xyz, r0, t0.z mul r0.xyz, r0, t0.z
max r0.w, v0.w, c1.y max r0.w, v0.w, c1.y
@@ -41,91 +39,86 @@
mov r0.w, v0.w mov r0.w, v0.w
mov oC0, r0 mov oC0, r0
// approximately 12 instruction slots used (1 texture, 11 arithmetic) // approximately 11 instruction slots used (1 texture, 10 arithmetic)
#endif #endif
const BYTE g_ps20_main[] = const BYTE g_ps20_main[] =
{ {
0, 2, 255, 255, 254, 255, 0, 2, 255, 255, 254, 255,
60, 0, 67, 84, 65, 66, 53, 0, 67, 84, 65, 66,
28, 0, 0, 0, 185, 0, 28, 0, 0, 0, 156, 0,
0, 0, 0, 2, 255, 255, 0, 0, 0, 2, 255, 255,
4, 0, 0, 0, 28, 0, 3, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
178, 0, 0, 0, 108, 0, 149, 0, 0, 0, 88, 0,
0, 0, 2, 0, 2, 0, 0, 0, 3, 0, 1, 0,
1, 0, 10, 0, 120, 0, 1, 0, 6, 0, 96, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
136, 0, 0, 0, 3, 0, 112, 0, 0, 0, 2, 0,
1, 0, 1, 0, 6, 0, 0, 0, 1, 0, 2, 0,
144, 0, 0, 0, 0, 0, 124, 0, 0, 0, 0, 0,
0, 0, 160, 0, 0, 0, 0, 0, 140, 0, 0, 0,
2, 0, 0, 0, 1, 0, 2, 0, 1, 0, 1, 0,
2, 0, 120, 0, 0, 0, 6, 0, 124, 0, 0, 0,
0, 0, 0, 0, 169, 0,
0, 0, 2, 0, 1, 0,
1, 0, 6, 0, 120, 0,
0, 0, 0, 0, 0, 0,
99, 111, 108, 111, 114, 67,
108, 97, 109, 112, 0, 171,
1, 0, 3, 0, 1, 0,
4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 101, 110, 0, 0, 0, 0, 101, 110,
118, 84, 101, 120, 0, 171, 118, 84, 101, 120, 0, 171,
4, 0, 12, 0, 1, 0, 4, 0, 12, 0, 1, 0,
1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0,
0, 0, 0, 0, 102, 111, 0, 0, 0, 0, 102, 111,
103, 67, 111, 108, 111, 114, 103, 67, 111, 108, 111, 114,
0, 102, 120, 112, 97, 114, 0, 171, 171, 171, 1, 0,
97, 109, 115, 0, 112, 115, 3, 0, 1, 0, 4, 0,
95, 50, 95, 48, 0, 77, 1, 0, 0, 0, 0, 0,
105, 99, 114, 111, 115, 111, 0, 0, 102, 120, 112, 97,
102, 116, 32, 40, 82, 41, 114, 97, 109, 115, 0, 112,
32, 72, 76, 83, 76, 32, 115, 95, 50, 95, 48, 0,
83, 104, 97, 100, 101, 114, 77, 105, 99, 114, 111, 115,
32, 67, 111, 109, 112, 105, 111, 102, 116, 32, 40, 82,
108, 101, 114, 32, 57, 46, 41, 32, 72, 76, 83, 76,
50, 57, 46, 57, 53, 50, 32, 83, 104, 97, 100, 101,
46, 51, 49, 49, 49, 0, 114, 32, 67, 111, 109, 112,
171, 171, 31, 0, 0, 2, 105, 108, 101, 114, 32, 57,
0, 0, 0, 128, 0, 0, 46, 50, 57, 46, 57, 53,
7, 176, 31, 0, 0, 2, 50, 46, 51, 49, 49, 49,
0, 0, 0, 128, 1, 0, 0, 171, 171, 171, 31, 0,
3, 176, 31, 0, 0, 2, 0, 2, 0, 0, 0, 128,
0, 0, 0, 128, 0, 0, 0, 0, 7, 176, 31, 0,
15, 144, 31, 0, 0, 2, 0, 2, 0, 0, 0, 128,
0, 0, 0, 144, 1, 8, 1, 0, 3, 176, 31, 0,
15, 160, 66, 0, 0, 3, 0, 2, 0, 0, 0, 128,
0, 0, 15, 128, 1, 0, 0, 0, 15, 144, 31, 0,
228, 176, 1, 8, 228, 160, 0, 2, 0, 0, 0, 128,
11, 0, 0, 3, 1, 0, 1, 0, 7, 144, 31, 0,
7, 128, 0, 0, 228, 144, 0, 2, 0, 0, 0, 144,
2, 0, 228, 160, 5, 0, 1, 8, 15, 160, 66, 0,
0, 3, 1, 0, 7, 128, 0, 3, 0, 0, 15, 128,
1, 0, 228, 128, 1, 0, 1, 0, 228, 176, 1, 8,
0, 160, 5, 0, 0, 3, 228, 160, 5, 0, 0, 3,
0, 0, 7, 128, 0, 0, 1, 0, 7, 128, 1, 0,
228, 128, 1, 0, 228, 128, 228, 144, 1, 0, 0, 160,
5, 0, 0, 3, 0, 0, 5, 0, 0, 3, 0, 0,
7, 128, 0, 0, 228, 128, 7, 128, 0, 0, 228, 128,
0, 0, 170, 176, 11, 0, 1, 0, 228, 128, 5, 0,
0, 3, 0, 0, 8, 128, 0, 3, 0, 0, 7, 128,
0, 0, 255, 144, 1, 0, 0, 0, 228, 128, 0, 0,
85, 160, 5, 0, 0, 3, 170, 176, 11, 0, 0, 3,
0, 0, 7, 128, 0, 0,
255, 128, 0, 0, 228, 128,
2, 0, 0, 3, 1, 0,
7, 128, 0, 0, 228, 144,
0, 0, 228, 161, 4, 0,
0, 4, 1, 0, 7, 128,
0, 0, 170, 176, 1, 0,
228, 128, 0, 0, 228, 160,
4, 0, 0, 4, 0, 0,
7, 128, 1, 0, 228, 128,
0, 0, 255, 144, 0, 0,
228, 128, 1, 0, 0, 2,
0, 0, 8, 128, 0, 0, 0, 0, 8, 128, 0, 0,
255, 144, 1, 0, 0, 2, 255, 144, 1, 0, 85, 160,
0, 8, 15, 128, 0, 0, 5, 0, 0, 3, 0, 0,
228, 128, 255, 255, 0, 0 7, 128, 0, 0, 255, 128,
0, 0, 228, 128, 2, 0,
0, 3, 1, 0, 7, 128,
0, 0, 228, 144, 0, 0,
228, 161, 4, 0, 0, 4,
1, 0, 7, 128, 0, 0,
170, 176, 1, 0, 228, 128,
0, 0, 228, 160, 4, 0,
0, 4, 0, 0, 7, 128,
1, 0, 228, 128, 0, 0,
255, 144, 0, 0, 228, 128,
1, 0, 0, 2, 0, 0,
8, 128, 0, 0, 255, 144,
1, 0, 0, 2, 0, 8,
15, 128, 0, 0, 228, 128,
255, 255, 0, 0
}; };
+2 -3
View File
@@ -3,6 +3,7 @@ struct VS_out {
float3 TexCoord0 : TEXCOORD0; float3 TexCoord0 : TEXCOORD0;
float2 TexCoord1 : TEXCOORD1; float2 TexCoord1 : TEXCOORD1;
float4 Color : COLOR0; float4 Color : COLOR0;
float4 EnvColor : COLOR1;
}; };
sampler2D diffTex : register(s0); sampler2D diffTex : register(s0);
@@ -11,7 +12,6 @@ sampler2D envTex : register(s1);
float4 fogColor : register(c0); float4 fogColor : register(c0);
float4 fxparams : register(c1); float4 fxparams : register(c1);
float4 colorClamp : register(c2);
#define shininess (fxparams.x) #define shininess (fxparams.x)
#define disableFBA (fxparams.y) #define disableFBA (fxparams.y)
@@ -19,12 +19,11 @@ float4 colorClamp : register(c2);
float4 main(VS_out input) : COLOR float4 main(VS_out input) : COLOR
{ {
float4 pass1 = input.Color; float4 pass1 = input.Color;
float4 envColor = max(pass1, colorClamp);
#ifdef TEX #ifdef TEX
pass1 *= tex2D(diffTex, input.TexCoord0.xy); pass1 *= tex2D(diffTex, input.TexCoord0.xy);
#endif #endif
float4 pass2 = envColor*shininess*tex2D(envTex, input.TexCoord1.xy); float4 pass2 = input.EnvColor*shininess*tex2D(envTex, input.TexCoord1.xy);
pass1.rgb = lerp(fogColor.rgb, pass1.rgb, input.TexCoord0.z); pass1.rgb = lerp(fogColor.rgb, pass1.rgb, input.TexCoord0.z);
pass2.rgb = lerp(float3(0.0, 0.0, 0.0), pass2.rgb, input.TexCoord0.z); pass2.rgb = lerp(float3(0.0, 0.0, 0.0), pass2.rgb, input.TexCoord0.z);
+4
View File
@@ -1,6 +1,8 @@
#include "standardConstants.h" #include "standardConstants.h"
float4x4 texMat : register(c41); float4x4 texMat : register(c41);
float4 colorClamp : register(c45);
float4 envColor : register(c46);
struct VS_in struct VS_in
{ {
@@ -15,6 +17,7 @@ struct VS_out {
float3 TexCoord0 : TEXCOORD0; // also fog float3 TexCoord0 : TEXCOORD0; // also fog
float2 TexCoord1 : TEXCOORD1; float2 TexCoord1 : TEXCOORD1;
float4 Color : COLOR0; float4 Color : COLOR0;
float4 EnvColor : COLOR1;
}; };
@@ -47,6 +50,7 @@ VS_out main(in VS_in input)
#endif #endif
// PS2 clamps before material color // PS2 clamps before material color
output.Color = clamp(output.Color, 0.0, 1.0); output.Color = clamp(output.Color, 0.0, 1.0);
output.EnvColor = max(output.Color, colorClamp) * envColor;
output.Color *= matCol; output.Color *= matCol;
output.TexCoord0.z = clamp((output.Position.w - fogEnd)*fogRange, fogDisable, 1.0); output.TexCoord0.z = clamp((output.Position.w - fogEnd)*fogRange, fogDisable, 1.0);
+93 -72
View File
@@ -9,7 +9,9 @@
// Parameters: // Parameters:
// //
// float4 ambientLight; // float4 ambientLight;
// float4 colorClamp;
// float4x4 combinedMat; // float4x4 combinedMat;
// float4 envColor;
// int4 firstLight; // int4 firstLight;
// float4 fogData; // float4 fogData;
// //
@@ -48,6 +50,8 @@
// firstLight c16 1 // firstLight c16 1
// lights c17 24 // lights c17 24
// texMat c41 4 // texMat c41 4
// colorClamp c45 1
// envColor c46 1
// //
vs_2_0 vs_2_0
@@ -141,79 +145,91 @@
mad r0.xy, c41, r1.x, r0 mad r0.xy, c41, r1.x, r0
mad r0.xy, c43, r1.z, r0 mad r0.xy, c43, r1.z, r0
add oT1.xy, r0, c44 add oT1.xy, r0, c44
max r1, r2, c45
mul oD1, r1, c46
add r0.x, r0.w, -c14.y add r0.x, r0.w, -c14.y
mul r0.x, r0.x, c14.z mul r0.x, r0.x, c14.z
max r0.x, r0.x, c14.w max r0.x, r0.x, c14.w
min oT0.z, r0.x, c11.z min oT0.z, r0.x, c11.z
mov oT0.xy, v2 mov oT0.xy, v2
// approximately 99 instruction slots used // approximately 101 instruction slots used
#endif #endif
const BYTE g_vs20_main[] = const BYTE g_vs20_main[] =
{ {
0, 2, 254, 255, 254, 255, 0, 2, 254, 255, 254, 255,
165, 0, 67, 84, 65, 66, 180, 0, 67, 84, 65, 66,
28, 0, 0, 0, 94, 2, 28, 0, 0, 0, 154, 2,
0, 0, 0, 2, 254, 255, 0, 0, 0, 2, 254, 255,
13, 0, 0, 0, 28, 0, 15, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
87, 2, 0, 0, 32, 1, 147, 2, 0, 0, 72, 1,
0, 0, 2, 0, 15, 0, 0, 0, 2, 0, 15, 0,
1, 0, 62, 0, 48, 1, 1, 0, 62, 0, 88, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
64, 1, 0, 0, 2, 0, 104, 1, 0, 0, 2, 0,
0, 0, 4, 0, 2, 0, 45, 0, 1, 0, 182, 0,
76, 1, 0, 0, 0, 0, 88, 1, 0, 0, 0, 0,
0, 0, 92, 1, 0, 0, 0, 0, 115, 1, 0, 0,
2, 0, 16, 0, 1, 0, 2, 0, 0, 0, 4, 0,
66, 0, 104, 1, 0, 0, 2, 0, 128, 1, 0, 0,
0, 0, 0, 0, 120, 1, 0, 0, 0, 0, 144, 1,
0, 0, 2, 0, 14, 0, 0, 0, 2, 0, 46, 0,
1, 0, 58, 0, 48, 1, 1, 0, 186, 0, 88, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
128, 1, 0, 0, 2, 0, 153, 1, 0, 0, 2, 0,
17, 0, 24, 0, 70, 0, 16, 0, 1, 0, 66, 0,
204, 1, 0, 0, 0, 0, 164, 1, 0, 0, 0, 0,
0, 0, 220, 1, 0, 0, 0, 0, 180, 1, 0, 0,
2, 0, 12, 0, 1, 0, 2, 0, 14, 0, 1, 0,
50, 0, 48, 1, 0, 0, 58, 0, 88, 1, 0, 0,
0, 0, 0, 0, 227, 1, 0, 0, 0, 0, 188, 1,
0, 0, 2, 0, 8, 0, 0, 0, 2, 0, 17, 0,
3, 0, 34, 0, 240, 1, 24, 0, 70, 0, 8, 2,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 2, 0, 0, 1, 0, 24, 2, 0, 0, 2, 0,
0, 0, 1, 0, 2, 0, 12, 0, 1, 0, 50, 0,
16, 2, 0, 0, 0, 0, 88, 1, 0, 0, 0, 0,
0, 0, 32, 2, 0, 0, 0, 0, 31, 2, 0, 0,
1, 0, 1, 0, 1, 0, 2, 0, 8, 0, 3, 0,
6, 0, 16, 2, 0, 0, 34, 0, 44, 2, 0, 0,
0, 0, 0, 0, 47, 2, 0, 0, 0, 0, 60, 2,
0, 0, 1, 0, 2, 0, 0, 0, 1, 0, 0, 0,
1, 0, 10, 0, 16, 2, 1, 0, 2, 0, 76, 2,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
61, 2, 0, 0, 2, 0, 92, 2, 0, 0, 1, 0,
13, 0, 1, 0, 54, 0, 1, 0, 1, 0, 6, 0,
48, 1, 0, 0, 0, 0, 76, 2, 0, 0, 0, 0,
0, 0, 71, 2, 0, 0, 0, 0, 107, 2, 0, 0,
2, 0, 41, 0, 4, 0, 1, 0, 2, 0, 1, 0,
166, 0, 76, 1, 0, 0, 10, 0, 76, 2, 0, 0,
0, 0, 0, 0, 78, 2, 0, 0, 0, 0, 121, 2,
0, 0, 2, 0, 4, 0, 0, 0, 2, 0, 13, 0,
4, 0, 18, 0, 76, 1, 1, 0, 54, 0, 88, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
97, 109, 98, 105, 101, 110, 131, 2, 0, 0, 2, 0,
116, 76, 105, 103, 104, 116, 41, 0, 4, 0, 166, 0,
0, 171, 171, 171, 1, 0, 128, 1, 0, 0, 0, 0,
3, 0, 1, 0, 4, 0, 0, 0, 138, 2, 0, 0,
1, 0, 0, 0, 0, 0, 2, 0, 4, 0, 4, 0,
0, 0, 99, 111, 109, 98, 18, 0, 128, 1, 0, 0,
105, 110, 101, 100, 77, 97, 0, 0, 0, 0, 97, 109,
116, 0, 3, 0, 3, 0, 98, 105, 101, 110, 116, 76,
4, 0, 4, 0, 1, 0,
0, 0, 0, 0, 0, 0,
102, 105, 114, 115, 116, 76,
105, 103, 104, 116, 0, 171, 105, 103, 104, 116, 0, 171,
171, 171, 1, 0, 3, 0,
1, 0, 4, 0, 1, 0,
0, 0, 0, 0, 0, 0,
99, 111, 108, 111, 114, 67,
108, 97, 109, 112, 0, 99,
111, 109, 98, 105, 110, 101,
100, 77, 97, 116, 0, 171,
3, 0, 3, 0, 4, 0,
4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 101, 110,
118, 67, 111, 108, 111, 114,
0, 102, 105, 114, 115, 116,
76, 105, 103, 104, 116, 0,
1, 0, 2, 0, 1, 0, 1, 0, 2, 0, 1, 0,
4, 0, 1, 0, 0, 0, 4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 102, 111, 0, 0, 0, 0, 102, 111,
@@ -226,13 +242,13 @@ const BYTE g_vs20_main[] =
0, 0, 112, 111, 115, 105, 0, 0, 112, 111, 115, 105,
116, 105, 111, 110, 0, 100, 116, 105, 111, 110, 0, 100,
105, 114, 101, 99, 116, 105, 105, 114, 101, 99, 116, 105,
111, 110, 0, 171, 135, 1, 111, 110, 0, 171, 195, 1,
0, 0, 144, 1, 0, 0, 0, 0, 204, 1, 0, 0,
160, 1, 0, 0, 144, 1, 220, 1, 0, 0, 204, 1,
0, 0, 169, 1, 0, 0, 0, 0, 229, 1, 0, 0,
144, 1, 0, 0, 5, 0, 204, 1, 0, 0, 5, 0,
0, 0, 1, 0, 12, 0, 0, 0, 1, 0, 12, 0,
8, 0, 3, 0, 180, 1, 8, 0, 3, 0, 240, 1,
0, 0, 109, 97, 116, 67, 0, 0, 109, 97, 116, 67,
111, 108, 0, 110, 111, 114, 111, 108, 0, 110, 111, 114,
109, 97, 108, 77, 97, 116, 109, 97, 108, 77, 97, 116,
@@ -497,18 +513,23 @@ const BYTE g_vs20_main[] =
0, 0, 228, 128, 2, 0, 0, 0, 228, 128, 2, 0,
0, 3, 1, 0, 3, 224, 0, 3, 1, 0, 3, 224,
0, 0, 228, 128, 44, 0, 0, 0, 228, 128, 44, 0,
228, 160, 2, 0, 0, 3, 228, 160, 11, 0, 0, 3,
0, 0, 1, 128, 0, 0, 1, 0, 15, 128, 2, 0,
255, 128, 14, 0, 85, 161, 228, 128, 45, 0, 228, 160,
5, 0, 0, 3, 0, 0, 5, 0, 0, 3, 1, 0,
1, 128, 0, 0, 0, 128, 15, 208, 1, 0, 228, 128,
14, 0, 170, 160, 11, 0, 46, 0, 228, 160, 2, 0,
0, 3, 0, 0, 1, 128, 0, 3, 0, 0, 1, 128,
0, 0, 0, 128, 14, 0, 0, 0, 255, 128, 14, 0,
255, 160, 10, 0, 0, 3, 85, 161, 5, 0, 0, 3,
0, 0, 4, 224, 0, 0, 0, 0, 1, 128, 0, 0,
0, 128, 11, 0, 170, 160, 0, 128, 14, 0, 170, 160,
1, 0, 0, 2, 0, 0, 11, 0, 0, 3, 0, 0,
3, 224, 2, 0, 228, 144, 1, 128, 0, 0, 0, 128,
255, 255, 0, 0 14, 0, 255, 160, 10, 0,
0, 3, 0, 0, 4, 224,
0, 0, 0, 128, 11, 0,
170, 160, 1, 0, 0, 2,
0, 0, 3, 224, 2, 0,
228, 144, 255, 255, 0, 0
}; };
+87 -66
View File
@@ -8,7 +8,9 @@
// Parameters: // Parameters:
// //
// float4 ambientLight; // float4 ambientLight;
// float4 colorClamp;
// float4x4 combinedMat; // float4x4 combinedMat;
// float4 envColor;
// float4 fogData; // float4 fogData;
// float4 matCol; // float4 matCol;
// float3x3 normalMat; // float3x3 normalMat;
@@ -27,6 +29,8 @@
// fogData c14 1 // fogData c14 1
// ambientLight c15 1 // ambientLight c15 1
// texMat c41 4 // texMat c41 4
// colorClamp c45 1
// envColor c46 1
// //
vs_2_0 vs_2_0
@@ -47,7 +51,9 @@
mov r0.w, v3.w mov r0.w, v3.w
max r0, r0, c4.x max r0, r0, c4.x
min r0, r0, c4.y min r0, r0, c4.y
max r1, r0, c45
mul oD0, r0, c12 mul oD0, r0, c12
mul oD1, r1, c46
mul r0, v0.y, c1 mul r0, v0.y, c1
mad r0, c0, v0.x, r0 mad r0, c0, v0.x, r0
mad r0, c2, v0.z, r0 mad r0, c2, v0.z, r0
@@ -59,56 +65,66 @@
min oT0.z, r0.x, c4.y min oT0.z, r0.x, c4.y
mov oT0.xy, v2 mov oT0.xy, v2
// approximately 23 instruction slots used // approximately 25 instruction slots used
#endif #endif
const BYTE g_vs20_main[] = const BYTE g_vs20_main[] =
{ {
0, 2, 254, 255, 254, 255, 0, 2, 254, 255, 254, 255,
88, 0, 67, 84, 65, 66, 103, 0, 67, 84, 65, 66,
28, 0, 0, 0, 40, 1, 28, 0, 0, 0, 100, 1,
0, 0, 0, 2, 254, 255, 0, 0, 0, 2, 254, 255,
7, 0, 0, 0, 28, 0, 9, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
33, 1, 0, 0, 168, 0, 93, 1, 0, 0, 208, 0,
0, 0, 2, 0, 15, 0, 0, 0, 2, 0, 15, 0,
1, 0, 62, 0, 184, 0, 1, 0, 62, 0, 224, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
200, 0, 0, 0, 2, 0, 240, 0, 0, 0, 2, 0,
0, 0, 4, 0, 2, 0, 45, 0, 1, 0, 182, 0,
212, 0, 0, 0, 0, 0, 224, 0, 0, 0, 0, 0,
0, 0, 228, 0, 0, 0, 0, 0, 251, 0, 0, 0,
2, 0, 14, 0, 1, 0, 2, 0, 0, 0, 4, 0,
58, 0, 184, 0, 0, 0, 2, 0, 8, 1, 0, 0,
0, 0, 0, 0, 236, 0, 0, 0, 0, 0, 24, 1,
0, 0, 2, 0, 12, 0, 0, 0, 2, 0, 46, 0,
1, 0, 50, 0, 184, 0, 1, 0, 186, 0, 224, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
243, 0, 0, 0, 2, 0, 33, 1, 0, 0, 2, 0,
8, 0, 3, 0, 34, 0, 14, 0, 1, 0, 58, 0,
0, 1, 0, 0, 0, 0, 224, 0, 0, 0, 0, 0,
0, 0, 16, 1, 0, 0, 0, 0, 41, 1, 0, 0,
2, 0, 13, 0, 1, 0, 2, 0, 12, 0, 1, 0,
54, 0, 184, 0, 0, 0, 50, 0, 224, 0, 0, 0,
0, 0, 0, 0, 26, 1, 0, 0, 0, 0, 48, 1,
0, 0, 2, 0, 41, 0, 0, 0, 2, 0, 8, 0,
4, 0, 166, 0, 212, 0, 3, 0, 34, 0, 60, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
97, 109, 98, 105, 101, 110, 76, 1, 0, 0, 2, 0,
116, 76, 105, 103, 104, 116, 13, 0, 1, 0, 54, 0,
0, 171, 171, 171, 1, 0, 224, 0, 0, 0, 0, 0,
3, 0, 1, 0, 4, 0, 0, 0, 86, 1, 0, 0,
1, 0, 0, 0, 0, 0, 2, 0, 41, 0, 4, 0,
0, 0, 99, 111, 109, 98, 166, 0, 8, 1, 0, 0,
105, 110, 101, 100, 77, 97, 0, 0, 0, 0, 97, 109,
116, 0, 3, 0, 3, 0, 98, 105, 101, 110, 116, 76,
4, 0, 4, 0, 1, 0, 105, 103, 104, 116, 0, 171,
171, 171, 1, 0, 3, 0,
1, 0, 4, 0, 1, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
102, 111, 103, 68, 97, 116, 99, 111, 108, 111, 114, 67,
97, 0, 109, 97, 116, 67, 108, 97, 109, 112, 0, 99,
111, 108, 0, 110, 111, 114, 111, 109, 98, 105, 110, 101,
109, 97, 108, 77, 97, 116, 100, 77, 97, 116, 0, 171,
0, 171, 171, 171, 3, 0, 3, 0, 3, 0, 4, 0,
4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 101, 110,
118, 67, 111, 108, 111, 114,
0, 102, 111, 103, 68, 97,
116, 97, 0, 109, 97, 116,
67, 111, 108, 0, 110, 111,
114, 109, 97, 108, 77, 97,
116, 0, 171, 171, 3, 0,
3, 0, 3, 0, 3, 0, 3, 0, 3, 0, 3, 0,
1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0,
0, 0, 115, 117, 114, 102, 0, 0, 115, 117, 114, 102,
@@ -170,35 +186,40 @@ const BYTE g_vs20_main[] =
0, 160, 10, 0, 0, 3, 0, 160, 10, 0, 0, 3,
0, 0, 15, 128, 0, 0, 0, 0, 15, 128, 0, 0,
228, 128, 4, 0, 85, 160, 228, 128, 4, 0, 85, 160,
11, 0, 0, 3, 1, 0,
15, 128, 0, 0, 228, 128,
45, 0, 228, 160, 5, 0,
0, 3, 0, 0, 15, 208,
0, 0, 228, 128, 12, 0,
228, 160, 5, 0, 0, 3,
1, 0, 15, 208, 1, 0,
228, 128, 46, 0, 228, 160,
5, 0, 0, 3, 0, 0, 5, 0, 0, 3, 0, 0,
15, 208, 0, 0, 228, 128, 15, 128, 0, 0, 85, 144,
12, 0, 228, 160, 5, 0, 1, 0, 228, 160, 4, 0,
0, 3, 0, 0, 15, 128,
0, 0, 85, 144, 1, 0,
228, 160, 4, 0, 0, 4,
0, 0, 15, 128, 0, 0,
228, 160, 0, 0, 0, 144,
0, 0, 228, 128, 4, 0,
0, 4, 0, 0, 15, 128, 0, 4, 0, 0, 15, 128,
2, 0, 228, 160, 0, 0, 0, 0, 228, 160, 0, 0,
170, 144, 0, 0, 228, 128, 0, 144, 0, 0, 228, 128,
4, 0, 0, 4, 0, 0, 4, 0, 0, 4, 0, 0,
15, 128, 3, 0, 228, 160, 15, 128, 2, 0, 228, 160,
0, 0, 255, 144, 0, 0, 0, 0, 170, 144, 0, 0,
228, 128, 2, 0, 0, 3, 228, 128, 4, 0, 0, 4,
1, 0, 1, 128, 0, 0, 0, 0, 15, 128, 3, 0,
255, 128, 14, 0, 85, 161, 228, 160, 0, 0, 255, 144,
1, 0, 0, 2, 0, 0, 0, 0, 228, 128, 2, 0,
15, 192, 0, 0, 228, 128, 0, 3, 1, 0, 1, 128,
5, 0, 0, 3, 0, 0, 0, 0, 255, 128, 14, 0,
1, 128, 1, 0, 0, 128, 85, 161, 1, 0, 0, 2,
14, 0, 170, 160, 11, 0, 0, 0, 15, 192, 0, 0,
0, 3, 0, 0, 1, 128, 228, 128, 5, 0, 0, 3,
0, 0, 0, 128, 14, 0, 0, 0, 1, 128, 1, 0,
255, 160, 10, 0, 0, 3, 0, 128, 14, 0, 170, 160,
0, 0, 4, 224, 0, 0, 11, 0, 0, 3, 0, 0,
0, 128, 4, 0, 85, 160, 1, 128, 0, 0, 0, 128,
1, 0, 0, 2, 0, 0, 14, 0, 255, 160, 10, 0,
3, 224, 2, 0, 228, 144, 0, 3, 0, 0, 4, 224,
255, 255, 0, 0 0, 0, 0, 128, 4, 0,
85, 160, 1, 0, 0, 2,
0, 0, 3, 224, 2, 0,
228, 144, 255, 255, 0, 0
}; };
+88 -67
View File
@@ -9,7 +9,9 @@
// Parameters: // Parameters:
// //
// float4 ambientLight; // float4 ambientLight;
// float4 colorClamp;
// float4x4 combinedMat; // float4x4 combinedMat;
// float4 envColor;
// int4 firstLight; // int4 firstLight;
// float4 fogData; // float4 fogData;
// //
@@ -42,6 +44,8 @@
// firstLight c16 1 // firstLight c16 1
// lights c17 24 // lights c17 24
// texMat c41 4 // texMat c41 4
// colorClamp c45 1
// envColor c46 1
// //
vs_2_0 vs_2_0
@@ -76,73 +80,85 @@
max r1, r2, c4.x max r1, r2, c4.x
min r1, r1, c4.z min r1, r1, c4.z
mul oD0, r1, c12 mul oD0, r1, c12
mul r1.xy, r0.y, c42 mul r2.xy, r0.y, c42
mad r0.xy, c41, r0.x, r1 mad r0.xy, c41, r0.x, r2
mad r0.xy, c43, r0.z, r0 mad r0.xy, c43, r0.z, r0
add oT1.xy, r0, c44 add oT1.xy, r0, c44
max r1, r1, c45
mul oD1, r1, c46
add r0.x, r0.w, -c14.y add r0.x, r0.w, -c14.y
mul r0.x, r0.x, c14.z mul r0.x, r0.x, c14.z
max r0.x, r0.x, c14.w max r0.x, r0.x, c14.w
min oT0.z, r0.x, c4.z min oT0.z, r0.x, c4.z
mov oT0.xy, v2 mov oT0.xy, v2
// approximately 38 instruction slots used // approximately 40 instruction slots used
#endif #endif
const BYTE g_vs20_main[] = const BYTE g_vs20_main[] =
{ {
0, 2, 254, 255, 254, 255, 0, 2, 254, 255, 254, 255,
141, 0, 67, 84, 65, 66, 156, 0, 67, 84, 65, 66,
28, 0, 0, 0, 252, 1, 28, 0, 0, 0, 56, 2,
0, 0, 0, 2, 254, 255, 0, 0, 0, 2, 254, 255,
10, 0, 0, 0, 28, 0, 12, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
245, 1, 0, 0, 228, 0, 49, 2, 0, 0, 12, 1,
0, 0, 2, 0, 15, 0, 0, 0, 2, 0, 15, 0,
1, 0, 62, 0, 244, 0, 1, 0, 62, 0, 28, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
4, 1, 0, 0, 2, 0, 44, 1, 0, 0, 2, 0,
0, 0, 4, 0, 2, 0, 45, 0, 1, 0, 182, 0,
16, 1, 0, 0, 0, 0, 28, 1, 0, 0, 0, 0,
0, 0, 32, 1, 0, 0, 0, 0, 55, 1, 0, 0,
2, 0, 16, 0, 1, 0, 2, 0, 0, 0, 4, 0,
66, 0, 44, 1, 0, 0, 2, 0, 68, 1, 0, 0,
0, 0, 0, 0, 60, 1, 0, 0, 0, 0, 84, 1,
0, 0, 2, 0, 14, 0, 0, 0, 2, 0, 46, 0,
1, 0, 58, 0, 244, 0, 1, 0, 186, 0, 28, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
68, 1, 0, 0, 2, 0, 93, 1, 0, 0, 2, 0,
17, 0, 24, 0, 70, 0, 16, 0, 1, 0, 66, 0,
144, 1, 0, 0, 0, 0, 104, 1, 0, 0, 0, 0,
0, 0, 160, 1, 0, 0, 0, 0, 120, 1, 0, 0,
2, 0, 12, 0, 1, 0, 2, 0, 14, 0, 1, 0,
50, 0, 244, 0, 0, 0, 58, 0, 28, 1, 0, 0,
0, 0, 0, 0, 167, 1, 0, 0, 0, 0, 128, 1,
0, 0, 2, 0, 8, 0, 0, 0, 2, 0, 17, 0,
3, 0, 34, 0, 180, 1, 24, 0, 70, 0, 204, 1,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
196, 1, 0, 0, 1, 0, 220, 1, 0, 0, 2, 0,
0, 0, 1, 0, 2, 0, 12, 0, 1, 0, 50, 0,
212, 1, 0, 0, 0, 0, 28, 1, 0, 0, 0, 0,
0, 0, 228, 1, 0, 0, 0, 0, 227, 1, 0, 0,
2, 0, 13, 0, 1, 0, 2, 0, 8, 0, 3, 0,
54, 0, 244, 0, 0, 0, 34, 0, 240, 1, 0, 0,
0, 0, 0, 0, 238, 1, 0, 0, 0, 0, 0, 2,
0, 0, 2, 0, 41, 0, 0, 0, 1, 0, 0, 0,
4, 0, 166, 0, 16, 1, 1, 0, 2, 0, 16, 2,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
97, 109, 98, 105, 101, 110, 32, 2, 0, 0, 2, 0,
116, 76, 105, 103, 104, 116, 13, 0, 1, 0, 54, 0,
0, 171, 171, 171, 1, 0, 28, 1, 0, 0, 0, 0,
3, 0, 1, 0, 4, 0, 0, 0, 42, 2, 0, 0,
1, 0, 0, 0, 0, 0, 2, 0, 41, 0, 4, 0,
0, 0, 99, 111, 109, 98, 166, 0, 68, 1, 0, 0,
105, 110, 101, 100, 77, 97, 0, 0, 0, 0, 97, 109,
116, 0, 3, 0, 3, 0, 98, 105, 101, 110, 116, 76,
4, 0, 4, 0, 1, 0,
0, 0, 0, 0, 0, 0,
102, 105, 114, 115, 116, 76,
105, 103, 104, 116, 0, 171, 105, 103, 104, 116, 0, 171,
171, 171, 1, 0, 3, 0,
1, 0, 4, 0, 1, 0,
0, 0, 0, 0, 0, 0,
99, 111, 108, 111, 114, 67,
108, 97, 109, 112, 0, 99,
111, 109, 98, 105, 110, 101,
100, 77, 97, 116, 0, 171,
3, 0, 3, 0, 4, 0,
4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 101, 110,
118, 67, 111, 108, 111, 114,
0, 102, 105, 114, 115, 116,
76, 105, 103, 104, 116, 0,
1, 0, 2, 0, 1, 0, 1, 0, 2, 0, 1, 0,
4, 0, 1, 0, 0, 0, 4, 0, 1, 0, 0, 0,
0, 0, 0, 0, 102, 111, 0, 0, 0, 0, 102, 111,
@@ -155,13 +171,13 @@ const BYTE g_vs20_main[] =
0, 0, 112, 111, 115, 105, 0, 0, 112, 111, 115, 105,
116, 105, 111, 110, 0, 100, 116, 105, 111, 110, 0, 100,
105, 114, 101, 99, 116, 105, 105, 114, 101, 99, 116, 105,
111, 110, 0, 171, 75, 1, 111, 110, 0, 171, 135, 1,
0, 0, 84, 1, 0, 0, 0, 0, 144, 1, 0, 0,
100, 1, 0, 0, 84, 1, 160, 1, 0, 0, 144, 1,
0, 0, 109, 1, 0, 0, 0, 0, 169, 1, 0, 0,
84, 1, 0, 0, 5, 0, 144, 1, 0, 0, 5, 0,
0, 0, 1, 0, 12, 0, 0, 0, 1, 0, 12, 0,
8, 0, 3, 0, 120, 1, 8, 0, 3, 0, 180, 1,
0, 0, 109, 97, 116, 67, 0, 0, 109, 97, 116, 67,
111, 108, 0, 110, 111, 114, 111, 108, 0, 110, 111, 114,
109, 97, 108, 77, 97, 116, 109, 97, 108, 77, 97, 116,
@@ -267,29 +283,34 @@ const BYTE g_vs20_main[] =
0, 3, 0, 0, 15, 208, 0, 3, 0, 0, 15, 208,
1, 0, 228, 128, 12, 0, 1, 0, 228, 128, 12, 0,
228, 160, 5, 0, 0, 3, 228, 160, 5, 0, 0, 3,
1, 0, 3, 128, 0, 0, 2, 0, 3, 128, 0, 0,
85, 128, 42, 0, 228, 160, 85, 128, 42, 0, 228, 160,
4, 0, 0, 4, 0, 0, 4, 0, 0, 4, 0, 0,
3, 128, 41, 0, 228, 160, 3, 128, 41, 0, 228, 160,
0, 0, 0, 128, 1, 0, 0, 0, 0, 128, 2, 0,
228, 128, 4, 0, 0, 4, 228, 128, 4, 0, 0, 4,
0, 0, 3, 128, 43, 0, 0, 0, 3, 128, 43, 0,
228, 160, 0, 0, 170, 128, 228, 160, 0, 0, 170, 128,
0, 0, 228, 128, 2, 0, 0, 0, 228, 128, 2, 0,
0, 3, 1, 0, 3, 224, 0, 3, 1, 0, 3, 224,
0, 0, 228, 128, 44, 0, 0, 0, 228, 128, 44, 0,
228, 160, 2, 0, 0, 3, 228, 160, 11, 0, 0, 3,
0, 0, 1, 128, 0, 0, 1, 0, 15, 128, 1, 0,
255, 128, 14, 0, 85, 161, 228, 128, 45, 0, 228, 160,
5, 0, 0, 3, 0, 0, 5, 0, 0, 3, 1, 0,
1, 128, 0, 0, 0, 128, 15, 208, 1, 0, 228, 128,
14, 0, 170, 160, 11, 0, 46, 0, 228, 160, 2, 0,
0, 3, 0, 0, 1, 128, 0, 3, 0, 0, 1, 128,
0, 0, 0, 128, 14, 0, 0, 0, 255, 128, 14, 0,
255, 160, 10, 0, 0, 3, 85, 161, 5, 0, 0, 3,
0, 0, 4, 224, 0, 0, 0, 0, 1, 128, 0, 0,
0, 128, 4, 0, 170, 160, 0, 128, 14, 0, 170, 160,
1, 0, 0, 2, 0, 0, 11, 0, 0, 3, 0, 0,
3, 224, 2, 0, 228, 144, 1, 128, 0, 0, 0, 128,
255, 255, 0, 0 14, 0, 255, 160, 10, 0,
0, 3, 0, 0, 4, 224,
0, 0, 0, 128, 4, 0,
170, 160, 1, 0, 0, 2,
0, 0, 3, 224, 2, 0,
228, 144, 255, 255, 0, 0
}; };
+74 -82
View File
@@ -7,7 +7,6 @@
// //
// Parameters: // Parameters:
// //
// float4 colorClamp;
// sampler2D diffTex; // sampler2D diffTex;
// sampler2D envTex; // sampler2D envTex;
// float4 fogColor; // float4 fogColor;
@@ -20,7 +19,6 @@
// ------------ ----- ---- // ------------ ----- ----
// fogColor c0 1 // fogColor c0 1
// fxparams c1 1 // fxparams c1 1
// colorClamp c2 1
// diffTex s0 1 // diffTex s0 1
// envTex s1 1 // envTex s1 1
// //
@@ -29,12 +27,12 @@
dcl t0.xyz dcl t0.xyz
dcl t1.xy dcl t1.xy
dcl v0 dcl v0
dcl v1.xyz
dcl_2d s0 dcl_2d s0
dcl_2d s1 dcl_2d s1
texld r0, t1, s1 texld r0, t1, s1
texld r1, t0, s0 texld r1, t0, s0
max r2.xyz, v0, c2 mul r2.xyz, v1, c1.x
mul r2.xyz, r2, c1.x
mul r0.xyz, r0, r2 mul r0.xyz, r0, r2
mul r0.xyz, r0, t0.z mul r0.xyz, r0, t0.z
mul r2.w, r1.w, v0.w mul r2.w, r1.w, v0.w
@@ -45,38 +43,30 @@
mad r2.xyz, r1, r2.w, r0 mad r2.xyz, r1, r2.w, r0
mov oC0, r2 mov oC0, r2
// approximately 13 instruction slots used (2 texture, 11 arithmetic) // approximately 12 instruction slots used (2 texture, 10 arithmetic)
#endif #endif
const BYTE g_ps20_main[] = const BYTE g_ps20_main[] =
{ {
0, 2, 255, 255, 254, 255, 0, 2, 255, 255, 254, 255,
71, 0, 67, 84, 65, 66, 64, 0, 67, 84, 65, 66,
28, 0, 0, 0, 229, 0, 28, 0, 0, 0, 200, 0,
0, 0, 0, 2, 255, 255, 0, 0, 0, 2, 255, 255,
5, 0, 0, 0, 28, 0, 4, 0, 0, 0, 28, 0,
0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0,
222, 0, 0, 0, 128, 0, 193, 0, 0, 0, 108, 0,
0, 0, 2, 0, 2, 0, 0, 0, 3, 0, 0, 0,
1, 0, 10, 0, 140, 0, 1, 0, 2, 0, 116, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
156, 0, 0, 0, 3, 0, 132, 0, 0, 0, 3, 0,
0, 0, 1, 0, 2, 0,
164, 0, 0, 0, 0, 0,
0, 0, 180, 0, 0, 0,
3, 0, 1, 0, 1, 0,
6, 0, 188, 0, 0, 0,
0, 0, 0, 0, 204, 0,
0, 0, 2, 0, 0, 0,
1, 0, 2, 0, 140, 0,
0, 0, 0, 0, 0, 0,
213, 0, 0, 0, 2, 0,
1, 0, 1, 0, 6, 0, 1, 0, 1, 0, 6, 0,
140, 0, 0, 0, 0, 0, 140, 0, 0, 0, 0, 0,
0, 0, 99, 111, 108, 111, 0, 0, 156, 0, 0, 0,
114, 67, 108, 97, 109, 112, 2, 0, 0, 0, 1, 0,
0, 171, 1, 0, 3, 0, 2, 0, 168, 0, 0, 0,
1, 0, 4, 0, 1, 0, 0, 0, 0, 0, 184, 0,
0, 0, 2, 0, 1, 0,
1, 0, 6, 0, 168, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
100, 105, 102, 102, 84, 101, 100, 105, 102, 102, 84, 101,
120, 0, 4, 0, 12, 0, 120, 0, 4, 0, 12, 0,
@@ -87,63 +77,65 @@ const BYTE g_ps20_main[] =
1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
102, 111, 103, 67, 111, 108, 102, 111, 103, 67, 111, 108,
111, 114, 0, 102, 120, 112, 111, 114, 0, 171, 171, 171,
97, 114, 97, 109, 115, 0, 1, 0, 3, 0, 1, 0,
112, 115, 95, 50, 95, 48, 4, 0, 1, 0, 0, 0,
0, 77, 105, 99, 114, 111, 0, 0, 0, 0, 102, 120,
115, 111, 102, 116, 32, 40, 112, 97, 114, 97, 109, 115,
82, 41, 32, 72, 76, 83, 0, 112, 115, 95, 50, 95,
76, 32, 83, 104, 97, 100, 48, 0, 77, 105, 99, 114,
101, 114, 32, 67, 111, 109, 111, 115, 111, 102, 116, 32,
112, 105, 108, 101, 114, 32, 40, 82, 41, 32, 72, 76,
57, 46, 50, 57, 46, 57, 83, 76, 32, 83, 104, 97,
53, 50, 46, 51, 49, 49, 100, 101, 114, 32, 67, 111,
49, 0, 171, 171, 31, 0, 109, 112, 105, 108, 101, 114,
0, 2, 0, 0, 0, 128, 32, 57, 46, 50, 57, 46,
0, 0, 7, 176, 31, 0, 57, 53, 50, 46, 51, 49,
0, 2, 0, 0, 0, 128, 49, 49, 0, 171, 171, 171,
1, 0, 3, 176, 31, 0, 31, 0, 0, 2, 0, 0,
0, 2, 0, 0, 0, 128, 0, 128, 0, 0, 7, 176,
0, 0, 15, 144, 31, 0, 31, 0, 0, 2, 0, 0,
0, 2, 0, 0, 0, 144, 0, 128, 1, 0, 3, 176,
0, 8, 15, 160, 31, 0, 31, 0, 0, 2, 0, 0,
0, 2, 0, 0, 0, 144, 0, 128, 0, 0, 15, 144,
1, 8, 15, 160, 66, 0, 31, 0, 0, 2, 0, 0,
0, 3, 0, 0, 15, 128, 0, 128, 1, 0, 7, 144,
1, 0, 228, 176, 1, 8, 31, 0, 0, 2, 0, 0,
228, 160, 66, 0, 0, 3, 0, 144, 0, 8, 15, 160,
1, 0, 15, 128, 0, 0, 31, 0, 0, 2, 0, 0,
228, 176, 0, 8, 228, 160, 0, 144, 1, 8, 15, 160,
11, 0, 0, 3, 2, 0, 66, 0, 0, 3, 0, 0,
7, 128, 0, 0, 228, 144, 15, 128, 1, 0, 228, 176,
2, 0, 228, 160, 5, 0, 1, 8, 228, 160, 66, 0,
0, 3, 2, 0, 7, 128, 0, 3, 1, 0, 15, 128,
2, 0, 228, 128, 1, 0, 0, 0, 228, 176, 0, 8,
0, 160, 5, 0, 0, 3, 228, 160, 5, 0, 0, 3,
0, 0, 7, 128, 0, 0, 2, 0, 7, 128, 1, 0,
228, 128, 2, 0, 228, 128, 228, 144, 1, 0, 0, 160,
5, 0, 0, 3, 0, 0, 5, 0, 0, 3, 0, 0,
7, 128, 0, 0, 228, 128, 7, 128, 0, 0, 228, 128,
0, 0, 170, 176, 5, 0, 2, 0, 228, 128, 5, 0,
0, 3, 2, 0, 8, 128,
1, 0, 255, 128, 0, 0,
255, 144, 4, 0, 0, 4,
1, 0, 7, 128, 0, 0,
228, 144, 1, 0, 228, 128,
0, 0, 228, 161, 4, 0,
0, 4, 1, 0, 7, 128,
0, 0, 170, 176, 1, 0,
228, 128, 0, 0, 228, 160,
11, 0, 0, 3, 0, 0,
8, 128, 2, 0, 255, 128,
1, 0, 85, 160, 5, 0,
0, 3, 0, 0, 7, 128, 0, 3, 0, 0, 7, 128,
0, 0, 255, 128, 0, 0, 0, 0, 228, 128, 0, 0,
228, 128, 4, 0, 0, 4, 170, 176, 5, 0, 0, 3,
2, 0, 7, 128, 1, 0, 2, 0, 8, 128, 1, 0,
228, 128, 2, 0, 255, 128, 255, 128, 0, 0, 255, 144,
0, 0, 228, 128, 1, 0, 4, 0, 0, 4, 1, 0,
0, 2, 0, 8, 15, 128, 7, 128, 0, 0, 228, 144,
2, 0, 228, 128, 255, 255, 1, 0, 228, 128, 0, 0,
0, 0 228, 161, 4, 0, 0, 4,
1, 0, 7, 128, 0, 0,
170, 176, 1, 0, 228, 128,
0, 0, 228, 160, 11, 0,
0, 3, 0, 0, 8, 128,
2, 0, 255, 128, 1, 0,
85, 160, 5, 0, 0, 3,
0, 0, 7, 128, 0, 0,
255, 128, 0, 0, 228, 128,
4, 0, 0, 4, 2, 0,
7, 128, 1, 0, 228, 128,
2, 0, 255, 128, 0, 0,
228, 128, 1, 0, 0, 2,
0, 8, 15, 128, 2, 0,
228, 128, 255, 255, 0, 0
}; };
+158 -93
View File
@@ -522,97 +522,137 @@ createTexture(int32 width, int32 height, int32 numlevels, uint32 format)
return levels; return levels;
} }
Raster* struct RasterFormatInfo
rasterCreate(Raster *raster)
{ {
static uint32 formatMap[] = { uint32 d3dformat;
D3DFMT_UNKNOWN, int32 depth;
D3DFMT_A1R5G5B5, bool32 hasAlpha;
D3DFMT_R5G6B5, uint32 rwFormat;
D3DFMT_A4R4G4B4, };
D3DFMT_L8,
D3DFMT_A8R8G8B8,
D3DFMT_X8R8G8B8,
D3DFMT_UNKNOWN,
D3DFMT_UNKNOWN,
D3DFMT_UNKNOWN,
D3DFMT_X1R5G5B5,
D3DFMT_UNKNOWN,
D3DFMT_UNKNOWN,
D3DFMT_UNKNOWN,
D3DFMT_UNKNOWN,
D3DFMT_UNKNOWN
};
static bool32 alphaMap[] = {
0,
1,
0,
1,
0,
1,
0,
0, 0, 0,
0,
0, 0, 0, 0, 0
};
XboxRaster *natras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); // indexed directly by RW format
uint32 format; static RasterFormatInfo formatInfoRW[16] = {
{ 0, 0, 0, 0},
{ D3DFMT_A1R5G5B5, 16, 1, Raster::C1555 },
{ D3DFMT_R5G6B5, 16, 0, Raster::C565 },
{ D3DFMT_A4R4G4B4, 16, 1, Raster::C4444 },
{ D3DFMT_L8, 8, 0, Raster::LUM8 },
{ D3DFMT_A8R8G8B8, 32, 1, Raster::C8888 },
{ D3DFMT_X8R8G8B8, 32, 0, Raster::C888 },
{ D3DFMT_UNKNOWN, 16, 0, Raster::D16 },
{ D3DFMT_UNKNOWN, 32, 0, Raster::D24 },
{ D3DFMT_UNKNOWN, 32, 0, Raster::D32 },
{ D3DFMT_X1R5G5B5, 16, 0, Raster::C555 }
};
static void
rasterSetFormat(Raster *raster)
{
assert(raster->format != 0); // no default yet
XboxRaster *natras = GETXBOXRASTEREXT(raster);
if(raster->format & (Raster::PAL4 | Raster::PAL8)){
natras->format = D3DFMT_P8;
raster->depth = 8;
}else{
natras->format = formatInfoRW[(raster->format >> 8) & 0xF].d3dformat;
raster->depth = formatInfoRW[(raster->format >> 8) & 0xF].depth;
}
natras->bpp = raster->depth/8;
natras->hasAlpha = formatInfoRW[(raster->format >> 8) & 0xF].hasAlpha;
raster->stride = raster->width&natras->bpp;
}
static Raster*
rasterCreateTexture(Raster *raster)
{
XboxRaster *natras = GETXBOXRASTEREXT(raster);
int32 levels; int32 levels;
// Dummy to use as subraster if(natras->format == D3DFMT_P8)
if(raster->width == 0 || raster->height == 0){
raster->flags |= Raster::DONTALLOCATE;
raster->stride = 0;
return raster;
}
switch(raster->type){
case Raster::NORMAL:
case Raster::TEXTURE:
if(raster->flags & Raster::DONTALLOCATE)
return raster;
if(raster->format & (Raster::PAL4 | Raster::PAL8)){
format = D3DFMT_P8;
natras->palette = (uint8*)rwNew(4*256, MEMDUR_EVENT | ID_DRIVER); natras->palette = (uint8*)rwNew(4*256, MEMDUR_EVENT | ID_DRIVER);
}else
format = formatMap[(raster->format >> 8) & 0xF];
natras->format = 0;
natras->hasAlpha = alphaMap[(raster->format >> 8) & 0xF];
levels = Raster::calculateNumLevels(raster->width, raster->height); levels = Raster::calculateNumLevels(raster->width, raster->height);
assert(natras->texture == nil);
natras->texture = createTexture(raster->width, raster->height, natras->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? levels : 1, raster->format & Raster::MIPMAP ? levels : 1,
format); natras->format);
if(natras->texture == nil){ if(natras->texture == nil){
RWERROR((ERR_NOTEXTURE)); RWERROR((ERR_NOTEXTURE));
return nil; return nil;
} }
return raster; return raster;
}
Raster*
rasterCreate(Raster *raster)
{
rasterSetFormat(raster);
Raster *ret = raster;
// Dummy to use as subraster
if(raster->width == 0 || raster->height == 0){
raster->flags |= Raster::DONTALLOCATE;
raster->stride = 0;
goto ret;
} }
// unsupported if(raster->flags & Raster::DONTALLOCATE)
goto ret;
switch(raster->type){
case Raster::NORMAL:
case Raster::TEXTURE:
ret = rasterCreateTexture(raster);
break;
default:
RWERROR((ERR_INVRASTER));
return nil; return nil;
}
ret:
raster->originalWidth = raster->width;
raster->originalHeight = raster->height;
raster->originalStride = raster->stride;
raster->originalPixels = raster->pixels;
return ret;
} }
uint8* uint8*
rasterLock(Raster *raster, int32 level, int32 lockMode) rasterLock(Raster *raster, int32 level, int32 lockMode)
{ {
// TODO? XboxRaster *natras = GETXBOXRASTEREXT(raster);
(void)lockMode;
// check if already locked
if(raster->privateFlags & (Raster::PRIVATELOCK_READ|Raster::PRIVATELOCK_WRITE))
return nil;
XboxRaster *natras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset);
RasterLevels *levels = (RasterLevels*)natras->texture; RasterLevels *levels = (RasterLevels*)natras->texture;
return levels->levels[level].data; raster->pixels = levels->levels[level].data;
raster->width = levels->levels[level].width;
raster->height = levels->levels[level].height;
raster->stride = raster->width*natras->bpp;
if(lockMode & Raster::LOCKREAD) raster->privateFlags |= Raster::PRIVATELOCK_READ;
if(lockMode & Raster::LOCKWRITE) raster->privateFlags |= Raster::PRIVATELOCK_WRITE;
return raster->pixels;
} }
void void
rasterUnlock(Raster*, int32) rasterUnlock(Raster *raster, int32 level)
{ {
raster->width = raster->originalWidth;
raster->height = raster->originalHeight;
raster->stride = raster->originalStride;
raster->pixels = raster->originalPixels;
raster->privateFlags &= ~(Raster::PRIVATELOCK_READ|Raster::PRIVATELOCK_WRITE);
} }
int32 int32
rasterNumLevels(Raster *raster) rasterNumLevels(Raster *raster)
{ {
XboxRaster *natras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); XboxRaster *natras = GETXBOXRASTEREXT(raster);
RasterLevels *levels = (RasterLevels*)natras->texture; RasterLevels *levels = (RasterLevels*)natras->texture;
return levels->numlevels; return levels->numlevels;
} }
@@ -656,12 +696,23 @@ rasterToImage(Raster *raster)
{ {
int32 depth; int32 depth;
Image *image; Image *image;
XboxRaster *natras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset);
if(natras->format){ bool unlock = false;
image = Image::create(raster->width, raster->height, 32); if(raster->pixels == nil){
raster->lock(0, Raster::LOCKREAD);
unlock = true;
}
XboxRaster *natras = GETXBOXRASTEREXT(raster);
if(natras->customFormat){
int w = raster->width;
int h = raster->height;
// pixels are in the upper right corner
if(w < 4) w = 4;
if(h < 4) h = 4;
image = Image::create(w, h, 32);
image->allocate(); image->allocate();
uint8 *pix = raster->lock(0, Raster::LOCKREAD); uint8 *pix = raster->pixels;
switch(natras->format){ switch(natras->format){
case D3DFMT_DXT1: case D3DFMT_DXT1:
image->setPixelsDXT(1, pix); image->setPixelsDXT(1, pix);
@@ -677,10 +728,16 @@ rasterToImage(Raster *raster)
break; break;
default: default:
assert(0 && "unknown format"); assert(0 && "unknown format");
raster->unlock(0);
image->destroy(); image->destroy();
if(unlock)
raster->unlock(0);
return nil; return nil;
} }
// fix it up again
image->width = raster->width;
image->height = raster->height;
if(unlock)
raster->unlock(0); raster->unlock(0);
return image; return image;
} }
@@ -714,47 +771,50 @@ rasterToImage(Raster *raster)
pallength = 256; pallength = 256;
} }
uint8 *in, *out;
image = Image::create(raster->width, raster->height, depth); image = Image::create(raster->width, raster->height, depth);
image->allocate(); image->allocate();
if(pallength){ if(pallength){
out = image->palette; uint8 *out = image->palette;
in = (uint8*)natras->palette; uint8 *in = (uint8*)natras->palette;
// bytes are BGRA unlike regular d3d!
for(int32 i = 0; i < pallength; i++){ for(int32 i = 0; i < pallength; i++){
out[0] = in[2]; conv_BGRA8888_from_RGBA8888(out, in);
out[1] = in[1];
out[2] = in[0];
out[3] = in[3];
in += 4; in += 4;
out += 4; out += 4;
} }
} }
out = image->pixels; uint8 *imgpixels = image->pixels;
in = raster->lock(0, Raster::LOCKREAD); uint8 *pixels = raster->pixels;
unswizzle(out, in, image->width, image->height, depth < 8 ? 1 : depth/8); // NB:
assert(image->bpp == (int)natras->bpp);
assert(image->stride == raster->stride);
unswizzle(imgpixels, pixels, image->width, image->height, image->bpp);
// Fix RGB order // Fix RGB order
// TODO: stride
uint8 tmp; uint8 tmp;
if(depth > 8) if(depth > 8)
for(int32 y = 0; y < image->height; y++) for(int32 y = 0; y < image->height; y++){
for(int32 x = 0; x < image->width; x++) uint8 *imgrow = imgpixels;
// uint8 *rasrow = pixels;
for(int32 x = 0; x < image->width; x++){
switch(raster->format & 0xF00){ switch(raster->format & 0xF00){
case Raster::C8888: case Raster::C8888:
tmp = out[0];
out[0] = out[2];
out[2] = tmp;
out += 4;
break;
case Raster::C888: case Raster::C888:
tmp = out[0]; tmp = imgrow[0];
out[0] = out[2]; imgrow[0] = imgrow[2];
out[2] = tmp; imgrow[2] = tmp;
out += 3; imgrow += image->bpp;
break; break;
} }
}
imgpixels += image->stride;
// pixels += raster->stride;
}
image->compressPalette();
if(unlock)
raster->unlock(0); raster->unlock(0);
return image; return image;
@@ -763,7 +823,7 @@ rasterToImage(Raster *raster)
int32 int32
getLevelSize(Raster *raster, int32 level) getLevelSize(Raster *raster, int32 level)
{ {
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); XboxRaster *ras = GETXBOXRASTEREXT(raster);
RasterLevels *levels = (RasterLevels*)ras->texture; RasterLevels *levels = (RasterLevels*)ras->texture;
return levels->levels[level].size; return levels->levels[level].size;
} }
@@ -776,6 +836,7 @@ createNativeRaster(void *object, int32 offset, int32)
raster->palette = nil; raster->palette = nil;
raster->format = 0; raster->format = 0;
raster->hasAlpha = 0; raster->hasAlpha = 0;
raster->customFormat = 0;
raster->unknownFlag = 0; raster->unknownFlag = 0;
return object; return object;
} }
@@ -822,8 +883,8 @@ readNativeTexture(Stream *stream)
RWERROR((ERR_PLATFORM, platform)); RWERROR((ERR_PLATFORM, platform));
return nil; return nil;
} }
if(version < 0x34001){ if(vers < 0x34001){
RWERROR((ERR_VERSION, version)); RWERROR((ERR_VERSION, vers));
return nil; return nil;
} }
Texture *tex = Texture::create(nil); Texture *tex = Texture::create(nil);
@@ -836,6 +897,9 @@ readNativeTexture(Stream *stream)
stream->read8(tex->name, 32); stream->read8(tex->name, 32);
stream->read8(tex->mask, 32); stream->read8(tex->mask, 32);
//if(strcmp(tex->name, "bluallu") == 0)
//__debugbreak();
// Raster // Raster
int32 format = stream->readI32(); int32 format = stream->readI32();
bool32 hasAlpha = stream->readI16(); bool32 hasAlpha = stream->readI16();
@@ -853,16 +917,17 @@ readNativeTexture(Stream *stream)
Raster *raster; Raster *raster;
if(compression){ if(compression){
raster = Raster::create(width, height, depth, format | type | Raster::DONTALLOCATE, PLATFORM_XBOX); raster = Raster::create(width, height, depth, format | type | Raster::DONTALLOCATE, PLATFORM_XBOX);
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); XboxRaster *ras = GETXBOXRASTEREXT(raster);
ras->format = compression; ras->format = compression;
ras->hasAlpha = hasAlpha; ras->hasAlpha = hasAlpha;
ras->texture = createTexture(raster->width, raster->height, ras->texture = createTexture(raster->width, raster->height,
raster->format & Raster::MIPMAP ? numLevels : 1, raster->format & Raster::MIPMAP ? numLevels : 1,
ras->format); ras->format);
ras->customFormat = 1;
raster->flags &= ~Raster::DONTALLOCATE; raster->flags &= ~Raster::DONTALLOCATE;
}else }else
raster = Raster::create(width, height, depth, format | type, PLATFORM_XBOX); raster = Raster::create(width, height, depth, format | type, PLATFORM_XBOX);
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); XboxRaster *ras = GETXBOXRASTEREXT(raster);
tex->raster = raster; tex->raster = raster;
if(raster->format & Raster::PAL4) if(raster->format & Raster::PAL4)
@@ -892,7 +957,7 @@ writeNativeTexture(Texture *tex, Stream *stream)
// Raster // Raster
Raster *raster = tex->raster; Raster *raster = tex->raster;
XboxRaster *ras = PLUGINOFFSET(XboxRaster, raster, nativeRasterOffset); XboxRaster *ras = GETXBOXRASTEREXT(raster);
int32 numLevels = raster->getNumLevels(); int32 numLevels = raster->getNumLevels();
stream->writeI32(raster->format); stream->writeI32(raster->format);
stream->writeI16(ras->hasAlpha); stream->writeI16(ras->hasAlpha);
+63 -22
View File
@@ -1,5 +1,6 @@
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h>
#include <assert.h> #include <assert.h>
#include <new> #include <new>
@@ -17,7 +18,6 @@
#include "gl/rwgl3.h" #include "gl/rwgl3.h"
#include "gl/rwwdgl.h" #include "gl/rwwdgl.h"
#define PLUGIN_ID 0 #define PLUGIN_ID 0
// on windows // on windows
@@ -126,6 +126,15 @@ free_managed(void *p)
free(mem->origPtr); free(mem->origPtr);
} }
void
printleaks(void)
{
FORLIST(lnk, allocations){
MemoryBlock *mem = LLLinkGetData(lnk, MemoryBlock, inAllocList);
printf("sz %zu hint %X\n %s\n", mem->sz, mem->hint, mem->codeline);
}
}
// TODO: make the debug out configurable // TODO: make the debug out configurable
void *mustmalloc_h(size_t sz, uint32 hint) void *mustmalloc_h(size_t sz, uint32 hint)
{ {
@@ -148,11 +157,34 @@ void *mustrealloc_h(void *p, size_t sz, uint32 hint)
return nil; return nil;
} }
//#define TRACK_ALLOCATIONS char *strdup_LOC(const char *s, uint32 hint, const char *here) {
char *t;
size_t sz = strlen(s)+1;
t = (char*)malloc_LOC(sz, hint, here);
if(t)
memcpy(t, s, sz);
return t;
}
MemoryFunctions defaultMemfuncs = {
malloc_h,
realloc_h,
free,
nil,
nil
};
MemoryFunctions managedMemfuncs = {
malloc_managed,
realloc_managed,
free_managed,
nil,
nil
};
// This function mainly registers engine plugins // This function mainly registers engine plugins
bool32 bool32
Engine::init(void) Engine::init(MemoryFunctions *memfuncs)
{ {
if(engine || Engine::state != Dead){ if(engine || Engine::state != Dead){
RWERROR((ERR_ENGINEINIT)); RWERROR((ERR_ENGINEINIT));
@@ -162,19 +194,15 @@ Engine::init(void)
totalMemoryAllocated = 0; totalMemoryAllocated = 0;
allocations.init(); allocations.init();
// TODO: make this an argument if(memfuncs)
#ifdef TRACK_ALLOCATIONS Engine::memfuncs = *memfuncs;
memfuncs.rwmalloc = malloc_managed; else
memfuncs.rwrealloc = realloc_managed; Engine::memfuncs = defaultMemfuncs;
memfuncs.rwfree = free_managed;
#else
memfuncs.rwmalloc = malloc_h;
memfuncs.rwrealloc = realloc_h;
memfuncs.rwfree = free;
#endif
memfuncs.rwmustmalloc = mustmalloc_h; if(Engine::memfuncs.rwmustmalloc == nil)
memfuncs.rwmustrealloc = mustrealloc_h; Engine::memfuncs.rwmustmalloc = mustmalloc_h;
if(Engine::memfuncs.rwmustrealloc == nil)
Engine::memfuncs.rwmustrealloc = mustrealloc_h;
PluginList::open(); PluginList::open();
@@ -304,13 +332,6 @@ Engine::term(void)
// TODO: maybe reset more stuff here? // TODO: maybe reset more stuff here?
d3d::nativeRasterOffset = 0; d3d::nativeRasterOffset = 0;
#ifdef TRACK_ALLOCATIONS
FORLIST(lnk, allocations){
MemoryBlock *mem = LLLinkGetData(lnk, MemoryBlock, inAllocList);
printf("sz %d hint %X\n %s\n", mem->sz, mem->hint, mem->codeline);
}
#endif
Engine::state = Dead; Engine::state = Dead;
} }
@@ -403,6 +424,25 @@ Engine::getVideoModeInfo(VideoMode *info, int32 mode)
} }
uint32
Engine::getMaxMultiSamplingLevels(void)
{
return engine->device.system(DEVICEGETMAXMULTISAMPLINGLEVELS, nil, 0);
}
uint32
Engine::getMultiSamplingLevels(void)
{
return engine->device.system(DEVICEGETMULTISAMPLINGLEVELS, nil, 0);
}
bool32
Engine::setMultiSamplingLevels(uint32 levels)
{
return engine->device.system(DEVICESETMULTISAMPLINGLEVELS, nil, levels);
}
namespace null { namespace null {
void beginUpdate(Camera*) { } void beginUpdate(Camera*) { }
@@ -497,6 +537,7 @@ deviceSystem(DeviceReq req, void *arg0, int32 n)
return 0; return 0;
case DEVICEGETSUBSSYSTEMINFO: case DEVICEGETSUBSSYSTEMINFO:
return 0; return 0;
default: break;
} }
return 1; return 1;
} }
+10 -8
View File
@@ -11,9 +11,6 @@
#include "rwobjects.h" #include "rwobjects.h"
#include "rwengine.h" #include "rwengine.h"
#include <vitasdk.h>
#include <vitaGL.h>
#define PLUGIN_ID ID_GEOMETRY #define PLUGIN_ID ID_GEOMETRY
namespace rw { namespace rw {
@@ -475,7 +472,7 @@ Geometry::generateTriangles(int8 *adc)
int32 matid = this->matList.findIndex(m->material); int32 matid = this->matList.findIndex(m->material);
if(header->flags == MeshHeader::TRISTRIP) if(header->flags == MeshHeader::TRISTRIP)
for(uint32 j = 0; j < m->numIndices-2; j++){ for(uint32 j = 0; j < m->numIndices-2; j++){
if(adc && adcbits[j+2] || if((adc && adcbits[j+2]) ||
isDegenerate(&m->indices[j])) isDegenerate(&m->indices[j]))
continue; continue;
tri->v[0] = m->indices[j+0]; tri->v[0] = m->indices[j+0];
@@ -619,7 +616,7 @@ Geometry::correctTristripWinding(void)
rwFree(header); rwFree(header);
// Now allocate indices and copy them // Now allocate indices and copy them
this->allocateMeshes(newhead->numMeshes, newhead->totalIndices, 0); this->allocateMeshes(newhead->numMeshes, newhead->totalIndices, 0);
memcpy_neon(this->meshHeader->getMeshes()->indices, indices, this->meshHeader->totalIndices*2); memcpy(this->meshHeader->getMeshes()->indices, indices, this->meshHeader->totalIndices*2);
rwFree(indices); rwFree(indices);
} }
@@ -674,7 +671,7 @@ Geometry::removeUnusedMaterials(void)
for(uint32 i = 0; i < mh->numMeshes; i++){ for(uint32 i = 0; i < mh->numMeshes; i++){
if(m[i].numIndices <= 0) if(m[i].numIndices <= 0)
continue; continue;
memcpy_neon(newm->indices, m[i].indices, memcpy(newm->indices, m[i].indices,
m[i].numIndices*sizeof(*m[i].indices)); m[i].numIndices*sizeof(*m[i].indices));
newm++; newm++;
} }
@@ -934,7 +931,10 @@ Material::streamRead(Stream *stream)
RWERROR((ERR_CHUNK, "STRUCT")); RWERROR((ERR_CHUNK, "STRUCT"));
return nil; return nil;
} }
stream->read32(&buf, sizeof(buf)); stream->read8(&buf, sizeof(buf));
RGBA col = buf.color;
memNative32(&buf, sizeof(buf));
buf.color = col;
Material *mat = Material::create(); Material *mat = Material::create();
if(mat == nil) if(mat == nil)
return nil; return nil;
@@ -976,7 +976,9 @@ Material::streamWrite(Stream *stream)
buf.flags = 0; buf.flags = 0;
buf.unused = 0; buf.unused = 0;
buf.textured = this->texture != nil; buf.textured = this->texture != nil;
stream->write32(&buf, sizeof(buf)); memLittle32(&buf, sizeof(buf));
buf.color = this->color;
stream->write8(&buf, sizeof(buf));
if(rw::version >= 0x30400){ if(rw::version >= 0x30400){
float32 surfaceProps[3]; float32 surfaceProps[3];
+2
View File
@@ -9,6 +9,7 @@
#include "../rwpipeline.h" #include "../rwpipeline.h"
#include "../rwobjects.h" #include "../rwobjects.h"
#include "../rwengine.h" #include "../rwengine.h"
#include "rwgl3.h" #include "rwgl3.h"
#include "rwgl3shader.h" #include "rwgl3shader.h"
@@ -32,6 +33,7 @@ driverOpen(void *o, int32, int32)
engine->driver[PLATFORM_GL3]->rasterNumLevels = rasterNumLevels; engine->driver[PLATFORM_GL3]->rasterNumLevels = rasterNumLevels;
engine->driver[PLATFORM_GL3]->imageFindRasterFormat = imageFindRasterFormat; engine->driver[PLATFORM_GL3]->imageFindRasterFormat = imageFindRasterFormat;
engine->driver[PLATFORM_GL3]->rasterFromImage = rasterFromImage; engine->driver[PLATFORM_GL3]->rasterFromImage = rasterFromImage;
engine->driver[PLATFORM_GL3]->rasterToImage = rasterToImage;
return o; return o;
} }
+839 -359
View File
File diff suppressed because it is too large Load Diff
+146 -83
View File
@@ -15,17 +15,14 @@
#include "rwgl3impl.h" #include "rwgl3impl.h"
#include "rwgl3shader.h" #include "rwgl3shader.h"
#include "psp2_shaders.h"
extern float *gVertexBufferIm2D;
extern uint16_t *gIndicesIm2D;
extern float *gVertexBufferIm3D;
extern uint16_t *gIndicesIm3D;
extern uint16_t *gConstIndices;
namespace rw { namespace rw {
namespace gl3 { namespace gl3 {
uint32 im2DVbo, im2DIbo;
#ifdef RW_GL_USE_VAOS
uint32 im2DVao;
#endif
Shader *im2dOverrideShader; Shader *im2dOverrideShader;
static int32 u_xform; static int32 u_xform;
@@ -46,7 +43,7 @@ static AttribDesc im2dattribDesc[3] = {
static int primTypeMap[] = { static int primTypeMap[] = {
GL_POINTS, // invalid GL_POINTS, // invalid
GL_LINES, GL_LINES,
GL_LINES,//_STRIP, GL_LINE_STRIP,
GL_TRIANGLES, GL_TRIANGLES,
GL_TRIANGLE_STRIP, GL_TRIANGLE_STRIP,
GL_TRIANGLE_FAN, GL_TRIANGLE_FAN,
@@ -56,29 +53,39 @@ static int primTypeMap[] = {
void void
openIm2D(void) openIm2D(void)
{ {
u_xform = registerUniform("u_xform"); // must already be registered by device. we just need the value
#ifdef PSP2_USE_SHADER_COMPILER u_xform = registerUniform("u_xform", UNIFORM_VEC4);
#ifdef RW_GLES2
#include "gl2_shaders/im2d_gl2.inc" #include "shaders/im2d_gl.inc"
#include "gl2_shaders/simple_fs_gl2.inc" #include "shaders/simple_fs_gl.inc"
#else const char *vs[] = { shaderDecl, header_vert_src, im2d_vert_src, nil };
#include "shaders/im2d_gl3.inc" const char *fs[] = { shaderDecl, header_frag_src, simple_frag_src, nil };
#include "shaders/simple_fs_gl3.inc" im2dShader = Shader::create(vs, fs);
#endif
const char *vs[] = { header_vert_src, im2d_vert_src, nil };
const char *fs[] = { header_frag_src, simple_frag_src, nil };
im2dShader = Shader::create(vs, fs, true);
#else
const char *vs[] = { (const char*)im2d_v, (const char*)&size_im2d_v, nil };
const char *fs[] = { (const char*)simple_f, (const char*)&size_simple_f, nil };
im2dShader = Shader::create(vs, fs, true);
#endif
assert(im2dShader); assert(im2dShader);
glGenBuffers(1, &im2DIbo);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im2DIbo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, STARTINDICES*2, nil, GL_STREAM_DRAW);
glGenBuffers(1, &im2DVbo);
glBindBuffer(GL_ARRAY_BUFFER, im2DVbo);
glBufferData(GL_ARRAY_BUFFER, STARTVERTICES*sizeof(Im2DVertex), nil, GL_STREAM_DRAW);
#ifdef RW_GL_USE_VAOS
glGenVertexArrays(1, &im2DVao);
glBindVertexArray(im2DVao);
setAttribPointers(im2dattribDesc, 3);
#endif
} }
void void
closeIm2D(void) closeIm2D(void)
{ {
glDeleteBuffers(1, &im2DIbo);
glDeleteBuffers(1, &im2DVbo);
#ifdef RW_GL_USE_VAOS
glDeleteVertexArrays(1, &im2DVao);
#endif
im2dShader->destroy(); im2dShader->destroy();
im2dShader = nil; im2dShader = nil;
} }
@@ -105,32 +112,58 @@ im2DRenderTriangle(void *vertices, int32 numVertices, int32 vert1, int32 vert2,
} }
void void
im2DRenderPrimitive(PrimitiveType primType, void *vertices, int32 numVertices) im2DSetXform(void)
{ {
GLfloat xform[4]; GLfloat xform[4];
Camera *cam; Camera *cam;
cam = (Camera*)engine->currentCamera; cam = (Camera*)engine->currentCamera;
xform[0] = 2.0f/cam->frameBuffer->width; xform[0] = 2.0f/cam->frameBuffer->width;
xform[1] = -2.0f/cam->frameBuffer->height; xform[1] = -2.0f/cam->frameBuffer->height;
xform[2] = -1.0f; xform[2] = -1.0f;
xform[3] = 1.0f; xform[3] = 1.0f;
setUniform(u_xform, xform);
// glUniform4fv(currentShader->uniformLocations[u_xform], 1, xform);
}
void
im2DRenderPrimitive(PrimitiveType primType, void *vertices, int32 numVertices)
{
#ifdef RW_GL_USE_VAOS
glBindVertexArray(im2DVao);
#endif
glBindBuffer(GL_ARRAY_BUFFER, im2DVbo);
#if defined(__SWITCH__) || defined(PSP2)
// Orphan with exactly the size we need, in one call that also uploads.
// The stock path orphans the whole STARTVERTICES buffer (~240KB) on every
// single 2D draw - even a 4-vertex sprite - and hundreds of those per frame
// exhaust nouveau's buffer allocator. It then hands back a buffer with no
// backing store and glBufferSubData memcpy's into null (Data Abort at 0).
// vitaGL behaves the same way: those orphans come out of its memory pools,
// which both costs most of the frame time and churns the allocator.
// Orphaning itself must stay: without it the GPU may still be reading the
// buffer we overwrite, which mixes geometry between draws.
glBufferData(GL_ARRAY_BUFFER, numVertices*sizeof(Im2DVertex), vertices, GL_STREAM_DRAW);
#else
glBufferData(GL_ARRAY_BUFFER, STARTVERTICES*sizeof(Im2DVertex), nil, GL_STREAM_DRAW);
glBufferSubData(GL_ARRAY_BUFFER, 0, numVertices*sizeof(Im2DVertex), vertices);
#endif
if(im2dOverrideShader) if(im2dOverrideShader)
im2dOverrideShader->use(); im2dOverrideShader->use();
else else
im2dShader->use(); im2dShader->use();
#ifndef RW_GL_USE_VAOS
setAttribPointers(im2dattribDesc, 3);
#endif
im2DSetXform();
flushCache(); flushCache();
glUniform4fv(currentShader->uniformLocations[u_xform], 1, xform); glDrawArrays(primTypeMap[primType], 0, numVertices);
#ifndef RW_GL_USE_VAOS
memcpy_neon(gVertexBufferIm2D, vertices, numVertices*sizeof(Im2DVertex)); disableAttribPointers(im2dattribDesc, 3);
vglVertexAttribPointerMapped(0, gVertexBufferIm2D); #endif
vglIndexPointerMapped(gConstIndices);
gVertexBufferIm2D += numVertices*(sizeof(Im2DVertex)/sizeof(float));
vglDrawObjects(primTypeMap[primType], numVertices);
} }
void void
@@ -138,32 +171,42 @@ im2DRenderIndexedPrimitive(PrimitiveType primType,
void *vertices, int32 numVertices, void *vertices, int32 numVertices,
void *indices, int32 numIndices) void *indices, int32 numIndices)
{ {
GLfloat xform[4]; #ifdef RW_GL_USE_VAOS
Camera *cam; glBindVertexArray(im2DVao);
cam = (Camera*)engine->currentCamera; #endif
xform[0] = 2.0f/cam->frameBuffer->width; glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im2DIbo);
xform[1] = -2.0f/cam->frameBuffer->height; #if defined(__SWITCH__) || defined(PSP2)
xform[2] = -1.0f; glBufferData(GL_ELEMENT_ARRAY_BUFFER, numIndices*2, indices, GL_STREAM_DRAW);
xform[3] = 1.0f; #else
glBufferData(GL_ELEMENT_ARRAY_BUFFER, STARTINDICES*2, nil, GL_STREAM_DRAW);
glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, numIndices*2, indices);
#endif
glBindBuffer(GL_ARRAY_BUFFER, im2DVbo);
#if defined(__SWITCH__) || defined(PSP2)
glBufferData(GL_ARRAY_BUFFER, numVertices*sizeof(Im2DVertex), vertices, GL_STREAM_DRAW);
#else
glBufferData(GL_ARRAY_BUFFER, STARTVERTICES*sizeof(Im2DVertex), nil, GL_STREAM_DRAW);
glBufferSubData(GL_ARRAY_BUFFER, 0, numVertices*sizeof(Im2DVertex), vertices);
#endif
if(im2dOverrideShader) if(im2dOverrideShader)
im2dOverrideShader->use(); im2dOverrideShader->use();
else else
im2dShader->use(); im2dShader->use();
#ifndef RW_GL_USE_VAOS
setAttribPointers(im2dattribDesc, 3);
#endif
im2DSetXform();
flushCache(); flushCache();
glUniform4fv(currentShader->uniformLocations[u_xform], 1, xform); glDrawElements(primTypeMap[primType], numIndices,
GL_UNSIGNED_SHORT, nil);
memcpy_neon(gIndicesIm2D, indices, numIndices * 2); #ifndef RW_GL_USE_VAOS
vglIndexPointerMapped(gIndicesIm2D); disableAttribPointers(im2dattribDesc, 3);
gIndicesIm2D += numIndices; #endif
memcpy_neon(gVertexBufferIm2D, vertices, numVertices*sizeof(Im2DVertex));
vglVertexAttribPointerMapped(0, gVertexBufferIm2D);
gVertexBufferIm2D += numVertices*(sizeof(Im2DVertex)/sizeof(float));
vglDrawObjects(primTypeMap[primType], numIndices);
} }
@@ -188,28 +231,36 @@ static int32 num3DVertices; // not actually needed here
void void
openIm3D(void) openIm3D(void)
{ {
#ifdef PSP2_USE_SHADER_COMPILER #include "shaders/im3d_gl.inc"
#ifdef RW_GLES2 #include "shaders/simple_fs_gl.inc"
#include "gl2_shaders/im3d_gl2.inc" const char *vs[] = { shaderDecl, header_vert_src, im3d_vert_src, nil };
#include "gl2_shaders/simple_fs_gl2.inc" const char *fs[] = { shaderDecl, header_frag_src, simple_frag_src, nil };
#else im3dShader = Shader::create(vs, fs);
#include "shaders/im3d_gl3.inc"
#include "shaders/simple_fs_gl3.inc"
#endif
const char *vs[] = { header_vert_src, im3d_vert_src, nil };
const char *fs[] = { header_frag_src, simple_frag_src, nil };
im3dShader = Shader::create(vs, fs, false);
#else
const char *vs[] = { (const char*)im3d_v, (const char*)&size_im3d_v, nil };
const char *fs[] = { (const char*)simple_f, (const char*)&size_simple_f, nil };
im3dShader = Shader::create(vs, fs, false);
#endif
assert(im3dShader); assert(im3dShader);
glGenBuffers(1, &im3DIbo);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im3DIbo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, STARTINDICES*2, nil, GL_STREAM_DRAW);
glGenBuffers(1, &im3DVbo);
glBindBuffer(GL_ARRAY_BUFFER, im3DVbo);
glBufferData(GL_ARRAY_BUFFER, STARTVERTICES*sizeof(Im3DVertex), nil, GL_STREAM_DRAW);
#ifdef RW_GL_USE_VAOS
glGenVertexArrays(1, &im3DVao);
glBindVertexArray(im3DVao);
setAttribPointers(im3dattribDesc, 3);
#endif
} }
void void
closeIm3D(void) closeIm3D(void)
{ {
glDeleteBuffers(1, &im3DIbo);
glDeleteBuffers(1, &im3DVbo);
#ifdef RW_GL_USE_VAOS
glDeleteVertexArrays(1, &im3DVao);
#endif
im3dShader->destroy(); im3dShader->destroy();
im3dShader = nil; im3dShader = nil;
} }
@@ -228,10 +279,19 @@ im3DTransform(void *vertices, int32 numVertices, Matrix *world, uint32 flags)
if((flags & im3d::VERTEXUV) == 0) if((flags & im3d::VERTEXUV) == 0)
SetRenderStatePtr(TEXTURERASTER, nil); SetRenderStatePtr(TEXTURERASTER, nil);
memcpy_neon(gVertexBufferIm3D, vertices, numVertices*sizeof(Im3DVertex)); #ifdef RW_GL_USE_VAOS
glBindVertexArray(im2DVao);
#endif
glBindBuffer(GL_ARRAY_BUFFER, im3DVbo);
#if defined(__SWITCH__) || defined(PSP2)
glBufferData(GL_ARRAY_BUFFER, numVertices*sizeof(Im3DVertex), vertices, GL_STREAM_DRAW);
#else
glBufferData(GL_ARRAY_BUFFER, STARTVERTICES*sizeof(Im3DVertex), nil, GL_STREAM_DRAW);
glBufferSubData(GL_ARRAY_BUFFER, 0, numVertices*sizeof(Im3DVertex), vertices);
#endif
#ifndef RW_GL_USE_VAOS #ifndef RW_GL_USE_VAOS
//setAttribPointers(im3dattribDesc, 3); setAttribPointers(im3dattribDesc, 3);
#endif #endif
num3DVertices = numVertices; num3DVertices = numVertices;
} }
@@ -239,23 +299,26 @@ im3DTransform(void *vertices, int32 numVertices, Matrix *world, uint32 flags)
void void
im3DRenderPrimitive(PrimitiveType primType) im3DRenderPrimitive(PrimitiveType primType)
{ {
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im3DIbo);
flushCache(); flushCache();
vglIndexPointerMapped(gConstIndices); glDrawArrays(primTypeMap[primType], 0, num3DVertices);
vglVertexAttribPointerMapped(0, gVertexBufferIm3D);
gVertexBufferIm3D += num3DVertices*(sizeof(Im3DVertex)/sizeof(float));
vglDrawObjects(primTypeMap[primType], num3DVertices);
} }
void void
im3DRenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices) im3DRenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices)
{ {
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im3DIbo);
#if defined(__SWITCH__) || defined(PSP2)
glBufferData(GL_ELEMENT_ARRAY_BUFFER, numIndices*2, indices, GL_STREAM_DRAW);
#else
glBufferData(GL_ELEMENT_ARRAY_BUFFER, STARTINDICES*2, nil, GL_STREAM_DRAW);
glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, numIndices*2, indices);
#endif
flushCache(); flushCache();
memcpy_neon(gIndicesIm3D, indices, numIndices * 2); glDrawElements(primTypeMap[primType], numIndices,
vglIndexPointerMapped(gIndicesIm3D); GL_UNSIGNED_SHORT, nil);
vglVertexAttribPointerMapped(0, gVertexBufferIm3D);
gVertexBufferIm3D += num3DVertices*(sizeof(Im3DVertex)/sizeof(float));
gIndicesIm3D += numIndices;
vglDrawObjects(primTypeMap[primType], numIndices);
} }
void void
+96 -63
View File
@@ -12,40 +12,48 @@
#include "../rwobjects.h" #include "../rwobjects.h"
#include "../rwanim.h" #include "../rwanim.h"
#include "../rwplugins.h" #include "../rwplugins.h"
#include "rwgl3.h" #include "rwgl3.h"
#include "rwgl3shader.h" #include "rwgl3shader.h"
#include "rwgl3plg.h" #include "rwgl3plg.h"
#include "rwgl3impl.h" #include "rwgl3impl.h"
#include "psp2_shaders.h"
namespace rw { namespace rw {
namespace gl3 { namespace gl3 {
#ifdef RW_OPENGL #ifdef RW_OPENGL
#define U(i) currentShader->uniformLocations[i] static Shader *envShader, *envShader_noAT;
static Shader *envShader_fullLight, *envShader_fullLight_noAT;
static Shader *envShader;
static int32 u_texMatrix; static int32 u_texMatrix;
static int32 u_fxparams; static int32 u_fxparams;
static int32 u_colorClamp; static int32 u_colorClamp;
static int32 u_envColor;
void void
matfxDefaultRender(InstanceDataHeader *header, InstanceData *inst) matfxDefaultRender(InstanceDataHeader *header, InstanceData *inst, int32 vsBits, uint32 flags)
{ {
Material *m = inst->material; Material *m;
m = inst->material;
defaultShader->use(); setMaterial(flags, m->color, m->surfaceProps);
rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
setTexture(0, m->texture); setTexture(0, m->texture);
setMaterial(m->color, m->surfaceProps); rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
flushCache(); if((vsBits & VSLIGHT_MASK) == 0){
if(getAlphaTest())
defaultShader->use();
else
defaultShader_noAT->use();
}else{
if(getAlphaTest())
defaultShader_fullLight->use();
else
defaultShader_fullLight_noAT->use();
}
drawInst(header, inst); drawInst(header, inst);
} }
@@ -68,55 +76,73 @@ uploadEnvMatrix(Frame *frame)
// cache the matrix across multiple meshes // cache the matrix across multiple meshes
static RawMatrix envMtx; static RawMatrix envMtx;
if(frame != lastEnvFrame){ // can't do it, frame matrix may change
lastEnvFrame = frame; // if(frame != lastEnvFrame){
// lastEnvFrame = frame;
{
RawMatrix invMtx; RawMatrix invMtx;
Matrix::invert(&invMat, frame->getLTM()); Matrix::invert(&invMat, frame->getLTM());
convMatrix(&invMtx, &invMat); convMatrix(&invMtx, &invMat);
invMtx.pos.set(0.0f, 0.0f, 0.0f); invMtx.pos.set(0.0f, 0.0f, 0.0f);
float uscale = fabs(normal2texcoord.right.x);
normal2texcoord.right.x = MatFX::envMapFlipU ? -uscale : uscale;
RawMatrix::mult(&envMtx, &invMtx, &normal2texcoord); RawMatrix::mult(&envMtx, &invMtx, &normal2texcoord);
} }
glUniformMatrix4fv(U(u_texMatrix), 1, GL_FALSE, (float*)&envMtx); setUniform(u_texMatrix, &envMtx);
} }
void void
matfxEnvRender(InstanceDataHeader *header, InstanceData *inst, MatFX::Env *env) matfxEnvRender(InstanceDataHeader *header, InstanceData *inst, int32 vsBits, uint32 flags, MatFX::Env *env)
{ {
Material *m; Material *m;
m = inst->material; m = inst->material;
if(env->tex == nil || env->coefficient == 0.0f){ if(env->tex == nil || env->coefficient == 0.0f){
matfxDefaultRender(header, inst); matfxDefaultRender(header, inst, vsBits, flags);
return; return;
} }
envShader->use(); setTexture(0, m->texture);
setTexture(1, env->tex);
uploadEnvMatrix(env->frame);
setMaterial(flags, m->color, m->surfaceProps);
float fxparams[4];
fxparams[0] = env->coefficient;
fxparams[1] = env->fbAlpha ? 0.0f : 1.0f;
fxparams[2] = fxparams[3] = 0.0f;
setUniform(u_fxparams, fxparams);
static float zero[4];
static float one[4] = { 1.0f, 1.0f, 1.0f, 1.0f };
// This clamps the vertex color below. With it we can achieve both PC and PS2 style matfx
if(MatFX::envMapApplyLight)
setUniform(u_colorClamp, zero);
else
setUniform(u_colorClamp, one);
RGBAf envcol[4];
if(MatFX::envMapUseMatColor)
convColor(envcol, &m->color);
else
convColor(envcol, &MatFX::envMapColor);
setUniform(u_envColor, envcol);
rw::SetRenderState(VERTEXALPHA, 1); rw::SetRenderState(VERTEXALPHA, 1);
rw::SetRenderState(SRCBLEND, BLENDONE); rw::SetRenderState(SRCBLEND, BLENDONE);
setTexture(0, m->texture); if((vsBits & VSLIGHT_MASK) == 0){
setTexture(1, env->tex); if(getAlphaTest())
envShader->use();
setMaterial(m->color, m->surfaceProps);
flushCache();
uploadEnvMatrix(env->frame);
float fxparams[2];
fxparams[0] = env->coefficient;
fxparams[1] = env->fbAlpha ? 0.0f : 1.0f;
glUniform2fv(U(u_fxparams), 1, fxparams);
static float zero[4];
static float one[4] = { 1.0f, 1.0f, 1.0f, 1.0f };
// This clamps the vertex color below. With it we can achieve both PC and PS2 style matfx
if(MatFX::modulateEnvMap)
glUniform4fv(U(u_colorClamp), 1, zero);
else else
glUniform4fv(U(u_colorClamp), 1, one); envShader_noAT->use();
}else{
if(getAlphaTest())
envShader_fullLight->use();
else
envShader_fullLight_noAT->use();
}
drawInst(header, inst); drawInst(header, inst);
@@ -126,10 +152,11 @@ matfxEnvRender(InstanceDataHeader *header, InstanceData *inst, MatFX::Env *env)
void void
matfxRenderCB(Atomic *atomic, InstanceDataHeader *header) matfxRenderCB(Atomic *atomic, InstanceDataHeader *header)
{ {
uint32 flags = atomic->geometry->flags;
setWorldMatrix(atomic->getFrame()->getLTM()); setWorldMatrix(atomic->getFrame()->getLTM());
lightingCB(atomic); int32 vsBits = lightingCB(atomic);
setAttribPointers(header->attribDesc, header->numAttribs); setupVertexInput(header);
lastEnvFrame = nil; lastEnvFrame = nil;
@@ -140,20 +167,18 @@ matfxRenderCB(Atomic *atomic, InstanceDataHeader *header)
MatFX *matfx = MatFX::get(inst->material); MatFX *matfx = MatFX::get(inst->material);
if(matfx == nil) if(matfx == nil)
matfxDefaultRender(header, inst); matfxDefaultRender(header, inst, vsBits, flags);
else switch(matfx->type){ else switch(matfx->type){
case MatFX::ENVMAP: case MatFX::ENVMAP:
matfxEnvRender(header, inst, &matfx->fx[0].env); matfxEnvRender(header, inst, vsBits, flags, &matfx->fx[0].env);
break; break;
default: default:
matfxDefaultRender(header, inst); matfxDefaultRender(header, inst, vsBits, flags);
break; break;
} }
inst++; inst++;
} }
#ifndef RW_GL_USE_VAOS teardownVertexInput(header);
disableAttribPointers(header->attribDesc, header->numAttribs);
#endif
} }
ObjPipeline* ObjPipeline*
@@ -172,21 +197,22 @@ static void*
matfxOpen(void *o, int32, int32) matfxOpen(void *o, int32, int32)
{ {
matFXGlobals.pipelines[PLATFORM_GL3] = makeMatFXPipeline(); matFXGlobals.pipelines[PLATFORM_GL3] = makeMatFXPipeline();
#ifdef PSP2_USE_SHADER_COMPILER
#ifdef RW_GLES2 #include "shaders/matfx_gl.inc"
#include "gl2_shaders/matfx_gl2.inc" const char *vs[] = { shaderDecl, header_vert_src, matfx_env_vert_src, nil };
#else const char *vs_fullLight[] = { shaderDecl, "#define DIRECTIONALS\n#define POINTLIGHTS\n#define SPOTLIGHTS\n", header_vert_src, matfx_env_vert_src, nil };
#include "shaders/matfx_gl3.inc" const char *fs[] = { shaderDecl, header_frag_src, matfx_env_frag_src, nil };
#endif const char *fs_noAT[] = { shaderDecl, "#define NO_ALPHATEST\n", header_frag_src, matfx_env_frag_src, nil };
const char *vs[] = { header_vert_src, matfx_env_vert_src, nil };
const char *fs[] = { header_frag_src, matfx_env_frag_src, nil }; envShader = Shader::create(vs, fs);
envShader = Shader::create(vs, fs, false);
#else
const char *vs[] = { (const char*)matfx_env_v, (const char*)&size_matfx_env_v, nil };
const char *fs[] = { (const char*)matfx_env_f, (const char*)&size_matfx_env_f, nil };
envShader = Shader::create(vs, fs, false);
#endif
assert(envShader); assert(envShader);
envShader_noAT = Shader::create(vs, fs_noAT);
assert(envShader_noAT);
envShader_fullLight = Shader::create(vs_fullLight, fs);
assert(envShader_fullLight);
envShader_fullLight_noAT = Shader::create(vs_fullLight, fs_noAT);
assert(envShader_fullLight_noAT);
return o; return o;
} }
@@ -199,6 +225,12 @@ matfxClose(void *o, int32, int32)
envShader->destroy(); envShader->destroy();
envShader = nil; envShader = nil;
envShader_noAT->destroy();
envShader_noAT = nil;
envShader_fullLight->destroy();
envShader_fullLight = nil;
envShader_fullLight_noAT->destroy();
envShader_fullLight_noAT = nil;
return o; return o;
} }
@@ -206,9 +238,10 @@ matfxClose(void *o, int32, int32)
void void
initMatFX(void) initMatFX(void)
{ {
u_texMatrix = registerUniform("u_texMatrix"); u_texMatrix = registerUniform("u_texMatrix", UNIFORM_MAT4);
u_fxparams = registerUniform("u_fxparams"); u_fxparams = registerUniform("u_fxparams", UNIFORM_VEC4);
u_colorClamp = registerUniform("u_colorClamp"); u_colorClamp = registerUniform("u_colorClamp", UNIFORM_VEC4);
u_envColor = registerUniform("u_envColor", UNIFORM_VEC4);
Driver::registerPlugin(PLATFORM_GL3, 0, ID_MATFX, Driver::registerPlugin(PLATFORM_GL3, 0, ID_MATFX,
matfxOpen, matfxClose); matfxOpen, matfxClose);
+34 -23
View File
@@ -9,6 +9,7 @@
#include "../rwpipeline.h" #include "../rwpipeline.h"
#include "../rwobjects.h" #include "../rwobjects.h"
#include "../rwengine.h" #include "../rwengine.h"
#include "rwgl3.h" #include "rwgl3.h"
#include "rwgl3shader.h" #include "rwgl3shader.h"
@@ -27,7 +28,11 @@ freeInstanceData(Geometry *geometry)
return; return;
InstanceDataHeader *header = (InstanceDataHeader*)geometry->instData; InstanceDataHeader *header = (InstanceDataHeader*)geometry->instData;
geometry->instData = nil; geometry->instData = nil;
glDeleteBuffers(1, &header->ibo);
glDeleteBuffers(1, &header->vbo);
#ifdef RW_GL_USE_VAOS
glDeleteBuffers(1, &header->vao);
#endif
rwFree(header->indexBuffer); rwFree(header->indexBuffer);
rwFree(header->vertexBuffer); rwFree(header->vertexBuffer);
rwFree(header->attribDesc); rwFree(header->attribDesc);
@@ -70,7 +75,7 @@ instanceMesh(rw::ObjPipeline *rwpipe, Geometry *geo)
inst->vertexAlpha = 0; inst->vertexAlpha = 0;
inst->program = 0; inst->program = 0;
inst->offset = offset; inst->offset = offset;
memcpy_neon((uint8*)header->indexBuffer + inst->offset, memcpy((uint8*)header->indexBuffer + inst->offset,
mesh->indices, inst->numIndex*2); mesh->indices, inst->numIndex*2);
offset += inst->numIndex*2; offset += inst->numIndex*2;
mesh++; mesh++;
@@ -83,6 +88,15 @@ instanceMesh(rw::ObjPipeline *rwpipe, Geometry *geo)
header->ibo = 0; header->ibo = 0;
header->vbo = 0; header->vbo = 0;
#ifdef RW_GL_USE_VAOS
glGenVertexArrays(1, &header->vao);
glBindVertexArray(header->vao);
#endif
glGenBuffers(1, &header->ibo);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, header->ibo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, header->totalNumIndex*2,
header->indexBuffer, GL_STATIC_DRAW);
return header; return header;
} }
@@ -188,9 +202,9 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
a->type = GL_FLOAT; a->type = GL_FLOAT;
a->normalized = GL_FALSE; a->normalized = GL_FALSE;
a->offset = stride; a->offset = stride;
stride += 12;
a++; a++;
} }
stride += 12;
// Prelighting // Prelighting
if(isPrelit){ if(isPrelit){
@@ -199,12 +213,10 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
a->type = GL_UNSIGNED_BYTE; a->type = GL_UNSIGNED_BYTE;
a->normalized = GL_TRUE; a->normalized = GL_TRUE;
a->offset = stride; a->offset = stride;
stride += 4;
a++; a++;
} }
stride += 4;
if (geo->numTexCoordSets <= 0) stride += 8;
else {
// Texture coordinates // Texture coordinates
for(int32 n = 0; n < geo->numTexCoordSets; n++){ for(int32 n = 0; n < geo->numTexCoordSets; n++){
a->index = ATTRIB_TEXCOORDS0+n; a->index = ATTRIB_TEXCOORDS0+n;
@@ -215,21 +227,20 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
stride += 8; stride += 8;
a++; a++;
} }
}
header->numAttribs = a - tmpAttribs; header->numAttribs = a - tmpAttribs;
for(a = tmpAttribs; a != &tmpAttribs[header->numAttribs]; a++) for(a = tmpAttribs; a != &tmpAttribs[header->numAttribs]; a++)
a->stride = stride; a->stride = stride;
header->attribDesc = rwNewT(AttribDesc, header->numAttribs, MEMDUR_EVENT | ID_GEOMETRY); header->attribDesc = rwNewT(AttribDesc, header->numAttribs, MEMDUR_EVENT | ID_GEOMETRY);
memcpy_neon(header->attribDesc, tmpAttribs, memcpy(header->attribDesc, tmpAttribs,
header->numAttribs*sizeof(AttribDesc)); header->numAttribs*sizeof(AttribDesc));
// //
// Allocate vertex buffer // Allocate vertex buffer
// //
header->vertexBuffer = rwNewT(uint8, header->totalNumVertex*stride, MEMDUR_EVENT | ID_GEOMETRY); header->vertexBuffer = rwNewT(uint8, header->totalNumVertex*stride, MEMDUR_EVENT | ID_GEOMETRY);
//assert(header->vbo == 0); assert(header->vbo == 0);
//glGenBuffers(1, &header->vbo); glGenBuffers(1, &header->vbo);
} }
attribs = header->attribDesc; attribs = header->attribDesc;
@@ -238,7 +249,7 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
// Fill vertex buffer // Fill vertex buffer
// //
uint8 *verts = (uint8*)header->vertexBuffer; uint8 *verts = header->vertexBuffer;
// Positions // Positions
if(!reinstance || geo->lockedSinceInst&Geometry::LOCKVERTICES){ if(!reinstance || geo->lockedSinceInst&Geometry::LOCKVERTICES){
@@ -256,11 +267,6 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
instV3d(VERT_FLOAT3, verts + a->offset, instV3d(VERT_FLOAT3, verts + a->offset,
geo->morphTargets[0].normals, geo->morphTargets[0].normals,
header->totalNumVertex, a->stride); header->totalNumVertex, a->stride);
} else if (!hasNormals) {
for (int i = 0; i < header->totalNumVertex; i++) {
float *verts_f = (float*)&verts[12 + i * 36];
verts_f[0] = verts_f[1] = verts_f[2] = 0;
}
} }
// Prelighting // Prelighting
@@ -277,13 +283,6 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
inst->numVertices, a->stride); inst->numVertices, a->stride);
inst++; inst++;
} }
} else if (!isPrelit) {
for (int i = 0; i < header->totalNumVertex; i++) {
verts[24 + i * 36] = 0;
verts[25 + i * 36] = 0;
verts[26 + i * 36] = 0;
verts[27 + i * 36] = 255;
}
} }
// Texture coordinates // Texture coordinates
@@ -296,6 +295,18 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
header->totalNumVertex, a->stride); header->totalNumVertex, a->stride);
} }
} }
#ifdef RW_GL_USE_VAOS
glBindVertexArray(header->vao);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, header->ibo);
#endif
glBindBuffer(GL_ARRAY_BUFFER, header->vbo);
glBufferData(GL_ARRAY_BUFFER, header->totalNumVertex*attribs[0].stride,
header->vertexBuffer, GL_STATIC_DRAW);
#ifdef RW_GL_USE_VAOS
setAttribPointers(header->attribDesc, header->numAttribs);
glBindVertexArray(0);
#endif
} }
void void
+651 -126
View File
File diff suppressed because it is too large Load Diff
+66 -18
View File
@@ -23,9 +23,9 @@ namespace gl3 {
void void
drawInst_simple(InstanceDataHeader *header, InstanceData *inst) drawInst_simple(InstanceDataHeader *header, InstanceData *inst)
{ {
vglIndexPointerMapped((uint8_t*)header->indexBuffer + inst->offset); flushCache();
vglVertexAttribPointerMapped(0, header->vertexBuffer); glDrawElements(header->primType, inst->numIndex,
vglDrawObjects(header->primType, inst->numIndex); GL_UNSIGNED_SHORT, (void*)(uintptr)inst->offset);
} }
// Emulate PS2 GS alpha test FB_ONLY case: failed alpha writes to frame- but not to depth buffer // Emulate PS2 GS alpha test FB_ONLY case: failed alpha writes to frame- but not to depth buffer
@@ -74,15 +74,58 @@ drawInst(InstanceDataHeader *header, InstanceData *inst)
void void
setAttribPointers(AttribDesc *attribDescs, int32 numAttribs) setAttribPointers(AttribDesc *attribDescs, int32 numAttribs)
{ {
//vglVertexAttribPointerMapped(0, gVertexBuffer); AttribDesc *a;
#ifdef PSP2
// Geometry without PRELIT has no colour array (see instancing), so in_color
// falls back to the constant vertex attribute. GL defines that as (0,0,0,1),
// but vitaGL leaves it zeroed - alpha included - so anything unlit came out
// with alpha 0: car bodies vanished (only their matfx specular survived, and
// only while the alpha test let it through) and 3D markers never appeared.
// Set the spec's default explicitly, then let a real array override it below.
bool hasColor = false;
for(a = attribDescs; a != &attribDescs[numAttribs]; a++)
if(a->index == ATTRIB_COLOR){
hasColor = true;
break;
}
if(!hasColor){
glDisableVertexAttribArray(ATTRIB_COLOR);
glVertexAttrib4f(ATTRIB_COLOR, 0.0f, 0.0f, 0.0f, 1.0f);
}
#endif
for(a = attribDescs; a != &attribDescs[numAttribs]; a++){
glEnableVertexAttribArray(a->index);
glVertexAttribPointer(a->index, a->size, a->type, a->normalized,
a->stride, (void*)(uint64)a->offset);
}
} }
void void
disableAttribPointers(AttribDesc *attribDescs, int32 numAttribs) disableAttribPointers(AttribDesc *attribDescs, int32 numAttribs)
{ {
/*AttribDesc *a; AttribDesc *a;
for(a = attribDescs; a != &attribDescs[numAttribs]; a++) for(a = attribDescs; a != &attribDescs[numAttribs]; a++)
glDisableVertexAttribArray(a->index);*/ glDisableVertexAttribArray(a->index);
}
void
setupVertexInput(InstanceDataHeader *header)
{
#ifdef RW_GL_USE_VAOS
glBindVertexArray(header->vao);
#else
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, header->ibo);
glBindBuffer(GL_ARRAY_BUFFER, header->vbo);
setAttribPointers(header->attribDesc, header->numAttribs);
#endif
}
void
teardownVertexInput(InstanceDataHeader *header)
{
#ifndef RW_GL_USE_VAOS
disableAttribPointers(header->attribDesc, header->numAttribs);
#endif
} }
int32 int32
@@ -110,40 +153,45 @@ lightingCB(Atomic *atomic)
} }
} }
#define U(i) currentShader->uniformLocations[i]
void void
defaultRenderCB(Atomic *atomic, InstanceDataHeader *header) defaultRenderCB(Atomic *atomic, InstanceDataHeader *header)
{ {
Material *m; Material *m;
uint32 flags = atomic->geometry->flags;
setWorldMatrix(atomic->getFrame()->getLTM()); setWorldMatrix(atomic->getFrame()->getLTM());
lightingCB(atomic); int32 vsBits = lightingCB(atomic);
setAttribPointers(header->attribDesc, header->numAttribs); setupVertexInput(header);
InstanceData *inst = header->inst; InstanceData *inst = header->inst;
int32 n = header->numMeshes; int32 n = header->numMeshes;
defaultShader->use();
while(n--){ while(n--){
m = inst->material; m = inst->material;
rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF); setMaterial(flags, m->color, m->surfaceProps);
setTexture(0, m->texture); setTexture(0, m->texture);
setMaterial(m->color, m->surfaceProps); rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
flushCache(); if((vsBits & VSLIGHT_MASK) == 0){
if(getAlphaTest())
defaultShader->use();
else
defaultShader_noAT->use();
}else{
if(getAlphaTest())
defaultShader_fullLight->use();
else
defaultShader_fullLight_noAT->use();
}
drawInst(header, inst); drawInst(header, inst);
inst++; inst++;
} }
#ifndef RW_GL_USE_VAOS teardownVertexInput(header);
disableAttribPointers(header->attribDesc, header->numAttribs);
#endif
} }
+144 -58
View File
@@ -16,30 +16,60 @@
namespace rw { namespace rw {
namespace gl3 { namespace gl3 {
#ifdef PSP2_USE_SHADER_COMPILER
#ifdef RW_GLES2
#include "gl2_shaders/header_vs.inc"
#include "gl2_shaders/header_fs.inc"
#else
#include "shaders/header_vs.inc" #include "shaders/header_vs.inc"
#include "shaders/header_fs.inc" #include "shaders/header_fs.inc"
#endif
#endif
UniformRegistry uniformRegistry; UniformRegistry uniformRegistry;
static char nameBuffer[(MAX_UNIFORMS + MAX_BLOCKS)*32]; // static because memory system isn't up yet when we register
static uint32 nameBufPtr;
static float uniformData[512*4]; // seems enough
static uint32 dataPtr;
static int uniformTypesize[] = {
0, 4, 4, 16
};
static char*
shader_strdup(const char *name)
{
size_t len = strlen(name)+1;
char *s = &nameBuffer[nameBufPtr];
nameBufPtr += len;
assert(nameBufPtr <= nelem(nameBuffer));
memcpy(s, name, len);
return s;
}
int32 int32
registerUniform(const char *name) registerUniform(const char *name, UniformType type, int32 num)
{ {
int i; int i;
i = findUniform(name); i = findUniform(name);
if(i >= 0) return i; if(i >= 0){
Uniform *u = &uniformRegistry.uniforms[i];
assert(u->type == type);
assert(u->num == num);
return i;
}
// TODO: print error // TODO: print error
if(uniformRegistry.numUniforms+1 >= MAX_UNIFORMS){ if(uniformRegistry.numUniforms+1 >= MAX_UNIFORMS){
assert(0 && "no space for uniform"); assert(0 && "no space for uniform");
return -1; return -1;
} }
uniformRegistry.uniformNames[uniformRegistry.numUniforms] = strdup(name); Uniform *u = &uniformRegistry.uniforms[uniformRegistry.numUniforms];
u->name = shader_strdup(name);
u->type = type;
u->serialNum = 0;
if(type == UNIFORM_NA){
u->num = 0;
u->data = nil;
}else{
u->num = num;
u->data = &uniformData[dataPtr];
dataPtr += uniformTypesize[type]*num;
assert(dataPtr <= nelem(uniformData));
}
return uniformRegistry.numUniforms++; return uniformRegistry.numUniforms++;
} }
@@ -48,7 +78,7 @@ findUniform(const char *name)
{ {
int i; int i;
for(i = 0; i < uniformRegistry.numUniforms; i++) for(i = 0; i < uniformRegistry.numUniforms; i++)
if(strcmp(name, uniformRegistry.uniformNames[i]) == 0) if(strcmp(name, uniformRegistry.uniforms[i].name) == 0)
return i; return i;
return -1; return -1;
} }
@@ -62,7 +92,7 @@ registerBlock(const char *name)
// TODO: print error // TODO: print error
if(uniformRegistry.numBlocks+1 >= MAX_BLOCKS) if(uniformRegistry.numBlocks+1 >= MAX_BLOCKS)
return -1; return -1;
uniformRegistry.blockNames[uniformRegistry.numBlocks] = strdup(name); uniformRegistry.blockNames[uniformRegistry.numBlocks] = shader_strdup(name);
return uniformRegistry.numBlocks++; return uniformRegistry.numBlocks++;
} }
@@ -76,6 +106,51 @@ findBlock(const char *name)
return -1; return -1;
} }
void
setUniform(int32 id, void *data)
{
Uniform *u = &uniformRegistry.uniforms[id];
assert(u->type != UNIFORM_NA);
if(memcmp(u->data, data, uniformTypesize[u->type]*u->num * sizeof(float)) != 0){
memcpy(u->data, data, uniformTypesize[u->type]*u->num * sizeof(float));
//u->dirty = true;
u->serialNum++;
}
}
void
flushUniforms(void)
{
for(int i = 0; i < uniformRegistry.numUniforms; i++){
// this is bad!
if(i >= currentShader->numUniforms){
printf("trying to set uniform %d %s that doesn't exist!\n", i, uniformRegistry.uniforms[i].name);
continue;
}
int32 loc = currentShader->uniformLocations[i];
if(loc == -1)
continue;
Uniform *u = &uniformRegistry.uniforms[i];
if(currentShader->serialNums[i] != u->serialNum)
switch(u->type){
case UNIFORM_NA:
break;
case UNIFORM_VEC4:
glUniform4fv(loc, u->num, (GLfloat*)u->data);
break;
case UNIFORM_IVEC4:
glUniform4iv(loc, u->num, (GLint*)u->data);
break;
case UNIFORM_MAT4:
glUniformMatrix4fv(loc, u->num, GL_FALSE, (GLfloat*)u->data);
break;
}
currentShader->serialNums[i] = u->serialNum;
}
}
Shader *currentShader; Shader *currentShader;
static void static void
@@ -100,36 +175,18 @@ printShaderSource(const char **src)
} }
} }
char shader_source_buffer[16 * 1024];
static int static int
compileshader(GLenum type, const char **src, GLuint *shader) compileshader(GLenum type, const char **src, GLuint *shader)
{ {
#ifdef PSP2_USE_SHADER_COMPILER
// vitaGL treats GL_VERTEX_SHADER/GL_FRAGMENT_SHADER as GLSL and runs its
// translator over the source; the shaders below are Cg, so ask for the
// Cg frontend explicitly.
GLenum shdrtype = type == GL_VERTEX_SHADER ?
GL_CG_VERTEX_SHADER_EXT : GL_CG_FRAGMENT_SHADER_EXT;
#else
GLenum shdrtype = type;
#endif
GLint shdr = glCreateShader(shdrtype);
#ifdef PSP2_USE_SHADER_COMPILER
GLint n; GLint n;
GLint success; GLint shdr, success;
GLint len; GLint len;
char *log; char *log;
shader_source_buffer[0] = 0; for(n = 0; src[n]; n++);
for(n = 0; src[n]; n++) { shdr = glCreateShader(type);
sprintf(shader_source_buffer, "%s%s", shader_source_buffer, src[n]); glShaderSource(shdr, n, src, nil);
}
const char *_src = (const char*)shader_source_buffer;
glShaderSource(shdr, 1, &_src, nil);
glCompileShader(shdr); glCompileShader(shdr);
glGetShaderiv(shdr, GL_COMPILE_STATUS, &success); glGetShaderiv(shdr, GL_COMPILE_STATUS, &success);
if(!success){ if(!success){
@@ -145,16 +202,10 @@ compileshader(GLenum type, const char **src, GLuint *shader)
} }
*shader = shdr; *shader = shdr;
return 0; return 0;
#else
unsigned int size = *((unsigned int*)src[1]);
glShaderBinary(1, (const uint32_t*)&shdr, 0, src[0], size - 1);
*shader = shdr;
return 0;
#endif
} }
static int static int
linkprogram(GLint vs, GLint fs, GLuint *program, bool is_2d) linkprogram(GLint vs, GLint fs, GLuint *program)
{ {
GLint prog, success; GLint prog, success;
GLint len; GLint len;
@@ -162,26 +213,40 @@ linkprogram(GLint vs, GLint fs, GLuint *program, bool is_2d)
prog = glCreateProgram(); prog = glCreateProgram();
// Attach before binding attribute locations. GL allows either order, but
// vitaGL's glBindAttribLocation dereferences the program's vertex shader
// right away, so binding first would hit a null pointer there.
glAttachShader(prog, vs); glAttachShader(prog, vs);
glAttachShader(prog, fs); glAttachShader(prog, fs);
int stride = 0; if(gl3Caps.glversion < 30){
int pos_size = is_2d ? 4 : 3; // TODO: perhaps just do this always and get rid of the layout stuff?
stride += vglBindPackedAttribLocation(prog, "in_pos" , pos_size, GL_FLOAT, stride, stride + sizeof(float) * pos_size) * (sizeof(float) * pos_size); glBindAttribLocation(prog, ATTRIB_POS, "in_pos");
stride += vglBindPackedAttribLocation(prog, "in_normal" , 3, GL_FLOAT, stride, stride + sizeof(float) * 3) * (sizeof(float) * 3); glBindAttribLocation(prog, ATTRIB_NORMAL, "in_normal");
stride += vglBindPackedAttribLocation(prog, "in_color" , 4, GL_UNSIGNED_BYTE, stride, stride + 4) * 4; glBindAttribLocation(prog, ATTRIB_COLOR, "in_color");
stride += vglBindPackedAttribLocation(prog, "in_tex0" , 2, GL_FLOAT, stride, stride + sizeof(float) * 2) * (sizeof(float) * 2); glBindAttribLocation(prog, ATTRIB_WEIGHTS, "in_weights");
stride += vglBindPackedAttribLocation(prog, "in_weights", 4, GL_FLOAT, stride, stride + sizeof(float) * 4) * (sizeof(float) * 4); glBindAttribLocation(prog, ATTRIB_INDICES, "in_indices");
vglBindPackedAttribLocation(prog, "in_indices", 4, GL_UNSIGNED_BYTE, stride, stride + 4); glBindAttribLocation(prog, ATTRIB_TEXCOORDS0, "in_tex0");
glBindAttribLocation(prog, ATTRIB_TEXCOORDS1, "in_tex1");
}
glLinkProgram(prog); glLinkProgram(prog);
glGetProgramiv(prog, GL_LINK_STATUS, &success);
if(!success){
fprintf(stderr, "Error in program\n");
glGetProgramiv(prog, GL_INFO_LOG_LENGTH, &len);
log = (char*)rwMalloc(len, MEMDUR_FUNCTION);
glGetProgramInfoLog(prog, len, nil, log);
fprintf(stderr, "%s\n", log);
rwFree(log);
return 1;
}
*program = prog; *program = prog;
return 0; return 0;
} }
Shader* Shader*
Shader::create(const char **vsrc, const char **fsrc, bool is_2d) Shader::create(const char **vsrc, const char **fsrc)
{ {
GLuint vs, fs, program; GLuint vs, fs, program;
int i; int i;
@@ -197,10 +262,11 @@ Shader::create(const char **vsrc, const char **fsrc, bool is_2d)
return nil; return nil;
} }
fail = linkprogram(vs, fs, &program, is_2d); fail = linkprogram(vs, fs, &program);
if(fail){
glDeleteShader(fs);
glDeleteShader(vs); glDeleteShader(vs);
glDeleteShader(fs);
if(fail){
return nil; return nil;
} }
@@ -233,15 +299,34 @@ Shader::create(const char **vsrc, const char **fsrc, bool is_2d)
printf("\n"); printf("\n");
#endif #endif
// set uniform block binding
for(i = 0; i < uniformRegistry.numBlocks; i++){
int idx = glGetUniformBlockIndex(program,
uniformRegistry.blockNames[i]);
if(idx >= 0)
glUniformBlockBinding(program, idx, i);
}
// query uniform locations // query uniform locations
sh->program = program; sh->program = program;
sh->numUniforms = uniformRegistry.numUniforms;
sh->uniformLocations = rwNewT(GLint, uniformRegistry.numUniforms, MEMDUR_EVENT | ID_DRIVER); sh->uniformLocations = rwNewT(GLint, uniformRegistry.numUniforms, MEMDUR_EVENT | ID_DRIVER);
for(i = 0; i < uniformRegistry.numUniforms; i++) sh->serialNums = rwNewT(uint32, uniformRegistry.numUniforms, MEMDUR_EVENT | ID_DRIVER);
for(i = 0; i < uniformRegistry.numUniforms; i++){
sh->uniformLocations[i] = glGetUniformLocation(program, sh->uniformLocations[i] = glGetUniformLocation(program,
uniformRegistry.uniformNames[i]); uniformRegistry.uniforms[i].name);
sh->serialNums[i] = ~0; // let's hope this means dirty
}
// set samplers // set samplers
glUseProgram(program); glUseProgram(program);
char name[64];
GLint loc;
for(i = 0; i < 4; i++){
sprintf(name, "tex%d", i);
loc = glGetUniformLocation(program, name);
glUniform1i(loc, i);
}
// reset program // reset program
if(currentShader) if(currentShader)
@@ -253,10 +338,10 @@ Shader::create(const char **vsrc, const char **fsrc, bool is_2d)
void void
Shader::use(void) Shader::use(void)
{ {
//if(currentShader != this){ if(currentShader != this){
glUseProgram(this->program); glUseProgram(this->program);
currentShader = this; currentShader = this;
//} }
} }
void void
@@ -264,6 +349,7 @@ Shader::destroy(void)
{ {
glDeleteProgram(this->program); glDeleteProgram(this->program);
rwFree(this->uniformLocations); rwFree(this->uniformLocations);
rwFree(this->serialNums);
rwFree(this); rwFree(this);
} }
+63 -53
View File
@@ -12,22 +12,20 @@
#include "../rwobjects.h" #include "../rwobjects.h"
#include "../rwanim.h" #include "../rwanim.h"
#include "../rwplugins.h" #include "../rwplugins.h"
#include "rwgl3.h" #include "rwgl3.h"
#include "rwgl3shader.h" #include "rwgl3shader.h"
#include "rwgl3plg.h" #include "rwgl3plg.h"
#include "rwgl3impl.h" #include "rwgl3impl.h"
#include "psp2_shaders.h"
namespace rw { namespace rw {
namespace gl3 { namespace gl3 {
#ifdef RW_OPENGL #ifdef RW_OPENGL
#define U(i) currentShader->uniformLocations[i] static Shader *skinShader, *skinShader_noAT;
static Shader *skinShader_fullLight, *skinShader_fullLight_noAT;
static Shader *skinShader;
static int32 u_boneMatrices; static int32 u_boneMatrices;
void void
@@ -65,9 +63,9 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
a->type = GL_FLOAT; a->type = GL_FLOAT;
a->normalized = GL_FALSE; a->normalized = GL_FALSE;
a->offset = stride; a->offset = stride;
stride += 12;
a++; a++;
} }
stride += 12;
// Prelighting // Prelighting
if(isPrelit){ if(isPrelit){
@@ -76,9 +74,9 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
a->type = GL_UNSIGNED_BYTE; a->type = GL_UNSIGNED_BYTE;
a->normalized = GL_TRUE; a->normalized = GL_TRUE;
a->offset = stride; a->offset = stride;
stride += 4;
a++; a++;
} }
stride += 4;
// Texture coordinates // Texture coordinates
for(int32 n = 0; n < geo->numTexCoordSets; n++){ for(int32 n = 0; n < geo->numTexCoordSets; n++){
@@ -113,15 +111,15 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
for(a = tmpAttribs; a != &tmpAttribs[header->numAttribs]; a++) for(a = tmpAttribs; a != &tmpAttribs[header->numAttribs]; a++)
a->stride = stride; a->stride = stride;
header->attribDesc = rwNewT(AttribDesc, header->numAttribs, MEMDUR_EVENT | ID_GEOMETRY); header->attribDesc = rwNewT(AttribDesc, header->numAttribs, MEMDUR_EVENT | ID_GEOMETRY);
memcpy_neon(header->attribDesc, tmpAttribs, memcpy(header->attribDesc, tmpAttribs,
header->numAttribs*sizeof(AttribDesc)); header->numAttribs*sizeof(AttribDesc));
// //
// Allocate vertex buffer // Allocate vertex buffer
// //
header->vertexBuffer = rwNewT(uint8, header->totalNumVertex*stride, MEMDUR_EVENT | ID_GEOMETRY); header->vertexBuffer = rwNewT(uint8, header->totalNumVertex*stride, MEMDUR_EVENT | ID_GEOMETRY);
//assert(header->vbo == 0); assert(header->vbo == 0);
//glGenBuffers(1, &header->vbo); glGenBuffers(1, &header->vbo);
} }
Skin *skin = Skin::get(geo); Skin *skin = Skin::get(geo);
@@ -131,7 +129,7 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
// Fill vertex buffer // Fill vertex buffer
// //
uint8 *verts = (uint8*)header->vertexBuffer; uint8 *verts = header->vertexBuffer;
// Positions // Positions
if(!reinstance || geo->lockedSinceInst&Geometry::LOCKVERTICES){ if(!reinstance || geo->lockedSinceInst&Geometry::LOCKVERTICES){
@@ -149,11 +147,6 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
instV3d(VERT_FLOAT3, verts + a->offset, instV3d(VERT_FLOAT3, verts + a->offset,
geo->morphTargets[0].normals, geo->morphTargets[0].normals,
header->totalNumVertex, a->stride); header->totalNumVertex, a->stride);
} else if (!hasNormals) {
for (int i = 0; i < header->totalNumVertex; i++) {
float *verts_f = (float*)&verts[12 + i * 56];
verts_f[0] = verts_f[1] = verts_f[2] = 0.0f;
}
} }
// Prelighting // Prelighting
@@ -163,13 +156,6 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
instColor(VERT_RGBA, verts + a->offset, instColor(VERT_RGBA, verts + a->offset,
geo->colors, geo->colors,
header->totalNumVertex, a->stride); header->totalNumVertex, a->stride);
} else if (!isPrelit) {
for (int i = 0; i < header->totalNumVertex; i++) {
verts[24 + i * 56] = 0;
verts[25 + i * 56] = 0;
verts[26 + i * 56] = 0;
verts[27 + i * 56] = 255;
}
} }
// Texture coordinates // Texture coordinates
@@ -202,6 +188,18 @@ skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
(RGBA*)skin->indices, (RGBA*)skin->indices,
header->totalNumVertex, a->stride); header->totalNumVertex, a->stride);
} }
#ifdef RW_GL_USE_VAOS
glBindVertexArray(header->vao);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, header->ibo);
#endif
glBindBuffer(GL_ARRAY_BUFFER, header->vbo);
glBufferData(GL_ARRAY_BUFFER, header->totalNumVertex*attribs[0].stride,
header->vertexBuffer, GL_STATIC_DRAW);
#ifdef RW_GL_USE_VAOS
setAttribPointers(header->attribDesc, header->numAttribs);
glBindVertexArray(0);
#endif
} }
void void
@@ -247,8 +245,7 @@ uploadSkinMatrices(Atomic *a)
m++; m++;
} }
} }
glUniformMatrix4fv(U(u_boneMatrices), 64, GL_FALSE, setUniform(u_boneMatrices, skinMatrices);
(GLfloat*)skinMatrices);
} }
void void
@@ -256,58 +253,65 @@ skinRenderCB(Atomic *atomic, InstanceDataHeader *header)
{ {
Material *m; Material *m;
uint32 flags = atomic->geometry->flags;
setWorldMatrix(atomic->getFrame()->getLTM()); setWorldMatrix(atomic->getFrame()->getLTM());
lightingCB(atomic); int32 vsBits = lightingCB(atomic);
setAttribPointers(header->attribDesc, header->numAttribs); setupVertexInput(header);
InstanceData *inst = header->inst; InstanceData *inst = header->inst;
int32 n = header->numMeshes; int32 n = header->numMeshes;
skinShader->use(); uploadSkinMatrices(atomic);
while(n--){ while(n--){
m = inst->material; m = inst->material;
rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF); setMaterial(flags, m->color, m->surfaceProps);
setTexture(0, m->texture); setTexture(0, m->texture);
setMaterial(m->color, m->surfaceProps); rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
flushCache(); if((vsBits & VSLIGHT_MASK) == 0){
if(getAlphaTest())
uploadSkinMatrices(atomic); skinShader->use();
else
skinShader_noAT->use();
}else{
if(getAlphaTest())
skinShader_fullLight->use();
else
skinShader_fullLight_noAT->use();
}
drawInst(header, inst); drawInst(header, inst);
inst++; inst++;
} }
#ifndef RW_GL_USE_VAOS teardownVertexInput(header);
disableAttribPointers(header->attribDesc, header->numAttribs);
#endif
} }
static void* static void*
skinOpen(void *o, int32, int32) skinOpen(void *o, int32, int32)
{ {
skinGlobals.pipelines[PLATFORM_GL3] = makeSkinPipeline(); skinGlobals.pipelines[PLATFORM_GL3] = makeSkinPipeline();
#ifdef PSP2_USE_SHADER_COMPILER
#ifdef RW_GLES2 #include "shaders/simple_fs_gl.inc"
#include "gl2_shaders/simple_fs_gl2.inc" #include "shaders/skin_gl.inc"
#include "gl2_shaders/skin_gl2.inc" const char *vs[] = { shaderDecl, header_vert_src, skin_vert_src, nil };
#else const char *vs_fullLight[] = { shaderDecl, "#define DIRECTIONALS\n#define POINTLIGHTS\n#define SPOTLIGHTS\n", header_vert_src, skin_vert_src, nil };
#include "shaders/simple_fs_gl3.inc" const char *fs[] = { shaderDecl, header_frag_src, simple_frag_src, nil };
#include "shaders/skin_gl3.inc" const char *fs_noAT[] = { shaderDecl, "#define NO_ALPHATEST\n", header_frag_src, simple_frag_src, nil };
#endif
const char *vs[] = { header_vert_src, skin_vert_src, nil }; skinShader = Shader::create(vs, fs);
const char *fs[] = { header_frag_src, simple_frag_src, nil };
skinShader = Shader::create(vs, fs, false);
#else
const char *vs[] = { (const char*)skin_v, (const char*)&size_skin_v, nil };
const char *fs[] = { (const char*)simple_f, (const char*)&size_simple_f, nil };
skinShader = Shader::create(vs, fs, false);
#endif
assert(skinShader); assert(skinShader);
skinShader_noAT = Shader::create(vs, fs_noAT);
assert(skinShader_noAT);
skinShader_fullLight = Shader::create(vs_fullLight, fs);
assert(skinShader_fullLight);
skinShader_fullLight_noAT = Shader::create(vs_fullLight, fs_noAT);
assert(skinShader_fullLight_noAT);
return o; return o;
} }
@@ -320,6 +324,12 @@ skinClose(void *o, int32, int32)
skinShader->destroy(); skinShader->destroy();
skinShader = nil; skinShader = nil;
skinShader_noAT->destroy();
skinShader_noAT = nil;
skinShader_fullLight->destroy();
skinShader_fullLight = nil;
skinShader_fullLight_noAT->destroy();
skinShader_fullLight_noAT = nil;
return o; return o;
} }
@@ -327,7 +337,7 @@ skinClose(void *o, int32, int32)
void void
initSkin(void) initSkin(void)
{ {
u_boneMatrices = registerUniform("u_boneMatrices"); u_boneMatrices = registerUniform("u_boneMatrices", UNIFORM_MAT4, 64);
Driver::registerPlugin(PLATFORM_GL3, 0, ID_SKIN, Driver::registerPlugin(PLATFORM_GL3, 0, ID_SKIN,
skinOpen, skinClose); skinOpen, skinClose);
+1590
View File
File diff suppressed because it is too large Load Diff
+2808
View File
File diff suppressed because it is too large Load Diff
+290
View File
@@ -0,0 +1,290 @@
#ifndef __khrplatform_h_
#define __khrplatform_h_
/*
** Copyright (c) 2008-2018 The Khronos Group Inc.
**
** Permission is hereby granted, free of charge, to any person obtaining a
** copy of this software and/or associated documentation files (the
** "Materials"), to deal in the Materials without restriction, including
** without limitation the rights to use, copy, modify, merge, publish,
** distribute, sublicense, and/or sell copies of the Materials, and to
** permit persons to whom the Materials are furnished to do so, subject to
** the following conditions:
**
** The above copyright notice and this permission notice shall be included
** in all copies or substantial portions of the Materials.
**
** THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
** EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
** MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
** IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
** CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
** TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
** MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
*/
/* Khronos platform-specific types and definitions.
*
* The master copy of khrplatform.h is maintained in the Khronos EGL
* Registry repository at https://github.com/KhronosGroup/EGL-Registry
* The last semantic modification to khrplatform.h was at commit ID:
* 67a3e0864c2d75ea5287b9f3d2eb74a745936692
*
* Adopters may modify this file to suit their platform. Adopters are
* encouraged to submit platform specific modifications to the Khronos
* group so that they can be included in future versions of this file.
* Please submit changes by filing pull requests or issues on
* the EGL Registry repository linked above.
*
*
* See the Implementer's Guidelines for information about where this file
* should be located on your system and for more details of its use:
* http://www.khronos.org/registry/implementers_guide.pdf
*
* This file should be included as
* #include <KHR/khrplatform.h>
* by Khronos client API header files that use its types and defines.
*
* The types in khrplatform.h should only be used to define API-specific types.
*
* Types defined in khrplatform.h:
* khronos_int8_t signed 8 bit
* khronos_uint8_t unsigned 8 bit
* khronos_int16_t signed 16 bit
* khronos_uint16_t unsigned 16 bit
* khronos_int32_t signed 32 bit
* khronos_uint32_t unsigned 32 bit
* khronos_int64_t signed 64 bit
* khronos_uint64_t unsigned 64 bit
* khronos_intptr_t signed same number of bits as a pointer
* khronos_uintptr_t unsigned same number of bits as a pointer
* khronos_ssize_t signed size
* khronos_usize_t unsigned size
* khronos_float_t signed 32 bit floating point
* khronos_time_ns_t unsigned 64 bit time in nanoseconds
* khronos_utime_nanoseconds_t unsigned time interval or absolute time in
* nanoseconds
* khronos_stime_nanoseconds_t signed time interval in nanoseconds
* khronos_boolean_enum_t enumerated boolean type. This should
* only be used as a base type when a client API's boolean type is
* an enum. Client APIs which use an integer or other type for
* booleans cannot use this as the base type for their boolean.
*
* Tokens defined in khrplatform.h:
*
* KHRONOS_FALSE, KHRONOS_TRUE Enumerated boolean false/true values.
*
* KHRONOS_SUPPORT_INT64 is 1 if 64 bit integers are supported; otherwise 0.
* KHRONOS_SUPPORT_FLOAT is 1 if floats are supported; otherwise 0.
*
* Calling convention macros defined in this file:
* KHRONOS_APICALL
* KHRONOS_APIENTRY
* KHRONOS_APIATTRIBUTES
*
* These may be used in function prototypes as:
*
* KHRONOS_APICALL void KHRONOS_APIENTRY funcname(
* int arg1,
* int arg2) KHRONOS_APIATTRIBUTES;
*/
#if defined(__SCITECH_SNAP__) && !defined(KHRONOS_STATIC)
# define KHRONOS_STATIC 1
#endif
/*-------------------------------------------------------------------------
* Definition of KHRONOS_APICALL
*-------------------------------------------------------------------------
* This precedes the return type of the function in the function prototype.
*/
#if defined(KHRONOS_STATIC)
/* If the preprocessor constant KHRONOS_STATIC is defined, make the
* header compatible with static linking. */
# define KHRONOS_APICALL
#elif defined(_WIN32)
# define KHRONOS_APICALL __declspec(dllimport)
#elif defined (__SYMBIAN32__)
# define KHRONOS_APICALL IMPORT_C
#elif defined(__ANDROID__)
# define KHRONOS_APICALL __attribute__((visibility("default")))
#else
# define KHRONOS_APICALL
#endif
/*-------------------------------------------------------------------------
* Definition of KHRONOS_APIENTRY
*-------------------------------------------------------------------------
* This follows the return type of the function and precedes the function
* name in the function prototype.
*/
#if defined(_WIN32) && !defined(_WIN32_WCE) && !defined(__SCITECH_SNAP__)
/* Win32 but not WinCE */
# define KHRONOS_APIENTRY __stdcall
#else
# define KHRONOS_APIENTRY
#endif
/*-------------------------------------------------------------------------
* Definition of KHRONOS_APIATTRIBUTES
*-------------------------------------------------------------------------
* This follows the closing parenthesis of the function prototype arguments.
*/
#if defined (__ARMCC_2__)
#define KHRONOS_APIATTRIBUTES __softfp
#else
#define KHRONOS_APIATTRIBUTES
#endif
/*-------------------------------------------------------------------------
* basic type definitions
*-----------------------------------------------------------------------*/
#if (defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) || defined(__GNUC__) || defined(__SCO__) || defined(__USLC__)
/*
* Using <stdint.h>
*/
#include <stdint.h>
typedef int32_t khronos_int32_t;
typedef uint32_t khronos_uint32_t;
typedef int64_t khronos_int64_t;
typedef uint64_t khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif defined(__VMS ) || defined(__sgi)
/*
* Using <inttypes.h>
*/
#include <inttypes.h>
typedef int32_t khronos_int32_t;
typedef uint32_t khronos_uint32_t;
typedef int64_t khronos_int64_t;
typedef uint64_t khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif defined(_WIN32) && !defined(__SCITECH_SNAP__)
/*
* Win32
*/
typedef __int32 khronos_int32_t;
typedef unsigned __int32 khronos_uint32_t;
typedef __int64 khronos_int64_t;
typedef unsigned __int64 khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif defined(__sun__) || defined(__digital__)
/*
* Sun or Digital
*/
typedef int khronos_int32_t;
typedef unsigned int khronos_uint32_t;
#if defined(__arch64__) || defined(_LP64)
typedef long int khronos_int64_t;
typedef unsigned long int khronos_uint64_t;
#else
typedef long long int khronos_int64_t;
typedef unsigned long long int khronos_uint64_t;
#endif /* __arch64__ */
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#elif 0
/*
* Hypothetical platform with no float or int64 support
*/
typedef int khronos_int32_t;
typedef unsigned int khronos_uint32_t;
#define KHRONOS_SUPPORT_INT64 0
#define KHRONOS_SUPPORT_FLOAT 0
#else
/*
* Generic fallback
*/
#include <stdint.h>
typedef int32_t khronos_int32_t;
typedef uint32_t khronos_uint32_t;
typedef int64_t khronos_int64_t;
typedef uint64_t khronos_uint64_t;
#define KHRONOS_SUPPORT_INT64 1
#define KHRONOS_SUPPORT_FLOAT 1
#endif
/*
* Types that are (so far) the same on all platforms
*/
typedef signed char khronos_int8_t;
typedef unsigned char khronos_uint8_t;
typedef signed short int khronos_int16_t;
typedef unsigned short int khronos_uint16_t;
/*
* Types that differ between LLP64 and LP64 architectures - in LLP64,
* pointers are 64 bits, but 'long' is still 32 bits. Win64 appears
* to be the only LLP64 architecture in current use.
*/
#ifdef _WIN64
typedef signed long long int khronos_intptr_t;
typedef unsigned long long int khronos_uintptr_t;
typedef signed long long int khronos_ssize_t;
typedef unsigned long long int khronos_usize_t;
#else
typedef signed long int khronos_intptr_t;
typedef unsigned long int khronos_uintptr_t;
typedef signed long int khronos_ssize_t;
typedef unsigned long int khronos_usize_t;
#endif
#if KHRONOS_SUPPORT_FLOAT
/*
* Float type
*/
typedef float khronos_float_t;
#endif
#if KHRONOS_SUPPORT_INT64
/* Time types
*
* These types can be used to represent a time interval in nanoseconds or
* an absolute Unadjusted System Time. Unadjusted System Time is the number
* of nanoseconds since some arbitrary system event (e.g. since the last
* time the system booted). The Unadjusted System Time is an unsigned
* 64 bit value that wraps back to 0 every 584 years. Time intervals
* may be either signed or unsigned.
*/
typedef khronos_uint64_t khronos_utime_nanoseconds_t;
typedef khronos_int64_t khronos_stime_nanoseconds_t;
#endif
/*
* Dummy value used to pad enum types to 32 bits.
*/
#ifndef KHRONOS_MAX_ENUM
#define KHRONOS_MAX_ENUM 0x7FFFFFFF
#endif
/*
* Enumerated boolean type
*
* Values other than zero should be considered to be true. Therefore
* comparisons should not be made against KHRONOS_TRUE.
*/
typedef enum {
KHRONOS_FALSE = 0,
KHRONOS_TRUE = 1,
KHRONOS_BOOLEAN_ENUM_FORCE_SIZE = KHRONOS_MAX_ENUM
} khronos_boolean_enum_t;
#endif /* __khrplatform_h_ */
+45 -21
View File
@@ -1,19 +1,10 @@
#ifdef RW_GL3 #ifdef RW_GL3
#ifdef __SWITCH__ // switch must be included early for some defines that are needed later on for opengl stuff
#include <switch.h>
#endif
#ifdef PSP2 #ifdef PSP2
// Vita uses vitaGL as its GL implementation; no glad/GLFW/SDL windowing here.
#include <vitasdk.h> #include <vitasdk.h>
#include <vitaGL.h> #include <vitaGL.h>
#else #else
#ifndef LIBRW_GLAD #include "glad/glad.h"
#include <GL/glew.h>
#else
#include <glad/glad.h>
#endif
#ifdef LIBRW_SDL2 #ifdef LIBRW_SDL2
#include <SDL.h> #include <SDL.h>
#else #else
@@ -60,18 +51,16 @@ enum AttribIndices
ATTRIB_POS = 0, ATTRIB_POS = 0,
ATTRIB_NORMAL, ATTRIB_NORMAL,
ATTRIB_COLOR, ATTRIB_COLOR,
ATTRIB_WEIGHTS,
ATTRIB_INDICES,
ATTRIB_TEXCOORDS0, ATTRIB_TEXCOORDS0,
ATTRIB_TEXCOORDS1, ATTRIB_TEXCOORDS1,
#ifndef RW_GLES2
ATTRIB_TEXCOORDS2, ATTRIB_TEXCOORDS2,
ATTRIB_TEXCOORDS3, ATTRIB_TEXCOORDS3,
ATTRIB_TEXCOORDS4, ATTRIB_TEXCOORDS4,
ATTRIB_TEXCOORDS5, ATTRIB_TEXCOORDS5,
ATTRIB_TEXCOORDS6, ATTRIB_TEXCOORDS6,
ATTRIB_TEXCOORDS7, ATTRIB_TEXCOORDS7,
#endif
ATTRIB_WEIGHTS,
ATTRIB_INDICES
}; };
// default uniform indices // default uniform indices
@@ -114,7 +103,8 @@ struct InstanceDataHeader : rw::InstanceDataHeader
struct Shader; struct Shader;
extern Shader *defaultShader; extern Shader *defaultShader, *defaultShader_noAT;
extern Shader *defaultShader_fullLight, *defaultShader_fullLight_noAT;
struct Im3DVertex struct Im3DVertex
{ {
@@ -147,8 +137,9 @@ struct Im2DVertex
void setScreenX(float32 x) { this->x = x; } void setScreenX(float32 x) { this->x = x; }
void setScreenY(float32 y) { this->y = y; } void setScreenY(float32 y) { this->y = y; }
void setScreenZ(float32 z) { this->z = z; } void setScreenZ(float32 z) { this->z = z; }
// This is a bit unefficient but we have to counteract GL's divide, so multiply
void setCameraZ(float32 z) { this->w = z; } void setCameraZ(float32 z) { this->w = z; }
void setRecipCameraZ(float32 recipz) { } void setRecipCameraZ(float32 recipz) { this->w = 1.0f/recipz; }
void setColor(uint8 r, uint8 g, uint8 b, uint8 a) { void setColor(uint8 r, uint8 g, uint8 b, uint8 a) {
this->r = r; this->g = g; this->b = b; this->a = a; } this->r = r; this->g = g; this->b = b; this->a = a; }
void setU(float32 u, float recipz) { this->u = u; } void setU(float32 u, float recipz) { this->u = u; }
@@ -166,6 +157,8 @@ struct Im2DVertex
void setAttribPointers(AttribDesc *attribDescs, int32 numAttribs); void setAttribPointers(AttribDesc *attribDescs, int32 numAttribs);
void disableAttribPointers(AttribDesc *attribDescs, int32 numAttribs); void disableAttribPointers(AttribDesc *attribDescs, int32 numAttribs);
void setupVertexInput(InstanceDataHeader *header);
void teardownVertexInput(InstanceDataHeader *header);
// Render state // Render state
@@ -197,11 +190,21 @@ int32 setLights(WorldLights *lightData);
// per Mesh // per Mesh
void setTexture(int32 n, Texture *tex); void setTexture(int32 n, Texture *tex);
void setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops); void setMaterial(const RGBA &color, const SurfaceProperties &surfaceprops, float extraSurfProp = 0.0f);
inline void setMaterial(uint32 flags, const RGBA &color, const SurfaceProperties &surfaceprops, float extraSurfProp = 0.0f)
{
static RGBA white = { 255, 255, 255, 255 };
if(flags & Geometry::MODULATE)
setMaterial(color, surfaceprops, extraSurfProp);
else
setMaterial(white, surfaceprops, extraSurfProp);
}
void setAlphaBlend(bool32 enable); void setAlphaBlend(bool32 enable);
bool32 getAlphaBlend(void); bool32 getAlphaBlend(void);
bool32 getAlphaTest(void);
void bindFramebuffer(uint32 fbo); void bindFramebuffer(uint32 fbo);
uint32 bindTexture(uint32 texid); uint32 bindTexture(uint32 texid);
@@ -238,8 +241,6 @@ ObjPipeline *makeDefaultPipeline(void);
// Native Texture and Raster // Native Texture and Raster
extern int32 nativeRasterOffset;
struct Gl3Raster struct Gl3Raster
{ {
// arguments to glTexImage2D // arguments to glTexImage2D
@@ -250,21 +251,44 @@ struct Gl3Raster
// texture object // texture object
uint32 texid; uint32 texid;
bool32 hasAlpha; bool isCompressed;
bool hasAlpha;
bool autogenMipmap;
int8 numLevels;
// cached filtermode and addressing // cached filtermode and addressing
uint8 filterMode; uint8 filterMode;
uint8 addressU; uint8 addressU;
uint8 addressV; uint8 addressV;
int32 maxAnisotropy;
uint32 fbo; // used for camera texture only! uint32 fbo; // used for camera texture only!
Raster *fboMate; // color or zbuffer raster mate of this one Raster *fboMate; // color or zbuffer raster mate of this one
RasterLevels *backingStore; // if we can't read back GPU memory but have to
}; };
struct Gl3Caps
{
int gles;
int glversion;
bool dxtSupported;
bool astcSupported; // not used yet
float maxAnisotropy;
};
extern Gl3Caps gl3Caps;
// GLES can't read back textures very nicely.
// In most cases that's not an issue, but when it is,
// this has to be set before the texture is filled:
extern bool32 needToReadBackTextures;
void allocateDXT(Raster *raster, int32 dxt, int32 numLevels, bool32 hasAlpha);
Texture *readNativeTexture(Stream *stream); Texture *readNativeTexture(Stream *stream);
void writeNativeTexture(Texture *tex, Stream *stream); void writeNativeTexture(Texture *tex, Stream *stream);
uint32 getSizeNativeTexture(Texture *tex); uint32 getSizeNativeTexture(Texture *tex);
extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);
#define GETGL3RASTEREXT(raster) PLUGINOFFSET(Gl3Raster, raster, rw::gl3::nativeRasterOffset)
} }
} }
+49
View File
@@ -21,6 +21,54 @@ void im3DTransform(void *vertices, int32 numVertices, Matrix *world, uint32 flag
void im3DRenderPrimitive(PrimitiveType primType); void im3DRenderPrimitive(PrimitiveType primType);
void im3DRenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices); void im3DRenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices);
void im3DEnd(void); void im3DEnd(void);
struct DisplayMode
{
#ifdef LIBRW_SDL2
SDL_DisplayMode mode;
#elif defined(PSP2)
// there is only one mode on Vita, but keep the shape of GLFWvidmode
// so the generic code below compiles unchanged
struct {
int width, height;
int redBits, greenBits, blueBits;
int refreshRate;
} mode;
#else
GLFWvidmode mode;
#endif
int32 depth;
uint32 flags;
};
struct GlGlobals
{
#ifdef LIBRW_SDL2
SDL_Window **pWindow;
SDL_Window *window;
SDL_GLContext glcontext;
#elif !defined(PSP2)
GLFWwindow **pWindow;
GLFWwindow *window;
GLFWmonitor *monitor;
int numMonitors;
int currentMonitor;
#endif
DisplayMode *modes;
int numModes;
int currentMode;
int presentWidth, presentHeight;
int presentOffX, presentOffY;
// for opening the window
int winWidth, winHeight;
const char *winTitle;
uint32 numSamples;
};
extern GlGlobals glGlobals;
#endif #endif
Raster *rasterCreate(Raster *raster); Raster *rasterCreate(Raster *raster);
@@ -30,6 +78,7 @@ int32 rasterNumLevels(Raster*);
bool32 imageFindRasterFormat(Image *img, int32 type, bool32 imageFindRasterFormat(Image *img, int32 type,
int32 *width, int32 *height, int32 *depth, int32 *format); int32 *width, int32 *height, int32 *depth, int32 *format);
bool32 rasterFromImage(Raster *raster, Image *image); bool32 rasterFromImage(Raster *raster, Image *image);
Image *rasterToImage(Raster *raster);
} }
} }
+26 -3
View File
@@ -9,20 +9,41 @@ enum {
MAX_BLOCKS = 20 MAX_BLOCKS = 20
}; };
enum UniformType
{
UNIFORM_NA, // managed by the user
UNIFORM_VEC4,
UNIFORM_IVEC4,
UNIFORM_MAT4
};
struct Uniform
{
char *name;
UniformType type;
//bool dirty;
uint32 serialNum;
int32 num;
void *data;
};
struct UniformRegistry struct UniformRegistry
{ {
int32 numUniforms; int32 numUniforms;
char *uniformNames[MAX_UNIFORMS]; Uniform uniforms[MAX_UNIFORMS];
int32 numBlocks; int32 numBlocks;
char *blockNames[MAX_BLOCKS]; char *blockNames[MAX_BLOCKS];
}; };
int32 registerUniform(const char *name); int32 registerUniform(const char *name, UniformType type = UNIFORM_NA, int32 num = 1);
int32 findUniform(const char *name); int32 findUniform(const char *name);
int32 registerBlock(const char *name); int32 registerBlock(const char *name);
int32 findBlock(const char *name); int32 findBlock(const char *name);
void setUniform(int32 id, void *data);
void flushUniforms(void);
extern UniformRegistry uniformRegistry; extern UniformRegistry uniformRegistry;
struct Shader struct Shader
@@ -30,8 +51,10 @@ struct Shader
GLuint program; GLuint program;
// same number of elements as UniformRegistry::numUniforms // same number of elements as UniformRegistry::numUniforms
GLint *uniformLocations; GLint *uniformLocations;
uint32 *serialNums;
int32 numUniforms; // just to be sure!
static Shader *create(const char **vsrc, const char **fsrc, bool is_2d); static Shader *create(const char **vsrc, const char **fsrc);
// static Shader *fromFiles(const char *vs, const char *fs); // static Shader *fromFiles(const char *vs, const char *fs);
// static Shader *fromStrings(const char *vsrc, const char *fsrc); // static Shader *fromStrings(const char *vsrc, const char *fsrc);
void use(void); void use(void);
+1
View File
@@ -32,6 +32,7 @@ struct InstanceDataHeader : rw::InstanceDataHeader
}; };
// only RW_OPENGL // only RW_OPENGL
void uploadGeo(Geometry *geo);
void setAttribPointers(InstanceDataHeader *inst); void setAttribPointers(InstanceDataHeader *inst);
void packattrib(uint8 *dst, float32 *src, AttribDesc *a, float32 scale); void packattrib(uint8 *dst, float32 *src, AttribDesc *a, float32 scale);
+13 -13
View File
@@ -1,4 +1,4 @@
all: header_vs.inc header_fs.inc im2d_gl3.inc im3d_gl3.inc default_vs_gl3.inc simple_fs_gl3.inc matfx_gl3.inc skin_gl3.inc all: header_vs.inc header_fs.inc im2d_gl.inc im3d_gl.inc default_vs_gl.inc simple_fs_gl.inc matfx_gl.inc skin_gl.inc
header_vs.inc: header.vert header_vs.inc: header.vert
(echo 'const char *header_vert_src =';\ (echo 'const char *header_vert_src =';\
@@ -10,36 +10,36 @@ header_fs.inc: header.frag
sed 's/..*/"&\\n"/' header.frag;\ sed 's/..*/"&\\n"/' header.frag;\
echo ';') >header_fs.inc echo ';') >header_fs.inc
im2d_gl3.inc: im2d.vert im2d_gl.inc: im2d.vert
(echo 'const char *im2d_vert_src =';\ (echo 'const char *im2d_vert_src =';\
sed 's/..*/"&\\n"/' im2d.vert;\ sed 's/..*/"&\\n"/' im2d.vert;\
echo ';') >im2d_gl3.inc echo ';') >im2d_gl.inc
im3d_gl3.inc: im3d.vert im3d_gl.inc: im3d.vert
(echo 'const char *im3d_vert_src =';\ (echo 'const char *im3d_vert_src =';\
sed 's/..*/"&\\n"/' im3d.vert;\ sed 's/..*/"&\\n"/' im3d.vert;\
echo ';') >im3d_gl3.inc echo ';') >im3d_gl.inc
default_vs_gl3.inc: default.vert default_vs_gl.inc: default.vert
(echo 'const char *default_vert_src =';\ (echo 'const char *default_vert_src =';\
sed 's/..*/"&\\n"/' default.vert;\ sed 's/..*/"&\\n"/' default.vert;\
echo ';') >default_vs_gl3.inc echo ';') >default_vs_gl.inc
simple_fs_gl3.inc: simple.frag simple_fs_gl.inc: simple.frag
(echo 'const char *simple_frag_src =';\ (echo 'const char *simple_frag_src =';\
sed 's/..*/"&\\n"/' simple.frag;\ sed 's/..*/"&\\n"/' simple.frag;\
echo ';') >simple_fs_gl3.inc echo ';') >simple_fs_gl.inc
matfx_gl3.inc: matfx_env.frag matfx_env.vert matfx_gl.inc: matfx_env.frag matfx_env.vert
(echo 'const char *matfx_env_vert_src =';\ (echo 'const char *matfx_env_vert_src =';\
sed 's/..*/"&\\n"/' matfx_env.vert;\ sed 's/..*/"&\\n"/' matfx_env.vert;\
echo ';';\ echo ';';\
echo 'const char *matfx_env_frag_src =';\ echo 'const char *matfx_env_frag_src =';\
sed 's/..*/"&\\n"/' matfx_env.frag;\ sed 's/..*/"&\\n"/' matfx_env.frag;\
echo ';') >matfx_gl3.inc echo ';') >matfx_gl.inc
skin_gl3.inc: skin.vert skin_gl.inc: skin.vert
(echo 'const char *skin_vert_src =';\ (echo 'const char *skin_vert_src =';\
sed 's/..*/"&\\n"/' skin.vert;\ sed 's/..*/"&\\n"/' skin.vert;\
echo ';') >skin_gl3.inc echo ';') >skin_gl.inc
+14 -35
View File
@@ -1,44 +1,23 @@
void main( VSIN(ATTRIB_POS) vec3 in_pos;
float3 in_pos,
float3 in_normal, VSOUT vec4 v_color;
fixed4 in_color, VSOUT vec2 v_tex0;
half2 in_tex0, VSOUT float v_fog;
uniform float4x4 u_wvp,
uniform float4x4 u_world, void
uniform half4 u_ambLight, main(void)
uniform half4 u_surfProps, {
uniform half4 u_fogData, vec4 Vertex = u_world * vec4(in_pos, 1.0);
uniform half4 u_matColor, gl_Position = u_proj * u_view * Vertex;
uniform half4 u_lightParams[MAX_LIGHTS], vec3 Normal = mat3(u_world) * in_normal;
uniform half4 u_lightDirection[MAX_LIGHTS],
uniform half4 u_lightColor[MAX_LIGHTS],
half4 out v_color : COLOR0,
half2 out v_tex0 : TEXCOORD0,
fixed out v_fog : FOG,
float4 out gl_Position : POSITION
) {
gl_Position = mul(float4(in_pos, 1.0), u_wvp);
float3 Normal = mul(in_normal, float3x3(u_world));
v_tex0 = in_tex0; v_tex0 = in_tex0;
v_color = in_color; v_color = in_color;
v_color.rgb += u_ambLight.rgb*surfAmbient; v_color.rgb += u_ambLight.rgb*surfAmbient;
v_color.rgb += DoDynamicLight(Vertex.xyz, Normal)*surfDiffuse;
half3 color = half3(0.0, 0.0, 0.0);
for(int i = 0; i < MAX_LIGHTS; i++){
if(u_lightParams[i].x == 0.0)
break;
if(u_lightParams[i].x == 1.0){
// direct
fixed l = max(0.0, dot(Normal, -u_lightDirection[i].xyz));
color += l*u_lightColor[i].rgb;
}
}
v_color.rgb += color*surfDiffuse;
v_color = clamp(v_color, 0.0, 1.0); v_color = clamp(v_color, 0.0, 1.0);
v_color *= u_matColor; v_color *= u_matColor;
v_fog = DoFog(gl_Position.w, u_fogData); v_fog = DoFog(gl_Position.w);
} }
+25
View File
@@ -0,0 +1,25 @@
const char *default_vert_src =
"VSIN(ATTRIB_POS) vec3 in_pos;\n"
"VSOUT vec4 v_color;\n"
"VSOUT vec2 v_tex0;\n"
"VSOUT float v_fog;\n"
"void\n"
"main(void)\n"
"{\n"
" vec4 Vertex = u_world * vec4(in_pos, 1.0);\n"
" gl_Position = u_proj * u_view * Vertex;\n"
" vec3 Normal = mat3(u_world) * in_normal;\n"
" v_tex0 = in_tex0;\n"
" v_color = in_color;\n"
" v_color.rgb += u_ambLight.rgb*surfAmbient;\n"
" v_color.rgb += DoDynamicLight(Vertex.xyz, Normal)*surfDiffuse;\n"
" v_color = clamp(v_color, 0.0, 1.0);\n"
" v_color *= u_matColor;\n"
" v_fog = DoFog(gl_Position.w);\n"
"}\n"
;
+21 -1
View File
@@ -1,10 +1,30 @@
#ifdef USE_UBOS
layout(std140) uniform State
{
vec2 u_alphaRef;
vec4 u_fogData;
vec4 u_fogColor;
};
#else
uniform vec4 u_alphaRef;
uniform vec4 u_fogData;
uniform vec4 u_fogColor;
#endif
#define u_fogStart (u_fogData.x) #define u_fogStart (u_fogData.x)
#define u_fogEnd (u_fogData.y) #define u_fogEnd (u_fogData.y)
#define u_fogRange (u_fogData.z) #define u_fogRange (u_fogData.z)
#define u_fogDisable (u_fogData.w) #define u_fogDisable (u_fogData.w)
void DoAlphaTest(float a, half2 u_alphaRef) #ifndef GL2
out vec4 fragColor;
#endif
void DoAlphaTest(float a)
{ {
#ifndef NO_ALPHATEST
if(a < u_alphaRef.x || a >= u_alphaRef.y) if(a < u_alphaRef.x || a >= u_alphaRef.y)
discard; discard;
#endif
} }
+114 -1
View File
@@ -1,15 +1,128 @@
//#define DIRECTIONALS
//#define POINTLIGHTS
//#define SPOTLIGHTS
#define ATTRIB_POS 0
#define ATTRIB_NORMAL 1
#define ATTRIB_COLOR 2
#define ATTRIB_WEIGHTS 3
#define ATTRIB_INDICES 4
#define ATTRIB_TEXCOORDS0 5
#define ATTRIB_TEXCOORDS1 6
VSIN(ATTRIB_NORMAL) vec3 in_normal;
VSIN(ATTRIB_COLOR) vec4 in_color;
VSIN(ATTRIB_WEIGHTS) vec4 in_weights;
VSIN(ATTRIB_INDICES) vec4 in_indices;
VSIN(ATTRIB_TEXCOORDS0) vec2 in_tex0;
VSIN(ATTRIB_TEXCOORDS1) vec2 in_tex1;
#ifdef USE_UBOS
layout(std140) uniform State
{
vec2 u_alphaRef;
vec4 u_fogData;
vec4 u_fogColor;
};
#else
uniform vec4 u_alphaRef;
uniform vec4 u_fogData;
uniform vec4 u_fogColor;
#endif
#define u_fogStart (u_fogData.x) #define u_fogStart (u_fogData.x)
#define u_fogEnd (u_fogData.y) #define u_fogEnd (u_fogData.y)
#define u_fogRange (u_fogData.z) #define u_fogRange (u_fogData.z)
#define u_fogDisable (u_fogData.w) #define u_fogDisable (u_fogData.w)
#ifdef USE_UBOS
layout(std140) uniform Scene
{
mat4 u_proj;
mat4 u_view;
};
#else
uniform mat4 u_proj;
uniform mat4 u_view;
#endif
#define MAX_LIGHTS 8 #define MAX_LIGHTS 8
#ifdef USE_UBOS
layout(std140) uniform Object
{
mat4 u_world;
vec4 u_ambLight;
vec4 u_lightParams[MAX_LIGHTS]; // type, radius, minusCosAngle, hardSpot
vec4 u_lightPosition[MAX_LIGHTS];
vec4 u_lightDirection[MAX_LIGHTS];
vec4 u_lightColor[MAX_LIGHTS];
};
#else
uniform mat4 u_world;
uniform vec4 u_ambLight;
uniform vec4 u_lightParams[MAX_LIGHTS]; // type, radius, minusCosAngle, hardSpot
uniform vec4 u_lightPosition[MAX_LIGHTS];
uniform vec4 u_lightDirection[MAX_LIGHTS];
uniform vec4 u_lightColor[MAX_LIGHTS];
#endif
uniform vec4 u_matColor;
uniform vec4 u_surfProps; // amb, spec, diff, extra
#define surfAmbient (u_surfProps.x) #define surfAmbient (u_surfProps.x)
#define surfSpecular (u_surfProps.y) #define surfSpecular (u_surfProps.y)
#define surfDiffuse (u_surfProps.z) #define surfDiffuse (u_surfProps.z)
fixed DoFog(float w, half4 u_fogData) vec3 DoDynamicLight(vec3 V, vec3 N)
{
vec3 color = vec3(0.0, 0.0, 0.0);
for(int i = 0; i < MAX_LIGHTS; i++){
if(u_lightParams[i].x == 0.0)
break;
#ifdef DIRECTIONALS
if(u_lightParams[i].x == 1.0){
// direct
float l = max(0.0, dot(N, -u_lightDirection[i].xyz));
color += l*u_lightColor[i].rgb;
}else
#endif
#ifdef POINTLIGHTS
if(u_lightParams[i].x == 2.0){
// point
vec3 dir = V - u_lightPosition[i].xyz;
float dist = length(dir);
float atten = max(0.0, (1.0 - dist/u_lightParams[i].y));
float l = max(0.0, dot(N, -normalize(dir)));
color += l*u_lightColor[i].rgb*atten;
}else
#endif
#ifdef SPOTLIGHTS
if(u_lightParams[i].x == 3.0){
// spot
vec3 dir = V - u_lightPosition[i].xyz;
float dist = length(dir);
float atten = max(0.0, (1.0 - dist/u_lightParams[i].y));
dir /= dist;
float l = max(0.0, dot(N, -dir));
float pcos = dot(dir, u_lightDirection[i].xyz); // cos to point
float ccos = -u_lightParams[i].z;
float falloff = (pcos-ccos)/(1.0-ccos);
if(falloff < 0.0) // outside of cone
l = 0.0;
l *= max(falloff, u_lightParams[i].w);
return l*u_lightColor[i].rgb*atten;
}else
#endif
;
}
return color;
}
float DoFog(float w)
{ {
return clamp((w - u_fogEnd)*u_fogRange, u_fogDisable, 1.0); return clamp((w - u_fogEnd)*u_fogRange, u_fogDisable, 1.0);
} }
+21 -1
View File
@@ -1,12 +1,32 @@
const char *header_frag_src = const char *header_frag_src =
"#ifdef USE_UBOS\n"
"layout(std140) uniform State\n"
"{\n"
" vec2 u_alphaRef;\n"
" vec4 u_fogData;\n"
" vec4 u_fogColor;\n"
"};\n"
"#else\n"
"uniform vec4 u_alphaRef;\n"
"uniform vec4 u_fogData;\n"
"uniform vec4 u_fogColor;\n"
"#endif\n"
"#define u_fogStart (u_fogData.x)\n" "#define u_fogStart (u_fogData.x)\n"
"#define u_fogEnd (u_fogData.y)\n" "#define u_fogEnd (u_fogData.y)\n"
"#define u_fogRange (u_fogData.z)\n" "#define u_fogRange (u_fogData.z)\n"
"#define u_fogDisable (u_fogData.w)\n" "#define u_fogDisable (u_fogData.w)\n"
"void DoAlphaTest(float a, half2 u_alphaRef)\n" "#ifndef GL2\n"
"out vec4 fragColor;\n"
"#endif\n"
"void DoAlphaTest(float a)\n"
"{\n" "{\n"
"#ifndef NO_ALPHATEST\n"
" if(a < u_alphaRef.x || a >= u_alphaRef.y)\n" " if(a < u_alphaRef.x || a >= u_alphaRef.y)\n"
" discard;\n" " discard;\n"
"#endif\n"
"}\n" "}\n"
; ;
+114 -1
View File
@@ -1,16 +1,129 @@
const char *header_vert_src = const char *header_vert_src =
"//#define DIRECTIONALS\n"
"//#define POINTLIGHTS\n"
"//#define SPOTLIGHTS\n"
"#define ATTRIB_POS 0\n"
"#define ATTRIB_NORMAL 1\n"
"#define ATTRIB_COLOR 2\n"
"#define ATTRIB_WEIGHTS 3\n"
"#define ATTRIB_INDICES 4\n"
"#define ATTRIB_TEXCOORDS0 5\n"
"#define ATTRIB_TEXCOORDS1 6\n"
"VSIN(ATTRIB_NORMAL) vec3 in_normal;\n"
"VSIN(ATTRIB_COLOR) vec4 in_color;\n"
"VSIN(ATTRIB_WEIGHTS) vec4 in_weights;\n"
"VSIN(ATTRIB_INDICES) vec4 in_indices;\n"
"VSIN(ATTRIB_TEXCOORDS0) vec2 in_tex0;\n"
"VSIN(ATTRIB_TEXCOORDS1) vec2 in_tex1;\n"
"#ifdef USE_UBOS\n"
"layout(std140) uniform State\n"
"{\n"
" vec2 u_alphaRef;\n"
" vec4 u_fogData;\n"
" vec4 u_fogColor;\n"
"};\n"
"#else\n"
"uniform vec4 u_alphaRef;\n"
"uniform vec4 u_fogData;\n"
"uniform vec4 u_fogColor;\n"
"#endif\n"
"#define u_fogStart (u_fogData.x)\n" "#define u_fogStart (u_fogData.x)\n"
"#define u_fogEnd (u_fogData.y)\n" "#define u_fogEnd (u_fogData.y)\n"
"#define u_fogRange (u_fogData.z)\n" "#define u_fogRange (u_fogData.z)\n"
"#define u_fogDisable (u_fogData.w)\n" "#define u_fogDisable (u_fogData.w)\n"
"#ifdef USE_UBOS\n"
"layout(std140) uniform Scene\n"
"{\n"
" mat4 u_proj;\n"
" mat4 u_view;\n"
"};\n"
"#else\n"
"uniform mat4 u_proj;\n"
"uniform mat4 u_view;\n"
"#endif\n"
"#define MAX_LIGHTS 8\n" "#define MAX_LIGHTS 8\n"
"#ifdef USE_UBOS\n"
"layout(std140) uniform Object\n"
"{\n"
" mat4 u_world;\n"
" vec4 u_ambLight;\n"
" vec4 u_lightParams[MAX_LIGHTS]; // type, radius, minusCosAngle, hardSpot\n"
" vec4 u_lightPosition[MAX_LIGHTS];\n"
" vec4 u_lightDirection[MAX_LIGHTS];\n"
" vec4 u_lightColor[MAX_LIGHTS];\n"
"};\n"
"#else\n"
"uniform mat4 u_world;\n"
"uniform vec4 u_ambLight;\n"
"uniform vec4 u_lightParams[MAX_LIGHTS]; // type, radius, minusCosAngle, hardSpot\n"
"uniform vec4 u_lightPosition[MAX_LIGHTS];\n"
"uniform vec4 u_lightDirection[MAX_LIGHTS];\n"
"uniform vec4 u_lightColor[MAX_LIGHTS];\n"
"#endif\n"
"uniform vec4 u_matColor;\n"
"uniform vec4 u_surfProps; // amb, spec, diff, extra\n"
"#define surfAmbient (u_surfProps.x)\n" "#define surfAmbient (u_surfProps.x)\n"
"#define surfSpecular (u_surfProps.y)\n" "#define surfSpecular (u_surfProps.y)\n"
"#define surfDiffuse (u_surfProps.z)\n" "#define surfDiffuse (u_surfProps.z)\n"
"fixed DoFog(float w, half4 u_fogData)\n" "vec3 DoDynamicLight(vec3 V, vec3 N)\n"
"{\n"
" vec3 color = vec3(0.0, 0.0, 0.0);\n"
" for(int i = 0; i < MAX_LIGHTS; i++){\n"
" if(u_lightParams[i].x == 0.0)\n"
" break;\n"
"#ifdef DIRECTIONALS\n"
" if(u_lightParams[i].x == 1.0){\n"
" // direct\n"
" float l = max(0.0, dot(N, -u_lightDirection[i].xyz));\n"
" color += l*u_lightColor[i].rgb;\n"
" }else\n"
"#endif\n"
"#ifdef POINTLIGHTS\n"
" if(u_lightParams[i].x == 2.0){\n"
" // point\n"
" vec3 dir = V - u_lightPosition[i].xyz;\n"
" float dist = length(dir);\n"
" float atten = max(0.0, (1.0 - dist/u_lightParams[i].y));\n"
" float l = max(0.0, dot(N, -normalize(dir)));\n"
" color += l*u_lightColor[i].rgb*atten;\n"
" }else\n"
"#endif\n"
"#ifdef SPOTLIGHTS\n"
" if(u_lightParams[i].x == 3.0){\n"
" // spot\n"
" vec3 dir = V - u_lightPosition[i].xyz;\n"
" float dist = length(dir);\n"
" float atten = max(0.0, (1.0 - dist/u_lightParams[i].y));\n"
" dir /= dist;\n"
" float l = max(0.0, dot(N, -dir));\n"
" float pcos = dot(dir, u_lightDirection[i].xyz); // cos to point\n"
" float ccos = -u_lightParams[i].z;\n"
" float falloff = (pcos-ccos)/(1.0-ccos);\n"
" if(falloff < 0.0) // outside of cone\n"
" l = 0.0;\n"
" l *= max(falloff, u_lightParams[i].w);\n"
" return l*u_lightColor[i].rgb*atten;\n"
" }else\n"
"#endif\n"
" ;\n"
" }\n"
" return color;\n"
"}\n"
"float DoFog(float w)\n"
"{\n" "{\n"
" return clamp((w - u_fogEnd)*u_fogRange, u_fogDisable, 1.0);\n" " return clamp((w - u_fogEnd)*u_fogRange, u_fogDisable, 1.0);\n"
"}\n" "}\n"
+12 -13
View File
@@ -1,18 +1,17 @@
void main( uniform vec4 u_xform;
float4 in_pos,
half4 in_color, VSIN(ATTRIB_POS) vec4 in_pos;
half2 in_tex0,
uniform half4 u_fogData, VSOUT vec4 v_color;
uniform float4 u_xform, VSOUT vec2 v_tex0;
half4 out v_color : COLOR0, VSOUT float v_fog;
half2 out v_tex0 : TEXCOORD0,
fixed out v_fog : FOG, void
float4 out gl_Position : POSITION main(void)
) { {
gl_Position = in_pos; gl_Position = in_pos;
gl_Position.w = 1.0;
gl_Position.xy = gl_Position.xy * u_xform.xy + u_xform.zw; gl_Position.xy = gl_Position.xy * u_xform.xy + u_xform.zw;
v_fog = DoFog(gl_Position.z, u_fogData); v_fog = DoFog(gl_Position.w);
gl_Position.xyz *= gl_Position.w; gl_Position.xyz *= gl_Position.w;
v_color = in_color; v_color = in_color;
v_tex0 = in_tex0; v_tex0 = in_tex0;
+20
View File
@@ -0,0 +1,20 @@
const char *im2d_vert_src =
"uniform vec4 u_xform;\n"
"VSIN(ATTRIB_POS) vec4 in_pos;\n"
"VSOUT vec4 v_color;\n"
"VSOUT vec2 v_tex0;\n"
"VSOUT float v_fog;\n"
"void\n"
"main(void)\n"
"{\n"
" gl_Position = in_pos;\n"
" gl_Position.xy = gl_Position.xy * u_xform.xy + u_xform.zw;\n"
" v_fog = DoFog(gl_Position.w);\n"
" gl_Position.xyz *= gl_Position.w;\n"
" v_color = in_color;\n"
" v_tex0 = in_tex0;\n"
"}\n"
;
+13 -14
View File
@@ -1,17 +1,16 @@
void main( VSIN(ATTRIB_POS) vec3 in_pos;
float3 in_pos,
half4 in_color, VSOUT vec4 v_color;
half2 in_tex0, VSOUT vec2 v_tex0;
uniform half4 u_fogData, VSOUT float v_fog;
uniform float4x4 u_wvp,
uniform float4x4 u_world, void
half4 out v_color : COLOR0, main(void)
half2 out v_tex0 : TEXCOORD0, {
fixed out v_fog : FOG, vec4 Vertex = u_world * vec4(in_pos, 1.0);
float4 out gl_Position : POSITION vec4 CamVertex = u_view * Vertex;
) { gl_Position = u_proj * CamVertex;
gl_Position = mul(float4(in_pos, 1.0), u_wvp);
v_color = in_color; v_color = in_color;
v_tex0 = in_tex0; v_tex0 = in_tex0;
v_fog = DoFog(gl_Position.w, u_fogData); v_fog = DoFog(gl_Position.w);
} }
+18
View File
@@ -0,0 +1,18 @@
const char *im3d_vert_src =
"VSIN(ATTRIB_POS) vec3 in_pos;\n"
"VSOUT vec4 v_color;\n"
"VSOUT vec2 v_tex0;\n"
"VSOUT float v_fog;\n"
"void\n"
"main(void)\n"
"{\n"
" vec4 Vertex = u_world * vec4(in_pos, 1.0);\n"
" vec4 CamVertex = u_view * Vertex;\n"
" gl_Position = u_proj * CamVertex;\n"
" v_color = in_color;\n"
" v_tex0 = in_tex0;\n"
" v_fog = DoFog(gl_Position.w);\n"
"}\n"
;
+23 -22
View File
@@ -1,33 +1,34 @@
uniform sampler2D tex0;
uniform sampler2D tex1;
uniform vec4 u_fxparams;
#define shininess (u_fxparams.x) #define shininess (u_fxparams.x)
#define disableFBA (u_fxparams.y) #define disableFBA (u_fxparams.y)
float4 main( FSIN vec4 v_color;
half4 v_color : COLOR0, FSIN vec4 v_envColor;
half2 v_tex0 : TEXCOORD0, FSIN vec2 v_tex0;
half2 v_tex1 : TEXCOORD1, FSIN vec2 v_tex1;
fixed v_fog : FOG, FSIN float v_fog;
uniform half4 u_fogColor,
uniform half2 u_alphaRef,
uniform half4 u_colorClamp,
uniform half2 u_fxparams,
uniform sampler2D tex0 : TEXUNIT0,
uniform sampler2D tex1 : TEXUNIT1
) {
half4 pass1 = v_color;
half4 envColor = max(pass1, u_colorClamp);
pass1 *= tex2D(tex0, half2(v_tex0.x, 1.0-v_tex0.y));
half4 pass2 = envColor*shininess*tex2D(tex1, half2(v_tex1.x, 1.0-v_tex1.y)); void
main(void)
{
vec4 pass1 = v_color;
pass1 *= texture(tex0, vec2(v_tex0.x, 1.0-v_tex0.y));
pass1.rgb = lerp(u_fogColor.rgb, pass1.rgb, v_fog); vec4 pass2 = v_envColor*shininess*texture(tex1, vec2(v_tex1.x, 1.0-v_tex1.y));
pass2.rgb = lerp(half3(0.0, 0.0, 0.0), pass2.rgb, v_fog);
half fba = max(pass1.a, disableFBA); pass1.rgb = mix(u_fogColor.rgb, pass1.rgb, v_fog);
float4 color; pass2.rgb = mix(vec3(0.0, 0.0, 0.0), pass2.rgb, v_fog);
float fba = max(pass1.a, disableFBA);
vec4 color;
color.rgb = pass1.rgb*pass1.a + pass2.rgb*fba; color.rgb = pass1.rgb*pass1.a + pass2.rgb*fba;
color.a = pass1.a; color.a = pass1.a;
DoAlphaTest(color.a, u_alphaRef); DoAlphaTest(color.a);
return color; FRAGCOLOR(color);
} }
+22 -38
View File
@@ -1,47 +1,31 @@
void main( uniform mat4 u_texMatrix;
float3 in_pos, uniform vec4 u_colorClamp;
float3 in_normal, uniform vec4 u_envColor;
fixed4 in_color,
half2 in_tex0, VSIN(ATTRIB_POS) vec3 in_pos;
uniform float4x4 u_wvp,
uniform float4x4 u_world, VSOUT vec4 v_color;
uniform float4x4 u_texMatrix, VSOUT vec4 v_envColor;
uniform half4 u_ambLight, VSOUT vec2 v_tex0;
uniform half4 u_surfProps, VSOUT vec2 v_tex1;
uniform half4 u_fogData, VSOUT float v_fog;
uniform half4 u_matColor,
uniform half4 u_lightParams[MAX_LIGHTS], void
uniform half4 u_lightDirection[MAX_LIGHTS], main(void)
uniform half4 u_lightColor[MAX_LIGHTS], {
half4 out v_color : COLOR0, vec4 Vertex = u_world * vec4(in_pos, 1.0);
half2 out v_tex0 : TEXCOORD0, gl_Position = u_proj * u_view * Vertex;
half2 out v_tex1 : TEXCOORD1, vec3 Normal = mat3(u_world) * in_normal;
fixed out v_fog : FOG,
float4 out gl_Position : POSITION
) {
gl_Position = mul(float4(in_pos, 1.0), u_wvp);
float3 Normal = mul(in_normal, float3x3(u_world));
v_tex0 = in_tex0; v_tex0 = in_tex0;
v_tex1 = (mul(float4(Normal, 1.0), u_texMatrix)).xy; v_tex1 = (u_texMatrix * vec4(Normal, 1.0)).xy;
v_color = in_color; v_color = in_color;
v_color.rgb += u_ambLight.rgb*surfAmbient; v_color.rgb += u_ambLight.rgb*surfAmbient;
v_color.rgb += DoDynamicLight(Vertex.xyz, Normal)*surfDiffuse;
half3 color = float3(0.0, 0.0, 0.0);
for(int i = 0; i < MAX_LIGHTS; i++){
if(u_lightParams[i].x == 0.0)
break;
if(u_lightParams[i].x == 1.0){
// direct
fixed l = max(0.0, dot(Normal, -u_lightDirection[i].xyz));
color += l*u_lightColor[i].rgb;
}
}
v_color.rgb += color*surfDiffuse;
v_color = clamp(v_color, 0.0, 1.0); v_color = clamp(v_color, 0.0, 1.0);
v_envColor = max(v_color, u_colorClamp) * u_envColor;
v_color *= u_matColor; v_color *= u_matColor;
v_fog = DoFog(gl_Position.w, u_fogData); v_fog = DoFog(gl_Position.w);
} }
+69
View File
@@ -0,0 +1,69 @@
const char *matfx_env_vert_src =
"uniform mat4 u_texMatrix;\n"
"uniform vec4 u_colorClamp;\n"
"uniform vec4 u_envColor;\n"
"\n"
"VSIN(ATTRIB_POS) vec3 in_pos;\n"
"\n"
"VSOUT vec4 v_color;\n"
"VSOUT vec4 v_envColor;\n"
"VSOUT vec2 v_tex0;\n"
"VSOUT vec2 v_tex1;\n"
"VSOUT float v_fog;\n"
"\n"
"void\n"
"main(void)\n"
"{\n"
" vec4 Vertex = u_world * vec4(in_pos, 1.0);\n"
" gl_Position = u_proj * u_view * Vertex;\n"
" vec3 Normal = mat3(u_world) * in_normal;\n"
"\n"
" v_tex0 = in_tex0;\n"
" v_tex1 = (u_texMatrix * vec4(Normal, 1.0)).xy;\n"
"\n"
" v_color = in_color;\n"
" v_color.rgb += u_ambLight.rgb*surfAmbient;\n"
" v_color.rgb += DoDynamicLight(Vertex.xyz, Normal)*surfDiffuse;\n"
" v_color = clamp(v_color, 0.0, 1.0);\n"
" v_envColor = max(v_color, u_colorClamp) * u_envColor;\n"
" v_color *= u_matColor;\n"
"\n"
" v_fog = DoFog(gl_Position.w);\n"
"}\n"
;
const char *matfx_env_frag_src =
"uniform sampler2D tex0;\n"
"uniform sampler2D tex1;\n"
"\n"
"uniform vec4 u_fxparams;\n"
"\n"
"#define shininess (u_fxparams.x)\n"
"#define disableFBA (u_fxparams.y)\n"
"\n"
"FSIN vec4 v_color;\n"
"FSIN vec4 v_envColor;\n"
"FSIN vec2 v_tex0;\n"
"FSIN vec2 v_tex1;\n"
"FSIN float v_fog;\n"
"\n"
"void\n"
"main(void)\n"
"{\n"
" vec4 pass1 = v_color;\n"
" pass1 *= texture(tex0, vec2(v_tex0.x, 1.0-v_tex0.y));\n"
"\n"
" vec4 pass2 = v_envColor*shininess*texture(tex1, vec2(v_tex1.x, 1.0-v_tex1.y));\n"
"\n"
" pass1.rgb = mix(u_fogColor.rgb, pass1.rgb, v_fog);\n"
" pass2.rgb = mix(vec3(0.0, 0.0, 0.0), pass2.rgb, v_fog);\n"
"\n"
" float fba = max(pass1.a, disableFBA);\n"
" vec4 color;\n"
" color.rgb = pass1.rgb*pass1.a + pass2.rgb*fba;\n"
" color.a = pass1.a;\n"
"\n"
" DoAlphaTest(color.a);\n"
"\n"
" FRAGCOLOR(color);\n"
"}\n"
;
+12 -12
View File
@@ -1,15 +1,15 @@
float4 main( uniform sampler2D tex0;
half4 v_color : COLOR0,
half2 v_tex0 : TEXCOORD0,
fixed v_fog : FOG,
uniform half4 u_fogColor,
uniform half2 u_alphaRef,
uniform sampler2D tex0
) {
half4 color = v_color*tex2D(tex0, half2(v_tex0.x, 1.0-v_tex0.y));
color.rgb = lerp(u_fogColor.rgb, color.rgb, v_fog);
DoAlphaTest(color.a, u_alphaRef);
return color; FSIN vec4 v_color;
FSIN vec2 v_tex0;
FSIN float v_fog;
void
main(void)
{
vec4 color = v_color*texture(tex0, vec2(v_tex0.x, 1.0-v_tex0.y));
color.rgb = mix(u_fogColor.rgb, color.rgb, v_fog);
DoAlphaTest(color.a);
FRAGCOLOR(color);
} }
+17
View File
@@ -0,0 +1,17 @@
const char *simple_frag_src =
"uniform sampler2D tex0;\n"
"FSIN vec4 v_color;\n"
"FSIN vec2 v_tex0;\n"
"FSIN float v_fog;\n"
"void\n"
"main(void)\n"
"{\n"
" vec4 color = v_color*texture(tex0, vec2(v_tex0.x, 1.0-v_tex0.y));\n"
" color.rgb = mix(u_fogColor.rgb, color.rgb, v_fog);\n"
" DoAlphaTest(color.a);\n"
" FRAGCOLOR(color);\n"
"}\n"
;
+21 -44
View File
@@ -1,55 +1,32 @@
void main( uniform mat4 u_boneMatrices[64];
float3 in_pos,
float3 in_normal,
fixed4 in_color,
half2 in_tex0,
float4 in_weights,
float4 in_indices,
uniform float4x4 u_wvp,
uniform float4x4 u_world,
uniform half4 u_ambLight,
uniform half4 u_surfProps,
uniform half4 u_fogData,
uniform half4 u_matColor,
uniform half4 u_lightParams[MAX_LIGHTS],
uniform half4 u_lightDirection[MAX_LIGHTS],
uniform half4 u_lightColor[MAX_LIGHTS],
uniform float4x4 u_boneMatrices[64],
half4 out v_color : COLOR0,
half2 out v_tex0 : TEXCOORD0,
fixed out v_fog : FOG,
float4 out gl_Position : POSITION
) {
float4x4 Skin = u_boneMatrices[(int)(in_indices.x * 255)] * in_weights.x
+ u_boneMatrices[(int)(in_indices.y * 255)] * in_weights.y
+ u_boneMatrices[(int)(in_indices.z * 255)] * in_weights.z
+ u_boneMatrices[(int)(in_indices.w * 255)] * in_weights.w;
float3 SkinVertex = (mul(float4(in_pos, 1.f), Skin)).xyz; VSIN(ATTRIB_POS) vec3 in_pos;
float3 SkinNormal = (mul(float4(in_normal, 0.f), Skin)).xyz;
gl_Position = mul(float4(SkinVertex, 1.0), u_wvp); VSOUT vec4 v_color;
float3 Normal = mul(SkinNormal, float3x3(u_world)); VSOUT vec2 v_tex0;
VSOUT float v_fog;
void
main(void)
{
vec3 SkinVertex = vec3(0.0, 0.0, 0.0);
vec3 SkinNormal = vec3(0.0, 0.0, 0.0);
for(int i = 0; i < 4; i++){
SkinVertex += (u_boneMatrices[int(in_indices[i])] * vec4(in_pos, 1.0)).xyz * in_weights[i];
SkinNormal += (mat3(u_boneMatrices[int(in_indices[i])]) * in_normal) * in_weights[i];
}
vec4 Vertex = u_world * vec4(SkinVertex, 1.0);
gl_Position = u_proj * u_view * Vertex;
vec3 Normal = mat3(u_world) * SkinNormal;
v_tex0 = in_tex0; v_tex0 = in_tex0;
v_color = in_color; v_color = in_color;
v_color.rgb += u_ambLight.rgb*surfAmbient; v_color.rgb += u_ambLight.rgb*surfAmbient;
v_color.rgb += DoDynamicLight(Vertex.xyz, Normal)*surfDiffuse;
half3 color = half3(0.0, 0.0, 0.0);
for(int i = 0; i < MAX_LIGHTS; i++){
if(u_lightParams[i].x == 0.0)
break;
if(u_lightParams[i].x == 1.0){
// direct
fixed l = max(0.0, dot(Normal, -u_lightDirection[i].xyz));
color += l*u_lightColor[i].rgb;
}
}
v_color.rgb += color*surfDiffuse;
v_color = clamp(v_color, 0.0, 1.0); v_color = clamp(v_color, 0.0, 1.0);
v_color *= u_matColor; v_color *= u_matColor;
v_fog = DoFog(gl_Position.z, u_fogData); v_fog = DoFog(gl_Position.z);
} }
+34
View File
@@ -0,0 +1,34 @@
const char *skin_vert_src =
"uniform mat4 u_boneMatrices[64];\n"
"VSIN(ATTRIB_POS) vec3 in_pos;\n"
"VSOUT vec4 v_color;\n"
"VSOUT vec2 v_tex0;\n"
"VSOUT float v_fog;\n"
"void\n"
"main(void)\n"
"{\n"
" vec3 SkinVertex = vec3(0.0, 0.0, 0.0);\n"
" vec3 SkinNormal = vec3(0.0, 0.0, 0.0);\n"
" for(int i = 0; i < 4; i++){\n"
" SkinVertex += (u_boneMatrices[int(in_indices[i])] * vec4(in_pos, 1.0)).xyz * in_weights[i];\n"
" SkinNormal += (mat3(u_boneMatrices[int(in_indices[i])]) * in_normal) * in_weights[i];\n"
" }\n"
" vec4 Vertex = u_world * vec4(SkinVertex, 1.0);\n"
" gl_Position = u_proj * u_view * Vertex;\n"
" vec3 Normal = mat3(u_world) * SkinNormal;\n"
" v_tex0 = in_tex0;\n"
" v_color = in_color;\n"
" v_color.rgb += u_ambLight.rgb*surfAmbient;\n"
" v_color.rgb += DoDynamicLight(Vertex.xyz, Normal)*surfDiffuse;\n"
" v_color = clamp(v_color, 0.0, 1.0);\n"
" v_color *= u_matColor;\n"
" v_fog = DoFog(gl_Position.z);\n"
"}\n"
;
+55 -10
View File
@@ -13,16 +13,12 @@
#include "../rwplugins.h" #include "../rwplugins.h"
#include "rwwdgl.h" #include "rwwdgl.h"
#ifdef RW_OPENGL
#ifdef PSP2 #ifdef PSP2
#include <vitasdk.h> #include <vitasdk.h>
#include <vitaGL.h> #include <vitaGL.h>
#else #else
#ifdef RW_OPENGL #include "glad/glad.h"
#ifndef LIBRW_GLAD
#include <GL/glew.h>
#else
#include <glad/glad.h>
#endif
#endif #endif
#endif #endif
@@ -86,6 +82,50 @@ printAttribInfo(AttribDesc *attribs, int n)
} }
*/ */
#ifdef RW_OPENGL
void
uploadGeo(Geometry *geo)
{
InstanceDataHeader *inst = (InstanceDataHeader*)geo->instData;
MeshHeader *meshHeader = geo->meshHeader;
glGenBuffers(1, &inst->vbo);
glBindBuffer(GL_ARRAY_BUFFER, inst->vbo);
glBufferData(GL_ARRAY_BUFFER, inst->dataSize,
inst->data, GL_STATIC_DRAW);
glGenBuffers(1, &inst->ibo);
glBindBuffer(GL_ARRAY_BUFFER, inst->ibo);
glBufferData(GL_ARRAY_BUFFER, meshHeader->totalIndices*2,
0, GL_STATIC_DRAW);
GLintptr offset = 0;
for(uint32 i = 0; i < meshHeader->numMeshes; i++){
Mesh *mesh = &meshHeader->getMeshes()[i];
glBufferSubData(GL_ARRAY_BUFFER, offset, mesh->numIndices*2,
mesh->indices);
offset += mesh->numIndices*2;
}
glBindBuffer(GL_ARRAY_BUFFER, 0);
}
void
setAttribPointers(InstanceDataHeader *inst)
{
static GLenum attribType[] = {
GL_FLOAT,
GL_BYTE, GL_UNSIGNED_BYTE,
GL_SHORT, GL_UNSIGNED_SHORT
};
for(int32 i = 0; i < inst->numAttribs; i++){
AttribDesc *a = &inst->attribs[i];
glEnableVertexAttribArray(a->index);
glVertexAttribPointer(a->index, a->size, attribType[a->type],
a->normalized, a->stride,
(void*)(uint64)a->offset);
}
}
#endif
void void
packattrib(uint8 *dst, float32 *src, AttribDesc *a, float32 scale=1.0f) packattrib(uint8 *dst, float32 *src, AttribDesc *a, float32 scale=1.0f)
{ {
@@ -95,7 +135,7 @@ packattrib(uint8 *dst, float32 *src, AttribDesc *a, float32 scale=1.0f)
switch(a->type){ switch(a->type){
case 0: // float case 0: // float
memcpy_neon(dst, src, a->size*4); memcpy(dst, src, a->size*4);
break; break;
// TODO: maybe have loop inside if? // TODO: maybe have loop inside if?
@@ -149,7 +189,7 @@ unpackattrib(float *dst, uint8 *src, AttribDesc *a, float32 scale=1.0f)
switch(a->type){ switch(a->type){
case 0: // float case 0: // float
memcpy_neon(dst, src, a->size*4); memcpy(dst, src, a->size*4);
break; break;
// TODO: maybe have loop inside if? // TODO: maybe have loop inside if?
@@ -616,7 +656,7 @@ skinUninstanceCB(Geometry *geo)
uint8 *data = skin->data; uint8 *data = skin->data;
float *invMats = skin->inverseMatrices; float *invMats = skin->inverseMatrices;
skin->init(skin->numBones, skin->numBones, geo->numVertices); skin->init(skin->numBones, skin->numBones, geo->numVertices);
memcpy_neon(skin->inverseMatrices, invMats, skin->numBones*64); memcpy(skin->inverseMatrices, invMats, skin->numBones*64);
rwFree(data); rwFree(data);
uint8 *p; uint8 *p;
@@ -798,7 +838,12 @@ Texture::upload(void)
static GLenum wrap[] = { static GLenum wrap[] = {
0, GL_REPEAT, GL_MIRRORED_REPEAT, 0, GL_REPEAT, GL_MIRRORED_REPEAT,
#ifdef PSP2
// vitaGL has no border clamp, gxm only does clamp/repeat/mirror
GL_CLAMP_TO_EDGE, GL_CLAMP_TO_EDGE GL_CLAMP_TO_EDGE, GL_CLAMP_TO_EDGE
#else
GL_CLAMP_TO_EDGE, GL_CLAMP_TO_BORDER
#endif
}; };
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S,
wrap[(this->filterAddressing >> 8) & 0xF]); wrap[(this->filterAddressing >> 8) & 0xF]);
@@ -807,7 +852,7 @@ Texture::upload(void)
switch(r->format & 0xF00){ switch(r->format & 0xF00){
case Raster::C8888: case Raster::C8888:
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, r->width, r->height, glTexImage2D(GL_TEXTURE_2D, 0, 4, r->width, r->height,
0, GL_RGBA, GL_UNSIGNED_BYTE, r->pixels); 0, GL_RGBA, GL_UNSIGNED_BYTE, r->pixels);
break; break;
default: default:
+3 -2
View File
@@ -307,7 +307,7 @@ getSizeHAnim(void *object, int32 offset, int32)
{ {
HAnimData *hanim = PLUGINOFFSET(HAnimData, object, offset); HAnimData *hanim = PLUGINOFFSET(HAnimData, object, offset);
if(!hAnimDoStream || if(!hAnimDoStream ||
version >= 0x35000 && hanim->id == -1 && hanim->hierarchy == nil) (version >= 0x35000 && hanim->id == -1 && hanim->hierarchy == nil))
return 0; return 0;
if(hanim->hierarchy) if(hanim->hierarchy)
return 12 + 8 + hanim->hierarchy->numNodes*12; return 12 + 8 + hanim->hierarchy->numNodes*12;
@@ -408,6 +408,7 @@ registerHAnimPlugin(void)
Frame::registerPluginStream(ID_HANIM, Frame::registerPluginStream(ID_HANIM,
readHAnim, readHAnim,
writeHAnim, writeHAnim,
getSizeHAnim);} getSizeHAnim);
}
} }
+251 -36
View File
@@ -17,9 +17,6 @@
#define PLUGIN_ID ID_IMAGE #define PLUGIN_ID ID_IMAGE
#include <vitasdk.h>
#include <vitaGL.h>
namespace rw { namespace rw {
int32 Image::numAllocated; int32 Image::numAllocated;
@@ -114,6 +111,15 @@ Image::setPixels(uint8 *pixels)
this->flags |= 1; this->flags |= 1;
} }
// The DXT decoders below read 16/32/64-bit words straight out of the
// compressed block with pointer casts. That is fine on x86 but faults on ARM:
// the block data is not guaranteed 8-byte aligned (e.g. the 64-bit alpha word
// sits at a +2 offset in DXT5), and an unaligned ldrd is a data abort. Read
// through memcpy, which the compiler lowers to alignment-safe access.
static inline uint16 rdU16(const uint8 *p){ uint16 v; memcpy(&v, p, sizeof(v)); return v; }
static inline uint32 rdU32(const uint8 *p){ uint32 v; memcpy(&v, p, sizeof(v)); return v; }
static inline uint64 rdU64(const uint8 *p){ uint64 v; memcpy(&v, p, sizeof(v)); return v; }
void void
decompressDXT1(uint8 *adst, int32 w, int32 h, uint8 *src) decompressDXT1(uint8 *adst, int32 w, int32 h, uint8 *src)
{ {
@@ -125,8 +131,8 @@ decompressDXT1(uint8 *adst, int32 w, int32 h, uint8 *src)
uint8 (*dst)[4] = (uint8(*)[4])adst; uint8 (*dst)[4] = (uint8(*)[4])adst;
for(int32 j = 0; j < w*h/2; j += 8){ for(int32 j = 0; j < w*h/2; j += 8){
/* calculate colors */ /* calculate colors */
uint32 col0 = *((uint16*)&src[j+0]); uint32 col0 = rdU16(&src[j+0]);
uint32 col1 = *((uint16*)&src[j+2]); uint32 col1 = rdU16(&src[j+2]);
c[0][0] = ((col0>>11) & 0x1F)*0xFF/0x1F; c[0][0] = ((col0>>11) & 0x1F)*0xFF/0x1F;
c[0][1] = ((col0>> 5) & 0x3F)*0xFF/0x3F; c[0][1] = ((col0>> 5) & 0x3F)*0xFF/0x3F;
c[0][2] = ( col0 & 0x1F)*0xFF/0x1F; c[0][2] = ( col0 & 0x1F)*0xFF/0x1F;
@@ -159,15 +165,15 @@ decompressDXT1(uint8 *adst, int32 w, int32 h, uint8 *src)
} }
/* make index list */ /* make index list */
uint32 indices = *((uint32*)&src[j+4]); uint32 indices = rdU32(&src[j+4]);
for(int32 k = 0; k < 16; k++){ for(int32 k = 0; k < 16; k++){
idx[k] = indices & 0x3; idx[k] = indices & 0x3;
indices >>= 2; indices >>= 2;
} }
/* write bytes */ /* write bytes */
for(uint32 k = 0; k < 4; k++) for(uint32 l = 0; l < 4; l++)
for(uint32 l = 0; l < 4; l++){ for(uint32 k = 0; k < 4; k++){
dst[(y+l)*w + x+k][0] = c[idx[l*4+k]][0]; dst[(y+l)*w + x+k][0] = c[idx[l*4+k]][0];
dst[(y+l)*w + x+k][1] = c[idx[l*4+k]][1]; dst[(y+l)*w + x+k][1] = c[idx[l*4+k]][1];
dst[(y+l)*w + x+k][2] = c[idx[l*4+k]][2]; dst[(y+l)*w + x+k][2] = c[idx[l*4+k]][2];
@@ -193,8 +199,8 @@ decompressDXT3(uint8 *adst, int32 w, int32 h, uint8 *src)
uint8 (*dst)[4] = (uint8(*)[4])adst; uint8 (*dst)[4] = (uint8(*)[4])adst;
for(int32 j = 0; j < w*h; j += 16){ for(int32 j = 0; j < w*h; j += 16){
/* calculate colors */ /* calculate colors */
uint32 col0 = *((uint16*)&src[j+8]); uint32 col0 = rdU16(&src[j+8]);
uint32 col1 = *((uint16*)&src[j+10]); uint32 col1 = rdU16(&src[j+10]);
c[0][0] = ((col0>>11) & 0x1F)*0xFF/0x1F; c[0][0] = ((col0>>11) & 0x1F)*0xFF/0x1F;
c[0][1] = ((col0>> 5) & 0x3F)*0xFF/0x3F; c[0][1] = ((col0>> 5) & 0x3F)*0xFF/0x3F;
c[0][2] = ( col0 & 0x1F)*0xFF/0x1F; c[0][2] = ( col0 & 0x1F)*0xFF/0x1F;
@@ -212,20 +218,20 @@ decompressDXT3(uint8 *adst, int32 w, int32 h, uint8 *src)
c[3][2] = (1*c[0][2] + 2*c[1][2])/3; c[3][2] = (1*c[0][2] + 2*c[1][2])/3;
/* make index list */ /* make index list */
uint32 indices = *((uint32*)&src[j+12]); uint32 indices = rdU32(&src[j+12]);
for(int32 k = 0; k < 16; k++){ for(int32 k = 0; k < 16; k++){
idx[k] = indices & 0x3; idx[k] = indices & 0x3;
indices >>= 2; indices >>= 2;
} }
uint64 alphas = *((uint64*)&src[j+0]); uint64 alphas = rdU64(&src[j+0]);
for(int32 k = 0; k < 16; k++){ for(int32 k = 0; k < 16; k++){
a[k] = (alphas & 0xF)*17; a[k] = (alphas & 0xF)*17;
alphas >>= 4; alphas >>= 4;
} }
/* write bytes */ /* write bytes */
for(uint32 k = 0; k < 4; k++) for(uint32 l = 0; l < 4; l++)
for(uint32 l = 0; l < 4; l++){ for(uint32 k = 0; k < 4; k++){
dst[(y+l)*w + x+k][0] = c[idx[l*4+k]][0]; dst[(y+l)*w + x+k][0] = c[idx[l*4+k]][0];
dst[(y+l)*w + x+k][1] = c[idx[l*4+k]][1]; dst[(y+l)*w + x+k][1] = c[idx[l*4+k]][1];
dst[(y+l)*w + x+k][2] = c[idx[l*4+k]][2]; dst[(y+l)*w + x+k][2] = c[idx[l*4+k]][2];
@@ -252,8 +258,8 @@ decompressDXT5(uint8 *adst, int32 w, int32 h, uint8 *src)
uint8 (*dst)[4] = (uint8(*)[4])adst; uint8 (*dst)[4] = (uint8(*)[4])adst;
for(int32 j = 0; j < w*h; j += 16){ for(int32 j = 0; j < w*h; j += 16){
/* calculate colors */ /* calculate colors */
uint32 col0 = *((uint16*)&src[j+8]); uint32 col0 = rdU16(&src[j+8]);
uint32 col1 = *((uint16*)&src[j+10]); uint32 col1 = rdU16(&src[j+10]);
c[0][0] = ((col0>>11) & 0x1F)*0xFF/0x1F; c[0][0] = ((col0>>11) & 0x1F)*0xFF/0x1F;
c[0][1] = ((col0>> 5) & 0x3F)*0xFF/0x3F; c[0][1] = ((col0>> 5) & 0x3F)*0xFF/0x3F;
c[0][2] = ( col0 & 0x1F)*0xFF/0x1F; c[0][2] = ( col0 & 0x1F)*0xFF/0x1F;
@@ -298,21 +304,21 @@ decompressDXT5(uint8 *adst, int32 w, int32 h, uint8 *src)
} }
/* make index list */ /* make index list */
uint32 indices = *((uint32*)&src[j+12]); uint32 indices = rdU32(&src[j+12]);
for(int32 k = 0; k < 16; k++){ for(int32 k = 0; k < 16; k++){
idx[k] = indices & 0x3; idx[k] = indices & 0x3;
indices >>= 2; indices >>= 2;
} }
// only 6 indices // only 6 indices
uint64 alphas = *((uint64*)&src[j+2]); uint64 alphas = rdU64(&src[j+2]);
for(int32 k = 0; k < 16; k++){ for(int32 k = 0; k < 16; k++){
aidx[k] = alphas & 0x7; aidx[k] = alphas & 0x7;
alphas >>= 3; alphas >>= 3;
} }
/* write bytes */ /* write bytes */
for(uint32 k = 0; k < 4; k++) for(uint32 l = 0; l < 4; l++)
for(uint32 l = 0; l < 4; l++){ for(uint32 k = 0; k < 4; k++){
dst[(y+l)*w + x+k][0] = c[idx[l*4+k]][0]; dst[(y+l)*w + x+k][0] = c[idx[l*4+k]][0];
dst[(y+l)*w + x+k][1] = c[idx[l*4+k]][1]; dst[(y+l)*w + x+k][1] = c[idx[l*4+k]][1];
dst[(y+l)*w + x+k][2] = c[idx[l*4+k]][2]; dst[(y+l)*w + x+k][2] = c[idx[l*4+k]][2];
@@ -326,6 +332,226 @@ decompressDXT5(uint8 *adst, int32 w, int32 h, uint8 *src)
} }
} }
// not strictly image but related
// flip a DXT 2-bit block
static void
flipBlock(uint8 *dst, uint8 *src)
{
// color
dst[0] = src[0];
dst[1] = src[1];
dst[2] = src[2];
dst[3] = src[3];
// bits
dst[4] = src[7];
dst[5] = src[6];
dst[6] = src[5];
dst[7] = src[4];
}
// flip top 2 rows of a DXT 2-bit block
static void
flipBlock_half(uint8 *dst, uint8 *src)
{
// color
dst[0] = src[0];
dst[1] = src[1];
dst[2] = src[2];
dst[3] = src[3];
// bits
dst[4] = src[5];
dst[5] = src[4];
dst[6] = src[6];
dst[7] = src[7];
}
// flip a DXT3 4-bit alpha block
static void
flipAlphaBlock3(uint8 *dst, uint8 *src)
{
dst[6] = src[0];
dst[7] = src[1];
dst[4] = src[2];
dst[5] = src[3];
dst[2] = src[4];
dst[3] = src[5];
dst[0] = src[6];
dst[1] = src[7];
}
// flip top 2 rows of a DXT3 4-bit alpha block
static void
flipAlphaBlock3_half(uint8 *dst, uint8 *src)
{
dst[0] = src[2];
dst[1] = src[3];
dst[2] = src[0];
dst[3] = src[1];
dst[4] = src[4];
dst[5] = src[5];
dst[6] = src[6];
dst[7] = src[7];
}
// flip a DXT5 3-bit alpha block
static void
flipAlphaBlock5(uint8 *dst, uint8 *src)
{
// color
dst[0] = src[0];
dst[1] = src[1];
// bits
uint64 bits = rdU64(&src[2]);
uint64 flipbits = 0;
for(int i = 0; i < 4; i++){
flipbits <<= 12;
flipbits |= bits & 0xFFF;
bits >>= 12;
}
memcpy(dst+2, &flipbits, 6);
}
// flip top 2 rows of a DXT5 3-bit alpha block
static void
flipAlphaBlock5_half(uint8 *dst, uint8 *src)
{
// color
dst[0] = src[0];
dst[1] = src[1];
// bits
uint64 bits = rdU64(&src[2]);
uint64 flipbits = bits & 0xFFFFFF000000;
flipbits |= (bits>>12) & 0xFFF;
flipbits |= (bits<<12) & 0xFFF000;
memcpy(dst+2, &flipbits, 6);
}
void
flipDXT1(uint8 *dst, uint8 *src, uint32 width, uint32 height)
{
int x, y;
int bw = (width+3)/4;
int bh = (height+3)/4;
if(height < 4){
// used pixels are always at the top
// so don't swap the full 4 rows
if(height == 2){
uint8 *s = src;
uint8 *d = dst;
for(x = 0; x < bw; x++){
flipBlock_half(dst, src);
s += 8;
d += 8;
}
}else
memcpy(dst, src, 8*bw);
return;
}
dst += 8*bw*bh;
for(y = 0; y < bh; y++){
dst -= 8*bw;
uint8 *s = src;
uint8 *d = dst;
for(x = 0; x < bw; x++){
flipBlock(d, s);
s += 8;
d += 8;
}
src += 8*bw;
}
}
void
flipDXT3(uint8 *dst, uint8 *src, uint32 width, uint32 height)
{
int x, y;
int bw = (width+3)/4;
int bh = (height+3)/4;
if(height < 4){
// used pixels are always at the top
// so don't swap the full 4 rows
if(height == 2){
uint8 *s = src;
uint8 *d = dst;
for(x = 0; x < bw; x++){
flipAlphaBlock3_half(d, s);
flipBlock_half(d+8, s+8);
s += 16;
d += 16;
}
}else
memcpy(dst, src, 16*bw);
return;
}
dst += 16*bw*bh;
for(y = 0; y < bh; y++){
dst -= 16*bw;
uint8 *s = src;
uint8 *d = dst;
for(x = 0; x < bw; x++){
flipAlphaBlock3(d, s);
flipBlock(d+8, s+8);
s += 16;
d += 16;
}
src += 16*bw;
}
}
void
flipDXT5(uint8 *dst, uint8 *src, uint32 width, uint32 height)
{
int x, y;
int bw = (width+3)/4;
int bh = (height+3)/4;
if(height < 4){
// used pixels are always at the top
// so don't swap the full 4 rows
if(height == 2){
uint8 *s = src;
uint8 *d = dst;
for(x = 0; x < bw; x++){
flipAlphaBlock5_half(d, s);
flipBlock_half(d+8, s+8);
s += 16;
d += 16;
}
}else
memcpy(dst, src, 16*bw);
return;
}
dst += 16*bw*bh;
for(y = 0; y < bh; y++){
dst -= 16*bw;
uint8 *s = src;
uint8 *d = dst;
for(x = 0; x < bw; x++){
flipAlphaBlock5(d, s);
flipBlock(d+8, s+8);
s += 16;
d += 16;
}
src += 16*bw;
}
}
void
flipDXT(int32 type, uint8 *dst, uint8 *src, uint32 width, uint32 height)
{
switch(type){
case 1:
flipDXT1(dst, src, width, height);
break;
case 3:
flipDXT3(dst, src, width, height);
break;
case 5:
flipDXT5(dst, src, width, height);
break;
}
}
void void
Image::setPixelsDXT(int32 type, uint8 *pixels) Image::setPixelsDXT(int32 type, uint8 *pixels)
{ {
@@ -479,7 +705,7 @@ Image::palettize(int32 depth)
this->palette = nil; this->palette = nil;
this->setPixels(newpixels); this->setPixels(newpixels);
this->allocate(); this->allocate();
memcpy_neon(this->palette, colors, 4*(1<<depth)); memcpy(this->palette, colors, 4*(1<<depth));
quant.destroy(); quant.destroy();
} }
@@ -677,17 +903,6 @@ Image::extractMask(void)
return img; return img;
} }
static char*
rwstrdup(const char *s)
{
char *t;
size_t len = strlen(s)+1;
t = (char*)rwMalloc(len, MEMDUR_EVENT);
if(t)
memcpy_neon(t, s, len);
return t;
}
void void
Image::setSearchPath(const char *path) Image::setSearchPath(const char *path)
{ {
@@ -696,7 +911,7 @@ Image::setSearchPath(const char *path)
rwFree(g->searchPaths); rwFree(g->searchPaths);
g->numSearchPaths = 0; g->numSearchPaths = 0;
if(path) if(path)
g->searchPaths = p = rwstrdup(path); g->searchPaths = p = rwStrdup(path, MEMDUR_EVENT);
else{ else{
g->searchPaths = nil; g->searchPaths = nil;
return; return;
@@ -729,7 +944,7 @@ Image::getFilename(const char *name)
char *s, *p = g->searchPaths; char *s, *p = g->searchPaths;
size_t len = strlen(name)+1; size_t len = strlen(name)+1;
if(g->numSearchPaths == 0){ if(g->numSearchPaths == 0){
s = rwstrdup(name); s = rwStrdup(name, MEMDUR_EVENT);
makePath(s); makePath(s);
f = fopen(s, "rb"); f = fopen(s, "rb");
if(f){ if(f){
@@ -819,9 +1034,9 @@ bool32
Image::registerFileFormat(const char *ext, fileRead read, fileWrite write) Image::registerFileFormat(const char *ext, fileRead read, fileWrite write)
{ {
ImageGlobals *g = PLUGINOFFSET(ImageGlobals, engine, imageModuleOffset); ImageGlobals *g = PLUGINOFFSET(ImageGlobals, engine, imageModuleOffset);
if(g->numFileFormats >= nelem(g->fileFormats)) if(g->numFileFormats >= (int)nelem(g->fileFormats))
return 0; return 0;
g->fileFormats[g->numFileFormats].extension = rwstrdup(ext); g->fileFormats[g->numFileFormats].extension = rwStrdup(ext, MEMDUR_EVENT);
g->fileFormats[g->numFileFormats].read = read; g->fileFormats[g->numFileFormats].read = read;
g->fileFormats[g->numFileFormats].write = write; g->fileFormats[g->numFileFormats].write = write;
g->numFileFormats++; g->numFileFormats++;
+5 -9
View File
@@ -27,8 +27,7 @@ freely, subject to the following restrictions:
The manual and changelog are in the header file "lodepng.h" The manual and changelog are in the header file "lodepng.h"
Rename this file to lodepng.cpp to use it for C++, or to lodepng.c to use it for C. Rename this file to lodepng.cpp to use it for C++, or to lodepng.c to use it for C.
*/ */
#include <vitasdk.h>
#include <vitaGL.h>
#include "lodepng.h" #include "lodepng.h"
#ifdef LODEPNG_COMPILE_DISK #ifdef LODEPNG_COMPILE_DISK
@@ -118,7 +117,7 @@ void lodepng_free(void* ptr);
where a full C library is not available. The compiler can recognize them and compile where a full C library is not available. The compiler can recognize them and compile
to something as fast. */ to something as fast. */
/*static void lodepng_memcpy(void* LODEPNG_RESTRICT dst, static void lodepng_memcpy(void* LODEPNG_RESTRICT dst,
const void* LODEPNG_RESTRICT src, size_t size) { const void* LODEPNG_RESTRICT src, size_t size) {
size_t i; size_t i;
for(i = 0; i < size; i++) ((char*)dst)[i] = ((const char*)src)[i]; for(i = 0; i < size; i++) ((char*)dst)[i] = ((const char*)src)[i];
@@ -130,17 +129,14 @@ static void lodepng_memset(void* LODEPNG_RESTRICT dst,
for(i = 0; i < num; i++) ((char*)dst)[i] = (char)value; for(i = 0; i < num; i++) ((char*)dst)[i] = (char)value;
} }
does not check memory out of bounds, do not use on untrusted data /* does not check memory out of bounds, do not use on untrusted data */
static size_t lodepng_strlen(const char* a) { static size_t lodepng_strlen(const char* a) {
const char* orig = a; const char* orig = a;
/* avoid warning about unused function in case of disabled COMPILE... macros /* avoid warning about unused function in case of disabled COMPILE... macros */
(void)(&lodepng_strlen); (void)(&lodepng_strlen);
while(*a) a++; while(*a) a++;
return (size_t)(a - orig); return (size_t)(a - orig);
}*/ }
#define lodepng_memcpy memcpy_neon
#define lodepng_memset memset
#define lodepng_strlen strlen
#define LODEPNG_MAX(a, b) (((a) > (b)) ? (a) : (b)) #define LODEPNG_MAX(a, b) (((a) > (b)) ? (a) : (b))
#define LODEPNG_MIN(a, b) (((a) < (b)) ? (a) : (b)) #define LODEPNG_MIN(a, b) (((a) < (b)) ? (a) : (b))
+7 -3
View File
@@ -24,7 +24,11 @@
namespace rw { namespace rw {
bool32 MatFX::modulateEnvMap; bool32 MatFX::envMapFlipU;
bool32 MatFX::envMapApplyLight;
bool32 MatFX::envMapUseMatColor;
RGBA MatFX::envMapColor = { 255, 255, 255, 255 };
// Atomic // Atomic
@@ -69,7 +73,7 @@ getSizeAtomicMatFX(void *object, int32 offset, int32)
// Material // Material
MatFXGlobals matFXGlobals = { 0, 0, { nil } }; MatFXGlobals matFXGlobals = { 0, 0, { nil }, nil };
// TODO: Frames and Matrices? // TODO: Frames and Matrices?
static void static void
@@ -375,7 +379,7 @@ copyMaterialMatFX(void *dst, void *src, int32 offset, int32)
return dst; return dst;
MatFX *dstfx = rwNewT(MatFX, 1, MEMDUR_EVENT | ID_MATFX); MatFX *dstfx = rwNewT(MatFX, 1, MEMDUR_EVENT | ID_MATFX);
*PLUGINOFFSET(MatFX*, dst, offset) = dstfx; *PLUGINOFFSET(MatFX*, dst, offset) = dstfx;
memcpy_neon(dstfx, srcfx, sizeof(MatFX)); memcpy(dstfx, srcfx, sizeof(MatFX));
for(int i = 0; i < 2; i++) for(int i = 0; i < 2; i++)
switch(dstfx->fx[i].type){ switch(dstfx->fx[i].type){
case MatFX::BUMPMAP: case MatFX::BUMPMAP:
+5 -8
View File
@@ -9,9 +9,6 @@
#include "rwobjects.h" #include "rwobjects.h"
#include "rwengine.h" #include "rwengine.h"
#include <vitasdk.h>
#include <vitaGL.h>
#define COLOR_ARGB(a,r,g,b) \ #define COLOR_ARGB(a,r,g,b) \
((uint32)((((a)&0xff)<<24)|(((r)&0xff)<<16)|(((g)&0xff)<<8)|((b)&0xff))) ((uint32)((((a)&0xff)<<24)|(((r)&0xff)<<16)|(((g)&0xff)<<8)|((b)&0xff)))
@@ -73,7 +70,7 @@ instV4d(int type, uint8 *dst, V4d *src, uint32 numVertices, uint32 stride)
{ {
if(type == VERT_FLOAT4) if(type == VERT_FLOAT4)
for(uint32 i = 0; i < numVertices; i++){ for(uint32 i = 0; i < numVertices; i++){
memcpy_neon(dst, src, 16); memcpy(dst, src, 16);
dst += stride; dst += stride;
src++; src++;
} }
@@ -86,7 +83,7 @@ instV3d(int type, uint8 *dst, V3d *src, uint32 numVertices, uint32 stride)
{ {
if(type == VERT_FLOAT3) if(type == VERT_FLOAT3)
for(uint32 i = 0; i < numVertices; i++){ for(uint32 i = 0; i < numVertices; i++){
memcpy_neon(dst, src, 12); memcpy(dst, src, 12);
dst += stride; dst += stride;
src++; src++;
} }
@@ -108,7 +105,7 @@ uninstV3d(int type, V3d *dst, uint8 *src, uint32 numVertices, uint32 stride)
{ {
if(type == VERT_FLOAT3) if(type == VERT_FLOAT3)
for(uint32 i = 0; i < numVertices; i++){ for(uint32 i = 0; i < numVertices; i++){
memcpy_neon(dst, src, 12); memcpy(dst, src, 12);
src += stride; src += stride;
dst++; dst++;
} }
@@ -138,7 +135,7 @@ instTexCoords(int type, uint8 *dst, TexCoords *src, uint32 numVertices, uint32 s
{ {
assert(type == VERT_FLOAT2); assert(type == VERT_FLOAT2);
for(uint32 i = 0; i < numVertices; i++){ for(uint32 i = 0; i < numVertices; i++){
memcpy_neon(dst, src, 8); memcpy(dst, src, 8);
dst += stride; dst += stride;
src++; src++;
} }
@@ -149,7 +146,7 @@ uninstTexCoords(int type, TexCoords *dst, uint8 *src, uint32 numVertices, uint32
{ {
assert(type == VERT_FLOAT2); assert(type == VERT_FLOAT2);
for(uint32 i = 0; i < numVertices; i++){ for(uint32 i = 0; i < numVertices; i++){
memcpy_neon(dst, src, 8); memcpy(dst, src, 8);
src += stride; src += stride;
dst++; dst++;
} }
+21
View File
@@ -95,6 +95,13 @@ PluginList::streamRead(Stream *stream, void *object)
cont: cont:
length -= header.length; length -= header.length;
} }
// now the always callbacks
FORLIST(lnk, this->plugins){
Plugin *p = PLG(lnk);
if(p->alwaysCallback)
p->alwaysCallback(object, p->offset, p->size);
}
return true; return true;
} }
@@ -176,6 +183,7 @@ PluginList::registerPlugin(int32 size, uint32 id,
p->write = nil; p->write = nil;
p->getSize = nil; p->getSize = nil;
p->rightsCallback = nil; p->rightsCallback = nil;
p->alwaysCallback = nil;
p->parentList = this; p->parentList = this;
this->plugins.add(&p->inParentList); this->plugins.add(&p->inParentList);
allPlugins.add(&p->inGlobalList); allPlugins.add(&p->inGlobalList);
@@ -211,6 +219,19 @@ PluginList::setStreamRightsCallback(uint32 id, RightsCallback cb)
return -1; return -1;
} }
int32
PluginList::setStreamAlwaysCallback(uint32 id, AlwaysCallback cb)
{
FORLIST(lnk, this->plugins){
Plugin *p = PLG(lnk);
if(p->id == id){
p->alwaysCallback = cb;
return p->offset;
}
}
return -1;
}
int32 int32
PluginList::getPluginOffset(uint32 id) PluginList::getPluginOffset(uint32 id)
{ {
+6 -14
View File
@@ -12,14 +12,6 @@
#include "lodepng/lodepng.h" #include "lodepng/lodepng.h"
#include <vitasdk.h>
#include <vitaGL.h>
#ifdef _WIN32
/* srsly? */
#define strdup _strdup
#endif
#define PLUGIN_ID 0 #define PLUGIN_ID 0
namespace rw { namespace rw {
@@ -28,7 +20,7 @@ namespace rw {
Image* Image*
readPNG(const char *filename) readPNG(const char *filename)
{ {
Image *image; Image *image = nil;
uint32 length; uint32 length;
uint8 *data = getFileContents(filename, &length); uint8 *data = getFileContents(filename, &length);
assert(data != nil); assert(data != nil);
@@ -49,20 +41,20 @@ readPNG(const char *filename)
if(state.info_raw.bitdepth == 4 && state.info_raw.colortype == LCT_PALETTE){ if(state.info_raw.bitdepth == 4 && state.info_raw.colortype == LCT_PALETTE){
image = Image::create(w, h, 4); image = Image::create(w, h, 4);
image->allocate(); image->allocate();
memcpy_neon(image->palette, state.info_raw.palette, state.info_raw.palettesize*4); memcpy(image->palette, state.info_raw.palette, state.info_raw.palettesize*4);
expandPal4_BE(image->pixels, image->stride, raw, w/2, w, h); expandPal4_BE(image->pixels, image->stride, raw, w/2, w, h);
}else if(state.info_raw.bitdepth == 8){ }else if(state.info_raw.bitdepth == 8){
switch(state.info_raw.colortype){ switch(state.info_raw.colortype){
case LCT_PALETTE: case LCT_PALETTE:
image = Image::create(w, h, state.info_raw.palettesize <= 16 ? 4 : 8); image = Image::create(w, h, state.info_raw.palettesize <= 16 ? 4 : 8);
image->allocate(); image->allocate();
memcpy_neon(image->palette, state.info_raw.palette, state.info_raw.palettesize*4); memcpy(image->palette, state.info_raw.palette, state.info_raw.palettesize*4);
memcpy_neon(image->pixels, raw, w*h); memcpy(image->pixels, raw, w*h);
break; break;
case LCT_RGB: case LCT_RGB:
image = Image::create(w, h, 24); image = Image::create(w, h, 24);
image->allocate(); image->allocate();
memcpy_neon(image->pixels, raw, w*h*3); memcpy(image->pixels, raw, w*h*3);
break; break;
default: default:
// Second try: just load as 32 bit // Second try: just load as 32 bit
@@ -77,7 +69,7 @@ readPNG(const char *filename)
case LCT_RGBA: case LCT_RGBA:
image = Image::create(w, h, 32); image = Image::create(w, h, 32);
image->allocate(); image->allocate();
memcpy_neon(image->pixels, raw, w*h*4); memcpy(image->pixels, raw, w*h*4);
break; break;
} }
} }
+8 -6
View File
@@ -588,13 +588,14 @@ getInstMeshInfo(MatPipeline *pipe, Geometry *g, Mesh *m)
im.numBrokenAttribs = 0; im.numBrokenAttribs = 0;
im.vertexSize = 0; im.vertexSize = 0;
for(uint i = 0; i < nelem(pipe->attribs); i++) for(uint i = 0; i < nelem(pipe->attribs); i++)
if(a = pipe->attribs[i]) if((a = pipe->attribs[i])) {
if(a->attrib & AT_RW) if(a->attrib & AT_RW)
im.numBrokenAttribs++; im.numBrokenAttribs++;
else{ else{
im.vertexSize += attribSize(a->attrib); im.vertexSize += attribSize(a->attrib);
im.numAttribs++; im.numAttribs++;
} }
}
if(g->meshHeader->flags == MeshHeader::TRISTRIP){ if(g->meshHeader->flags == MeshHeader::TRISTRIP){
im.numBatches = (m->numIndices-2) / (pipe->triStripCount-2); im.numBatches = (m->numIndices-2) / (pipe->triStripCount-2);
im.batchVertCount = pipe->triStripCount; im.batchVertCount = pipe->triStripCount;
@@ -758,13 +759,14 @@ MatPipeline::collectData(Geometry *g, InstanceData *inst, Mesh *m, uint8 *data[]
uint8 *raw = rwNewT(uint8, im.vertexSize*m->numIndices, MEMDUR_EVENT | ID_GEOMETRY); uint8 *raw = rwNewT(uint8, im.vertexSize*m->numIndices, MEMDUR_EVENT | ID_GEOMETRY);
uint8 *dp = raw; uint8 *dp = raw;
for(uint i = 0; i < nelem(this->attribs); i++) for(uint i = 0; i < nelem(this->attribs); i++)
if(a = this->attribs[i]) if((a = this->attribs[i])) {
if(a->attrib & AT_RW){ if(a->attrib & AT_RW){
data[i] = inst->data + im.attribPos[i]*0x10; data[i] = inst->data + im.attribPos[i]*0x10;
}else{ }else{
data[i] = dp; data[i] = dp;
dp += m->numIndices*attribSize(a->attrib); dp += m->numIndices*attribSize(a->attrib);
} }
}
uint8 *datap[nelem(this->attribs)]; uint8 *datap[nelem(this->attribs)];
memcpy(datap, data, sizeof(datap)); memcpy(datap, data, sizeof(datap));
@@ -965,8 +967,8 @@ void
genericPreCB(MatPipeline *pipe, Geometry *geo) genericPreCB(MatPipeline *pipe, Geometry *geo)
{ {
PipeAttribute *a; PipeAttribute *a;
for(int32 i = 0; i < nelem(pipe->attribs); i++) for(int32 i = 0; i < (int)nelem(pipe->attribs); i++)
if(a = pipe->attribs[i]) if((a = pipe->attribs[i]))
if(a == &attribXYZW){ if(a == &attribXYZW){
allocateADC(geo); allocateADC(geo);
break; break;
@@ -988,8 +990,8 @@ genericUninstanceCB(MatPipeline *pipe, Geometry *geo, uint32 flags[], Mesh *mesh
skin = Skin::get(geo); skin = Skin::get(geo);
PipeAttribute *a; PipeAttribute *a;
for(int32 i = 0; i < nelem(pipe->attribs); i++) for(int32 i = 0; i < (int)nelem(pipe->attribs); i++)
if(a = pipe->attribs[i]){ if((a = pipe->attribs[i])){
if(a == &attribXYZ) xyz = (float32*)data[i]; if(a == &attribXYZ) xyz = (float32*)data[i];
else if(a == &attribXYZW) xyzw = (float32*)data[i]; else if(a == &attribXYZW) xyzw = (float32*)data[i];
else if(a == &attribUV) uv = (float32*)data[i]; else if(a == &attribUV) uv = (float32*)data[i];
+62 -62
View File
@@ -76,7 +76,7 @@ transferMinSize(int32 psm, int32 flags, int32 *minw, int32 *minh)
} }
} }
#define PS2ALIGN(x,a) ((x) + (a)-1 & ~((a)-1)) #define ALIGN(x,a) ((x) + (a)-1 & ~((a)-1))
#define ALIGN16(x) ((x) + 0xF & ~0xF) #define ALIGN16(x) ((x) + 0xF & ~0xF)
#define ALIGN64(x) ((x) + 0x3F & ~0x3F) #define ALIGN64(x) ((x) + 0x3F & ~0x3F)
#define NSIZE(dim,pagedim) (((dim) + (pagedim)-1)/(pagedim)) #define NSIZE(dim,pagedim) (((dim) + (pagedim)-1)/(pagedim))
@@ -129,8 +129,8 @@ getRasterFormat(Raster *raster)
} }
raster->depth = cameraZDepth; raster->depth = cameraZDepth;
if(pixelformat){ if(pixelformat){
if(raster->depth == 16 && pixelformat != Raster::D16 || if((raster->depth == 16 && pixelformat != Raster::D16) ||
raster->depth == 32 && pixelformat != Raster::D32){ (raster->depth == 32 && pixelformat != Raster::D32)){
RWERROR((ERR_INVRASTER)); RWERROR((ERR_INVRASTER));
return 0; return 0;
} }
@@ -668,29 +668,29 @@ calcOffsets(int32 width_Px, int32 height_Px, int32 psm, uint64 *bufferBase_B, ui
case PSMT4HL: case PSMT4HL:
case PSMT4HH: case PSMT4HH:
// ABCDE -> CADBE // ABCDE -> CADBE
bufferBase_B[n] = bufferBase_B[n]&~0x1F | (uint64)blockmap_PSMCT32[bufferBase_B[n]&0x1F]; bufferBase_B[n] = (bufferBase_B[n]&~0x1F) | (uint64)blockmap_PSMCT32[bufferBase_B[n]&0x1F];
break; break;
case PSMT4: case PSMT4:
case PSMCT16: case PSMCT16:
// ABCDE -> ADBEC // ABCDE -> ADBEC
bufferBase_B[n] = bufferBase_B[n]&~0x1F | (uint64)blockmap_PSMCT16[bufferBase_B[n]&0x1F]; bufferBase_B[n] = (bufferBase_B[n]&~0x1F) | (uint64)blockmap_PSMCT16[bufferBase_B[n]&0x1F];
break; break;
case PSMCT16S: case PSMCT16S:
// ABCDE -> DBAEC // ABCDE -> DBAEC
bufferBase_B[n] = bufferBase_B[n]&~0x1F | (uint64)blockmap_PSMCT16S[bufferBase_B[n]&0x1F]; bufferBase_B[n] = (bufferBase_B[n]&~0x1F) | (uint64)blockmap_PSMCT16S[bufferBase_B[n]&0x1F];
break; break;
case PSMZ32: case PSMZ32:
case PSMZ24: case PSMZ24:
// ABCDE -> ~C~ADBE // ABCDE -> ~C~ADBE
bufferBase_B[n] = bufferBase_B[n]&~0x1F | (uint64)blockmap_PSMZ32[bufferBase_B[n]&0x1F]; bufferBase_B[n] = (bufferBase_B[n]&~0x1F) | (uint64)blockmap_PSMZ32[bufferBase_B[n]&0x1F];
break; break;
case PSMZ16: case PSMZ16:
// ABCDE -> ~A~DBEC // ABCDE -> ~A~DBEC
bufferBase_B[n] = bufferBase_B[n]&~0x1F | (uint64)blockmap_PSMZ16[bufferBase_B[n]&0x1F]; bufferBase_B[n] = (bufferBase_B[n]&~0x1F) | (uint64)blockmap_PSMZ16[bufferBase_B[n]&0x1F];
break; break;
case PSMZ16S: case PSMZ16S:
// ABCDE -> ~D~BAEC // ABCDE -> ~D~BAEC
bufferBase_B[n] = bufferBase_B[n]&~0x1F | (uint64)blockmap_PSMZ16S[bufferBase_B[n]&0x1F]; bufferBase_B[n] = (bufferBase_B[n]&~0x1F) | (uint64)blockmap_PSMZ16S[bufferBase_B[n]&0x1F];
break; break;
default: break; default: break;
} }
@@ -712,24 +712,24 @@ calcOffsets(int32 width_Px, int32 height_Px, int32 psm, uint64 *bufferBase_B, ui
case PSMT8H: case PSMT8H:
case PSMT4HL: case PSMT4HL:
case PSMT4HH: case PSMT4HH:
paletteBase_B = paletteBase_B&~0x1F | (uint64)blockmap_PSMCT32[paletteBase_B&0x1F]; paletteBase_B = (paletteBase_B&~0x1F) | (uint64)blockmap_PSMCT32[paletteBase_B&0x1F];
break; break;
case PSMT4: case PSMT4:
case PSMCT16: case PSMCT16:
paletteBase_B = paletteBase_B&~0x1F | (uint64)blockmap_PSMCT16[paletteBase_B&0x1F]; paletteBase_B = (paletteBase_B&~0x1F) | (uint64)blockmap_PSMCT16[paletteBase_B&0x1F];
break; break;
case PSMCT16S: case PSMCT16S:
paletteBase_B = paletteBase_B&~0x1F | (uint64)blockmap_PSMCT16S[paletteBase_B&0x1F]; paletteBase_B = (paletteBase_B&~0x1F) | (uint64)blockmap_PSMCT16S[paletteBase_B&0x1F];
break; break;
case PSMZ32: case PSMZ32:
case PSMZ24: case PSMZ24:
paletteBase_B = paletteBase_B&~0x1F | (uint64)blockmap_PSMZ32[paletteBase_B&0x1F]; paletteBase_B = (paletteBase_B&~0x1F) | (uint64)blockmap_PSMZ32[paletteBase_B&0x1F];
break; break;
case PSMZ16: case PSMZ16:
paletteBase_B = paletteBase_B&~0x1F | (uint64)blockmap_PSMZ16[paletteBase_B&0x1F]; paletteBase_B = (paletteBase_B&~0x1F) | (uint64)blockmap_PSMZ16[paletteBase_B&0x1F];
break; break;
case PSMZ16S: case PSMZ16S:
paletteBase_B = paletteBase_B&~0x1F | (uint64)blockmap_PSMZ16S[paletteBase_B&0x1F]; paletteBase_B = (paletteBase_B&~0x1F) | (uint64)blockmap_PSMZ16S[paletteBase_B&0x1F];
break; break;
default: break; default: break;
} }
@@ -792,7 +792,7 @@ rasterCreateTexture(Raster *raster)
int32 palettePagewidth, palettePageheight; int32 palettePagewidth, palettePageheight;
Ps2Raster *ras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *ras = GETPS2RASTEREXT(raster);
pixelformat = raster->format & 0xF00; pixelformat = raster->format & 0xF00;
palformat = raster->format & 0x6000; palformat = raster->format & 0x6000;
width = raster->width; width = raster->width;
@@ -915,8 +915,8 @@ rasterCreateTexture(Raster *raster)
// If buffer width changes, align next address to page // If buffer width changes, align next address to page
if(bufferWidth[n] != lastBufferWidth){ if(bufferWidth[n] != lastBufferWidth){
nPagW = ((width >> n-1) + pageWidth-1)/pageWidth; nPagW = ((width >> (n-1)) + pageWidth-1)/pageWidth;
nPagH = ((height >> n-1) + pageHeight-1)/pageHeight; nPagH = ((height >> (n-1)) + pageHeight-1)/pageHeight;
nextaddress = (lastaddress + nPagW*nPagH*WD2PG) & ~(WD2PG-1); nextaddress = (lastaddress + nPagW*nPagH*WD2PG) & ~(WD2PG-1);
} }
lastBufferWidth = bufferWidth[n]; lastBufferWidth = bufferWidth[n];
@@ -1052,8 +1052,8 @@ rasterCreateTexture(Raster *raster)
ras->flags |= Ps2Raster::SWIZZLED8; ras->flags |= Ps2Raster::SWIZZLED8;
if(cpsm == PSMCT32 && bufferWidth[numLevels-1] == 2){ // one page if(cpsm == PSMCT32 && bufferWidth[numLevels-1] == 2){ // one page
// unswizzle the starting block of the last buffer and palette // unswizzle the starting block of the last buffer and palette
uint32 bufbase_B = bufferBase[numLevels-1]&~0x1F | (uint64)blockmaprev_PSMCT32[bufferBase[numLevels-1]&0x1F]; uint32 bufbase_B = (bufferBase[numLevels-1]&~0x1F) | (uint64)blockmaprev_PSMCT32[bufferBase[numLevels-1]&0x1F];
uint32 palbase_B = ras->paletteBase&~0x1F | (uint64)blockmaprev_PSMCT32[ras->paletteBase&0x1F]; uint32 palbase_B = (ras->paletteBase&~0x1F) | (uint64)blockmaprev_PSMCT32[ras->paletteBase&0x1F];
// find start of page of last level (16,16 are PSMT8 block dimensions) // find start of page of last level (16,16 are PSMT8 block dimensions)
uint32 page_B = bufbase_B - 8*(dsay/16) - dsax/16; uint32 page_B = bufbase_B - 8*(dsay/16) - dsax/16;
// find palette DSAX/Y (in PSMCT32!) // find palette DSAX/Y (in PSMCT32!)
@@ -1072,8 +1072,8 @@ rasterCreateTexture(Raster *raster)
// Looks like they wanted to swizzle palettes too... // Looks like they wanted to swizzle palettes too...
if(cpsm == PSMCT16){ if(cpsm == PSMCT16){
// unswizzle the starting block of the last buffer and palette // unswizzle the starting block of the last buffer and palette
uint32 bufbase_B = bufferBase[numLevels-1]&~0x1F | (uint64)blockmaprev_PSMCT16[bufferBase[numLevels-1]&0x1F]; uint32 bufbase_B = (bufferBase[numLevels-1]&~0x1F) | (uint64)blockmaprev_PSMCT16[bufferBase[numLevels-1]&0x1F];
uint32 palbase_B = ras->paletteBase&~0x1F | (uint64)blockmaprev_PSMCT16[ras->paletteBase&0x1F]; uint32 palbase_B = (ras->paletteBase&~0x1F) | (uint64)blockmaprev_PSMCT16[ras->paletteBase&0x1F];
// find start of page of last level (32,16 are PSMT4 block dimensions) // find start of page of last level (32,16 are PSMT4 block dimensions)
uint32 page_B = bufbase_B - 4*(dsay/32) - dsax/16; uint32 page_B = bufbase_B - 4*(dsay/32) - dsax/16;
// find palette DSAX/Y (in PSMCT16!) // find palette DSAX/Y (in PSMCT16!)
@@ -1121,9 +1121,9 @@ rasterCreateTexture(Raster *raster)
} }
// What happens here? // What happens here?
if(ras->paletteSize && paltrxpos == 0) if(ras->paletteSize && paltrxpos == 0)
ras->dataSize = PS2ALIGN(ras->pixelSize,128) + PS2ALIGN(ras->paletteSize,64) + extrasize + 0x70; ras->dataSize = ALIGN(ras->pixelSize,128) + ALIGN(ras->paletteSize,64) + extrasize + 0x70;
else else
ras->dataSize = PS2ALIGN(ras->paletteSize+ras->pixelSize,64) + extrasize + 0x70; ras->dataSize = ALIGN(ras->paletteSize+ras->pixelSize,64) + extrasize + 0x70;
uint8 *data = (uint8*)mallocalign(ras->dataSize, 0x40); uint8 *data = (uint8*)mallocalign(ras->dataSize, 0x40);
uint32 *xferchain = (uint32*)(data + 0x10); uint32 *xferchain = (uint32*)(data + 0x10);
assert(data); assert(data);
@@ -1131,10 +1131,10 @@ rasterCreateTexture(Raster *raster)
Ps2Raster::PixelPtr *pp = (Ps2Raster::PixelPtr*)data; Ps2Raster::PixelPtr *pp = (Ps2Raster::PixelPtr*)data;
pp->numTransfers = numTransfers; pp->numTransfers = numTransfers;
pp->numTotalTransfers = numTransfers; pp->numTotalTransfers = numTransfers;
pp->pixels = (uint8*)PS2ALIGN((uintptr)data + extrasize, 128); pp->pixels = (uint8*)ALIGN((uintptr)data + extrasize, 128);
raster->pixels = (uint8*)pp; raster->pixels = (uint8*)pp;
if(ras->paletteSize) if(ras->paletteSize)
raster->palette = pp->pixels + PS2ALIGN(ras->pixelSize, 128) + 0x50; raster->palette = pp->pixels + ALIGN(ras->pixelSize, 128) + 0x50;
uint32 *p = (uint32*)pp->pixels; uint32 *p = (uint32*)pp->pixels;
w = raster->width; w = raster->width;
h = raster->height; h = raster->height;
@@ -1149,8 +1149,8 @@ rasterCreateTexture(Raster *raster)
*p++ = 0; *p++ = 0;
// TRXPOS // TRXPOS
if(ras->flags & Ps2Raster::SWIZZLED8 && psm == PSMT8 || if((ras->flags & Ps2Raster::SWIZZLED8 && psm == PSMT8) ||
ras->flags & Ps2Raster::SWIZZLED4 && psm == PSMT4){ (ras->flags & Ps2Raster::SWIZZLED4 && psm == PSMT4)){
*p++ = 0; // SSAX/Y is always 0 *p++ = 0; // SSAX/Y is always 0
*p++ = (trxpos_hi[n] & ~0x10001)/2; // divide both DSAX/Y by 2 *p++ = (trxpos_hi[n] & ~0x10001)/2; // divide both DSAX/Y by 2
}else{ }else{
@@ -1161,8 +1161,8 @@ rasterCreateTexture(Raster *raster)
*p++ = 0; *p++ = 0;
// TRXREG // TRXREG
if(ras->flags & Ps2Raster::SWIZZLED8 && psm == PSMT8 || if((ras->flags & Ps2Raster::SWIZZLED8 && psm == PSMT8) ||
ras->flags & Ps2Raster::SWIZZLED4 && psm == PSMT4){ (ras->flags & Ps2Raster::SWIZZLED4 && psm == PSMT4)){
*p++ = mipw/2; *p++ = mipw/2;
*p++ = miph/2; *p++ = miph/2;
}else{ }else{
@@ -1361,10 +1361,10 @@ swizzle(uint32 x, uint32 y, uint32 logw)
uint32 nx, ny, n; uint32 nx, ny, n;
x ^= (Y(1)^Y(2))<<2; x ^= (Y(1)^Y(2))<<2;
nx = x&7 | (x>>1)&~7; nx = (x&7) | ((x>>1)&~7);
ny = y&1 | (y>>1)&~1; ny = (y&1) | ((y>>1)&~1);
n = Y(1) | X(3)<<1; n = Y(1) | X(3)<<1;
return n | nx<<2 | ny<<logw-1+2; return n | nx<<2 | ny<<(logw-1+2);
} }
void void
@@ -1375,7 +1375,7 @@ unswizzleRaster(Raster *raster)
int32 x, y, w, h; int32 x, y, w, h;
int32 i; int32 i;
int32 logw; int32 logw;
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
uint8 *px; uint8 *px;
if((raster->format & (Raster::PAL4|Raster::PAL8)) == 0) if((raster->format & (Raster::PAL4|Raster::PAL8)) == 0)
@@ -1388,17 +1388,17 @@ unswizzleRaster(Raster *raster)
px = raster->pixels; px = raster->pixels;
logw = 0; logw = 0;
for(i = 1; i < w; i *= 2) logw++; for(i = 1; i < w; i *= 2) logw++;
mask = (1<<logw+2)-1; mask = (1<<(logw+2))-1;
if(raster->format & Raster::PAL4 && natras->flags & Ps2Raster::SWIZZLED4){ if(raster->format & Raster::PAL4 && natras->flags & Ps2Raster::SWIZZLED4){
for(y = 0; y < h; y += 4){ for(y = 0; y < h; y += 4){
memcpy(tmpbuf, &px[y<<logw-1], 2*w); memcpy(tmpbuf, &px[y<<(logw-1)], 2*w);
for(i = 0; i < 4; i++) for(i = 0; i < 4; i++)
for(x = 0; x < w; x++){ for(x = 0; x < w; x++){
uint32 a = (y+i<<logw)+x; uint32 a = ((y+i)<<logw)+x;
uint32 s = swizzle(x, y+i, logw)&mask; uint32 s = swizzle(x, y+i, logw)&mask;
uint8 c = s & 1 ? tmpbuf[s>>1] >> 4 : tmpbuf[s>>1] & 0xF; uint8 c = s & 1 ? tmpbuf[s>>1] >> 4 : tmpbuf[s>>1] & 0xF;
px[a>>1] = a & 1 ? px[a>>1]&0xF | c<<4 : px[a>>1]&0xF0 | c; px[a>>1] = a & 1 ? (px[a>>1]&0xF) | c<<4 : (px[a>>1]&0xF0) | c;
} }
} }
}else if(raster->format & Raster::PAL8 && natras->flags & Ps2Raster::SWIZZLED8){ }else if(raster->format & Raster::PAL8 && natras->flags & Ps2Raster::SWIZZLED8){
@@ -1406,7 +1406,7 @@ unswizzleRaster(Raster *raster)
memcpy(tmpbuf, &px[y<<logw], 4*w); memcpy(tmpbuf, &px[y<<logw], 4*w);
for(i = 0; i < 4; i++) for(i = 0; i < 4; i++)
for(x = 0; x < w; x++){ for(x = 0; x < w; x++){
uint32 a = (y+i<<logw)+x; uint32 a = ((y+i)<<logw)+x;
uint32 s = swizzle(x, y+i, logw)&mask; uint32 s = swizzle(x, y+i, logw)&mask;
px[a] = tmpbuf[s]; px[a] = tmpbuf[s];
} }
@@ -1422,7 +1422,7 @@ swizzleRaster(Raster *raster)
int32 x, y, w, h; int32 x, y, w, h;
int32 i; int32 i;
int32 logw; int32 logw;
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
uint8 *px; uint8 *px;
if((raster->format & (Raster::PAL4|Raster::PAL8)) == 0) if((raster->format & (Raster::PAL4|Raster::PAL8)) == 0)
@@ -1435,24 +1435,24 @@ swizzleRaster(Raster *raster)
px = raster->pixels; px = raster->pixels;
logw = 0; logw = 0;
for(i = 1; i < raster->width; i *= 2) logw++; for(i = 1; i < raster->width; i *= 2) logw++;
mask = (1<<logw+2)-1; mask = (1<<(logw+2))-1;
if(raster->format & Raster::PAL4 && natras->flags & Ps2Raster::SWIZZLED4){ if(raster->format & Raster::PAL4 && natras->flags & Ps2Raster::SWIZZLED4){
for(y = 0; y < h; y += 4){ for(y = 0; y < h; y += 4){
for(i = 0; i < 4; i++) for(i = 0; i < 4; i++)
for(x = 0; x < w; x++){ for(x = 0; x < w; x++){
uint32 a = (y+i<<logw)+x; uint32 a = ((y+i)<<logw)+x;
uint32 s = swizzle(x, y+i, logw)&mask; uint32 s = swizzle(x, y+i, logw)&mask;
uint8 c = a & 1 ? px[a>>1] >> 4 : px[a>>1] & 0xF; uint8 c = a & 1 ? px[a>>1] >> 4 : px[a>>1] & 0xF;
tmpbuf[s>>1] = s & 1 ? tmpbuf[s>>1]&0xF | c<<4 : tmpbuf[s>>1]&0xF0 | c; tmpbuf[s>>1] = s & 1 ? (tmpbuf[s>>1]&0xF) | c<<4 : (tmpbuf[s>>1]&0xF0) | c;
} }
memcpy(&px[y<<logw-1], tmpbuf, 2*w); memcpy(&px[y<<(logw-1)], tmpbuf, 2*w);
} }
}else if(raster->format & Raster::PAL8 && natras->flags & Ps2Raster::SWIZZLED8){ }else if(raster->format & Raster::PAL8 && natras->flags & Ps2Raster::SWIZZLED8){
for(y = 0; y < h; y += 4){ for(y = 0; y < h; y += 4){
for(i = 0; i < 4; i++) for(i = 0; i < 4; i++)
for(x = 0; x < w; x++){ for(x = 0; x < w; x++){
uint32 a = (y+i<<logw)+x; uint32 a = ((y+i)<<logw)+x;
uint32 s = swizzle(x, y+i, logw)&mask; uint32 s = swizzle(x, y+i, logw)&mask;
tmpbuf[s] = px[a]; tmpbuf[s] = px[a];
} }
@@ -1464,7 +1464,7 @@ swizzleRaster(Raster *raster)
uint8* uint8*
rasterLock(Raster *raster, int32 level, int32 lockMode) rasterLock(Raster *raster, int32 level, int32 lockMode)
{ {
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
assert(raster->depth != 24); assert(raster->depth != 24);
if(level > 0){ if(level > 0){
@@ -1490,7 +1490,7 @@ rasterLock(Raster *raster, int32 level, int32 lockMode)
void void
rasterUnlock(Raster *raster, int32 level) rasterUnlock(Raster *raster, int32 level)
{ {
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
if(raster->format & (Raster::PAL4 | Raster::PAL8)) if(raster->format & (Raster::PAL4 | Raster::PAL8))
swizzleRaster(raster); swizzleRaster(raster);
@@ -1615,7 +1615,7 @@ imageFindRasterFormat(Image *img, int32 type,
bool32 bool32
rasterFromImage(Raster *raster, Image *image) rasterFromImage(Raster *raster, Image *image)
{ {
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
int32 pallength = 0; int32 pallength = 0;
switch(image->depth){ switch(image->depth){
@@ -1708,7 +1708,7 @@ rasterToImage(Raster *raster)
{ {
Image *image; Image *image;
int depth; int depth;
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
int32 rasterFormat = raster->format & 0xF00; int32 rasterFormat = raster->format & 0xF00;
switch(rasterFormat){ switch(rasterFormat){
@@ -1812,7 +1812,7 @@ rasterToImage(Raster *raster)
int32 int32
rasterNumLevels(Raster *raster) rasterNumLevels(Raster *raster)
{ {
Ps2Raster *ras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *ras = GETPS2RASTEREXT(raster);
if(raster->pixels == nil) return 0; if(raster->pixels == nil) return 0;
if(raster->format & Raster::MIPMAP) if(raster->format & Raster::MIPMAP)
return MAXLEVEL(ras)+1; return MAXLEVEL(ras)+1;
@@ -1822,7 +1822,7 @@ rasterNumLevels(Raster *raster)
static void* static void*
createNativeRaster(void *object, int32 offset, int32) createNativeRaster(void *object, int32 offset, int32)
{ {
Ps2Raster *raster = PLUGINOFFSET(Ps2Raster, object, offset); Ps2Raster *raster = GETPS2RASTEREXT(object);
raster->tex0 = 0; raster->tex0 = 0;
raster->paletteBase = 0; raster->paletteBase = 0;
raster->kl = defaultMipMapKL; raster->kl = defaultMipMapKL;
@@ -1843,7 +1843,7 @@ createNativeRaster(void *object, int32 offset, int32)
static void* static void*
destroyNativeRaster(void *object, int32 offset, int32) destroyNativeRaster(void *object, int32 offset, int32)
{ {
Ps2Raster *raster = PLUGINOFFSET(Ps2Raster, object, offset); Ps2Raster *raster = GETPS2RASTEREXT(object);
freealign(raster->data); freealign(raster->data);
return object; return object;
} }
@@ -1851,8 +1851,8 @@ destroyNativeRaster(void *object, int32 offset, int32)
static void* static void*
copyNativeRaster(void *dst, void *src, int32 offset, int32) copyNativeRaster(void *dst, void *src, int32 offset, int32)
{ {
Ps2Raster *dstraster = PLUGINOFFSET(Ps2Raster, dst, offset); Ps2Raster *dstraster = GETPS2RASTEREXT(dst);
Ps2Raster *srcraster = PLUGINOFFSET(Ps2Raster, src, offset); Ps2Raster *srcraster = GETPS2RASTEREXT(src);
*dstraster = *srcraster; *dstraster = *srcraster;
return dst; return dst;
} }
@@ -1864,7 +1864,7 @@ readMipmap(Stream *stream, int32, void *object, int32 offset, int32)
Texture *tex = (Texture*)object; Texture *tex = (Texture*)object;
if(tex->raster == nil) if(tex->raster == nil)
return stream; return stream;
Ps2Raster *raster = PLUGINOFFSET(Ps2Raster, tex->raster, offset); Ps2Raster *raster = GETPS2RASTEREXT(tex->raster);
raster->kl = val; raster->kl = val;
return stream; return stream;
} }
@@ -1877,7 +1877,7 @@ writeMipmap(Stream *stream, int32, void *object, int32 offset, int32)
stream->writeI32(defaultMipMapKL); stream->writeI32(defaultMipMapKL);
return stream; return stream;
} }
Ps2Raster *raster = PLUGINOFFSET(Ps2Raster, tex->raster, offset); Ps2Raster *raster = GETPS2RASTEREXT(tex->raster);
stream->writeI32(raster->kl); stream->writeI32(raster->kl);
return stream; return stream;
} }
@@ -1904,7 +1904,7 @@ registerNativeRaster(void)
void void
printTEX0(uint64 tex0) printTEX0(uint64 tex0)
{ {
printf("%016llX ", tex0); printf("%016lX ", tex0);
uint32 tbp0 = tex0 & 0x3FFF; tex0 >>= 14; uint32 tbp0 = tex0 & 0x3FFF; tex0 >>= 14;
uint32 tbw = tex0 & 0x3F; tex0 >>= 6; uint32 tbw = tex0 & 0x3F; tex0 >>= 6;
uint32 psm = tex0 & 0x3F; tex0 >>= 6; uint32 psm = tex0 & 0x3F; tex0 >>= 6;
@@ -1924,7 +1924,7 @@ printTEX0(uint64 tex0)
void void
printTEX1(uint64 tex1) printTEX1(uint64 tex1)
{ {
printf("%016llX ", tex1); printf("%016lX ", tex1);
uint32 lcm = tex1 & 0x1; tex1 >>= 2; uint32 lcm = tex1 & 0x1; tex1 >>= 2;
uint32 mxl = tex1 & 0x7; tex1 >>= 3; uint32 mxl = tex1 & 0x7; tex1 >>= 3;
uint32 mmag = tex1 & 0x1; tex1 >>= 1; uint32 mmag = tex1 & 0x1; tex1 >>= 1;
@@ -1947,7 +1947,7 @@ calcTEX1(Raster *raster, uint64 *tex1, int32 filter)
LINEAR_MIPMAP_NEAREST, LINEAR_MIPMAP_NEAREST,
LINEAR_MIPMAP_LINEAR, LINEAR_MIPMAP_LINEAR,
}; };
Ps2Raster *natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *natras = GETPS2RASTEREXT(raster);
uint64 t1 = natras->tex1low; uint64 t1 = natras->tex1low;
uint64 k = natras->kl & 0xFFF; uint64 k = natras->kl & 0xFFF;
uint64 l = (natras->kl >> 12) & 0x3; uint64 l = (natras->kl >> 12) & 0x3;
@@ -2071,7 +2071,7 @@ streamExt.mipmapVal);
noNewStyleRasters = 0; noNewStyleRasters = 0;
rw::version = oldversion; rw::version = oldversion;
tex->raster = raster; tex->raster = raster;
natras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); natras = GETPS2RASTEREXT(raster);
//printf("%X %X\n", natras->paletteBase, natras->tex1low); //printf("%X %X\n", natras->paletteBase, natras->tex1low);
// printf("%08X%08X %08X%08X %08X%08X\n", // printf("%08X%08X %08X%08X %08X%08X\n",
// (uint32)natras->tex0, (uint32)(natras->tex0>>32), // (uint32)natras->tex0, (uint32)(natras->tex0>>32),
@@ -2176,7 +2176,7 @@ void
writeNativeTexture(Texture *tex, Stream *stream) writeNativeTexture(Texture *tex, Stream *stream)
{ {
Raster *raster = tex->raster; Raster *raster = tex->raster;
Ps2Raster *ras = PLUGINOFFSET(Ps2Raster, raster, nativeRasterOffset); Ps2Raster *ras = GETPS2RASTEREXT(raster);
writeChunkHeader(stream, ID_STRUCT, 8); writeChunkHeader(stream, ID_STRUCT, 8);
stream->writeU32(FOURCC_PS2); stream->writeU32(FOURCC_PS2);
stream->writeU32(tex->filterAddressing); stream->writeU32(tex->filterAddressing);
@@ -2229,7 +2229,7 @@ getSizeNativeTexture(Texture *tex)
size += 12 + strlen(tex->mask)+4 & ~3; size += 12 + strlen(tex->mask)+4 & ~3;
size += 12; size += 12;
size += 12 + 64; size += 12 + 64;
Ps2Raster *ras = PLUGINOFFSET(Ps2Raster, tex->raster, nativeRasterOffset); Ps2Raster *ras = GETPS2RASTEREXT(tex->raster);
size += 12 + ras->pixelSize + ras->paletteSize; size += 12 + ras->pixelSize + ras->paletteSize;
return size; return size;
} }
+1
View File
@@ -248,6 +248,7 @@ struct Ps2Raster
extern int32 nativeRasterOffset; extern int32 nativeRasterOffset;
void registerNativeRaster(void); void registerNativeRaster(void);
#define GETPS2RASTEREXT(raster) PLUGINOFFSET(rw::ps2::Ps2Raster, raster, rw::ps2::nativeRasterOffset)
Texture *readNativeTexture(Stream *stream); Texture *readNativeTexture(Stream *stream);
void writeNativeTexture(Texture *tex, Stream *stream); void writeNativeTexture(Texture *tex, Stream *stream);
+194 -9
View File
@@ -10,10 +10,11 @@
#include "rwobjects.h" #include "rwobjects.h"
#include "rwengine.h" #include "rwengine.h"
//#include "ps2/rwps2.h" //#include "ps2/rwps2.h"
//#include "d3d/rwd3d.h" #include "d3d/rwd3d.h"
//#include "d3d/rwxbox.h" #include "d3d/rwxbox.h"
//#include "d3d/rwd3d8.h" //#include "d3d/rwd3d8.h"
//#include "d3d/rwd3d9.h" //#include "d3d/rwd3d9.h"
#include "gl/rwgl3.h"
#define PLUGIN_ID 0 #define PLUGIN_ID 0
@@ -36,7 +37,7 @@ rasterOpen(void *object, int32 offset, int32 size)
int i; int i;
rasterModuleOffset = offset; rasterModuleOffset = offset;
RASTERGLOBAL(sp) = -1; RASTERGLOBAL(sp) = -1;
for(i = 0; i < nelem(RASTERGLOBAL(stack)); i++) for(i = 0; i < (int)nelem(RASTERGLOBAL(stack)); i++)
RASTERGLOBAL(stack)[i] = nil; RASTERGLOBAL(stack)[i] = nil;
return object; return object;
} }
@@ -71,6 +72,7 @@ Raster::create(int32 width, int32 height, int32 depth, int32 format, int32 platf
raster->width = width; raster->width = width;
raster->height = height; raster->height = height;
raster->depth = depth; raster->depth = depth;
raster->stride = 0;
raster->pixels = raster->palette = nil; raster->pixels = raster->palette = nil;
s_plglist.construct(raster); s_plglist.construct(raster);
@@ -85,8 +87,8 @@ Raster::subRaster(Raster *parent, Rect *r)
return; return;
this->width = r->w; this->width = r->w;
this->height = r->h; this->height = r->h;
this->offsetX += r->x; this->offsetX = parent->offsetX + r->x;
this->offsetY += r->y; this->offsetY = parent->offsetY + r->y;
this->parent = parent->parent; this->parent = parent->parent;
} }
@@ -293,19 +295,31 @@ conv_RGBA5551_from_ARGB1555(uint8 *out, uint8 *in)
uint32 r, g, b, a; uint32 r, g, b, a;
a = (in[1]>>7) & 1; a = (in[1]>>7) & 1;
r = (in[1]>>2) & 0x1F; r = (in[1]>>2) & 0x1F;
g = (in[1]&3)<<3 | (in[0]>>5)&7; g = (in[1]&3)<<3 | ((in[0]>>5)&7);
b = in[0] & 0x1F; b = in[0] & 0x1F;
out[0] = a | b<<1 | g<<6; out[0] = a | b<<1 | g<<6;
out[1] = g>>2 | r<<3; out[1] = g>>2 | r<<3;
} }
void
conv_ARGB1555_from_RGBA5551(uint8 *out, uint8 *in)
{
uint32 r, g, b, a;
a = in[0] & 1;
b = (in[0]>>1) & 0x1F;
g = (in[1]&7)<<2 | ((in[0]>>6)&3);
r = (in[1]>>3) & 0x1F;
out[0] = b | g<<5;
out[1] = g>>3 | r<<2 | a<<7;
}
void void
conv_RGBA8888_from_ARGB1555(uint8 *out, uint8 *in) conv_RGBA8888_from_ARGB1555(uint8 *out, uint8 *in)
{ {
uint32 r, g, b, a; uint32 r, g, b, a;
a = (in[1]>>7) & 1; a = (in[1]>>7) & 1;
r = (in[1]>>2) & 0x1F; r = (in[1]>>2) & 0x1F;
g = (in[1]&3)<<3 | (in[0]>>5)&7; g = (in[1]&3)<<3 | ((in[0]>>5)&7);
b = in[0] & 0x1F; b = in[0] & 0x1F;
out[0] = r*0xFF/0x1f; out[0] = r*0xFF/0x1f;
out[1] = g*0xFF/0x1f; out[1] = g*0xFF/0x1f;
@@ -319,8 +333,8 @@ conv_ABGR1555_from_ARGB1555(uint8 *out, uint8 *in)
uint32 r, b; uint32 r, b;
r = (in[1]>>2) & 0x1F; r = (in[1]>>2) & 0x1F;
b = in[0] & 0x1F; b = in[0] & 0x1F;
out[1] = in[1]&0x83 | b<<2; out[1] = (in[1]&0x83) | b<<2;
out[0] = in[0]&0xE0 | r; out[0] = (in[0]&0xE0) | r;
} }
void void
@@ -371,4 +385,175 @@ copyPal8(uint8 *dst, uint32 dststride, uint8 *src, uint32 srcstride, int32 w, in
} }
// Platform conversion
static rw::Raster*
xbox_to_d3d(rw::Raster *ras)
{
using namespace rw;
int dxt = 0;
xbox::XboxRaster *xboxras = GETXBOXRASTEREXT(ras);
if(xboxras->customFormat){
switch(xboxras->format){
case xbox::D3DFMT_DXT1: dxt = 1; break;
case xbox::D3DFMT_DXT3: dxt = 3; break;
case xbox::D3DFMT_DXT5: dxt = 5; break;
}
}
if(dxt == 0)
return nil;
Raster *newras = Raster::create(ras->width, ras->height, ras->depth,
ras->format | Raster::TEXTURE | Raster::DONTALLOCATE);
int numLevels = ras->getNumLevels();
d3d::allocateDXT(newras, dxt, numLevels, xboxras->hasAlpha);
for(int i = 0; i < numLevels; i++){
uint8 *srcpx = ras->lock(i, Raster::LOCKREAD);
// uint8 *dstpx = newras->lock(i, Raster::LOCKWRITE | Raster::LOCKNOFETCH);
d3d::setTexels(newras, srcpx, i);
// flipDXT(dxt, dstpx, srcpx, ras->width, ras->height);
ras->unlock(i);
// newras->unlock(i);
}
return newras;
}
static rw::Raster*
d3d_to_gl3(rw::Raster *ras)
{
#ifdef RW_GL3
using namespace rw;
if(!gl3::gl3Caps.dxtSupported)
return nil;
int dxt = 0;
d3d::D3dRaster *d3dras = GETD3DRASTEREXT(ras);
if(d3dras->customFormat){
switch(d3dras->format){
case d3d::D3DFMT_DXT1: dxt = 1; break;
case d3d::D3DFMT_DXT3: dxt = 3; break;
case d3d::D3DFMT_DXT5: dxt = 5; break;
}
}
if(dxt == 0)
return nil;
Raster *newras = Raster::create(ras->width, ras->height, ras->depth,
ras->format | Raster::TEXTURE | Raster::DONTALLOCATE);
int numLevels = ras->getNumLevels();
gl3::allocateDXT(newras, dxt, numLevels, d3dras->hasAlpha);
for(int i = 0; i < numLevels; i++){
uint8 *srcpx = ras->lock(i, Raster::LOCKREAD);
uint8 *dstpx = newras->lock(i, Raster::LOCKWRITE | Raster::LOCKNOFETCH);
flipDXT(dxt, dstpx, srcpx, ras->width, ras->height);
ras->unlock(i);
newras->unlock(i);
}
return newras;
#else
return nil;
#endif
}
static rw::Raster*
xbox_to_gl3(rw::Raster *ras)
{
#ifdef RW_GL3
using namespace rw;
int dxt = 0;
xbox::XboxRaster *xboxras = GETXBOXRASTEREXT(ras);
if(xboxras->customFormat){
switch(xboxras->format){
case xbox::D3DFMT_DXT1: dxt = 1; break;
case xbox::D3DFMT_DXT3: dxt = 3; break;
case xbox::D3DFMT_DXT5: dxt = 5; break;
}
}
if(dxt == 0)
return nil;
Raster *newras = Raster::create(ras->width, ras->height, ras->depth,
ras->format | Raster::TEXTURE | Raster::DONTALLOCATE);
int numLevels = ras->getNumLevels();
gl3::allocateDXT(newras, dxt, numLevels, xboxras->hasAlpha);
for(int i = 0; i < numLevels; i++){
uint8 *srcpx = ras->lock(i, Raster::LOCKREAD);
uint8 *dstpx = newras->lock(i, Raster::LOCKWRITE | Raster::LOCKNOFETCH);
flipDXT(dxt, dstpx, srcpx, ras->width, ras->height);
ras->unlock(i);
newras->unlock(i);
}
return newras;
#else
return nil;
#endif
}
rw::Raster*
Raster::convertTexToCurrentPlatform(rw::Raster *ras)
{
using namespace rw;
if(ras->platform == rw::platform)
return ras;
// compatible platforms
if((ras->platform == PLATFORM_D3D8 && rw::platform == PLATFORM_D3D9) ||
(ras->platform == PLATFORM_D3D9 && rw::platform == PLATFORM_D3D8))
return ras;
// special cased conversion for DXT
if((ras->platform == PLATFORM_D3D8 || ras->platform == PLATFORM_D3D9) && rw::platform == PLATFORM_GL3){
Raster *newras = d3d_to_gl3(ras);
if(newras){
ras->destroy();
return newras;
}
}else if(ras->platform == PLATFORM_XBOX && (rw::platform == PLATFORM_D3D9 || rw::platform == PLATFORM_D3D8)){
Raster *newras = xbox_to_d3d(ras);
if(newras){
ras->destroy();
return newras;
}
}else if(ras->platform == PLATFORM_XBOX && rw::platform == PLATFORM_GL3){
Raster *newras = xbox_to_gl3(ras);
if(newras){
ras->destroy();
return newras;
}
}
// fall back to going through Image directly
int32 width, height, depth, format;
Image *img = ras->toImage();
// TODO: maybe don't *always* do this?
img->unpalettize();
Raster::imageFindRasterFormat(img, Raster::TEXTURE, &width, &height, &depth, &format);
format |= ras->format & (Raster::MIPMAP | Raster::AUTOMIPMAP);
Raster *newras = Raster::create(width, height, depth, format);
newras->setFromImage(img);
img->destroy();
int numLevels = ras->getNumLevels();
for(int i = 1; i < numLevels; i++){
ras->lock(i, Raster::LOCKREAD);
img = ras->toImage();
// TODO: maybe don't *always* do this?
img->unpalettize();
newras->lock(i, Raster::LOCKWRITE|Raster::LOCKNOFETCH);
newras->setFromImage(img);
newras->unlock(i);
ras->unlock(i);
}
ras->destroy();
ras = newras;
return ras;
}
} }
+18
View File
@@ -3,6 +3,7 @@
#include "rwbase.h" #include "rwbase.h"
#include "rwplg.h" #include "rwplg.h"
#include "rwengine.h" #include "rwengine.h"
#include "rwrender.h"
namespace rw { namespace rw {
@@ -57,6 +58,23 @@ Transform(void *vertices, int32 numVertices, Matrix *world, uint32 flags)
engine->device.im3DTransform(vertices, numVertices, world, flags); engine->device.im3DTransform(vertices, numVertices, world, flags);
} }
void void
RenderLine(int32 vert1, int32 vert2)
{
int16 indices[2];
indices[0] = vert1;
indices[1] = vert2;
RenderIndexedPrimitive(rw::PRIMTYPELINELIST, indices, 2);
}
void
RenderTriangle(int32 vert1, int32 vert2, int32 vert3)
{
int16 indices[3];
indices[0] = vert1;
indices[1] = vert2;
indices[2] = vert3;
RenderIndexedPrimitive(rw::PRIMTYPETRILIST, indices, 3);
}
void
RenderPrimitive(PrimitiveType primType) RenderPrimitive(PrimitiveType primType)
{ {
engine->device.im3DRenderPrimitive(primType); engine->device.im3DRenderPrimitive(primType);
+18 -19
View File
@@ -5,9 +5,7 @@
#ifndef M_PI #ifndef M_PI
#define M_PI 3.14159265358979323846 #define M_PI 3.14159265358979323846
#endif #endif
extern "C"{
#include <math_neon.h>
};
// TODO: clean up the opengl defines // TODO: clean up the opengl defines
// and figure out what we even want here... // and figure out what we even want here...
#ifdef RW_GL3 #ifdef RW_GL3
@@ -242,7 +240,7 @@ inline V3d add(const V3d &a, const V3d &b) { return makeV3d(a.x+b.x, a.y+b.y, a.
inline V3d sub(const V3d &a, const V3d &b) { return makeV3d(a.x-b.x, a.y-b.y, a.z-b.z); } inline V3d sub(const V3d &a, const V3d &b) { return makeV3d(a.x-b.x, a.y-b.y, a.z-b.z); }
inline V3d scale(const V3d &a, float32 r) { return makeV3d(a.x*r, a.y*r, a.z*r); } inline V3d scale(const V3d &a, float32 r) { return makeV3d(a.x*r, a.y*r, a.z*r); }
inline float32 length(const V3d &v) { return sqrtf(v.x*v.x + v.y*v.y + v.z*v.z); } inline float32 length(const V3d &v) { return sqrtf(v.x*v.x + v.y*v.y + v.z*v.z); }
inline V3d normalize(const V3d &v) { V3d r; normalize3_neon((float*)&v.x, &r.x); return r; } inline V3d normalize(const V3d &v) { return scale(v, 1.0f/length(v)); }
inline V3d setlength(const V3d &v, float32 l) { return scale(v, l/length(v)); } inline V3d setlength(const V3d &v, float32 l) { return scale(v, l/length(v)); }
V3d cross(const V3d &a, const V3d &b); V3d cross(const V3d &a, const V3d &b);
inline float32 dot(const V3d &a, const V3d &b) { return a.x*b.x + a.y*b.y + a.z*b.z; } inline float32 dot(const V3d &a, const V3d &b) { return a.x*b.x + a.y*b.y + a.z*b.z; }
@@ -275,15 +273,12 @@ struct Quat
float32 x, y, z, w; float32 x, y, z, w;
static Quat rotation(float32 angle, const V3d &axis){ static Quat rotation(float32 angle, const V3d &axis){
float cs[2]; return makeQuat(cosf(angle/2.0f), scale(normalize(axis), sinf(angle/2.0f))); }
sincosf_c(angle/2.0f, cs);
return makeQuat(cs[1], scale(normalize(axis), cs[0]));
}
void set(float32 w, float32 x, float32 y, float32 z){ void set(float32 w, float32 x, float32 y, float32 z){
this->w = w; this->x = x; this->y = y; this->z = z; } this->w = w; this->x = x; this->y = y; this->z = z; }
V3d vec(void){ return makeV3d(x, y, z); } V3d vec(void){ return makeV3d(x, y, z); }
Quat *rotate(const V3d *axis, float32 angle, CombineOp op); Quat *rotate(const V3d *axis, float32 angle, CombineOp op = rw::COMBINEPOSTCONCAT);
}; };
inline Quat makeQuat(float32 w, float32 x, float32 y, float32 z) { Quat q = { x, y, z, w }; return q; } inline Quat makeQuat(float32 w, float32 x, float32 y, float32 z) { Quat q = { x, y, z, w }; return q; }
@@ -291,10 +286,10 @@ inline Quat makeQuat(float32 w, const V3d &vec) { Quat q = { vec.x, vec.y, vec.z
inline Quat add(const Quat &q, const Quat &p) { return makeQuat(q.w+p.w, q.x+p.x, q.y+p.y, q.z+p.z); } inline Quat add(const Quat &q, const Quat &p) { return makeQuat(q.w+p.w, q.x+p.x, q.y+p.y, q.z+p.z); }
inline Quat sub(const Quat &q, const Quat &p) { return makeQuat(q.w-p.w, q.x-p.x, q.y-p.y, q.z-p.z); } inline Quat sub(const Quat &q, const Quat &p) { return makeQuat(q.w-p.w, q.x-p.x, q.y-p.y, q.z-p.z); }
inline Quat negate(const Quat &q) { return makeQuat(-q.w, -q.x, -q.y, -q.z); } inline Quat negate(const Quat &q) { return makeQuat(-q.w, -q.x, -q.y, -q.z); }
inline float32 dot(const Quat &q, const Quat &p) { return dot4_neon((float*)&q.x, (float*)&p.x); } inline float32 dot(const Quat &q, const Quat &p) { return q.w*p.w + q.x*p.x + q.y*p.y + q.z*p.z; }
inline Quat scale(const Quat &q, float32 r) { return makeQuat(q.w*r, q.x*r, q.y*r, q.z*r); } inline Quat scale(const Quat &q, float32 r) { return makeQuat(q.w*r, q.x*r, q.y*r, q.z*r); }
inline float32 length(const Quat &q) { return sqrtf(q.w*q.w + q.x*q.x + q.y*q.y + q.z*q.z); } inline float32 length(const Quat &q) { return sqrtf(q.w*q.w + q.x*q.x + q.y*q.y + q.z*q.z); }
inline Quat normalize(const Quat &q) { float r[4]; normalize4_neon((float*)&q.x, r); return makeQuat(r[0], r[1], r[2], r[3]); } inline Quat normalize(const Quat &q) { return scale(q, 1.0f/length(q)); }
inline Quat conj(const Quat &q) { return makeQuat(q.w, -q.x, -q.y, -q.z); } inline Quat conj(const Quat &q) { return makeQuat(q.w, -q.x, -q.y, -q.z); }
Quat mult(const Quat &q, const Quat &p); Quat mult(const Quat &q, const Quat &p);
inline V3d rotate(const V3d &v, const Quat &q) { return mult(mult(q, makeQuat(0.0f, v)), conj(q)).vec(); } inline V3d rotate(const V3d &v, const Quat &q) { return mult(mult(q, makeQuat(0.0f, v)), conj(q)).vec(); }
@@ -310,8 +305,9 @@ struct RawMatrix
V3d at; V3d at;
float32 atw; float32 atw;
V3d pos; V3d pos;
float32 posw;; float32 posw;
// NB: this is dst = src2*src1, i.e. src1 is applied first, then src2
static void mult(RawMatrix *dst, RawMatrix *src1, RawMatrix *src2); static void mult(RawMatrix *dst, RawMatrix *src1, RawMatrix *src2);
static void transpose(RawMatrix *dst, RawMatrix *src); static void transpose(RawMatrix *dst, RawMatrix *src);
static void setIdentity(RawMatrix *dst); static void setIdentity(RawMatrix *dst);
@@ -351,11 +347,11 @@ struct Matrix
static Matrix *mult(Matrix *dst, const Matrix *src1, const Matrix *src2); static Matrix *mult(Matrix *dst, const Matrix *src1, const Matrix *src2);
static Matrix *invert(Matrix *dst, const Matrix *src); static Matrix *invert(Matrix *dst, const Matrix *src);
static Matrix *transpose(Matrix *dst, const Matrix *src); static Matrix *transpose(Matrix *dst, const Matrix *src);
Matrix *rotate(const V3d *axis, float32 angle, CombineOp op); Matrix *rotate(const V3d *axis, float32 angle, CombineOp op = rw::COMBINEPOSTCONCAT);
Matrix *rotate(const Quat &q, CombineOp op); Matrix *rotate(const Quat &q, CombineOp op = rw::COMBINEPOSTCONCAT);
Matrix *translate(const V3d *translation, CombineOp op); Matrix *translate(const V3d *translation, CombineOp op = rw::COMBINEPOSTCONCAT);
Matrix *scale(const V3d *scl, CombineOp op); Matrix *scale(const V3d *scl, CombineOp op = rw::COMBINEPOSTCONCAT);
Matrix *transform(const Matrix *mat, CombineOp op); Matrix *transform(const Matrix *mat, CombineOp op = rw::COMBINEPOSTCONCAT);
Quat getRotation(void); Quat getRotation(void);
void lookAt(const V3d &dir, const V3d &up); void lookAt(const V3d &dir, const V3d &up);
@@ -491,11 +487,12 @@ public:
class StreamMemory : public Stream class StreamMemory : public Stream
{ {
public:
uint8 *data; uint8 *data;
uint32 length; uint32 length;
uint32 capacity; uint32 capacity;
uint32 position; uint32 position;
public:
void close(void); void close(void);
uint32 write8(const void *data, uint32 length); uint32 write8(const void *data, uint32 length);
uint32 read8(void *data, uint32 length); uint32 read8(void *data, uint32 length);
@@ -512,8 +509,9 @@ public:
class StreamFile : public Stream class StreamFile : public Stream
{ {
FILE *file;
public: public:
FILE *file;
StreamFile(void) { file = nil; } StreamFile(void) { file = nil; }
void close(void); void close(void);
uint32 write8(const void *data, uint32 length); uint32 write8(const void *data, uint32 length);
@@ -597,6 +595,7 @@ enum PluginID
ID_HANIM = MAKEPLUGINID(VEND_CRITERIONTK, 0x1E), ID_HANIM = MAKEPLUGINID(VEND_CRITERIONTK, 0x1E),
ID_USERDATA = MAKEPLUGINID(VEND_CRITERIONTK, 0x1F), ID_USERDATA = MAKEPLUGINID(VEND_CRITERIONTK, 0x1F),
ID_MATFX = MAKEPLUGINID(VEND_CRITERIONTK, 0x20), ID_MATFX = MAKEPLUGINID(VEND_CRITERIONTK, 0x20),
ID_ANISOT = MAKEPLUGINID(VEND_CRITERIONTK, 0x27),
ID_PDS = MAKEPLUGINID(VEND_CRITERIONTK, 0x31), ID_PDS = MAKEPLUGINID(VEND_CRITERIONTK, 0x31),
ID_ADC = MAKEPLUGINID(VEND_CRITERIONTK, 0x34), ID_ADC = MAKEPLUGINID(VEND_CRITERIONTK, 0x34),
ID_UVANIMATION = MAKEPLUGINID(VEND_CRITERIONTK, 0x35), ID_UVANIMATION = MAKEPLUGINID(VEND_CRITERIONTK, 0x35),
+18 -2
View File
@@ -27,7 +27,13 @@ enum DeviceReq
DEVICEGETNUMVIDEOMODES, DEVICEGETNUMVIDEOMODES,
DEVICEGETCURRENTVIDEOMODE, DEVICEGETCURRENTVIDEOMODE,
DEVICESETVIDEOMODE, DEVICESETVIDEOMODE,
DEVICEGETVIDEOMODEINFO DEVICEGETVIDEOMODEINFO,
// Multisampling
DEVICEGETMAXMULTISAMPLINGLEVELS,
DEVICEGETMULTISAMPLINGLEVELS,
DEVICESETMULTISAMPLINGLEVELS,
}; };
typedef int DeviceSystem(DeviceReq req, void *arg, int32 n); typedef int DeviceSystem(DeviceReq req, void *arg, int32 n);
@@ -159,7 +165,7 @@ struct Engine
static MemoryFunctions memfuncs; static MemoryFunctions memfuncs;
static State state; static State state;
static bool32 init(void); static bool32 init(MemoryFunctions *memfuncs = nil);
static bool32 open(EngineOpenParams*); static bool32 open(EngineOpenParams*);
static bool32 start(void); static bool32 start(void);
static void term(void); static void term(void);
@@ -176,6 +182,9 @@ struct Engine
static bool32 setVideoMode(int32 mode); static bool32 setVideoMode(int32 mode);
static VideoMode *getVideoModeInfo(VideoMode *info, int32 mode); static VideoMode *getVideoModeInfo(VideoMode *info, int32 mode);
static uint32 getMaxMultiSamplingLevels(void);
static uint32 getMultiSamplingLevels(void);
static bool32 setMultiSamplingLevels(uint32 levels);
static PluginList s_plglist; static PluginList s_plglist;
static int32 registerPlugin(int32 size, uint32 id, static int32 registerPlugin(int32 size, uint32 id,
@@ -197,6 +206,8 @@ inline void *realloc_LOC(void *p, size_t sz, uint32 hint, const char *here) { al
inline void *mustmalloc_LOC(size_t sz, uint32 hint, const char *here) { allocLocation = here; return rw::Engine::memfuncs.rwmustmalloc(sz,hint); } inline void *mustmalloc_LOC(size_t sz, uint32 hint, const char *here) { allocLocation = here; return rw::Engine::memfuncs.rwmustmalloc(sz,hint); }
inline void *mustrealloc_LOC(void *p, size_t sz, uint32 hint, const char *here) { allocLocation = here; return rw::Engine::memfuncs.rwmustrealloc(p,sz,hint); } inline void *mustrealloc_LOC(void *p, size_t sz, uint32 hint, const char *here) { allocLocation = here; return rw::Engine::memfuncs.rwmustrealloc(p,sz,hint); }
char *strdup_LOC(const char *s, uint32 hint, const char *here);
#define rwMalloc(s, h) rw::malloc_LOC(s,h,RWHERE) #define rwMalloc(s, h) rw::malloc_LOC(s,h,RWHERE)
#define rwMallocT(t, s, h) (t*)rw::malloc_LOC((s)*sizeof(t),h,RWHERE) #define rwMallocT(t, s, h) (t*)rw::malloc_LOC((s)*sizeof(t),h,RWHERE)
#define rwRealloc(p, s, h) rw::realloc_LOC(p,s,h,RWHERE) #define rwRealloc(p, s, h) rw::realloc_LOC(p,s,h,RWHERE)
@@ -206,6 +217,11 @@ inline void *mustrealloc_LOC(void *p, size_t sz, uint32 hint, const char *here)
#define rwNewT(t, s, h) (t*)rw::mustmalloc_LOC((s)*sizeof(t),h,RWHERE) #define rwNewT(t, s, h) (t*)rw::mustmalloc_LOC((s)*sizeof(t),h,RWHERE)
#define rwResize(p, s, h) rw::mustrealloc_LOC(p,s,h,RWHERE) #define rwResize(p, s, h) rw::mustrealloc_LOC(p,s,h,RWHERE)
#define rwResizeT(t, p, s, h) (t*)rw::mustrealloc_LOC(p,(s)*sizeof(t),h,RWHERE) #define rwResizeT(t, p, s, h) (t*)rw::mustrealloc_LOC(p,(s)*sizeof(t),h,RWHERE)
#define rwStrdup(s, h) rw::strdup_LOC(s,h,RWHERE)
extern MemoryFunctions defaultMemfuncs;
extern MemoryFunctions managedMemfuncs;
void printleaks(void); // when using managed mem funcs
namespace null { namespace null {
void beginUpdate(Camera*); void beginUpdate(Camera*);
+2 -2
View File
@@ -17,8 +17,8 @@ char *dbgsprint(uint32 code, ...);
rw::Error _e; \ rw::Error _e; \
_e.plugin = PLUGIN_ID; \ _e.plugin = PLUGIN_ID; \
_e.code = _ERRORCODE ecode; \ _e.code = _ERRORCODE ecode; \
printf("%s:%d: ", __FILE__, __LINE__); \ fprintf(stderr, "%s:%d: ", __FILE__, __LINE__); \
printf("%s\n", rw::dbgsprint ecode); \ fprintf(stderr, "%s\n", rw::dbgsprint ecode); \
rw::setError(&_e); \ rw::setError(&_e); \
}while(0) }while(0)
+19 -9
View File
@@ -70,10 +70,10 @@ struct Frame
bool32 dirty(void) const { bool32 dirty(void) const {
return !!(this->root->object.privateFlags & HIERARCHYSYNC); } return !!(this->root->object.privateFlags & HIERARCHYSYNC); }
Matrix *getLTM(void); Matrix *getLTM(void);
void rotate(const V3d *axis, float32 angle, CombineOp op); void rotate(const V3d *axis, float32 angle, CombineOp op = rw::COMBINEPOSTCONCAT);
void translate(const V3d *trans, CombineOp op); void translate(const V3d *trans, CombineOp op = rw::COMBINEPOSTCONCAT);
void scale(const V3d *scale, CombineOp op); void scale(const V3d *scale, CombineOp op = rw::COMBINEPOSTCONCAT);
void transform(const Matrix *mat, CombineOp op); void transform(const Matrix *mat, CombineOp op = rw::COMBINEPOSTCONCAT);
void updateObjects(void); void updateObjects(void);
@@ -268,6 +268,7 @@ struct Raster
static Raster *getCurrentContext(void); static Raster *getCurrentContext(void);
bool32 renderFast(int32 x, int32 y); bool32 renderFast(int32 x, int32 y);
static Raster *convertTexToCurrentPlatform(Raster *ras);
#ifndef RWPUBLIC #ifndef RWPUBLIC
static void registerModule(void); static void registerModule(void);
#endif #endif
@@ -323,6 +324,7 @@ void conv_BGR888_from_RGB888(uint8 *out, uint8 *in);
void conv_ARGB1555_from_ARGB1555(uint8 *out, uint8 *in); void conv_ARGB1555_from_ARGB1555(uint8 *out, uint8 *in);
void conv_ARGB1555_from_RGB555(uint8 *out, uint8 *in); void conv_ARGB1555_from_RGB555(uint8 *out, uint8 *in);
void conv_RGBA5551_from_ARGB1555(uint8 *out, uint8 *in); void conv_RGBA5551_from_ARGB1555(uint8 *out, uint8 *in);
void conv_ARGB1555_from_RGBA5551(uint8 *out, uint8 *in);
void conv_RGBA8888_from_ARGB1555(uint8 *out, uint8 *in); void conv_RGBA8888_from_ARGB1555(uint8 *out, uint8 *in);
void conv_ABGR1555_from_ARGB1555(uint8 *out, uint8 *in); void conv_ABGR1555_from_ARGB1555(uint8 *out, uint8 *in);
inline void conv_8_from_8(uint8 *out, uint8 *in) { *out = *in; } inline void conv_8_from_8(uint8 *out, uint8 *in) { *out = *in; }
@@ -337,6 +339,7 @@ void expandPal4_BE(uint8 *dst, uint32 dststride, uint8 *src, uint32 srcstride, i
void compressPal4_BE(uint8 *dst, uint32 dststride, uint8 *src, uint32 srcstride, int32 w, int32 h); void compressPal4_BE(uint8 *dst, uint32 dststride, uint8 *src, uint32 srcstride, int32 w, int32 h);
void copyPal8(uint8 *dst, uint32 dststride, uint8 *src, uint32 srcstride, int32 w, int32 h); void copyPal8(uint8 *dst, uint32 dststride, uint8 *src, uint32 srcstride, int32 w, int32 h);
void flipDXT(int32 type, uint8 *dst, uint8 *src, uint32 width, uint32 height);
#define IGNORERASTERIMP 0 #define IGNORERASTERIMP 0
@@ -348,9 +351,9 @@ struct Texture
enum FilterMode { enum FilterMode {
NEAREST = 1, NEAREST = 1,
LINEAR, LINEAR,
MIPNEAREST, MIPNEAREST, // one mipmap
MIPLINEAR, MIPLINEAR,
LINEARMIPNEAREST, LINEARMIPNEAREST, // mipmap interpolated
LINEARMIPLINEAR LINEARMIPLINEAR
}; };
enum Addressing { enum Addressing {
@@ -401,11 +404,18 @@ struct Texture
static bool32 getMipmapping(void); static bool32 getMipmapping(void);
static bool32 getAutoMipmapping(void); static bool32 getAutoMipmapping(void);
void setMaxAnisotropy(int32 maxaniso); // only if plugin is attached
int32 getMaxAnisotropy(void);
#ifndef RWPUBLIC #ifndef RWPUBLIC
static void registerModule(void); static void registerModule(void);
#endif #endif
}; };
extern int32 anisotOffset;
#define GETANISOTROPYEXT(texture) PLUGINOFFSET(int32, texture, rw::anisotOffset)
void registerAnisotropyPlugin(void);
int32 getMaxSupportedMaxAnisotropy(void);
struct SurfaceProperties struct SurfaceProperties
{ {
@@ -723,7 +733,7 @@ struct Camera
PLUGINBASE PLUGINBASE
enum { ID = 4 }; enum { ID = 4 };
enum { PERSPECTIVE = 1, PARALLEL }; enum { PERSPECTIVE = 1, PARALLEL };
enum { CLEARIMAGE = 0x1, CLEARZ = 0x2}; enum { CLEARIMAGE = 0x1, CLEARZ = 0x2, CLEARSTENCIL = 0x4 };
// return value of frustumTestSphere // return value of frustumTestSphere
enum { SPHEREOUTSIDE, SPHEREBOUNDARY, SPHEREINSIDE }; enum { SPHEREOUTSIDE, SPHEREBOUNDARY, SPHEREINSIDE };
@@ -746,7 +756,7 @@ struct Camera
Raster *frameBuffer; Raster *frameBuffer;
Raster *zBuffer; Raster *zBuffer;
// Device dependant view and projection matrices // Device dependent view and projection matrices
// optional // optional
RawMatrix devView; RawMatrix devView;
RawMatrix devProj; RawMatrix devProj;
@@ -850,7 +860,7 @@ struct World
static int32 numAllocated; static int32 numAllocated;
static World *create(void); static World *create(BBox *bbox = nil); // TODO: should probably make this non-optional
void destroy(void); void destroy(void);
void addLight(Light *light); void addLight(Light *light);
void removeLight(Light *light); void removeLight(Light *light);
+6
View File
@@ -10,6 +10,7 @@ typedef Stream *(*StreamRead)(Stream *stream, int32 length, void *object, int32
typedef Stream *(*StreamWrite)(Stream *stream, int32 length, void *object, int32 offset, int32 size); typedef Stream *(*StreamWrite)(Stream *stream, int32 length, void *object, int32 offset, int32 size);
typedef int32 (*StreamGetSize)(void *object, int32 offset, int32 size); typedef int32 (*StreamGetSize)(void *object, int32 offset, int32 size);
typedef void (*RightsCallback)(void *object, int32 offset, int32 size, uint32 data); typedef void (*RightsCallback)(void *object, int32 offset, int32 size, uint32 data);
typedef void (*AlwaysCallback)(void *object, int32 offset, int32 size);
struct PluginList struct PluginList
{ {
@@ -38,6 +39,7 @@ struct PluginList
Constructor, Destructor, CopyConstructor); Constructor, Destructor, CopyConstructor);
int32 registerStream(uint32 id, StreamRead, StreamWrite, StreamGetSize); int32 registerStream(uint32 id, StreamRead, StreamWrite, StreamGetSize);
int32 setStreamRightsCallback(uint32 id, RightsCallback cb); int32 setStreamRightsCallback(uint32 id, RightsCallback cb);
int32 setStreamAlwaysCallback(uint32 id, AlwaysCallback cb);
int32 getPluginOffset(uint32 id); int32 getPluginOffset(uint32 id);
}; };
@@ -53,6 +55,7 @@ struct Plugin
StreamWrite write; StreamWrite write;
StreamGetSize getSize; StreamGetSize getSize;
RightsCallback rightsCallback; RightsCallback rightsCallback;
AlwaysCallback alwaysCallback;
PluginList *parentList; PluginList *parentList;
LLLink inParentList; LLLink inParentList;
LLLink inGlobalList; LLLink inGlobalList;
@@ -71,6 +74,9 @@ struct Plugin
static int32 setStreamRightsCallback(uint32 id, RightsCallback cb){ \ static int32 setStreamRightsCallback(uint32 id, RightsCallback cb){ \
return s_plglist.setStreamRightsCallback(id, cb); \ return s_plglist.setStreamRightsCallback(id, cb); \
} \ } \
static int32 setStreamAlwaysCallback(uint32 id, AlwaysCallback cb){ \
return s_plglist.setStreamAlwaysCallback(id, cb); \
} \
static int32 getPluginOffset(uint32 id){ \ static int32 getPluginOffset(uint32 id){ \
return s_plglist.getPluginOffset(id); \ return s_plglist.getPluginOffset(id); \
} }
+5 -1
View File
@@ -160,7 +160,10 @@ struct MatFX
static void disableEffects(Atomic *atomic); static void disableEffects(Atomic *atomic);
static bool32 getEffects(Atomic *atomic); static bool32 getEffects(Atomic *atomic);
static bool32 modulateEnvMap; static bool32 envMapFlipU; // PS2 does this for some reason
static bool32 envMapApplyLight; // modulate env map by lighting
static bool32 envMapUseMatColor; // modulate env map by material color
static RGBA envMapColor; // if !envMapUseMatColor, use this
}; };
struct MatFXGlobals struct MatFXGlobals
@@ -218,6 +221,7 @@ struct Skin
uint8 *data; // only used by delete uint8 *data; // only used by delete
void *platformData; // a place to store platform specific stuff void *platformData; // a place to store platform specific stuff
bool32 legacyType; // old skin attached to atomic, needed for always CB
void init(int32 numBones, int32 numUsedBones, int32 numVertices); void init(int32 numBones, int32 numUsedBones, int32 numVertices);
void findNumWeights(int32 numVertices); void findNumWeights(int32 numVertices);
+3
View File
@@ -20,6 +20,7 @@ enum RenderState
// TODO: // TODO:
// fog type, density ? // fog type, density ?
// ? shademode // ? shademode
STENCILENABLE, STENCILENABLE,
STENCILFAIL, STENCILFAIL,
STENCILZFAIL, STENCILZFAIL,
@@ -126,6 +127,8 @@ enum TransformFlags
}; };
void Transform(void *vertices, int32 numVertices, Matrix *world, uint32 flags); void Transform(void *vertices, int32 numVertices, Matrix *world, uint32 flags);
void RenderLine(int32 vert1, int32 vert2);
void RenderTriangle(int32 vert1, int32 vert2, int32 vert3);
void RenderPrimitive(PrimitiveType primType); void RenderPrimitive(PrimitiveType primType);
void RenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices); void RenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices);
void End(void); void End(void);
+19 -5
View File
@@ -24,7 +24,7 @@
namespace rw { namespace rw {
SkinGlobals skinGlobals = { 0, 0, { nil } }; SkinGlobals skinGlobals = { 0, 0, { nil }, nil };
static void* static void*
createSkin(void *object, int32 offset, int32) createSkin(void *object, int32 offset, int32)
@@ -64,11 +64,11 @@ copySkin(void *dst, void *src, int32 offset, int32)
assert(0 && "can't copy skin yet"); assert(0 && "can't copy skin yet");
dstskin->init(srcskin->numBones, srcskin->numUsedBones, dstskin->init(srcskin->numBones, srcskin->numUsedBones,
geometry->numVertices); geometry->numVertices);
memcpy_neon(dstskin->usedBones, srcskin->usedBones, srcskin->numUsedBones); memcpy(dstskin->usedBones, srcskin->usedBones, srcskin->numUsedBones);
memcpy_neon(dstskin->inverseMatrices, srcskin->inverseMatrices, memcpy(dstskin->inverseMatrices, srcskin->inverseMatrices,
srcskin->numBones*64); srcskin->numBones*64);
memcpy_neon(dstskin->indices, srcskin->indices, geometry->numVertices*4); memcpy(dstskin->indices, srcskin->indices, geometry->numVertices*4);
memcpy_neon(dstskin->weights, srcskin->weights, geometry->numVertices*16); memcpy(dstskin->weights, srcskin->weights, geometry->numVertices*16);
return dst; return dst;
} }
@@ -265,6 +265,7 @@ readSkinLegacy(Stream *stream, int32 len, void *object, int32, int32)
Skin *skin = rwNewT(Skin, 1, MEMDUR_EVENT | ID_SKIN); Skin *skin = rwNewT(Skin, 1, MEMDUR_EVENT | ID_SKIN);
*PLUGINOFFSET(Skin*, geometry, skinGlobals.geoOffset) = skin; *PLUGINOFFSET(Skin*, geometry, skinGlobals.geoOffset) = skin;
skin->init(numBones, numBones, numVertices); skin->init(numBones, numBones, numVertices);
skin->legacyType = 1;
skin->numWeights = 4; skin->numWeights = 4;
stream->read8(skin->indices, numVertices*4); stream->read8(skin->indices, numVertices*4);
@@ -307,6 +308,17 @@ skinRights(void *object, int32, int32, uint32)
Skin::setPipeline((Atomic*)object, 1); Skin::setPipeline((Atomic*)object, 1);
} }
static void
skinAlways(void *object, int32, int32)
{
Atomic *atomic = (Atomic*)object;
Geometry *geo = atomic->geometry;
if(geo == nil) return;
Skin *skin = Skin::get(geo);
if(skin == nil) return;
Skin::setPipeline((Atomic*)object, 1);
}
static void* static void*
createSkinAtm(void *object, int32 offset, int32) createSkinAtm(void *object, int32 offset, int32)
{ {
@@ -373,6 +385,7 @@ registerSkinPlugin(void)
skinGlobals.atomicOffset = o; skinGlobals.atomicOffset = o;
Atomic::registerPluginStream(ID_SKIN, readSkinLegacy, nil, nil); Atomic::registerPluginStream(ID_SKIN, readSkinLegacy, nil, nil);
Atomic::setStreamRightsCallback(ID_SKIN, skinRights); Atomic::setStreamRightsCallback(ID_SKIN, skinRights);
Atomic::setStreamAlwaysCallback(ID_SKIN, skinAlways);
} }
void void
@@ -417,6 +430,7 @@ Skin::init(int32 numBones, int32 numUsedBones, int32 numVertices)
this->rle = nil; this->rle = nil;
this->platformData = nil; this->platformData = nil;
this->legacyType = 0;
} }
+76
View File
@@ -3,6 +3,7 @@
#include <string.h> #include <string.h>
#include <assert.h> #include <assert.h>
#define WITH_D3D
#include "rwbase.h" #include "rwbase.h"
#include "rwerror.h" #include "rwerror.h"
#include "rwplg.h" #include "rwplg.h"
@@ -14,6 +15,7 @@
#include "d3d/rwxbox.h" #include "d3d/rwxbox.h"
#include "d3d/rwd3d8.h" #include "d3d/rwd3d8.h"
#include "d3d/rwd3d9.h" #include "d3d/rwd3d9.h"
#include "d3d/rwd3dimpl.h"
#include "gl/rwgl3.h" #include "gl/rwgl3.h"
#define PLUGIN_ID 0 #define PLUGIN_ID 0
@@ -517,4 +519,78 @@ Texture::streamGetSizeNative(void)
return 0; return 0;
} }
int32 anisotOffset;
static void*
createAnisot(void *object, int32 offset, int32)
{
*GETANISOTROPYEXT(object) = 1;
return object;
}
static void*
copyAnisot(void *dst, void *src, int32 offset, int32)
{
*GETANISOTROPYEXT(dst) = *GETANISOTROPYEXT(src);
return dst;
}
static Stream*
readAnisot(Stream *stream, int32, void *object, int32 offset, int32)
{
*GETANISOTROPYEXT(object) = stream->readI32();
return stream;
}
static Stream*
writeAnisot(Stream *stream, int32, void *object, int32 offset, int32)
{
stream->writeI32(*GETANISOTROPYEXT(object));
return stream;
}
static int32
getSizeAnisot(void *object, int32 offset, int32)
{
if(*GETANISOTROPYEXT(object) == 1)
return 0;
return sizeof(int32);
}
void
registerAnisotropyPlugin(void)
{
anisotOffset = Texture::registerPlugin(sizeof(int32), ID_ANISOT, createAnisot, nil, copyAnisot);
Texture::registerPluginStream(ID_ANISOT, readAnisot, writeAnisot, getSizeAnisot);
}
void
Texture::setMaxAnisotropy(int32 maxaniso)
{
if(anisotOffset > 0)
*GETANISOTROPYEXT(this) = maxaniso;
}
int32
Texture::getMaxAnisotropy(void)
{
if(anisotOffset > 0)
return *GETANISOTROPYEXT(this);
return 1;
}
int32
getMaxSupportedMaxAnisotropy(void)
{
#ifdef RW_D3D9
return d3d::d3d9Globals.caps.MaxAnisotropy;
#endif
#ifdef RW_GL3
return (int32)gl3::gl3Caps.maxAnisotropy;
#endif
return 1;
}
} }
+4 -7
View File
@@ -11,9 +11,6 @@
#include "rwobjects.h" #include "rwobjects.h"
#include "rwengine.h" #include "rwengine.h"
#include <vitasdk.h>
#include <vitaGL.h>
#define PLUGIN_ID 2 #define PLUGIN_ID 2
namespace rw { namespace rw {
@@ -612,7 +609,7 @@ printSmesh(&smesh);
md[i].numIndices = ms[i].numIndices; md[i].numIndices = ms[i].numIndices;
md[i].indices = indices; md[i].indices = indices;
indices += md[i].numIndices; indices += md[i].numIndices;
memcpy_neon(md[i].indices, ms[i].indices, md[i].numIndices*sizeof(uint16)); memcpy(md[i].indices, ms[i].indices, md[i].numIndices*sizeof(uint16));
rwFree(ms[i].indices); rwFree(ms[i].indices);
} }
rwFree(header); rwFree(header);
@@ -658,9 +655,9 @@ trace("%d %d %d\n", a, b, c);
for(k = 0; k < geo->numTriangles; k++){ for(k = 0; k < geo->numTriangles; k++){
t = &geo->triangles[k]; t = &geo->triangles[k];
if(seen[k] || t->matId != m) continue; if(seen[k] || t->matId != m) continue;
if(t->v[0] == a && t->v[1] == b && t->v[2] == c || if((t->v[0] == a && t->v[1] == b && t->v[2] == c) ||
t->v[1] == a && t->v[2] == b && t->v[0] == c || (t->v[1] == a && t->v[2] == b && t->v[0] == c) ||
t->v[2] == a && t->v[0] == b && t->v[1] == c){ (t->v[2] == a && t->v[0] == b && t->v[1] == c)){
seen[k] = 1; seen[k] = 1;
goto found; goto found;
} }
+3 -6
View File
@@ -11,9 +11,6 @@
#include "rwengine.h" #include "rwengine.h"
#include "rwuserdata.h" #include "rwuserdata.h"
#include <vitasdk.h>
#include <vitaGL.h>
#define PLUGIN_ID ID_USERDATA #define PLUGIN_ID ID_USERDATA
namespace rw { namespace rw {
@@ -93,11 +90,11 @@ copyUserData(void *dst, void *src, int32 offset, int32)
switch(srca->datatype){ switch(srca->datatype){
case USERDATAINT: case USERDATAINT:
dsta->data = (int32*)udMalloc(sizeof(int32)*dsta->numElements); dsta->data = (int32*)udMalloc(sizeof(int32)*dsta->numElements);
memcpy_neon(dsta->data, srca->data, sizeof(int32)*dsta->numElements); memcpy(dsta->data, srca->data, sizeof(int32)*dsta->numElements);
break; break;
case USERDATAFLOAT: case USERDATAFLOAT:
dsta->data = (float32*)udMalloc(sizeof(float32)*dsta->numElements); dsta->data = (float32*)udMalloc(sizeof(float32)*dsta->numElements);
memcpy_neon(dsta->data, srca->data, sizeof(float32)*dsta->numElements); memcpy(dsta->data, srca->data, sizeof(float32)*dsta->numElements);
break; break;
case USERDATASTRING: case USERDATASTRING:
dststrar = (char**)udMalloc(sizeof(char*)*dsta->numElements); dststrar = (char**)udMalloc(sizeof(char*)*dsta->numElements);
@@ -244,7 +241,7 @@ UserDataExtension::add(const char *name, int32 datatype, int32 numElements)
a = (UserDataArray*)udMalloc((this->numArrays+1)*sizeof(UserDataArray)); a = (UserDataArray*)udMalloc((this->numArrays+1)*sizeof(UserDataArray));
if(a == nil) if(a == nil)
return -1; return -1;
memcpy_neon(a, this->arrays, this->numArrays*sizeof(UserDataArray)); memcpy(a, this->arrays, this->numArrays*sizeof(UserDataArray));
rwFree(this->arrays); rwFree(this->arrays);
this->arrays = a; this->arrays = a;
i = this->numArrays++; i = this->numArrays++;
+1 -1
View File
@@ -19,7 +19,7 @@ int32 World::numAllocated = 0;
PluginList World::s_plglist(sizeof(World)); PluginList World::s_plglist(sizeof(World));
World* World*
World::create(void) World::create(BBox *bbox)
{ {
World *world = (World*)rwMalloc(s_plglist.size, MEMDUR_EVENT | ID_WORLD); World *world = (World*)rwMalloc(s_plglist.size, MEMDUR_EVENT | ID_WORLD);
if(world == nil){ if(world == nil){