Merge gles1 and master

# Conflicts:
#	TODO.md
#	group/bld.inf
#	group/common.mmh
#	src/skel/symbian/symbian.cpp
This commit is contained in:
Shinovon 2026-05-06 22:01:55 +05:00
commit 55aecc66f3
82 changed files with 4082 additions and 129 deletions

2
.gitignore vendored
View file

@ -2,6 +2,8 @@
.project
*.bat
*.sis
*.sisx
*.d
## Ignore Visual Studio temporary files, build results, and
## files generated by popular Visual Studio add-ons.

View file

@ -3,6 +3,7 @@ DEFAULT ARMV6
PRJ_MMPFILES
gnumakefile shaders.mk
gnumakefile Icons_scalable_dc.mk
librw.mmp
re3.mmp
//librw_gles2.mmp
//re3_gles2.mmp
librw_gles1.mmp
re3_gles1.mmp

View file

@ -1,16 +1,12 @@
SYSTEMINCLUDE /epoc32/include
SYSTEMINCLUDE /epoc32/include/stdapis/stlportv5
SYSTEMINCLUDE /epoc32/include/stdapis
SYSTEMINCLUDE /epoc32/include/mw
SYSTEMINCLUDE /epoc32/include/platform
SYSTEMINCLUDE /epoc32/include/platform/mw
SYSTEMINCLUDE /epoc32/include/gles
USERINCLUDE .
MACRO LIBRW
MACRO RW_GL3
MACRO RW_OPENGL // because carbide is too stupid
MACRO MASTER
DEBUGGABLE
@ -26,4 +22,13 @@ OPTION_REPLACE ARMCC -O2 -O3
ALWAYS_BUILD_AS_ARM
#endif
#ifdef SYMBIAN_3
SYSTEMINCLUDE /epoc32/include/stdapis/stlportv5
STDCPP
MACRO RW_GL3
#else
SYSTEMINCLUDE /epoc32/include/stdapis/stlport
SYSTEMINCLUDE /epoc32/include/stdapis/stlport/stl
MACRO RW_GLES1
MACRO S60V5
#endif

View file

@ -1,9 +1,7 @@
#include "common.mmh"
TARGET librw.lib
TARGETTYPE lib
USERINCLUDE ../vendor/librw
USERINCLUDE ../vendor/librw/src
@ -15,6 +13,8 @@ SOURCEPATH ../vendor/librw/src
SOURCE engine.cpp error.cpp frame.cpp geometry.cpp geoplg.cpp
SOURCEPATH ../vendor/librw/src/gl
SOURCE gl3.cpp gl3device.cpp gl3immed.cpp gl3matfx.cpp gl3pipe.cpp gl3raster.cpp gl3render.cpp gl3shader.cpp gl3skin.cpp wdgl.cpp
SOURCEPATH ../vendor/librw/src/gles1
SOURCE gl1.cpp gl1device.cpp gl1immed.cpp gl1matfx.cpp gl1pipe.cpp gl1raster.cpp gl1render.cpp gl1skin.cpp
SOURCEPATH ../vendor/librw/src
SOURCE hanim.cpp image.cpp light.cpp
SOURCEPATH ../vendor/librw/src/lodepng

4
group/librw_gles1.mmp Normal file
View file

@ -0,0 +1,4 @@
#undef SYMBIAN3
#define S60V3
TARGET librw_gles1.lib
#include "librw.mmh"

4
group/librw_gles2.mmp Normal file
View file

@ -0,0 +1,4 @@
#undef S60V3
#define SYMBIAN_3
TARGET librw_gles2.lib
#include "librw.mmh"

View file

@ -1,29 +1,22 @@
#include "common.mmh"
TARGET re3.exe
TARGETTYPE exe
UID 0 0xe0d67647
LIBRARY euser.lib
LIBRARY libstdcppv5.lib
LIBRARY libc.lib
LIBRARY libm.lib
LIBRARY libpthread.lib
LIBRARY libglesv2.lib
LIBRARY libegl.lib
LIBRARY apparc.lib
LIBRARY cone.lib
LIBRARY eikcore.lib
LIBRARY avkon.lib
LIBRARY ws32.lib
LIBRARY hal.lib
LIBRARY platformver.lib
EPOCSTACKSIZE 0x14000
EPOCHEAPSIZE 0x80000 0x4000000
STATICLIBRARY librw.lib
SYSTEMINCLUDE ../vendor/librw
SOURCEPATH .

9
group/re3_gles1.mmp Normal file
View file

@ -0,0 +1,9 @@
#undef SYMBIAN_3
#define S60V3
//TARGET re3_gles1.exe
TARGET re3.exe
LIBRARY libstdcpp.lib
LIBRARY libgles_cm.lib
STATICLIBRARY librw_gles1.lib
ARMFPU softvfp
#include "re3.mmh"

10
group/re3_gles2.mmp Normal file
View file

@ -0,0 +1,10 @@
#undef S60V3
#define SYMBIAN_3
TARGET re3_gles2.exe
LIBRARY libstdcppv5.lib
LIBRARY libglesv2.lib
LIBRARY libegl.lib
LIBRARY platformver.lib
STATICLIBRARY librw_gles2.lib
ARMFPU softvfp+vfpv2
#include "re3.mmh"

View file

@ -5,17 +5,16 @@ do_nothing :
MAKMAKE: do_nothing
BLD: do_nothing
BLD:
$(MAKE) -C ../vendor/librw/src/gl/shaders/ -f Makefile all
CLEAN:
rm ../vendor/librw/src/gl/shaders/*.inc
CLEAN: do_nothing
LIB: do_nothing
CLEANLIB: do_nothing
RESOURCE:
$(MAKE) -C ../vendor/librw/src/gl/shaders/ -f Makefile all
RESOURCE: do_nothing
FREEZE: do_nothing

View file

@ -0,0 +1 @@
OpenC version 1.5 or later is required for installation.

View file

@ -1,10 +1,21 @@
#{"GTA III"},(0xe0d67647),1,0,0
[0x101F7961], 0, 0, 0, {"S60ProductID"}
[0x1028315F], 0, 0, 0, {"S60ProductID"}
[0x20022E6D], 0, 0, 0, {"S60ProductID"}
%{"nnproject"}
:"nnproject"
;IF (NOT package(0x20009A80)) OR (NOT package(0x2002372A)) ; old or missing openc
; "incompatible_openc.txt"-"", FT, FORCEABORT
;ENDIF
;IF exists("z:\system\install\Series60v5.2.sis") AND exists("z:\sys\bin\libGLESv2.dll")
; "$(EPOCROOT)epoc32\release\$(PLATFORM)\$(TARGET)\re3_gles2.exe"-"!:\sys\bin\re3.exe"
;ELSE
; "$(EPOCROOT)epoc32\release\$(PLATFORM)\$(TARGET)\re3_gles1.exe"-"!:\sys\bin\re3.exe"
;ENDIF
"$(EPOCROOT)epoc32\release\$(PLATFORM)\$(TARGET)\re3.exe"-"!:\sys\bin\re3.exe"
"$(EPOCROOT)\epoc32\data\z\private\10003a3f\import\apps\re3_reg.rsc" - "!:\private\10003a3f\import\apps\re3_reg.rsc"
"$(EPOCROOT)\epoc32\data\z\resource\apps\re3.rsc" - "!:\resource\apps\re3.rsc"

View file

@ -84,7 +84,7 @@ public:
inline float GetTimeLeft() { return hierarchy->totalLength - currentTime; }
static CAnimBlendAssociation *FromLink(CAnimBlendLink *l) {
return (CAnimBlendAssociation*)((uint8*)l - offsetof(CAnimBlendAssociation, link));
return (CAnimBlendAssociation*)((uint8*)l - OFFSET_OF(CAnimBlendAssociation, link));
}
};

View file

@ -30,4 +30,4 @@ public:
void MoveMemory(bool onlyone = false);
};
VALIDATE_SIZE(CAnimBlendHierarchy, 0x28);
VALIDATE_SIZE(CAnimBlendHierarchy, 0x28);

View file

@ -207,4 +207,4 @@ enum AnimationId
ANIM_STD_PHONE_TALK,
ANIM_STD_NUM
};
};

View file

@ -670,4 +670,4 @@ static char StreamedNameTable[][25] =
"AUDIO\\k1_b.WAV",
"AUDIO\\cat1.WAV"
};
#endif
#endif

View file

@ -13,4 +13,4 @@ struct CColBox
CVector GetSize(void) { return max - min; }
CColBox& operator=(const CColBox &other);
};
};

View file

@ -11,4 +11,4 @@ struct CColLine
CColLine(void) { };
CColLine(const CVector &p0, const CVector &p1) { this->p0 = p0; this->p1 = p1; };
void Set(const CVector &p0, const CVector &p1);
};
};

View file

@ -34,4 +34,4 @@ struct CColModel
void GetTrianglePoint(CVector &v, int i) const;
CColModel& operator=(const CColModel& other);
};
};

View file

@ -10,4 +10,4 @@ struct CColSphere
uint8 surface;
uint8 piece;
void Set(float radius, const CVector &center, uint8 surf = SURFACE_DEFAULT, uint8 piece = 0);
};
};

View file

@ -65,4 +65,4 @@ struct CColTrianglePlane
void GetNormal(CVector &n) const { n = normal; }
float CalcPoint(const CVector &v) const { return DotProduct(normal, v) - dist; };
#endif
};
};

View file

@ -33,4 +33,4 @@ struct CompressedVector
CVector Get(void) const { return CVector(x, y, z); };
void Set(float x, float y, float z) { this->x = x; this->y = y; this->z = z; };
#endif
};
};

View file

@ -28,4 +28,4 @@ public:
bool WorkToDoForMedics();
};
extern CAccidentManager gAccidentManager;
extern CAccidentManager gAccidentManager;

View file

@ -43,7 +43,7 @@ void CControllerConfigManager::MakeControllerActionsBlank()
}
}
#ifdef RW_GL3
#if defined RW_GL3 || defined RW_GLES1
int MapIdToButtonId(int mapId) {
#ifdef __SYMBIAN32__
// TODO
@ -102,7 +102,7 @@ int32 CControllerConfigManager::GetJoyButtonJustDown()
if (m_NewState.rgbButtons[i] & 0x80 && !(m_OldState.rgbButtons[i] & 0x80))
return i + 1;
}
#elif defined RW_GL3
#elif defined RW_GL3 || defined RW_GLES1
if (m_NewState.isGamepad) {
for (int32 i = 0; i < MAX_BUTTONS; i++) {
if (m_NewState.mappedButtons[i] && !(m_OldState.mappedButtons[i]))
@ -2773,7 +2773,7 @@ void CControllerConfigManager::UpdateJoyButtonState(int32 padnumber)
else
m_aButtonStates[i] = false;
}
#elif defined RW_GL3
#elif defined RW_GL3 || defined RW_GLES1
if (m_NewState.isGamepad) {
for (int32 i = 0; i < MAX_BUTTONS; i++) {
#if !defined __SYMBIAN32__

View file

@ -103,7 +103,7 @@ class CControllerState;
#define ACTIONNAME_LENGTH 40
#ifdef RW_GL3
#if defined RW_GL3 || defined RW_GLES1
struct GlfwJoyState {
int8 id;
bool isGamepad;
@ -129,7 +129,7 @@ public:
};
bool m_bFirstCapture;
#if defined RW_GL3
#if defined RW_GL3 || defined RW_GLES1
GlfwJoyState m_OldState;
GlfwJoyState m_NewState;
#else
@ -219,8 +219,8 @@ public:
void ResetSettingOrder (e_ControllerAction action);
};
#ifndef RW_GL3
#if !defined RW_GL3 && !defined RW_GLES1
VALIDATE_SIZE(CControllerConfigManager, 0x143C);
#endif
extern CControllerConfigManager ControlsManager;
extern CControllerConfigManager ControlsManager;

View file

@ -62,4 +62,4 @@ public:
static void ReportCrimeForEvent(eEventType type, intptr, bool);
};
extern CEvent gaEvent[NUMEVENTS];
extern CEvent gaEvent[NUMEVENTS];

View file

@ -5138,7 +5138,7 @@ CMenuManager::ProcessButtonPresses(void)
ControlsManager.MakeControllerActionsBlank();
ControlsManager.InitDefaultControlConfiguration();
ControlsManager.InitDefaultControlConfigMouse(MousePointerStateHelper.GetMouseSetUp());
#if !defined RW_GL3
#if !defined RW_GL3 && !defined RW_GLES1
if (AllValidWinJoys.m_aJoys[JOYSTICK1].m_bInitialised) {
DIDEVCAPS devCaps;
devCaps.dwSize = sizeof(DIDEVCAPS);

View file

@ -1124,7 +1124,7 @@ CRadar::LoadTextures()
|| (x2 < 1 && y2 == 1)) // one pixel on each side of second to first/last line is transparent
pixels[x + y * 16] = 0;
else if((x2 == 2 && y2 >= 2)|| (y2 == 2 && x2 >= 2) )// colored square inside
#ifdef RW_GL3
#if defined RW_GL3 || defined RW_GLES1
pixels[x + y * 16] = WAYPOINT_R | (WAYPOINT_G << 8) | (WAYPOINT_B << 16) | (255 << 24);
#else
pixels[x + y * 16] = WAYPOINT_B | (WAYPOINT_G << 8) | (WAYPOINT_R << 16) | (255 << 24);

View file

@ -8,4 +8,4 @@ public:
bool IsInRange(CVector2D vec);
void DebugShowRange(float, int);
CVector2D GetRandomPointInRange();
};
};

View file

@ -354,7 +354,7 @@ __inline__ void TRACE(char *f, ...) { } // this is re3 only, and so the function
#else
#define debug(f, ...) re3_debug("[DBG]: " f, ## __VA_ARGS__)
#define Error(f, ...) re3_debug("[ERROR]: " f, ## __VA_ARGS__)
#ifndef MASTER
#if !defined MASTER || defined LOGS
#define TRACE(f, ...) re3_trace(__FILE__, __LINE__, __FUNCTION__, f, ## __VA_ARGS__)
#define USERERROR(f, ...) re3_usererror(f, ## __VA_ARGS__)
#else
@ -367,7 +367,7 @@ __inline__ void TRACE(char *f, ...) { } // this is re3 only, and so the function
#undef ASSERT
#endif
#ifndef MASTER
#if !defined MASTER || defined LOGS
#define assert(_Expression) (void)( (!!(_Expression)) || (re3_assert(#_Expression, __FILE__, __LINE__, __FUNCTION__), 0) )
#else
#define assert(_Expression) (_Expression)

View file

@ -1,5 +1,8 @@
#pragma once
#define LOGS
#define LOGS_RDEBUG
// disables (most) stuff that wasn't in original gta3.exe
#ifdef __MWERKS__
#define VANILLA_DEFINES

View file

@ -1140,6 +1140,8 @@ DisplayGameDebugText()
"D3D8 "
#elif defined RW_GL3
"OpenGL "
#elif defined RW_GLES1
"GLES1 "
#endif
#if defined AUDIO_OAL
"OAL "
@ -1633,7 +1635,7 @@ Idle(void *arg)
if((!FrontEndMenuManager.m_bMenuActive || FrontEndMenuManager.m_bRenderGameInMenu) &&
TheCamera.GetScreenFadeStatus() != FADE_2)
{
#if defined(GTA_PC) && !defined(RW_GL3) && defined(FIX_BUGS)
#if defined(GTA_PC) && !defined(RW_GL3) && !defined(RW_GLES1) && defined(FIX_BUGS)
// This is from SA, but it's nice for windowed mode
if (!FrontEndMenuManager.m_bRenderGameInMenu) {
RwV2d pos;

View file

@ -69,7 +69,7 @@ myrand(void)
{
#ifdef USE_PS2_RAND
// Use our own implementation of rand, stolen from PS2
myrand_seed = 0x5851F42D4C957F2D * myrand_seed + 1;
myrand_seed = 0x5851F42D4C957F2DULL * myrand_seed + 1;
return ((myrand_seed >> 32) & 0x7FFFFFFF);
#else
// or original codewarrior rand
@ -1105,12 +1105,12 @@ extern bool gbRenderWorld2;
#endif
#ifndef __MWERKS__
#ifndef MASTER
#if !defined MASTER || defined LOGS
const int re3_buffsize = 1024;
static char re3_buff[re3_buffsize];
#endif
#ifndef MASTER
#if !defined MASTER || defined LOGS
void re3_assert(const char *expr, const char *filename, unsigned int lineno, const char *func)
{
#ifdef _WIN32
@ -1166,9 +1166,13 @@ void re3_assert(const char *expr, const char *filename, unsigned int lineno, con
}
#endif
#ifdef LOGS_RDEBUG
extern "C" void RDebug_Printf(const char*, ...);
#endif
void re3_debug(const char *format, ...)
{
#ifndef MASTER
#if !defined MASTER || defined LOGS
va_list va;
va_start(va, format);
#ifdef _WIN32
@ -1179,11 +1183,15 @@ void re3_debug(const char *format, ...)
va_end(va);
printf("%s", re3_buff);
#ifdef LOGS_RDEBUG
RDebug_Printf("%s", re3_buff);
#else
CDebug::DebugAddText(re3_buff);
#endif
#endif
}
#ifndef MASTER
#if !defined MASTER || defined LOGS
void re3_trace(const char *filename, unsigned int lineno, const char *func, const char *format, ...)
{
char buff[re3_buffsize *2];
@ -1205,7 +1213,7 @@ void re3_trace(const char *filename, unsigned int lineno, const char *func, cons
}
#endif
#ifndef MASTER
#if !defined MASTER || defined LOGS
void re3_usererror(const char *format, ...)
{
va_list va;

View file

@ -201,4 +201,4 @@ inline DebugMenuEntry *DebugMenuAddVarBool8(const char *path, const char *name,
{
return DebugMenuAddVarBool8(path, name, (int8_t*)ptr, triggerFunc);
}
#endif
#endif

View file

@ -541,4 +541,4 @@ CCompressedMatrixNotAligned::DecompressIntoFullMatrix(CMatrix &other)
other.GetUp() = CrossProduct(other.GetRight(), other.GetForward());
other.GetPosition() = m_vecPos;
other.Reorthogonalise();
}
}

View file

@ -174,4 +174,4 @@ CQuaternion::Set(float f1, float f2, float f3)
y = ((s1 * c2) * c3) + ((s2 * c1) * s3);
z = ((s2 * c1) * c3) - ((s1 * c2) * s3);
w = ((c2 * c1) * c3) + ((s2 * s1) * s3);
}
}

View file

@ -14,4 +14,4 @@ CRect::CRect(float l, float t, float r, float b)
top = t;
right = r;
bottom = b;
}
}

View file

@ -126,4 +126,4 @@ class CMatrix;
CVector Multiply3x3(const CMatrix &mat, const CVector &vec);
CVector Multiply3x3(const CVector &vec, const CMatrix &mat);
CVector operator*(const CMatrix &mat, const CVector &vec);
CVector operator*(const CMatrix &mat, const CVector &vec);

View file

@ -80,7 +80,8 @@ void TransformPoints(CVuVector *out, int n, const CMatrix &mat, const RwV3d *in,
": : "r" (out) , "r" (n), "r" (&mat), "r" (in), "r" (stride): "memory");
#else
while(n--){
*out = mat * *in;
const RwV3d i = *in;
*out = mat * i;
in = (RwV3d*)((uint8*)in + stride);
out++;
}
@ -110,7 +111,8 @@ void TransformPoints(CVuVector *out, int n, const CMatrix &mat, const CVuVector
": : "r" (out) , "r" (n), "r" (&mat) ,"r" (in): "memory");
#else
while(n--){
*out = mat * *in;
const RwV3d i = *in;
*out = mat * i;
in++;
out++;
}

View file

@ -11,4 +11,4 @@ public:
public:
CMloModelInfo(void) : CClumpModelInfo(MITYPE_MLO) {}
void ConstructClump();
};
};

View file

@ -506,4 +506,4 @@ IsFence(int16 id)
{
return id == MI_FENCE ||
id == MI_FENCE2;
}
}

View file

@ -64,4 +64,4 @@ public:
};
#ifndef PED_SKIN
VALIDATE_SIZE(CPedModelInfo, 0x48);
#endif
#endif

View file

@ -10,4 +10,4 @@ public:
void Shutdown(void) {};
RwObject *CreateInstance(void) { return nil; }
void SetClump(RpClump*) {};
};
};

View file

@ -464,4 +464,4 @@ CPed::RunToReportCrime(eCrimeType crimeToReport)
m_phoneId = phoneId;
m_crimeToReportOnPhone = crimeToReport;
return true;
}
}

View file

@ -149,4 +149,4 @@ CPed::Say(uint16 audio)
m_queuedSound = audio;
}
}
}
}

View file

@ -307,4 +307,4 @@ CPed::DebugRenderClosePedText()
{
// TODO: mobile code
}
#endif
#endif

View file

@ -5,4 +5,4 @@ public:
static void FindZCoorForPed(CVector* pos);
static CEntity* IsPositionClearOfCars(Const CVector*);
static bool IsPositionClearForPed(CVector*);
};
};

View file

@ -170,4 +170,4 @@ public:
static ePedStats GetPedStatType(char *name);
};
VALIDATE_SIZE(CPedStats, 0x34);
VALIDATE_SIZE(CPedStats, 0x34);

View file

@ -24,4 +24,4 @@ public:
extern CConsole TheConsole;
void cprintf(char*, ...);
void cprintf(char*, ...);

View file

@ -60,4 +60,4 @@ void RestoreAlphaTest();
#else
#define SetAlphaTest(a) (0)
#define RestoreAlphaTest() (0)
#endif
#endif

View file

@ -93,36 +93,106 @@ static int clamp(int size, int targetSize)
return size;
}
static void downscaleTexture(RwTexture *texture)
{
RwRaster *oldRaster = RwTextureGetRaster(texture);
if (oldRaster == nil)
return;
void debugRaster(RwRaster *r){
if(!r){
debug("Raster NULL");
return;
}
extern bool moreVram;
int targetSize = moreVram ? 64 : 32;
int oldWidth = RwRasterGetWidth(oldRaster);
int oldHeight = RwRasterGetHeight(oldRaster);
if (oldWidth <= targetSize && oldHeight <= targetSize) return;
debug("Raster: %dx%d | depth: %d | format: 0x%X | stride: %d | platform: %d | pixels: %p",
r->width,
r->height,
r->depth,
r->format,
r->stride,
r->platform,
r->pixels);
}
int newWidth = clamp(oldWidth, targetSize);
int newHeight = clamp(oldHeight, targetSize);
if (newWidth == oldWidth && newHeight == oldHeight) return;
static void downscaleTexture(RwTexture *texture){
#ifdef RW_GLES1
if(texture == nil)
return;
RwImage *image = oldRaster->toImage();
if (image == nil) return;
RwRaster *oldRaster = RwTextureGetRaster(texture);
if(oldRaster == nil)
return;
RwImage *resized = resizeImage(image, newWidth, newHeight);
RwImageDestroy(image);
if (resized == nil) return;
int oldWidth = RwRasterGetWidth(oldRaster);
int oldHeight = RwRasterGetHeight(oldRaster);
RwRaster *newRaster = rw::Raster::createFromImage(resized);
RwImageDestroy(resized);
if (newRaster == nil) return;
// dividir a la mitad, mínimo 16x16
int newWidth = oldWidth > 16 ? oldWidth / 2 : oldWidth;
int newHeight = oldHeight > 16 ? oldHeight / 2 : oldHeight;
RwTextureSetRaster(texture, newRaster);
RwRasterDestroy(oldRaster);
// si ya es suficientemente chica, no hacer nada
if(newWidth == oldWidth && newHeight == oldHeight)
return;
// toImage() funciona porque el backingStore está populado
RwImage *image = oldRaster->toImage();
if(image == nil){
debug("downscaleTexture: toImage FAILED for %dx%d", oldWidth, oldHeight);
return;
}
RwImage *resized = resizeImage(image, newWidth, newHeight);
RwImageDestroy(image);
if(resized == nil){
debug("downscaleTexture: resizeImage FAILED");
return;
}
// crear nuevo raster en formato compatible con GLES1
int32 w, h, d, f;
rw::Raster::imageFindRasterFormat(resized, rw::Raster::TEXTURE, &w, &h, &d, &f);
RwRaster *newRaster = rw::Raster::create(w, h, d, f | rw::Raster::TEXTURE, rw::PLATFORM_GLES1);
if(newRaster == nil){
debug("downscaleTexture: raster create FAILED");
RwImageDestroy(resized);
return;
}
if(newRaster->setFromImage(resized) == nil){
debug("downscaleTexture: setFromImage FAILED");
RwRasterDestroy(newRaster);
RwImageDestroy(resized);
return;
}
RwImageDestroy(resized);
RwTextureSetRaster(texture, newRaster);
RwRasterDestroy(oldRaster);
#else
RwRaster *oldRaster = RwTextureGetRaster(texture);
if (oldRaster == nil)
return;
extern bool moreVram;
int targetSize = moreVram ? 64 : 32;
int oldWidth = RwRasterGetWidth(oldRaster);
int oldHeight = RwRasterGetHeight(oldRaster);
if (oldWidth <= targetSize && oldHeight <= targetSize) return;
int newWidth = clamp(oldWidth, targetSize);
int newHeight = clamp(oldHeight, targetSize);
if (newWidth == oldWidth && newHeight == oldHeight) return;
RwImage *image = oldRaster->toImage();
if (image == nil) return;
RwImage *resized = resizeImage(image, newWidth, newHeight);
RwImageDestroy(image);
if (resized == nil) return;
RwRaster *newRaster = rw::Raster::createFromImage(resized);
RwImageDestroy(resized);
if (newRaster == nil) return;
RwTextureSetRaster(texture, newRaster);
RwRasterDestroy(oldRaster);
#endif
}
#endif

View file

@ -70,4 +70,4 @@ ZeroSaveBuf(uint8 *&buf, uint32 length)
} while(0)
#else
#define CheckSaveHeader(buf, a, b, c, d, size) SkipSaveBuf(buf, 8);
#endif
#endif

View file

@ -56,7 +56,7 @@ int _caserename(const char *old_filename, const char *new_filename);
#define caserename _caserename
#endif
#ifdef RW_GL3
#if defined RW_GL3 || defined RW_GLES1
typedef struct
{
#ifndef __SYMBIAN32__

View file

@ -9,11 +9,19 @@
#include <eikstart.h>
#include <hal.h>
#include <pthread.h>
#include <gles2/gl2.h>
#ifdef RW_GL3
#include <EGL/egl.h>
#else
#include <GLES/egl.h>
#endif
#include <locale.h>
#include <versioninfo.h>
#include <aknwseventobserver.h>
#include <featdiscovery.h>
#include <aknutils.h>
#ifndef KFeatureIdQwertyInput
#include <featureinfo.h>
#endif
#include "common.h"
#include "rwcore.h"
@ -79,10 +87,12 @@ static psGlobalType PsGlobal;
static TBool foreground;
bool moreVram;
static bool spinning;
bool qwerty;
bool touch;
bool moreVram;
void _InputTranslateShiftKeyUpDown(RsKeyCodes *rs) {
}
@ -292,22 +302,40 @@ static int MapScanCode(TInt aScanCode, TInt aModifiers) {
return JOY_DPAD_RIGHT;
}
return JOY_DPAD_DOWN;
case 'z':
case 'Z':
case '1':
return JOY_B;
case 'x':
case 'X':
case '2':
return JOY_X;
case 'c':
case 'C':
case 'a':
case 'A':
case '4':
return JOY_A;
case 's':
case 'S':
case '3':
return JOY_Y;
case '5':
return JOY_L1;
case '6':
return JOY_R1;
case '7':
return JOY_L2;
case '8':
return JOY_R2;
case EStdKeyDevice0:
return JOY_BACK;
case EStdKeyDevice1:
case EStdKeySpace:
case ' ':
return JOY_START;
case EStdKeyEnter:
case EStdKeyNkpEnter:
case EStdKeyDevice3:
return JOY_Y;
}
return -1;
}
@ -414,39 +442,54 @@ public:
CreateWindowL();
iAppUi->SetOrientationL(CAknAppUiBase::EAppUiOrientationLandscape);
SetExtentToWholeScreen();
SetFocus(ETrue);
#ifdef RW_GL3
Window().EnableAdvancedPointers();
#endif
EnableDragEvents();
ActivateL();
#ifdef RW_GL3
// VC4 check
VersionInfo::TPlatformVersion platformVersion;
VersionInfo::GetVersion(platformVersion);
moreVram = platformVersion.iMajorVersion == 5 && platformVersion.iMinorVersion >= 4;
#endif
TSize size = Size();
RsGlobal.width = size.iWidth;
RsGlobal.height = size.iHeight;
EGLint attribs[] = {
EGL_BUFFER_SIZE, 16,
EGL_BUFFER_SIZE, 24,
EGL_DEPTH_SIZE, 16,
EGL_STENCIL_SIZE, 0,
EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
#ifdef RW_GL3
EGL_SAMPLES, 0,
EGL_COLOR_BUFFER_TYPE, EGL_RGB_BUFFER,
EGL_SURFACE_TYPE, EGL_WINDOW_BIT,
EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT,
#endif
EGL_NONE
};
eglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY);
eglInitialize(eglDisplay, NULL, NULL);
#ifdef RW_GL3
eglBindAPI(EGL_OPENGL_ES_API);
#endif
EGLint numConfigs;
eglChooseConfig(eglDisplay, attribs, &eglConfig, 1, &numConfigs);
#ifdef RW_GL3
EGLint contextAttribs[ 3 ] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE };
eglContext = eglCreateContext(eglDisplay, eglConfig, EGL_NO_CONTEXT, contextAttribs);
#else
eglContext = eglCreateContext(eglDisplay, eglConfig, EGL_NO_CONTEXT, NULL);
#endif
RWindow& window = Window();
eglSurface = eglCreateWindowSurface(eglDisplay, eglConfig, &window, NULL);
@ -458,6 +501,9 @@ public:
setlocale(LC_COLLATE, "C");
setlocale(LC_NUMERIC, "C");
touch = AknLayoutUtils::PenEnabled();
TRAP_IGNORE(qwerty = CFeatureDiscovery::IsFeatureSupportedL(KFeatureIdQwertyInput));
chdir("E:\\Data\\gta3\\");
gGameState = GS_START_UP;
FrontEndMenuManager.LoadSettings();
@ -471,7 +517,6 @@ public:
openParams.width = RsGlobal.width;
openParams.height = RsGlobal.height;
openParams.windowtitle = RsGlobal.appName;
ControlsManager.MakeControllerActionsBlank();
ControlsManager.InitDefaultControlConfiguration();
@ -523,9 +568,12 @@ public:
// CCoeControl::HandlePointerEventL(aPointerEvent);
// return;
// }
#ifdef RW_GL3
const TAdvancedPointerEvent* advpointer = aPointerEvent.AdvancedPointerEvent();
int i = advpointer != NULL ? advpointer->PointerNumber() : 0;
#else
int i = 0;
#endif
static int activeZone[10];
static int stickCenterX[10];

View file

@ -78,4 +78,4 @@ VALIDATE_SIZE(CBoat, 0x484);
extern float MAX_WAKE_LENGTH;
extern float MIN_WAKE_INTERVAL;
extern float WAKE_LIFETIME;
extern float WAKE_LIFETIME;

View file

@ -75,4 +75,4 @@ public:
};
VALIDATE_SIZE(CWeapon, 0x18);
void FireOneInstantHitRound(CVector *source, CVector *target, int32 damage);
void FireOneInstantHitRound(CVector *source, CVector *target, int32 damage);

View file

@ -49,4 +49,4 @@ public:
bool IsFlagSet(uint32 flag) const { return (m_Flags & flag) != 0; }
};
VALIDATE_SIZE(CWeaponInfo, 0x54);
VALIDATE_SIZE(CWeaponInfo, 0x54);

View file

@ -46,4 +46,4 @@ enum eWeaponState
WEAPONSTATE_RELOADING,
WEAPONSTATE_OUT_OF_AMMO,
WEAPONSTATE_MELEE_MADECONTACT
};
};

1
vendor/librw/rw.h vendored
View file

@ -25,3 +25,4 @@
#include "src/gl/rwgl3.h"
#include "src/gl/rwgl3shader.h"
#include "src/gl/rwgl3plg.h"
#include "src/gles1/rwgles1.h"

View file

@ -26,13 +26,15 @@ namespace rw {
int32 version = 0x36003;
int32 build = 0xFFFF;
#ifdef RW_PS2
#if defined RW_PS2
int32 platform = PLATFORM_PS2;
#elif RW_WDGL
#elif defined RW_WDGL
int32 platform = PLATFORM_WDGL;
#elif RW_GL3
#elif defined RW_GL3
int32 platform = PLATFORM_GL3;
#elif RW_D3D9
#elif defined RW_GLES1
int32 platform = PLATFORM_GLES1;
#elif defined RW_D3D9
int32 platform = PLATFORM_D3D9;
#else
int32 platform = PLATFORM_NULL;

View file

@ -12,6 +12,7 @@
#include "ps2/rwps2.h"
#include "d3d/rwd3d.h"
#include "gl/rwgl3.h"
#include "gles1/rwgles1.h"
#define PLUGIN_ID 1000 // TODO: find a better ID

View file

@ -554,7 +554,7 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
// We expect some attributes to always be there, use the constant buffer as fallback
if(!isPrelit){
dcl[i].stream = 2;
dcl[i].offset = offsetof(VertexConstantData, color);
dcl[i].offset = OFFSET_OF(VertexConstantData, color);
dcl[i].type = D3DDECLTYPE_D3DCOLOR;
dcl[i].method = D3DDECLMETHOD_DEFAULT;
dcl[i].usage = D3DDECLUSAGE_COLOR;
@ -563,7 +563,7 @@ defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
}
if(geo->numTexCoordSets == 0){
dcl[i].stream = 2;
dcl[i].offset = offsetof(VertexConstantData, texCoors[0]);
dcl[i].offset = OFFSET_OF(VertexConstantData, texCoors);
dcl[i].type = D3DDECLTYPE_FLOAT2;
dcl[i].method = D3DDECLMETHOD_DEFAULT;
dcl[i].usage = D3DDECLUSAGE_TEXCOORD;

View file

@ -17,6 +17,7 @@
#include "d3d/rwd3d9.h"
#include "gl/rwgl3.h"
#include "gl/rwwdgl.h"
#include "gles1/rwgles1.h"
#define PLUGIN_ID 0
@ -243,6 +244,9 @@ Engine::init(MemoryFunctions *memfuncs)
d3d9::registerPlatformPlugins();
wdgl::registerPlatformPlugins();
gl3::registerPlatformPlugins();
#ifdef RW_GLES1
gles1::registerPlatformPlugins();
#endif
Engine::state = Initialized;
return 1;
@ -264,11 +268,13 @@ Engine::open(EngineOpenParams *p)
// Initialize device
// Device and possibly OS specific!
#ifdef RW_PS2
#if defined RW_PS2
engine->device = ps2::renderdevice;
#elif RW_GL3
#elif defined RW_GL3
engine->device = gl3::renderdevice;
#elif RW_D3D9
#elif defined RW_GLES1
engine->device = gles1::renderdevice;
#elif defined RW_D3D9
engine->device = d3d::renderdevice;
#else
engine->device = null::renderdevice;

View file

@ -18,6 +18,7 @@
#include "d3d/rwd3d9.h"
#include "gl/rwwdgl.h"
#include "gl/rwgl3.h"
#include "gles1/rwgles1.h"
#define PLUGIN_ID 2
@ -251,6 +252,10 @@ destroyNativeData(void *object, int32 offset, int32 size)
return d3d9::destroyNativeData(object, offset, size);
if(geometry->instData->platform == PLATFORM_GL3)
return gl3::destroyNativeData(object, offset, size);
#ifdef RW_GLES1
if(geometry->instData->platform == PLATFORM_GLES1)
return gles1::destroyNativeData(object, offset, size);
#endif
return object;
}

View file

@ -1565,7 +1565,6 @@ openSymbian(EngineOpenParams *openparams)
{
glGlobals.winWidth = openparams->width;
glGlobals.winHeight = openparams->height;
glGlobals.winTitle = openparams->windowtitle;
glGlobals.modes = (DisplayMode*)rwMalloc(sizeof(DisplayMode), ID_DRIVER | MEMDUR_EVENT);
glGlobals.modes[0].width = openparams->width;

View file

@ -14,9 +14,13 @@
#include "rwwdgl.h"
#ifdef __SYMBIAN32__
#ifdef RW_GL3
#include <gles2/gl2.h>
#include <gles2/gl2ext.h>
#else
#include <gles/gl.h>
#endif
#else
#ifdef RW_OPENGL
#include "glad/glad.h"
#endif

54
vendor/librw/src/gles1/gl1.cpp vendored Normal file
View file

@ -0,0 +1,54 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "../rwbase.h"
#include "../rwerror.h"
#include "../rwplg.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#include "../rwengine.h"
#include "rwgles1.h"
#include "rwgles1impl.h"
#ifdef RW_GLES1
namespace rw {
namespace gles1 {
static void*
driverOpen(void* object, int32 offset, int32 size)
{
engine->driver[PLATFORM_GLES1]->defaultPipeline = makeDefaultPipeline();
engine->driver[PLATFORM_GLES1]->rasterNativeOffset = nativeRasterOffset;
engine->driver[PLATFORM_GLES1]->rasterCreate = rasterCreate;
engine->driver[PLATFORM_GLES1]->rasterLock = rasterLock;
engine->driver[PLATFORM_GLES1]->rasterUnlock = rasterUnlock;
engine->driver[PLATFORM_GLES1]->rasterNumLevels = rasterNumLevels;
engine->driver[PLATFORM_GLES1]->imageFindRasterFormat = imageFindRasterFormat;
engine->driver[PLATFORM_GLES1]->rasterFromImage = rasterFromImage;
engine->driver[PLATFORM_GLES1]->rasterToImage = rasterToImage;
return object;
}
static void*
driverClose(void* object, int32 offset, int32 size)
{
// stub: no hace nada
return object;
}
void
registerPlatformPlugins(void)
{
Driver::registerPlugin(PLATFORM_GLES1, 0, PLATFORM_GLES1,
driverOpen, driverClose);
registerNativeRaster();
}
}
}
#endif

1500
vendor/librw/src/gles1/gl1device.cpp vendored Normal file

File diff suppressed because it is too large Load diff

243
vendor/librw/src/gles1/gl1immed.cpp vendored Normal file
View file

@ -0,0 +1,243 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "../rwbase.h"
#include "../rwerror.h"
#include "../rwplg.h"
#include "../rwrender.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#include "../rwengine.h"
#ifdef RW_GLES1
#include "rwgles1.h"
#include "rwgles1impl.h"
namespace rw {
namespace gles1 {
uint32 im2DVbo, im2DIbo;
static int primTypeMap[] = {
GL_POINTS, // invalid
GL_LINES,
GL_LINE_STRIP,
GL_TRIANGLES,
GL_TRIANGLE_STRIP,
GL_TRIANGLE_FAN,
GL_POINTS
};
void
openIm2D(void)
{
glGenBuffers(1, &im2DIbo);
glGenBuffers(1, &im2DVbo);
}
void
closeIm2D(void)
{
glDeleteBuffers(1, &im2DIbo);
glDeleteBuffers(1, &im2DVbo);
}
static Im2DVertex tmpprimbuf[3];
void
im2DRenderLine(void *vertices, int32 numVertices, int32 vert1, int32 vert2)
{
Im2DVertex *verts = (Im2DVertex*)vertices;
tmpprimbuf[0] = verts[vert1];
tmpprimbuf[1] = verts[vert2];
im2DRenderPrimitive(PRIMTYPELINELIST, tmpprimbuf, 2);
}
void
im2DRenderTriangle(void *vertices, int32 numVertices, int32 vert1, int32 vert2, int32 vert3)
{
Im2DVertex *verts = (Im2DVertex*)vertices;
tmpprimbuf[0] = verts[vert1];
tmpprimbuf[1] = verts[vert2];
tmpprimbuf[2] = verts[vert3];
im2DRenderPrimitive(PRIMTYPETRILIST, tmpprimbuf, 3);
}
void
im2DRenderPrimitive(PrimitiveType primType, void *vertices, int32 numVertices)
{
Camera *cam;
cam = (Camera*)engine->currentCamera;
glBindBuffer(GL_ARRAY_BUFFER, im2DVbo);
glBufferData(GL_ARRAY_BUFFER, numVertices*sizeof(Im2DVertex), vertices, GL_DYNAMIC_DRAW);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, sizeof(Im2DVertex), (void*)0);
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_UNSIGNED_BYTE, sizeof(Im2DVertex), (void*)OFFSET_OF(Im2DVertex, r));
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glTexCoordPointer(2, GL_FLOAT, sizeof(Im2DVertex), (void*)OFFSET_OF(Im2DVertex, u));
glMatrixMode(GL_PROJECTION);
glPushMatrix();
glLoadIdentity();
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
glLoadIdentity();
glOrthof(0.0f, (float)cam->frameBuffer->width, (float)cam->frameBuffer->height, 0.0f, -1000.0f, 1000.0f);
flushCache();
glDrawArrays(primTypeMap[primType], 0, numVertices);
glMatrixMode(GL_PROJECTION);
glPopMatrix();
glMatrixMode(GL_MODELVIEW);
glPopMatrix();
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
void im2DRenderIndexedPrimitive(PrimitiveType primType,
void *vertices, int32 numVertices,
void *indices, int32 numIndices)
{
Camera *cam;
cam = (Camera*)engine->currentCamera;
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im2DIbo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, numIndices*2, indices, GL_DYNAMIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, im2DVbo);
glBufferData(GL_ARRAY_BUFFER, numVertices*sizeof(Im2DVertex), vertices, GL_DYNAMIC_DRAW);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, sizeof(Im2DVertex), (void*)0);
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_UNSIGNED_BYTE, sizeof(Im2DVertex), (void*)OFFSET_OF(Im2DVertex, r));
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glTexCoordPointer(2, GL_FLOAT, sizeof(Im2DVertex), (void*)OFFSET_OF(Im2DVertex, u));
glMatrixMode(GL_PROJECTION);
glPushMatrix();
glLoadIdentity();
glOrthof(0.0f, (float)cam->frameBuffer->width, (float)cam->frameBuffer->height, 0.0f, -1000.0f, 1000.0f);
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
glLoadIdentity();
flushCache();
glDrawElements(primTypeMap[primType], numIndices, GL_UNSIGNED_SHORT, nil);
glMatrixMode(GL_PROJECTION);
glPopMatrix();
glMatrixMode(GL_MODELVIEW);
glPopMatrix();
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
// Im3D
static AttribDesc im3dattribDesc[3] = {
{ ATTRIB_POS, GL_FLOAT, GL_FALSE, 3,
sizeof(Im3DVertex), 0 },
{ ATTRIB_COLOR, GL_UNSIGNED_BYTE, GL_TRUE, 4,
sizeof(Im3DVertex), OFFSET_OF(Im3DVertex, r) },
{ ATTRIB_TEXCOORDS0, GL_FLOAT, GL_FALSE, 2,
sizeof(Im3DVertex), OFFSET_OF(Im3DVertex, u) },
};
static uint32 im3DVbo, im3DIbo;
static int32 num3DVertices; // not actually needed here
static void* currentIm3dVertices;
void
openIm3D(void)
{
glGenBuffers(1, &im3DIbo);
glGenBuffers(1, &im3DVbo);
}
void
closeIm3D(void)
{
glDeleteBuffers(1, &im3DIbo);
glDeleteBuffers(1, &im3DVbo);
}
void
im3DTransform(void *vertices, int32 numVertices, Matrix *world, uint32 flags)
{
if(world == nil){
static Matrix ident;
ident.setIdentity();
world = &ident;
}
setWorldMatrix(world);
if((flags & im3d::VERTEXUV) == 0)
SetRenderStatePtr(TEXTURERASTER, nil);
glBindBuffer(GL_ARRAY_BUFFER, im3DVbo);
glBufferData(GL_ARRAY_BUFFER, numVertices*sizeof(Im3DVertex), vertices, GL_DYNAMIC_DRAW);
num3DVertices = numVertices;
}
void
im3DRenderPrimitive(PrimitiveType primType)
{
glBindBuffer(GL_ARRAY_BUFFER, im3DVbo);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, sizeof(Im3DVertex), (void*)0);
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_UNSIGNED_BYTE, sizeof(Im3DVertex), (void*)OFFSET_OF(Im3DVertex, r));
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glTexCoordPointer(2, GL_FLOAT, sizeof(Im3DVertex), (void*)OFFSET_OF(Im3DVertex, u));
flushCache();
glDrawArrays(primTypeMap[primType], 0, num3DVertices);
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
void
im3DRenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices)
{
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, im3DIbo);
glBufferData(GL_ELEMENT_ARRAY_BUFFER, numIndices*2, indices, GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER, im3DVbo);
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(3, GL_FLOAT, sizeof(Im3DVertex), (void*)0);
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(4, GL_UNSIGNED_BYTE, sizeof(Im3DVertex), (void*)OFFSET_OF(Im3DVertex, r));
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glTexCoordPointer(2, GL_FLOAT, sizeof(Im3DVertex), (void*)OFFSET_OF(Im3DVertex, u));
flushCache();
glDrawElements(primTypeMap[primType], numIndices, GL_UNSIGNED_SHORT, nil);
glDisableClientState(GL_VERTEX_ARRAY);
glDisableClientState(GL_COLOR_ARRAY);
glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
void
im3DEnd(void)
{
}
}
}
#endif

86
vendor/librw/src/gles1/gl1matfx.cpp vendored Normal file
View file

@ -0,0 +1,86 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "../rwbase.h"
#include "../rwplg.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#include "../rwengine.h"
#include "../rwrender.h"
#include "../rwanim.h"
#include "../rwplugins.h"
#include "rwgles1.h"
#include "rwgles1plg.h"
#include "rwgles1impl.h"
#ifdef RW_GLES1
namespace rw {
namespace gles1 {
void
matfxRenderCB(Atomic *atomic, InstanceDataHeader *header)
{
uint32 flags = atomic->geometry->flags;
setWorldMatrix(atomic->getFrame()->getLTM());
glDisable(GL_LIGHTING);
setupVertexInput(header);
InstanceData *inst = header->inst;
int32 n = header->numMeshes;
while(n--){
MatFX *matfx = MatFX::get(inst->material);
Material *m = inst->material;
// En GLES1 sin shaders: ignoramos env map, solo dibujamos textura base
setMaterial(flags, m->color, m->surfaceProps);
setTexture(0, m->texture);
rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
drawInst(header, inst);
inst++;
}
teardownVertexInput(header);
}
ObjPipeline*
makeMatFXPipeline(void)
{
ObjPipeline *pipe = ObjPipeline::create();
pipe->instanceCB = defaultInstanceCB;
pipe->uninstanceCB = defaultUninstanceCB;
pipe->renderCB = matfxRenderCB;
pipe->pluginID = ID_MATFX;
pipe->pluginData = 0;
return pipe;
}
static void*
matfxOpen(void *o, int32, int32)
{
matFXGlobals.pipelines[PLATFORM_GLES1] = makeMatFXPipeline();
return o;
}
static void*
matfxClose(void *o, int32, int32)
{
((ObjPipeline*)matFXGlobals.pipelines[PLATFORM_GLES1])->destroy();
matFXGlobals.pipelines[PLATFORM_GLES1] = nil;
return o;
}
void
initMatFX(void)
{
Driver::registerPlugin(PLATFORM_GLES1, 0, ID_MATFX, matfxOpen, matfxClose);
}
}
}
#endif

319
vendor/librw/src/gles1/gl1pipe.cpp vendored Normal file
View file

@ -0,0 +1,319 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "../rwbase.h"
#include "../rwerror.h"
#include "../rwplg.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#include "../rwengine.h"
#include "rwgles1.h"
namespace rw {
namespace gles1 {
// TODO: make some of these things platform-independent
#ifdef RW_GLES1
void
freeInstanceData(Geometry *geometry)
{
if(geometry->instData == nil ||
geometry->instData->platform != PLATFORM_GLES1)
return;
InstanceDataHeader *header = (InstanceDataHeader*)geometry->instData;
geometry->instData = nil;
glDeleteBuffers(1, &header->ibo);
glDeleteBuffers(1, &header->vbo);
rwFree(header->indexBuffer);
rwFree(header->vertexBuffer);
rwFree(header->attribDesc);
rwFree(header->inst);
rwFree(header);
}
void*
destroyNativeData(void *object, int32, int32)
{
freeInstanceData((Geometry*)object);
return object;
}
static InstanceDataHeader*
instanceMesh(rw::ObjPipeline *rwpipe, Geometry *geo)
{
InstanceDataHeader *header = rwNewT(InstanceDataHeader, 1, MEMDUR_EVENT | ID_GEOMETRY);
MeshHeader *meshh = geo->meshHeader;
geo->instData = header;
header->platform = PLATFORM_GLES1;
header->serialNumber = meshh->serialNum;
header->numMeshes = meshh->numMeshes;
header->primType = meshh->flags == 1 ? GL_TRIANGLE_STRIP : GL_TRIANGLES;
header->totalNumVertex = geo->numVertices;
header->totalNumIndex = meshh->totalIndices;
header->inst = rwNewT(InstanceData, header->numMeshes, MEMDUR_EVENT | ID_GEOMETRY);
header->indexBuffer = rwNewT(uint16, header->totalNumIndex, MEMDUR_EVENT | ID_GEOMETRY);
InstanceData *inst = header->inst;
Mesh *mesh = meshh->getMeshes();
uint32 offset = 0;
for(uint32 i = 0; i < header->numMeshes; i++){
findMinVertAndNumVertices(mesh->indices, mesh->numIndices,
&inst->minVert, &inst->numVertices);
assert(inst->minVert != 0xFFFFFFFF);
inst->numIndex = mesh->numIndices;
inst->material = mesh->material;
inst->vertexAlpha = 0;
inst->program = 0;
inst->offset = offset;
memcpy((uint8*)header->indexBuffer + inst->offset,
mesh->indices, inst->numIndex*2);
offset += inst->numIndex*2;
mesh++;
inst++;
}
header->vertexBuffer = nil;
header->numAttribs = 0;
header->attribDesc = nil;
header->ibo = 0;
header->vbo = 0;
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;
}
static void
instance(rw::ObjPipeline *rwpipe, Atomic *atomic)
{
ObjPipeline *pipe = (ObjPipeline*)rwpipe;
Geometry *geo = atomic->geometry;
// don't try to (re)instance native data
if(geo->flags & Geometry::NATIVE)
return;
InstanceDataHeader *header = (InstanceDataHeader*)geo->instData;
if(geo->instData){
// Already have instanced data, so check if we have to reinstance
assert(header->platform == PLATFORM_GLES1);
if(header->serialNumber != geo->meshHeader->serialNum){
// Mesh changed, so reinstance everything
freeInstanceData(geo);
}
}
// no instance or complete reinstance
if(geo->instData == nil){
geo->instData = instanceMesh(rwpipe, geo);
pipe->instanceCB(geo, (InstanceDataHeader*)geo->instData, 0);
}else if(geo->lockedSinceInst)
pipe->instanceCB(geo, (InstanceDataHeader*)geo->instData, 1);
geo->lockedSinceInst = 0;
}
static void
uninstance(rw::ObjPipeline *rwpipe, Atomic *atomic)
{
assert(0 && "can't uninstance");
}
static void render(rw::ObjPipeline *rwpipe, Atomic *atomic){
ObjPipeline *pipe = (ObjPipeline*)rwpipe;
Geometry *geo = atomic->geometry;
pipe->instance(atomic);
assert(geo->instData != nil);
assert(geo->instData->platform == PLATFORM_GLES1);
if(pipe->renderCB)
pipe->renderCB(atomic, (InstanceDataHeader*)geo->instData);
else {
FILE *f = fopen("E:\\re3_debug.txt", "a");
if(f){ fprintf(f, "render: renderCB is nil!\n"); fclose(f); }
}
}
void
ObjPipeline::init(void)
{
this->rw::ObjPipeline::init(PLATFORM_GLES1);
this->impl.instance = gles1::instance;
this->impl.uninstance = gles1::uninstance;
this->impl.render = gles1::render;
this->instanceCB = nil;
this->uninstanceCB = nil;
this->renderCB = nil;
}
ObjPipeline*
ObjPipeline::create(void)
{
ObjPipeline *pipe = rwNewT(ObjPipeline, 1, MEMDUR_GLOBAL);
pipe->init();
return pipe;
}
void
defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
{
AttribDesc *attribs, *a;
bool isPrelit = !!(geo->flags & Geometry::PRELIT);
bool hasNormals = !!(geo->flags & Geometry::NORMALS);
if(!reinstance){
AttribDesc tmpAttribs[12];
uint32 stride;
//
// Create attribute descriptions
//
a = tmpAttribs;
stride = 0;
// Positions
a->index = ATTRIB_POS;
a->size = 3;
a->type = GL_FLOAT;
a->normalized = GL_FALSE;
a->offset = stride;
stride += 12;
a++;
// Normals
// TODO: compress
if(hasNormals){
a->index = ATTRIB_NORMAL;
a->size = 3;
a->type = GL_FLOAT;
a->normalized = GL_FALSE;
a->offset = stride;
stride += 12;
a++;
}
// Prelighting
if(isPrelit){
a->index = ATTRIB_COLOR;
a->size = 4;
a->type = GL_UNSIGNED_BYTE;
a->normalized = GL_TRUE;
a->offset = stride;
stride += 4;
a++;
}
// Texture coordinates
for(int32 n = 0; n < geo->numTexCoordSets; n++){
a->index = ATTRIB_TEXCOORDS0+n;
a->size = 2;
a->type = GL_FLOAT;
a->normalized = GL_FALSE;
a->offset = stride;
stride += 8;
a++;
}
header->numAttribs = a - tmpAttribs;
for(a = tmpAttribs; a != &tmpAttribs[header->numAttribs]; a++)
a->stride = stride;
header->attribDesc = rwNewT(AttribDesc, header->numAttribs, MEMDUR_EVENT | ID_GEOMETRY);
memcpy(header->attribDesc, tmpAttribs,
header->numAttribs*sizeof(AttribDesc));
//
// Allocate vertex buffer
//
header->vertexBuffer = rwNewT(uint8, header->totalNumVertex*stride, MEMDUR_EVENT | ID_GEOMETRY);
assert(header->vbo == 0);
glGenBuffers(1, &header->vbo);
}
attribs = header->attribDesc;
//
// Fill vertex buffer
//
uint8 *verts = header->vertexBuffer;
// Positions
if(!reinstance || geo->lockedSinceInst&Geometry::LOCKVERTICES){
for(a = attribs; a->index != ATTRIB_POS; a++)
;
instV3d(VERT_FLOAT3, verts + a->offset,
geo->morphTargets[0].vertices,
header->totalNumVertex, a->stride);
}
// Normals
if(hasNormals && (!reinstance || geo->lockedSinceInst&Geometry::LOCKNORMALS)){
for(a = attribs; a->index != ATTRIB_NORMAL; a++)
;
instV3d(VERT_FLOAT3, verts + a->offset,
geo->morphTargets[0].normals,
header->totalNumVertex, a->stride);
}
// Prelighting
if(isPrelit && (!reinstance || geo->lockedSinceInst&Geometry::LOCKPRELIGHT)){
for(a = attribs; a->index != ATTRIB_COLOR; a++)
;
int n = header->numMeshes;
InstanceData *inst = header->inst;
while(n--){
assert(inst->minVert != 0xFFFFFFFF);
inst->vertexAlpha = instColor(VERT_RGBA,
verts + a->offset + a->stride*inst->minVert,
geo->colors + inst->minVert,
inst->numVertices, a->stride);
inst++;
}
}
// Texture coordinates
for(int32 n = 0; n < geo->numTexCoordSets; n++){
if(!reinstance || geo->lockedSinceInst&(Geometry::LOCKTEXCOORDS<<n)){
for(a = attribs; a->index != ATTRIB_TEXCOORDS0+n; a++)
;
instTexCoords(VERT_FLOAT2, verts + a->offset,
geo->texCoords[n],
header->totalNumVertex, a->stride);
}
}
glBindBuffer(GL_ARRAY_BUFFER, header->vbo);
glBufferData(GL_ARRAY_BUFFER, header->totalNumVertex*attribs[0].stride,
header->vertexBuffer, GL_STATIC_DRAW);
}
void
defaultUninstanceCB(Geometry *geo, InstanceDataHeader *header)
{
assert(0 && "can't uninstance");
}
ObjPipeline*
makeDefaultPipeline(void)
{
ObjPipeline *pipe = ObjPipeline::create();
pipe->instanceCB = defaultInstanceCB;
pipe->uninstanceCB = defaultUninstanceCB;
pipe->renderCB = defaultRenderCB;
return pipe;
}
#else
void *destroyNativeData(void *object, int32, int32) { return object; }
#endif
}
}

934
vendor/librw/src/gles1/gl1raster.cpp vendored Normal file
View file

@ -0,0 +1,934 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "../rwbase.h"
#include "../rwerror.h"
#include "../rwplg.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#include "../rwengine.h"
#include "rwgles1.h"
#include "rwgles1impl.h"
#define PLUGIN_ID ID_DRIVER
namespace rw {
namespace gles1 {
int32 nativeRasterOffset;
static uint32
getLevelSize(Raster *raster, int32 level)
{
int i;
Gl1Raster *natras = GETGL1RASTEREXT(raster);
int w = raster->originalWidth;
int h = raster->originalHeight;
int s = raster->originalStride;
int minDim = 1;
//#ifdef RW_GLES1
// switch(natras->internalFormat){
// case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
// case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
// case GL_COMPRESSED_RGBA_S3TC_DXT3_EXT:
// case GL_COMPRESSED_RGBA_S3TC_DXT5_EXT:
// minDim = 4;
// break;
// }
//#endif
for(i = 0; i < level; i++){
if(w > minDim){
w /= 2;
s /= 2;
}
if(h > minDim)
h /= 2;
}
return s*h;
}
#ifdef RW_GLES1
static Raster*
rasterCreateTexture(Raster *raster)
{
if(raster->format & (Raster::PAL4 | Raster::PAL8)){
RWERROR((ERR_NOTEXTURE));
return nil;
}
Gl1Raster *natras = GETGL1RASTEREXT(raster);
switch(raster->format & 0xF00){
case Raster::C8888:
natras->internalFormat = GL_RGBA;
natras->format = GL_RGBA;
natras->type = GL_UNSIGNED_BYTE;
natras->hasAlpha = 1;
natras->bpp = 4;
raster->depth = 32;
break;
case Raster::C888:
natras->internalFormat = GL_RGB;
natras->format = GL_RGB;
natras->type = GL_UNSIGNED_BYTE;
natras->hasAlpha = 0;
natras->bpp = 3;
raster->depth = 24;
break;
case Raster::C565:
natras->internalFormat = GL_RGB;
natras->format = GL_RGB;
natras->type = GL_UNSIGNED_SHORT_5_6_5;
natras->hasAlpha = 0;
natras->bpp = 2;
raster->depth = 16;
break;
case Raster::C4444:
natras->internalFormat = GL_RGBA;
natras->format = GL_RGBA;
natras->type = GL_UNSIGNED_SHORT_4_4_4_4;
natras->hasAlpha = 1;
natras->bpp = 2;
raster->depth = 16;
break;
case Raster::C1555:
// natras->internalFormat = GL_RGB5_A1;
natras->internalFormat = GL_RGBA;
natras->format = GL_RGBA;
natras->type = GL_UNSIGNED_SHORT_5_5_5_1;
natras->hasAlpha = 1;
natras->bpp = 2;
raster->depth = 16;
break;
default:
RWERROR((ERR_INVRASTER));
return nil;
}
natras->internalFormat = natras->format;
raster->stride = raster->width*natras->bpp;
if(raster->format & Raster::MIPMAP){
int w = raster->width;
int h = raster->height;
natras->numLevels = 1;
while(w != 1 || h != 1){
natras->numLevels++;
if(w > 1) w /= 2;
if(h > 1) h /= 2;
}
}
natras->autogenMipmap = (raster->format & (Raster::MIPMAP|Raster::AUTOMIPMAP)) == (Raster::MIPMAP|Raster::AUTOMIPMAP);
if(natras->autogenMipmap)
natras->numLevels = 1;
glGenTextures(1, &natras->texid);
uint32 prev = bindTexture(natras->texid);
// glTexImage2D(GL_TEXTURE_2D, 0, natras->internalFormat,
//// raster->width, raster->height,
// 1,1,
// 0, natras->format, natras->type, nil);
// TODO: allocate other levels...probably
natras->filterMode = 0;
natras->addressU = 0;
natras->addressV = 0;
natras->maxAnisotropy = 1;
bindTexture(prev);
return raster;
}
static Raster*
rasterCreateCameraTexture(Raster *raster)
{
if(raster->format & (Raster::PAL4 | Raster::PAL8)){
RWERROR((ERR_NOTEXTURE));
return nil;
}
// TODO: figure out what the backbuffer is and use that as a default
Gl1Raster *natras = GETGL1RASTEREXT(raster);
switch(raster->format & 0xF00){
case Raster::C8888:
natras->internalFormat = GL_RGBA;
natras->format = GL_RGBA;
natras->type = GL_UNSIGNED_BYTE;
natras->hasAlpha = 1;
natras->bpp = 4;
break;
case Raster::C4444:
natras->internalFormat = GL_RGBA;
natras->format = GL_RGBA;
natras->type = GL_UNSIGNED_SHORT_4_4_4_4;
natras->hasAlpha = 1;
natras->bpp = 2;
break;
case Raster::C888:
default:
natras->internalFormat = GL_RGB;
natras->format = GL_RGB;
natras->type = GL_UNSIGNED_BYTE;
natras->hasAlpha = 0;
natras->bpp = 3;
break;
case Raster::C565:
natras->internalFormat = GL_RGB;
natras->format = GL_RGB;
natras->type = GL_UNSIGNED_SHORT_5_6_5;
natras->hasAlpha = 0;
natras->bpp = 2;
break;
case Raster::C1555:
// natras->internalFormat = GL_RGB5_A1;
natras->internalFormat = GL_RGBA;
natras->format = GL_RGBA;
natras->type = GL_UNSIGNED_SHORT_5_5_5_1;
natras->hasAlpha = 1;
natras->bpp = 2;
break;
}
natras->internalFormat = natras->format;
raster->stride = raster->width*natras->bpp;
natras->autogenMipmap = (raster->format & (Raster::MIPMAP|Raster::AUTOMIPMAP)) == (Raster::MIPMAP|Raster::AUTOMIPMAP);
glGenTextures(1, &natras->texid);
uint32 prev = bindTexture(natras->texid);
glTexImage2D(GL_TEXTURE_2D, 0, natras->internalFormat,
// raster->width, raster->height,
1,1,
0, natras->format, natras->type, nil);
natras->filterMode = 0;
natras->addressU = 0;
natras->addressV = 0;
natras->maxAnisotropy = 1;
bindTexture(prev);
// glGenFramebuffers(1, &natras->fbo);
// bindFramebuffer(natras->fbo);
// glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, natras->texid, 0);
// bindFramebuffer(0);
natras->fboMate = nil;
return raster;
}
static Raster*
rasterCreateCamera(Raster *raster)
{
Gl1Raster *natras = GETGL1RASTEREXT(raster);
// TODO: set/check width, height, depth, format?
// used for locking right now
// raster->format = Raster::C888;
// natras->internalFormat = GL_RGB;
// natras->format = GL_RGB;
// natras->type = GL_UNSIGNED_BYTE;
// natras->hasAlpha = 0;
// natras->bpp = 3;
//
// natras->autogenMipmap = 0;
raster->originalWidth = raster->width;
raster->originalHeight = raster->height;
raster->stride = 0;
raster->pixels = nil;
natras->texid = 0;
natras->fbo = 0;
natras->fboMate = nil;
return raster;
}
static Raster*
rasterCreateZbuffer(Raster *raster)
{
Gl1Raster *natras = GETGL1RASTEREXT(raster);
raster->originalWidth = raster->width;
raster->originalHeight = raster->height;
raster->stride = 0;
raster->pixels = nil;
return raster;
}
#endif
/*
{ 0, 0, 0 },
{ 16, 4, GL_RGBA }, // 1555
{ 16, 3, GL_RGB }, // 565
{ 16, 4, GL_RGBA }, // 4444
{ 0, 0, 0 }, // LUM8
{ 32, 4, GL_RGBA }, // 8888
{ 24, 3, GL_RGB }, // 888
{ 16, 3, GL_RGB }, // D16
{ 24, 3, GL_RGB }, // D24
{ 32, 4, GL_RGBA }, // D32
{ 16, 3, GL_RGB }, // 555
0,
GL_RGB5_A1,
GL_RGB5,
GL_RGBA4,
0,
GL_RGBA8,
GL_RGB8,
GL_RGB5,
GL_RGB8,
GL_RGBA8,
GL_RGB5
*/
Raster*
rasterCreate(Raster *raster)
{
Gl1Raster *natras = GETGL1RASTEREXT(raster);
natras->isCompressed = 0;
natras->hasAlpha = 0;
natras->numLevels = 1;
Raster *ret = raster;
if(raster->width == 0 || raster->height == 0){
raster->flags |= Raster::DONTALLOCATE;
raster->stride = 0;
goto ret;
}
if(raster->flags & Raster::DONTALLOCATE)
goto ret;
switch(raster->type){
#ifdef RW_GLES1
case Raster::NORMAL:
case Raster::TEXTURE:
ret = rasterCreateTexture(raster);
break;
case Raster::CAMERATEXTURE:
ret = rasterCreateCameraTexture(raster);
break;
case Raster::ZBUFFER:
ret = rasterCreateZbuffer(raster);
break;
case Raster::CAMERA:
ret = rasterCreateCamera(raster);
break;
#endif
default:
RWERROR((ERR_INVRASTER));
return nil;
}
ret:
raster->originalWidth = raster->width;
raster->originalHeight = raster->height;
raster->originalStride = raster->stride;
raster->originalPixels = raster->pixels;
return ret;
}
uint8*
rasterLock(Raster *raster, int32 level, int32 lockMode)
{
#ifdef RW_GLES1
Gl1Raster *natras = GETGL1RASTEREXT(raster);
uint8 *px;
uint32 allocSz;
int i;
assert(raster->privateFlags == 0);
switch(raster->type){
case Raster::NORMAL:
case Raster::TEXTURE:
case Raster::CAMERATEXTURE:
for(i = 0; i < level; i++){
if(raster->width > 1){
raster->width /= 2;
raster->stride /= 2;
}
if(raster->height > 1)
raster->height /= 2;
}
allocSz = getLevelSize(raster, level);
px = (uint8*)rwMalloc(allocSz, MEMDUR_EVENT | ID_DRIVER);
assert(raster->pixels == nil);
raster->pixels = px;
if(lockMode & Raster::LOCKREAD || !(lockMode & Raster::LOCKNOFETCH)){
if(natras->backingStore){
assert(level < natras->backingStore->numlevels);
assert(allocSz >= natras->backingStore->levels[level].size);
memcpy(px, natras->backingStore->levels[level].data, allocSz);
} else {
memset(px, 0, allocSz);
}
}
raster->privateFlags = lockMode;
break;
case Raster::CAMERA:
if(lockMode & Raster::PRIVATELOCK_WRITE)
assert(0 && "can't lock framebuffer for writing");
raster->width = glGlobals.presentWidth;
raster->height = glGlobals.presentHeight;
raster->stride = raster->width*natras->bpp;
assert(natras->bpp == 3);
allocSz = raster->height*raster->stride;
px = (uint8*)rwMalloc(allocSz, MEMDUR_EVENT | ID_DRIVER);
assert(raster->pixels == nil);
raster->pixels = px;
#ifdef __SYMBIAN32__
memset(px, 0, allocSz);
#else
glReadBuffer(GL_BACK);
#endif
glReadPixels(0, 0, raster->width, raster->height, GL_RGB, GL_UNSIGNED_BYTE, px);
raster->privateFlags = lockMode;
break;
default:
assert(0 && "cannot lock this type of raster yet");
return nil;
}
return px;
#else
return nil;
#endif
}
void rasterUnlock(Raster *raster, int32 level){
#ifdef RW_GLES1
Gl1Raster *natras = GETGL1RASTEREXT(raster);
assert(raster->pixels);
switch(raster->type){
case Raster::NORMAL:
case Raster::TEXTURE:
case Raster::CAMERATEXTURE:
if(raster->privateFlags & Raster::LOCKWRITE){
if(level != 0) break;
// === GUARDAR EN BACKING STORE ANTES DE SUBIR A GPU ===
if(natras->backingStore == nil){
int numLevels = natras->numLevels;
// RasterLevels tiene: int numlevels; struct { uint32 size; uint8 *data; } levels[];
natras->backingStore = (RasterLevels*)malloc(
sizeof(RasterLevels) + sizeof(natras->backingStore->levels[0]) * numLevels);
natras->backingStore->numlevels = numLevels;
for(int i = 0; i < numLevels; i++){
uint32 sz = getLevelSize(raster, i);
natras->backingStore->levels[i].size = sz;
natras->backingStore->levels[i].data = (uint8*)malloc(sz);
memset(natras->backingStore->levels[i].data, 0, sz);
}
}
// copiar píxeles actuales al backing store
{
uint32 sz = getLevelSize(raster, level);
assert(level < natras->backingStore->numlevels);
memcpy(natras->backingStore->levels[level].data, raster->pixels, sz);
}
// === FIN BACKING STORE ===
uint32 prev = bindTexture(natras->texid);
// flip vertical (igual que antes)
{
int stride = raster->width * natras->bpp;
uint8_t *tmp = (uint8_t*)malloc(stride);
for(int y = 0; y < raster->height / 2; y++){
uint8_t *a = (uint8_t*)raster->pixels + y * stride;
uint8_t *b = (uint8_t*)raster->pixels + (raster->height - 1 - y) * stride;
memcpy(tmp, a, stride);
memcpy(a, b, stride);
memcpy(b, tmp, stride);
}
free(tmp);
}
if(!natras->isCompressed){
if(natras->format == GL_RGBA && natras->type == GL_UNSIGNED_BYTE){
// convertir RGBA8888 → RGBA4444
uint16_t *pixels16 = (uint16_t*)malloc(raster->width * raster->height * 2);
uint8_t *pixels8 = (uint8_t*)raster->pixels;
for(int i = 0; i < raster->width * raster->height; i++){
uint8_t r = pixels8[i*4+0];
uint8_t g = pixels8[i*4+1];
uint8_t b = pixels8[i*4+2];
uint8_t a = pixels8[i*4+3];
pixels16[i] = ((r>>4)<<12)|((g>>4)<<8)|((b>>4)<<4)|(a>>4);
}
glTexImage2D(GL_TEXTURE_2D, level, GL_RGBA,
raster->width, raster->height, 0,
GL_RGBA, GL_UNSIGNED_SHORT_4_4_4_4, pixels16);
free(pixels16);
} else {
glTexImage2D(GL_TEXTURE_2D, level, natras->internalFormat,
raster->width, raster->height, 0,
natras->format, natras->type, raster->pixels);
}
}
bindTexture(prev);
}
break;
case Raster::CAMERA:
break;
}
rwFree(raster->pixels);
raster->pixels = nil;
#endif
raster->width = raster->originalWidth;
raster->height = raster->originalHeight;
raster->stride = raster->originalStride;
raster->pixels = raster->originalPixels;
raster->privateFlags = 0;
}
int32
rasterNumLevels(Raster *raster)
{
return GETGL1RASTEREXT(raster)->numLevels;
}
// Almost the same as d3d9 and ps2 function
bool32
imageFindRasterFormat(Image *img, int32 type,
int32 *pWidth, int32 *pHeight, int32 *pDepth, int32 *pFormat)
{
int32 width, height, depth, format;
assert((type&0xF) == Raster::TEXTURE);
// for(width = 1; width < img->width; width <<= 1);
// for(height = 1; height < img->height; height <<= 1);
// Perhaps non-power-of-2 textures are acceptable?
width = img->width;
height = img->height;
depth = img->depth;
if(depth <= 8)
depth = 32;
switch(depth){
case 32:
if(img->hasAlpha())
format = Raster::C8888;
else{
format = Raster::C888;
depth = 24;
}
break;
case 24:
format = Raster::C888;
break;
case 16:
format = Raster::C1555;
break;
case 8:
case 4:
default:
RWERROR((ERR_INVRASTER));
return 0;
}
format |= type;
*pWidth = width;
*pHeight = height;
*pDepth = depth;
*pFormat = format;
return 1;
}
bool32
rasterFromImage(Raster *raster, Image *image)
{
if((raster->type&0xF) != Raster::TEXTURE)
return 0;
void (*conv)(uint8 *out, uint8 *in) = nil;
// Unpalettize image if necessary but don't change original
Image *truecolimg = nil;
if(image->depth <= 8){
truecolimg = Image::create(image->width, image->height, image->depth);
truecolimg->pixels = image->pixels;
truecolimg->stride = image->stride;
truecolimg->palette = image->palette;
truecolimg->unpalettize();
image = truecolimg;
}
Gl1Raster *natras = GETGL1RASTEREXT(raster);
int32 format = raster->format&0xF00;
assert(!natras->isCompressed);
switch(image->depth){
case 32:
if(format == Raster::C8888)
conv = conv_RGBA8888_from_RGBA8888;
else if(format == Raster::C888)
conv = conv_RGB888_from_RGB888;
else
goto err;
break;
case 24:
if(format == Raster::C8888)
conv = conv_RGBA8888_from_RGB888;
else if(format == Raster::C888)
conv = conv_RGB888_from_RGB888;
else
goto err;
break;
case 16:
if(format == Raster::C8888)
conv = conv_RGBA8888_from_ARGB1555;
else if(format == Raster::C1555)
conv = conv_RGBA5551_from_ARGB1555;
else
goto err;
break;
case 8:
case 4:
default:
err:
RWERROR((ERR_INVRASTER));
return 0;
}
natras->hasAlpha = image->hasAlpha();
bool unlock = false;
if(raster->pixels == nil){
raster->lock(0, Raster::LOCKWRITE|Raster::LOCKNOFETCH);
unlock = true;
}
uint8 *pixels = raster->pixels;
assert(pixels);
uint8 *imgpixels = image->pixels + (image->height-1)*image->stride;
int x, y;
assert(image->width == raster->width);
assert(image->height == raster->height);
for(y = 0; y < image->height; y++){
uint8 *imgrow = imgpixels;
uint8 *rasrow = pixels;
for(x = 0; x < image->width; x++){
conv(rasrow, imgrow);
imgrow += image->bpp;
rasrow += natras->bpp;
}
imgpixels -= image->stride;
pixels += raster->stride;
}
if(unlock)
raster->unlock(0);
if(truecolimg)
truecolimg->destroy();
return 1;
}
Image*
rasterToImage(Raster *raster)
{
int32 depth;
Image *image;
bool unlock = false;
if(raster->pixels == nil){
raster->lock(0, Raster::LOCKREAD);
unlock = true;
}
Gl1Raster *natras = GETGL1RASTEREXT(raster);
if(natras->isCompressed){
// TODO
RWERROR((ERR_INVRASTER));
return nil;
}
void (*conv)(uint8 *out, uint8 *in) = nil;
switch(raster->format & 0xF00){
case Raster::C1555:
depth = 16;
conv = conv_ARGB1555_from_RGBA5551;
break;
case Raster::C8888:
depth = 32;
conv = conv_RGBA8888_from_RGBA8888;
break;
case Raster::C888:
depth = 24;
conv = conv_RGB888_from_RGB888;
break;
default:
case Raster::C555:
case Raster::C565:
case Raster::C4444:
case Raster::LUM8:
RWERROR((ERR_INVRASTER));
return nil;
}
if(raster->format & Raster::PAL4 ||
raster->format & Raster::PAL8){
RWERROR((ERR_INVRASTER));
return nil;
}
uint8 *in, *out;
image = Image::create(raster->width, raster->height, depth);
image->allocate();
uint8 *imgpixels = image->pixels + (image->height-1)*image->stride;
uint8 *pixels = raster->pixels;
int x, y;
assert(image->width == raster->width);
assert(image->height == raster->height);
for(y = 0; y < image->height; y++){
uint8 *imgrow = imgpixels;
uint8 *rasrow = pixels;
for(x = 0; x < image->width; x++){
conv(imgrow, rasrow);
imgrow += image->bpp;
rasrow += natras->bpp;
}
imgpixels -= image->stride;
pixels += raster->stride;
}
if(unlock)
raster->unlock(0);
return image;
}
static void*
createNativeRaster(void *object, int32 offset, int32)
{
Gl1Raster *ras = PLUGINOFFSET(Gl1Raster, object, offset);
ras->texid = 0;
ras->fbo = 0;
ras->fboMate = nil;
ras->backingStore = nil;
return object;
}
void evictRaster(Raster *raster);
static void*
destroyNativeRaster(void *object, int32 offset, int32)
{
Raster *raster = (Raster*)object;
Gl1Raster *natras = PLUGINOFFSET(Gl1Raster, object, offset);
#ifdef RW_GLES1
evictRaster(raster);
switch(raster->type){
case Raster::NORMAL:
case Raster::TEXTURE:
glDeleteTextures(1, &natras->texid);
break;
case Raster::CAMERATEXTURE:
break;
case Raster::ZBUFFER:
break;
case Raster::CAMERA:
if(natras->fboMate){
// Break apart from currently associated zbuffer
Gl1Raster *zras = GETGL1RASTEREXT(natras->fboMate);
zras->fboMate = nil;
natras->fboMate = nil;
}
break;
}
natras->texid = 0;
natras->fbo = 0;
if(natras->backingStore){
for(int i = 0; i < natras->backingStore->numlevels; i++)
free(natras->backingStore->levels[i].data);
free(natras->backingStore);
natras->backingStore = nil;
}
#endif
return object;
}
static void*
copyNativeRaster(void *dst, void *, int32 offset, int32)
{
Gl1Raster *d = PLUGINOFFSET(Gl1Raster, dst, offset);
d->texid = 0;
d->fbo = 0;
d->fboMate = nil;
d->backingStore = nil;
return dst;
}
Texture*
readNativeTexture(Stream *stream)
{
uint32 platform;
if(!findChunk(stream, ID_STRUCT, nil, nil)){
RWERROR((ERR_CHUNK, "STRUCT"));
return nil;
}
platform = stream->readU32();
if(platform != PLATFORM_GLES1){
RWERROR((ERR_PLATFORM, platform));
return nil;
}
Texture *tex = Texture::create(nil);
if(tex == nil)
return nil;
// Texture
tex->filterAddressing = stream->readU32();
stream->read8(tex->name, 32);
stream->read8(tex->mask, 32);
// Raster
uint32 format = stream->readU32();
int32 width = stream->readI32();
int32 height = stream->readI32();
int32 depth = stream->readI32();
int32 numLevels = stream->readI32();
// Native raster
int32 subplatform = stream->readI32();
int32 flags = stream->readI32();
int32 compression = stream->readI32();
Raster *raster;
Gl1Raster *natras;
if(flags & 2){
tex->destroy();
RWERROR((ERR_FORMAT_UNSUPPORTED));
return nil;
}else{
raster = Raster::create(width, height, depth, format | Raster::TEXTURE, PLATFORM_GLES1);
}
assert(raster);
natras = GETGL1RASTEREXT(raster);
tex->raster = raster;
uint32 size;
uint8 *data;
for(int32 i = 0; i < numLevels; i++){
size = stream->readU32();
data = raster->lock(i, Raster::LOCKWRITE|Raster::LOCKNOFETCH);
stream->read8(data, size);
raster->unlock(i);
}
return tex;
}
void
writeNativeTexture(Texture *tex, Stream *stream)
{
Raster *raster = tex->raster;
Gl1Raster *natras = GETGL1RASTEREXT(raster);
int32 chunksize = getSizeNativeTexture(tex);
writeChunkHeader(stream, ID_STRUCT, chunksize-12);
stream->writeU32(PLATFORM_GLES1);
// Texture
stream->writeU32(tex->filterAddressing);
stream->write8(tex->name, 32);
stream->write8(tex->mask, 32);
// Raster
int32 numLevels = natras->numLevels;
stream->writeI32(raster->format);
stream->writeI32(raster->width);
stream->writeI32(raster->height);
stream->writeI32(raster->depth);
stream->writeI32(numLevels);
// Native raster
int32 flags = 0;
int32 compression = 0;
if(natras->hasAlpha)
flags |= 1;
if(natras->isCompressed){
flags |= 2;
switch(natras->internalFormat){
default:
assert(0 && "unknown compression");
}
}
stream->writeI32(1);
stream->writeI32(flags);
stream->writeI32(compression);
// TODO: auto mipmaps?
uint32 size;
uint8 *data;
for(int32 i = 0; i < numLevels; i++){
size = getLevelSize(raster, i);
stream->writeU32(size);
data = raster->lock(i, Raster::LOCKREAD);
stream->write8(data, size);
raster->unlock(i);
}
}
uint32
getSizeNativeTexture(Texture *tex)
{
uint32 size = 12 + 72 + 32;
int32 levels = tex->raster->getNumLevels();
for(int32 i = 0; i < levels; i++)
size += 4 + getLevelSize(tex->raster, i);
return size;
}
void registerNativeRaster(void)
{
nativeRasterOffset = Raster::registerPlugin(sizeof(Gl1Raster),
ID_RASTERGLES1,
createNativeRaster,
destroyNativeRaster,
copyNativeRaster);
}
}
}

138
vendor/librw/src/gles1/gl1render.cpp vendored Normal file
View file

@ -0,0 +1,138 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "../rwbase.h"
#include "../rwerror.h"
#include "../rwplg.h"
#include "../rwrender.h"
#include "../rwengine.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#ifdef RW_GLES1
#include "rwgles1.h"
#include "rwgles1impl.h"
namespace rw {
namespace gles1 {
#define MAX_LIGHTS
void
drawInst_simple(InstanceDataHeader *header, InstanceData *inst)
{
flushCache();
glDrawElements(header->primType, inst->numIndex,
GL_UNSIGNED_SHORT, (void*)(uintptr)inst->offset);
}
void
drawInst(InstanceDataHeader *header, InstanceData *inst)
{
drawInst_simple(header, inst);
}
void
setupVertexInput(InstanceDataHeader *header)
{
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, header->ibo);
glBindBuffer(GL_ARRAY_BUFFER, header->vbo);
bool hasNormal = false;
bool hasColor = false;
bool hasTex = false;
for (int32 i = 0; i < header->numAttribs; i++) {
AttribDesc *a = &header->attribDesc[i];
if (a->index == ATTRIB_POS) {
glEnableClientState(GL_VERTEX_ARRAY);
glVertexPointer(a->size, a->type, a->stride, (void*)(uintptr)a->offset);
} else if (a->index == ATTRIB_NORMAL) {
glEnableClientState(GL_NORMAL_ARRAY);
glNormalPointer(a->type, a->stride, (void*)(uintptr)a->offset);
hasNormal = true;
} else if (a->index == ATTRIB_COLOR){
glEnableClientState(GL_COLOR_ARRAY);
glColorPointer(a->size, a->type, a->stride, (void*)(uintptr)a->offset);
hasColor = true;
} else if(a->index == ATTRIB_TEXCOORDS0){
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glTexCoordPointer(a->size, a->type, a->stride, (void*)(uintptr)a->offset);
hasTex = true;
}
}
if (!hasNormal) glDisableClientState(GL_NORMAL_ARRAY);
if (!hasColor) {
glDisableClientState(GL_COLOR_ARRAY);
glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
}
if(!hasTex) glDisableClientState(GL_TEXTURE_COORD_ARRAY);
}
void
teardownVertexInput(InstanceDataHeader *header)
{
}
int32
lightingCB(Atomic *atomic)
{
WorldLights lightData;
Light *directionals[8];
Light *locals[8];
lightData.directionals = directionals;
lightData.numDirectionals = 0; // 8;
lightData.locals = locals;
lightData.numLocals = 0; // 8;
if(atomic->geometry->flags & rw::Geometry::LIGHT){
((World*)engine->currentWorld)->enumerateLights(atomic, &lightData);
if((atomic->geometry->flags & rw::Geometry::NORMALS) == 0){
// Get rid of lights that need normals when we don't have any
lightData.numDirectionals = 0;
lightData.numLocals = 0;
}
return setLights(&lightData);
}else{
memset(&lightData, 0, sizeof(lightData));
return setLights(&lightData);
}
}
void
defaultRenderCB(Atomic *atomic, InstanceDataHeader *header)
{
Material *m;
uint32 flags = atomic->geometry->flags;
setWorldMatrix(atomic->getFrame()->getLTM());
//int32 vsBits = lightingCB(atomic);
glDisable(GL_LIGHTING);
setupVertexInput(header);
InstanceData *inst = header->inst;
int32 n = header->numMeshes;
while(n--){
m = inst->material;
setMaterial(flags, m->color, m->surfaceProps);
setTexture(0, m->texture);
rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
drawInst(header, inst);
inst++;
}
teardownVertexInput(header);
}
}
}
#endif

98
vendor/librw/src/gles1/gl1skin.cpp vendored Normal file
View file

@ -0,0 +1,98 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <assert.h>
#include "../rwbase.h"
#include "../rwplg.h"
#include "../rwpipeline.h"
#include "../rwobjects.h"
#include "../rwengine.h"
#include "../rwrender.h"
#include "../rwanim.h"
#include "../rwplugins.h"
#include "rwgles1.h"
#include "rwgles1plg.h"
#include "rwgles1impl.h"
#ifdef RW_GLES1
namespace rw {
namespace gles1 {
void
skinRenderCB(Atomic *atomic, InstanceDataHeader *header)
{
Material *m;
uint32 flags = atomic->geometry->flags;
setWorldMatrix(atomic->getFrame()->getLTM());
glDisable(GL_LIGHTING);
setupVertexInput(header);
InstanceData *inst = header->inst;
int32 n = header->numMeshes;
while(n--){
m = inst->material;
setMaterial(flags, m->color, m->surfaceProps);
setTexture(0, m->texture);
rw::SetRenderState(VERTEXALPHA, inst->vertexAlpha || m->color.alpha != 0xFF);
drawInst(header, inst);
inst++;
}
teardownVertexInput(header);
}
// skinInstanceCB: igual que defaultInstanceCB, sin pesos/indices
// porque GLES1 no puede hacer skinning en GPU
void
skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance)
{
defaultInstanceCB(geo, header, reinstance);
}
void
skinUninstanceCB(Geometry *geo, InstanceDataHeader *header)
{
assert(0 && "can't uninstance");
}
ObjPipeline*
makeSkinPipeline(void)
{
ObjPipeline *pipe = ObjPipeline::create();
pipe->instanceCB = skinInstanceCB;
pipe->uninstanceCB = skinUninstanceCB;
pipe->renderCB = skinRenderCB;
pipe->pluginID = ID_SKIN;
pipe->pluginData = 1;
return pipe;
}
static void*
skinOpen(void *o, int32, int32)
{
skinGlobals.pipelines[PLATFORM_GLES1] = makeSkinPipeline();
return o;
}
static void*
skinClose(void *o, int32, int32)
{
((ObjPipeline*)skinGlobals.pipelines[PLATFORM_GLES1])->destroy();
skinGlobals.pipelines[PLATFORM_GLES1] = nil;
return o;
}
void
initSkin(void)
{
Driver::registerPlugin(PLATFORM_GLES1, 0, ID_SKIN, skinOpen, skinClose);
}
}
}
#endif

255
vendor/librw/src/gles1/rwgles1.h vendored Normal file
View file

@ -0,0 +1,255 @@
#ifdef RW_GLES1
#include <gles/gl.h>
//#include <gles/glext.h>
#include <gles/egl.h>
#endif
namespace rw {
#ifdef RW_GLES1
struct EngineOpenParams
{
int width, height;
const char *windowtitle;
};
#endif
namespace gles1 {
void registerPlatformPlugins(void);
extern Device renderdevice;
// arguments to glVertexAttribPointer basically
struct AttribDesc
{
uint32 index;
int32 type;
bool32 normalized;
int32 size;
uint32 stride;
uint32 offset;
};
enum AttribIndices
{
ATTRIB_POS = 0,
ATTRIB_NORMAL,
ATTRIB_COLOR,
ATTRIB_WEIGHTS,
ATTRIB_INDICES,
ATTRIB_TEXCOORDS0,
ATTRIB_TEXCOORDS1,
#if 0
ATTRIB_TEXCOORDS2,
ATTRIB_TEXCOORDS3,
ATTRIB_TEXCOORDS4,
ATTRIB_TEXCOORDS5,
ATTRIB_TEXCOORDS6,
ATTRIB_TEXCOORDS7,
#endif
};
// default uniform indices
extern int32 u_matColor;
extern int32 u_surfProps;
struct InstanceData
{
uint32 numIndex;
uint32 minVert; // not used for rendering
int32 numVertices; //
Material *material;
bool32 vertexAlpha;
uint32 program;
uint32 offset;
};
struct InstanceDataHeader : rw::InstanceDataHeader
{
uint32 serialNumber;
uint32 numMeshes;
uint16 *indexBuffer;
uint32 primType;
uint8 *vertexBuffer;
int32 numAttribs;
AttribDesc *attribDesc;
uint32 totalNumIndex;
uint32 totalNumVertex;
uint32 ibo;
uint32 vbo; // or 2?
InstanceData *inst;
};
#ifdef RW_GLES1
struct Im3DVertex
{
V3d position;
uint8 r, g, b, a;
float32 u, v;
void setX(float32 x) { this->position.x = x; }
void setY(float32 y) { this->position.y = y; }
void setZ(float32 z) { this->position.z = z; }
void setColor(uint8 r, uint8 g, uint8 b, uint8 a) {
this->r = r; this->g = g; this->b = b; this->a = a; }
void setU(float32 u) { this->u = u; }
void setV(float32 v) { this->v = v; }
float getX(void) { return this->position.x; }
float getY(void) { return this->position.y; }
float getZ(void) { return this->position.z; }
RGBA getColor(void) { return makeRGBA(this->r, this->g, this->b, this->a); }
float getU(void) { return this->u; }
float getV(void) { return this->v; }
};
struct Im2DVertex
{
float32 x, y, z, w;
uint8 r, g, b, a;
float32 u, v;
void setScreenX(float32 x) { this->x = x; }
void setScreenY(float32 y) { this->y = y; }
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 setRecipCameraZ(float32 recipz) { this->w = 1.0f/recipz; }
void setColor(uint8 r, uint8 g, uint8 b, uint8 a) {
this->r = r; this->g = g; this->b = b; this->a = a; }
void setU(float32 u, float recipz) { this->u = u; }
void setV(float32 v, float recipz) { this->v = v; }
float getScreenX(void) { return this->x; }
float getScreenY(void) { return this->y; }
float getScreenZ(void) { return this->z; }
float getCameraZ(void) { return this->w; }
float getRecipCameraZ(void) { return 1.0f/this->w; }
RGBA getColor(void) { return makeRGBA(this->r, this->g, this->b, this->a); }
float getU(void) { return this->u; }
float getV(void) { return this->v; }
};
void setupVertexInput(InstanceDataHeader *header);
void teardownVertexInput(InstanceDataHeader *header);
// Render state
// Vertex shader bits
enum
{
// These should be low so they could be used as indices
VSLIGHT_DIRECT = 1,
VSLIGHT_POINT = 2,
VSLIGHT_SPOT = 4,
VSLIGHT_MASK = 7, // all the above
// less critical
VSLIGHT_AMBIENT = 8,
};
// per Scene
void setProjectionMatrix(float32*);
void setViewMatrix(float32*);
// per Object
void setWorldMatrix(Matrix*);
int32 setLights(WorldLights *lightData);
// per Mesh
void setTexture(int32 n, Texture *tex);
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);
bool32 getAlphaBlend(void);
bool32 getAlphaTest(void);
void bindFramebuffer(uint32 fbo);
uint32 bindTexture(uint32 texid);
void flushCache(void);
#endif
class ObjPipeline : public rw::ObjPipeline
{
public:
void init(void);
static ObjPipeline *create(void);
void (*instanceCB)(Geometry *geo, InstanceDataHeader *header, bool32 reinstance);
void (*uninstanceCB)(Geometry *geo, InstanceDataHeader *header);
void (*renderCB)(Atomic *atomic, InstanceDataHeader *header);
};
void defaultInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance);
void defaultUninstanceCB(Geometry *geo, InstanceDataHeader *header);
void defaultRenderCB(Atomic *atomic, InstanceDataHeader *header);
int32 lightingCB(Atomic *atomic);
void drawInst_simple(InstanceDataHeader *header, InstanceData *inst);
// Emulate PS2 GS alpha test FB_ONLY case: failed alpha writes to frame- but not to depth buffer
void drawInst_GSemu(InstanceDataHeader *header, InstanceData *inst);
// This one switches between the above two depending on render state;
void drawInst(InstanceDataHeader *header, InstanceData *inst);
void *destroyNativeData(void *object, int32, int32);
ObjPipeline *makeDefaultPipeline(void);
void setVertexAlpha(bool32 enable);
// Native Texture and Raster
struct Gl1Raster
{
// arguments to glTexImage2D
int32 internalFormat;
int32 type;
int32 format;
int32 bpp; // bytes per pixel
// texture object
uint32 texid;
bool isCompressed;
bool hasAlpha;
bool autogenMipmap;
int8 numLevels;
// cached filtermode and addressing
uint8 filterMode;
uint8 addressU;
uint8 addressV;
int32 maxAnisotropy;
uint32 fbo; // used for camera texture only!
Raster *fboMate; // color or zbuffer raster mate of this one
RasterLevels *backingStore; // if we can't read back GPU memory but have to
};
// 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;
Texture *readNativeTexture(Stream *stream);
void writeNativeTexture(Texture *tex, Stream *stream);
uint32 getSizeNativeTexture(Texture *tex);
extern int32 nativeRasterOffset;
void registerNativeRaster(void);
#define GETGL1RASTEREXT(raster) PLUGINOFFSET(Gl1Raster, raster, rw::gles1::nativeRasterOffset)
}
}

83
vendor/librw/src/gles1/rwgles1impl.h vendored Normal file
View file

@ -0,0 +1,83 @@
namespace rw {
namespace gles1 {
#ifdef RW_GLES1
extern uint32 im2DVbo, im2DIbo;
void openIm2D(void);
void closeIm2D(void);
void im2DRenderLine(void *vertices, int32 numVertices,
int32 vert1, int32 vert2);
void im2DRenderTriangle(void *vertices, int32 numVertices,
int32 vert1, int32 vert2, int32 vert3);
void im2DRenderPrimitive(PrimitiveType primType,
void *vertices, int32 numVertices);
void im2DRenderIndexedPrimitive(PrimitiveType primType,
void *vertices, int32 numVertices, void *indices, int32 numIndices);
void openIm3D(void);
void closeIm3D(void);
void im3DTransform(void *vertices, int32 numVertices, Matrix *world, uint32 flags);
void im3DRenderPrimitive(PrimitiveType primType);
void im3DRenderIndexedPrimitive(PrimitiveType primType, void *indices, int32 numIndices);
void im3DEnd(void);
struct DisplayMode
{
#ifdef __SYMBIAN32__
uint32 width;
uint32 height;
#else
#ifdef LIBRW_SDL2
SDL_DisplayMode mode;
#else
GLFWvidmode mode;
#endif
#endif
int32 depth;
uint32 flags;
};
struct GlGlobals
{
#ifdef LIBRW_SDL2
SDL_Window **pWindow;
SDL_Window *window;
SDL_GLContext glcontext;
#else
#ifndef __SYMBIAN32__
GLFWwindow **pWindow;
GLFWwindow *window;
GLFWmonitor *monitor;
#endif
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
Raster *rasterCreate(Raster *raster);
uint8 *rasterLock(Raster*, int32 level, int32 lockMode);
void rasterUnlock(Raster*, int32);
int32 rasterNumLevels(Raster*);
bool32 imageFindRasterFormat(Image *img, int32 type,
int32 *width, int32 *height, int32 *depth, int32 *format);
bool32 rasterFromImage(Raster *raster, Image *image);
Image *rasterToImage(Raster *raster);
}
}

13
vendor/librw/src/gles1/rwgles1plg.h vendored Normal file
View file

@ -0,0 +1,13 @@
namespace rw {
namespace gles1 {
void initMatFX(void);
ObjPipeline *makeMatFXPipeline(void);
void matfxRenderCB(Atomic *atomic, InstanceDataHeader *header);
void initSkin(void);
ObjPipeline *makeSkinPipeline(void);
void skinInstanceCB(Geometry *geo, InstanceDataHeader *header, bool32 reinstance);
void skinRenderCB(Atomic *atomic, InstanceDataHeader *header);
void uploadSkinMatrices(Atomic *atomic);
}
}

View file

@ -413,9 +413,9 @@ flipAlphaBlock5_half(uint8 *dst, uint8 *src)
dst[1] = src[1];
// bits
uint64 bits = *(uint64*)&src[2];
uint64 flipbits = bits & 0xFFFFFF000000;
flipbits |= (bits>>12) & 0xFFF;
flipbits |= (bits<<12) & 0xFFF000;
uint64 flipbits = bits & 0xFFFFFF000000ULL;
flipbits |= (bits>>12) & 0xFFFULL;
flipbits |= (bits<<12) & 0xFFF000ULL;
memcpy(dst+2, &flipbits, 6);
}

View file

@ -19,6 +19,8 @@
#include "gl/rwwdgl.h"
#include "gl/rwgl3.h"
#include "gl/rwgl3plg.h"
#include "gles1/rwgles1.h"
#include "gles1/rwgles1plg.h"
#define PLUGIN_ID ID_MATFX
@ -619,6 +621,9 @@ registerMatFXPlugin(void)
d3d9::initMatFX();
wdgl::initMatFX();
gl3::initMatFX();
#ifdef RW_GLES1
gles1::initMatFX();
#endif
matFXGlobals.atomicOffset =
Atomic::registerPlugin(sizeof(int32), ID_MATFX,

View file

@ -9,7 +9,13 @@
#endif
#ifdef __SYMBIAN32__
#undef stderr
#define stderr stdout
#ifdef S60V5
#define OFFSET_OF(type, member) ((size_t)&(((type*)0)->member))
#else
#define OFFSET_OF offsetof
#endif
#endif
// TODO: clean up the opengl defines
@ -46,6 +52,11 @@
#define RW_OPENGL
#endif
#ifdef RW_GLES1
//#define RW_OPENGL
#define RWDEVICE gles1
#endif
namespace rw {
#ifdef RW_PS2
@ -106,8 +117,9 @@ struct LLLink
}
};
#define LLLinkGetData(linkvar,type,entry) \
((type*)(((rw::uint8*)(linkvar))-offsetof(type,entry)))
((type*)(((rw::uint8*)(linkvar))-OFFSET_OF(type,entry)))
// Have to be careful since the link might be deleted.
#define FORLIST(_link, _list) \
@ -546,6 +558,7 @@ enum Platform
PLATFORM_WDGL = 11, // WarDrum OpenGL
PLATFORM_GL3 = 12, // my GL3 implementation
PLATFORM_GLES1 = 13,
NUM_PLATFORMS,
@ -619,6 +632,7 @@ enum PluginID
ID_RASTERD3D9 = MAKEPLUGINID(VEND_RASTER, PLATFORM_D3D9),
ID_RASTERWDGL = MAKEPLUGINID(VEND_RASTER, PLATFORM_WDGL),
ID_RASTERGL3 = MAKEPLUGINID(VEND_RASTER, PLATFORM_GL3),
ID_RASTERGLES1 = MAKEPLUGINID(VEND_RASTER, PLATFORM_GLES1),
// anything driver/device related (only as allocation tag)
ID_DRIVER = MAKEPLUGINID(VEND_DRIVER, 0)

View file

@ -19,6 +19,8 @@
#include "gl/rwwdgl.h"
#include "gl/rwgl3.h"
#include "gl/rwgl3plg.h"
#include "gles1/rwgles1.h"
#include "gles1/rwgles1plg.h"
#define PLUGIN_ID ID_SKIN
@ -373,7 +375,10 @@ registerSkinPlugin(void)
d3d9::initSkin();
wdgl::initSkin();
gl3::initSkin();
#ifdef RW_GLES1
gles1::initSkin();
#endif
int32 o;
o = Geometry::registerPlugin(sizeof(Skin*), ID_SKIN,
createSkin, destroySkin, copySkin);

View file

@ -17,6 +17,7 @@
#include "d3d/rwd3d9.h"
#include "d3d/rwd3dimpl.h"
#include "gl/rwgl3.h"
#include "gles1/rwgles1.h"
#define PLUGIN_ID 0
@ -481,6 +482,11 @@ Texture::streamReadNative(Stream *stream)
return xbox::readNativeTexture(stream);
if(platform == PLATFORM_GL3)
return gl3::readNativeTexture(stream);
#ifdef RW_GLES1
if(platform == PLATFORM_GLES1){
return gles1::readNativeTexture(stream);
}
#endif
assert(0 && "unsupported platform");
return nil;
}
@ -498,6 +504,11 @@ Texture::streamWriteNative(Stream *stream)
xbox::writeNativeTexture(this, stream);
else if(this->raster->platform == PLATFORM_GL3)
gl3::writeNativeTexture(this, stream);
#ifdef RW_GLES1
else if(this->raster->platform == PLATFORM_GLES1){
gles1::writeNativeTexture(this, stream);
}
#endif
else
assert(0 && "unsupported platform");
}
@ -515,6 +526,11 @@ Texture::streamGetSizeNative(void)
return xbox::getSizeNativeTexture(this);
if(this->raster->platform == PLATFORM_GL3)
return gl3::getSizeNativeTexture(this);
#ifdef RW_GLES1
if(this->raster->platform == PLATFORM_GLES1){
return gles1::getSizeNativeTexture(this);
}
#endif
assert(0 && "unsupported platform");
return 0;
}