Managed to get loading the ROM and graphics decompression/overworld tile building stuff to compile, now it's just a matter of translating that data into the Bitmap to display properly.

This commit is contained in:
Justin Scofield
2022-06-10 23:51:00 -04:00
parent 2ad2e3c199
commit 31bf9dad4b
12 changed files with 244 additions and 160 deletions

View File

@@ -9,6 +9,20 @@ namespace Data {
using namespace Core; using namespace Core;
using namespace Graphics; using namespace Graphics;
Overworld::~Overworld() {
for (int i = 0; i < tiles32.size(); i++) {
free(allmapsTilesLW[i]);
free(allmapsTilesDW[i]);
free(allmapsTilesSP[i]);
}
free(allmapsTilesLW);
free(allmapsTilesDW);
free(allmapsTilesSP);
delete overworldMapPointer;
delete owactualMapPointer;
}
static TileInfo GetTilesInfo(ushort tile) { static TileInfo GetTilesInfo(ushort tile) {
// vhopppcc cccccccc // vhopppcc cccccccc
ushort o = 0; ushort o = 0;
@@ -24,12 +38,13 @@ static TileInfo GetTilesInfo(ushort tile) {
return TileInfo(tid, p, v, h, o); return TileInfo(tid, p, v, h, o);
} }
Overworld::Overworld(Utils::ROM rom) : rom_(rom) { void Overworld::Load(Utils::ROM rom) {
rom_ = rom;
for (int i = 0; i < 0x2B; i++) { for (int i = 0; i < 0x2B; i++) {
tileLeftEntrance[i] = (ushort)rom_.ReadShort( tileLeftEntrance.push_back(
Constants::overworldEntranceAllowedTilesLeft + (i * 2)); rom_.ReadShort(Constants::overworldEntranceAllowedTilesLeft + (i * 2)));
tileRightEntrance[i] = (ushort)rom_.ReadShort( tileRightEntrance.push_back(rom_.ReadShort(
Constants::overworldEntranceAllowedTilesRight + (i * 2)); Constants::overworldEntranceAllowedTilesRight + (i * 2)));
} }
AssembleMap32Tiles(); AssembleMap32Tiles();
@@ -38,21 +53,20 @@ Overworld::Overworld(Utils::ROM rom) : rom_(rom) {
// Map Initialization : // Map Initialization :
for (int i = 0; i < 160; i++) { for (int i = 0; i < 160; i++) {
allmaps.push_back(OverworldMap(rom_, (byte)i)); allmaps.push_back(OverworldMap(rom_, tiles16, (byte)i));
} }
FetchLargeMaps(); FetchLargeMaps();
LoadOverworldMap(); LoadOverworldMap();
auto size = tiles16.size(); auto size = tiles16.size();
for (int i = 0; i < 160; i++) { for (int i = 0; i < 160; i++) {
allmaps[i].BuildMap(mapParent, size, gameState); allmaps[i].BuildMap(mapParent, size, gameState, allmapsTilesLW,
allmapsTilesDW, allmapsTilesSP);
} }
isLoaded = true; isLoaded = true;
} }
void Overworld::Load(Utils::ROM rom) {}
ushort Overworld::GenerateTile32(int i, int k, int dimension) { ushort Overworld::GenerateTile32(int i, int k, int dimension) {
return (ushort)(rom_.GetRawData()[map32address[dimension] + k + (i)] + return (ushort)(rom_.GetRawData()[map32address[dimension] + k + (i)] +
(((rom_.GetRawData()[map32address[dimension] + (i) + (((rom_.GetRawData()[map32address[dimension] + (i) +
@@ -73,6 +87,18 @@ void Overworld::AssembleMap32Tiles() {
tiles32.push_back(Tile32(tl, tr, bl, br)); tiles32.push_back(Tile32(tl, tr, bl, br));
} }
} }
allmapsTilesLW = (ushort**)malloc(tiles32.size() * sizeof(ushort*));
for (int i = 0; i < tiles32.size(); i++)
allmapsTilesLW[i] = (ushort*)malloc(tiles32.size() * sizeof(ushort));
allmapsTilesDW = (ushort**)malloc(tiles32.size() * sizeof(ushort*));
for (int i = 0; i < tiles32.size(); i++)
allmapsTilesDW[i] = (ushort*)malloc(tiles32.size() * sizeof(ushort));
allmapsTilesSP = (ushort**)malloc(tiles32.size() * sizeof(ushort*));
for (int i = 0; i < tiles32.size(); i++)
allmapsTilesSP[i] = (ushort*)malloc(tiles32.size() * sizeof(ushort));
} }
void Overworld::AssembleMap16Tiles() { void Overworld::AssembleMap16Tiles() {
@@ -94,11 +120,9 @@ void Overworld::AssembleMap16Tiles() {
void Overworld::DecompressAllMapTiles() { void Overworld::DecompressAllMapTiles() {
int lowest = 0x0FFFFF; int lowest = 0x0FFFFF;
int highest = 0x0F8000; int highest = 0x0F8000;
// int npos = 0;
int sx = 0; int sx = 0;
int sy = 0; int sy = 0;
int c = 0; int c = 0;
// int furthestPtr = 0;
for (int i = 0; i < 160; i++) { for (int i = 0; i < 160; i++) {
int p1 = (rom_.GetRawData()[(Constants::compressedAllMap32PointersHigh) + int p1 = (rom_.GetRawData()[(Constants::compressedAllMap32PointersHigh) +
2 + (int)(3 * i)] 2 + (int)(3 * i)]
@@ -155,9 +179,6 @@ void Overworld::DecompressAllMapTiles() {
int tpos = tidD; int tpos = tidD;
if (tpos < tiles32.size()) { if (tpos < tiles32.size()) {
// map16tiles[npos] = new Tile32(tiles32[tpos].tile0,
// tiles32[tpos].tile1, tiles32[tpos].tile2, tiles32[tpos].tile3);
if (i < 64) { if (i < 64) {
allmapsTilesLW[(x * 2) + (sx * 32)][(y * 2) + (sy * 32)] = allmapsTilesLW[(x * 2) + (sx * 32)][(y * 2) + (sy * 32)] =
tiles32[tpos].tile0_; tiles32[tpos].tile0_;
@@ -268,13 +289,13 @@ void Overworld::FetchLargeMaps() {
} }
void Overworld::LoadOverworldMap() { void Overworld::LoadOverworldMap() {
// GFX.overworldMapBitmap = new Bitmap( overworldMapBitmap = new Bitmap(128, 128, overworldMapPointer);
// 128, 128, 128, PixelFormat.Format8bppIndexed, GFX.overworldMapPointer); overworldMapBitmap->Create(&overworldMapTexture);
// GFX.owactualMapBitmap = new Bitmap( owactualMapBitmap = new Bitmap(512, 512, owactualMapPointer);
// 512, 512, 512, PixelFormat.Format8bppIndexed, GFX.owactualMapPointer); owactualMapBitmap->Create(&owactualMapTexture);
// Mode 7 // Mode 7
byte* ptr = (byte*)overworldMapPointer.get(); byte* ptr = overworldMapPointer;
int pos = 0; int pos = 0;
for (int sy = 0; sy < 16; sy++) { for (int sy = 0; sy < 16; sy++) {

View File

@@ -15,25 +15,33 @@ namespace yaze {
namespace Application { namespace Application {
namespace Data { namespace Data {
using ushort = ushort; using ushort = unsigned short;
using byte = unsigned char; using byte = unsigned char;
class Overworld { class Overworld {
public: public:
Overworld() = default; Overworld() = default;
Overworld(Utils::ROM rom); ~Overworld();
void Load(Utils::ROM rom); void Load(Utils::ROM rom);
byte* overworldMapPointer = new byte[0x40000];
Graphics::Bitmap* overworldMapBitmap;
GLuint overworldMapTexture;
byte* owactualMapPointer = new byte[0x40000];
Graphics::Bitmap* owactualMapBitmap;
GLuint owactualMapTexture;
private: private:
Utils::ROM rom_; Utils::ROM rom_;
Utils::ALTTPCompression alttp_compressor_; Utils::ALTTPCompression alttp_compressor_;
int gameState = 1; int gameState = 1;
byte mapParent[160]; byte mapParent[160];
unsigned short **allmapsTilesLW; ushort **allmapsTilesLW; // 64 maps * (32*32 tiles)
std::vector<std::vector<ushort>> allmapsTilesDW; // 64 maps * (32*32 tiles) ushort **allmapsTilesDW; // 64 maps * (32*32 tiles)
std::vector<std::vector<ushort>> allmapsTilesSP; // 32 maps * (32*32 tiles) ushort **allmapsTilesSP; // 32 maps * (32*32 tiles)
std::vector<Graphics::Tile16> tiles16; std::vector<Graphics::Tile16> tiles16;
std::vector<Graphics::Tile32> tiles32; std::vector<Graphics::Tile32> tiles32;
@@ -50,11 +58,6 @@ class Overworld {
Core::Constants::map32TilesTL, Core::Constants::map32TilesTR, Core::Constants::map32TilesTL, Core::Constants::map32TilesTR,
Core::Constants::map32TilesBL, Core::Constants::map32TilesBR}; Core::Constants::map32TilesBL, Core::Constants::map32TilesBR};
std::unique_ptr<int> overworldMapPointer;
Graphics::Bitmap overworldMapBitmap;
std::unique_ptr<int> owactualMapPointer;
Graphics::Bitmap owactualMapBitmap;
enum Dimension { enum Dimension {
map32TilesTL = 0, map32TilesTL = 0,

View File

@@ -7,12 +7,10 @@ namespace Data {
using namespace Core; using namespace Core;
using namespace Graphics; using namespace Graphics;
OverworldMap::OverworldMap(Utils::ROM rom, byte index) OverworldMap::OverworldMap(Utils::ROM rom,
: rom_(rom), index(index), parent(index) { const std::vector<Graphics::Tile16> tiles16,
// gfxBitmap = new Bitmap(512, 512, 512, PixelFormat.Format8bppIndexed, byte index)
// gfxPtr); messageID = (short)ROM.ReadShort(Constants::overworldMessages + : rom_(rom), index(index), tiles16_(tiles16), parent(index) {
// (parent * 2));
if (index != 0x80) { if (index != 0x80) {
if (index <= 150) { if (index <= 150) {
if (rom_.GetRawData()[Constants::overworldMapSize + (index & 0x3F)] != if (rom_.GetRawData()[Constants::overworldMapSize + (index & 0x3F)] !=
@@ -105,15 +103,16 @@ OverworldMap::OverworldMap(Utils::ROM rom, byte index)
} }
} }
void OverworldMap::BuildMap(byte* mapParent, int count, int gameState) { void OverworldMap::BuildMap(byte* mapParent, int count, int gameState,
ushort** allmapsTilesLW, ushort** allmapsTilesDW,
ushort** allmapsTilesSP) {
tilesUsed = new ushort*[32];
for (int i = 0; i < 32; i++) tilesUsed[i] = new ushort;
if (largeMap) { if (largeMap) {
this->parent = mapParent[index]; this->parent = mapParent[index];
if (parent != index) { if (parent != index) {
// sprgfx[0] = rom_.GetRawData()[Constants::overworldSpriteset + parent];
// sprgfx[1] = rom_.GetRawData()[Constants::overworldSpriteset + parent +
// 64]; sprgfx[2] = rom_.GetRawData()[Constants::overworldSpriteset +
// parent + 128];
if (!firstLoad) { if (!firstLoad) {
gfx = rom_.GetRawData()[Constants::mapGfx + parent]; gfx = rom_.GetRawData()[Constants::mapGfx + parent];
palette = rom_.GetRawData()[Constants::overworldMapPalette + parent]; palette = rom_.GetRawData()[Constants::overworldMapPalette + parent];
@@ -124,21 +123,19 @@ void OverworldMap::BuildMap(byte* mapParent, int count, int gameState) {
BuildTileset(gameState); BuildTileset(gameState);
BuildTiles16Gfx(count); // build on GFX.mapgfx16Ptr BuildTiles16Gfx(count); // build on GFX.mapgfx16Ptr
//LoadPalette(); // LoadPalette();
int world = 0; int world = 0;
// fix !! if (index < 64) {
/* if (index < 64) { tilesUsed = allmapsTilesLW;
tilesUsed = ow_.allmapsTilesLW; } else if (index < 128 && index >= 64) {
} tilesUsed = allmapsTilesDW;
else if (index < 128 && index >= 64) {
tilesUsed = ow_.allmapsTilesDW.data();
world = 1; world = 1;
} else { } else {
tilesUsed = ow_.allmapsTilesSP.data(); tilesUsed = allmapsTilesSP;
world = 2; world = 2;
} */ }
int superY = ((index - (world * 64)) / 8); int superY = ((index - (world * 64)) / 8);
int superX = index - (world * 64) - (superY * 8); int superX = index - (world * 64) - (superY * 8);
@@ -146,15 +143,13 @@ void OverworldMap::BuildMap(byte* mapParent, int count, int gameState) {
for (int y = 0; y < 32; y++) { for (int y = 0; y < 32; y++) {
for (int x = 0; x < 32; x++) { for (int x = 0; x < 32; x++) {
CopyTile8bpp16((x * 16), (y * 16), CopyTile8bpp16((x * 16), (y * 16),
tilesUsed[x + (superX * 32)][y + (superY * 32)], tilesUsed[x + (superX * 32)][y + (superY * 32)], gfxPtr,
gfxPtr.get(), // fix mapblockset16);
mapblockset16.get()); // fix
} }
} }
} }
void OverworldMap::CopyTile8bpp16(int x, int y, int tile, void OverworldMap::CopyTile8bpp16(int x, int y, int tile, int* destbmpPtr,
int* destbmpPtr,
int* sourcebmpPtr) { int* sourcebmpPtr) {
int sourceY = (tile / 8); int sourceY = (tile / 8);
int sourceX = (tile) - ((sourceY)*8); int sourceX = (tile) - ((sourceY)*8);
@@ -163,7 +158,7 @@ void OverworldMap::CopyTile8bpp16(int x, int y, int tile,
byte* sourcePtr = (byte*)sourcebmpPtr; byte* sourcePtr = (byte*)sourcebmpPtr;
int destPtrPos = (x + (y * 512)); int destPtrPos = (x + (y * 512));
byte* destPtr = (byte*) destbmpPtr; byte* destPtr = (byte*)destbmpPtr;
for (int ystrip = 0; ystrip < 16; ystrip++) { for (int ystrip = 0; ystrip < 16; ystrip++) {
for (int xstrip = 0; xstrip < 16; xstrip++) { for (int xstrip = 0; xstrip < 16; xstrip++) {
@@ -174,22 +169,17 @@ void OverworldMap::CopyTile8bpp16(int x, int y, int tile,
} }
void OverworldMap::CopyTile8bpp16From8(int xP, int yP, int tileID, void OverworldMap::CopyTile8bpp16From8(int xP, int yP, int tileID,
int* destbmpPtr, int* destbmpPtr, int* sourcebmpPtr) {
int* sourcebmpPtr) { auto gfx16Data = (byte*)destbmpPtr;
auto gfx16Data = (byte*) destbmpPtr;
auto gfx8Data = new byte[(128 * 512) / 2]; auto gfx8Data = currentOWgfx16Ptr;
// (byte*)
// GFX.currentOWgfx16Ptr.ToPointer()
int offsets[] = {0, 8, 4096, 4104}; int offsets[] = {0, 8, 4096, 4104};
//auto tiles = ow_.tiles16[tileID]; auto tiles = tiles16_[tileID];
auto tiles = nullptr;
for (auto tile = 0; tile < 4; tile++) { for (auto tile = 0; tile < 4; tile++) {
//TileInfo info = tiles.tiles_info[tile]; TileInfo info = tiles.tiles_info[tile];
TileInfo info;
int offset = offsets[tile]; int offset = offsets[tile];
for (auto y = 0; y < 8; y++) { for (auto y = 0; y < 8; y++) {
@@ -201,11 +191,9 @@ void OverworldMap::CopyTile8bpp16From8(int xP, int yP, int tileID,
} }
void OverworldMap::BuildTiles16Gfx(int count) { void OverworldMap::BuildTiles16Gfx(int count) {
auto gfx16Data = new byte[1024]; byte* gfx16Data = (byte*)mapblockset16;
// (byte*)GFX.mapblockset16.get(); //(byte*)allgfx8Ptr.ToPointer(); byte* gfx8Data = currentOWgfx16Ptr;
auto gfx8Data = new byte [1024];
// (byte*)
// GFX.currentOWgfx16Ptr.get(); //(byte*)allgfx16Ptr.ToPointer();
int offsets[] = {0, 8, 1024, 1032}; int offsets[] = {0, 8, 1024, 1032};
auto yy = 0; auto yy = 0;
auto xx = 0; auto xx = 0;
@@ -213,12 +201,11 @@ void OverworldMap::BuildTiles16Gfx(int count) {
for (auto i = 0; i < count; i++) // number of tiles16 3748? for (auto i = 0; i < count; i++) // number of tiles16 3748?
{ {
// 8x8 tile draw // 8x8 tile draw
// gfx8 = 4bpp so everyting is /2 // gfx8 = 4bpp so everyting is /2F
// auto tiles = ow_.tiles16[i]; auto tiles = tiles16_[i];
for (auto tile = 0; tile < 4; tile++) { for (auto tile = 0; tile < 4; tile++) {
//TileInfo info = ow_.tiles16[i].tiles_info[tile]; TileInfo info = tiles16_[i].tiles_info[tile];
TileInfo info;
int offset = offsets[tile]; int offset = offsets[tile];
for (auto y = 0; y < 8; y++) { for (auto y = 0; y < 8; y++) {
@@ -286,7 +273,7 @@ void OverworldMap::CopyTileToMap(int x, int y, int xx, int yy, int offset,
gfx16Pointer[index + r] = (byte)(((pixel >> 4) & 0x0F) + tile.palette_ * 16); gfx16Pointer[index + r] = (byte)(((pixel >> 4) & 0x0F) + tile.palette_ * 16);
} }
/* /*
void OverworldMap::LoadPalette() { void OverworldMap::LoadPalette() {
int previousPalId = 0; int previousPalId = 0;
int previousSprPalId = 0; int previousSprPalId = 0;
@@ -615,12 +602,12 @@ void OverworldMap::BuildTileset(int gameState) {
staticgfx[7] = 91; staticgfx[7] = 91;
} }
byte* currentmapgfx8Data = new byte [1024]; byte* currentmapgfx8Data = new byte[(128 * 512) / 2];
// (byte*)GFX.currentOWgfx16Ptr.ToPointer(); // loaded gfx for the current // (byte*)GFX.currentOWgfx16Ptr.ToPointer(); // loaded gfx for the current
// // map (empty at this point) // // map (empty at this point)
byte* allgfxData = new byte [1024]; byte* allgfxData = new byte[(128 * 7136) / 2];
// (byte*)GFX.allgfx16Ptr // (byte*)GFX.allgfx16Ptr
// .ToPointer(); // all gfx of the game pack of 2048 bytes (4bpp) // .ToPointer(); // all gfx of the game pack of 2048 bytes (4bpp)
for (int i = 0; i < 16; i++) { for (int i = 0; i < 16; i++) {
for (int j = 0; j < 2048; j++) { for (int j = 0; j < 2048; j++) {

View File

@@ -26,19 +26,22 @@ class OverworldMap {
byte sprpalette[3]; byte sprpalette[3];
byte musics[4]; byte musics[4];
// 512 * 512 int* gfxPtr = new int[512 * 512];
std::unique_ptr<int> gfxPtr; int* mapblockset16 = new int[1048576];
std::unique_ptr<int> mapblockset16; Graphics::Bitmap mapblockset16Bitmap;
// Bitmap gfxBitmap; // Needs to be removed Graphics::Bitmap gfxBitmap;
byte staticgfx[16]; // Need to be used to display map and not pre render it! byte* staticgfx = new byte[16]; // Need to be used to display map and not pre render it!
ushort** tilesUsed; ushort** tilesUsed;
bool needRefresh = false; bool needRefresh = false;
Utils::ROM rom_; Utils::ROM rom_;
OverworldMap(Utils::ROM rom, byte index); byte *currentOWgfx16Ptr = new byte[(128 * 512) / 2];
void BuildMap(byte* mapParent, int count, int gameState); std::vector<Graphics::Tile16> tiles16_;
OverworldMap(Utils::ROM rom, const std::vector<Graphics::Tile16> tiles16, byte index);
void BuildMap(byte* mapParent, int count, int gameState, ushort** allmapsTilesLW, ushort** allmapsTilesDW, ushort** allmapsTilesSP);
void CopyTile8bpp16(int x, int y, int tile, int* destbmpPtr, void CopyTile8bpp16(int x, int y, int tile, int* destbmpPtr,
int* sourcebmpPtr); int* sourcebmpPtr);
void CopyTile8bpp16From8(int xP, int yP, int tileID, int* destbmpPtr, void CopyTile8bpp16From8(int xP, int yP, int tileID, int* destbmpPtr,
@@ -50,16 +53,15 @@ class OverworldMap {
void CopyTile(int x, int y, int xx, int yy, int offset, void CopyTile(int x, int y, int xx, int yy, int offset,
Graphics::TileInfo tile, byte* gfx16Pointer, byte* gfx8Pointer); Graphics::TileInfo tile, byte* gfx16Pointer, byte* gfx8Pointer);
void CopyTileToMap(int x, int y, int xx, int yy, int offset, void CopyTileToMap(int x, int y, int xx, int yy, int offset,
Graphics::TileInfo tile, byte* gfx16Pointer, Graphics::TileInfo tile, byte* gfx16Pointer,
byte* gfx8Pointer); byte* gfx8Pointer);
/* void LoadPalette(); void LoadPalette();
void SetColorsPalette(int index, ImVec4 main, ImVec4 animated, ImVec4 aux1, void SetColorsPalette(int index, ImVec4 main, ImVec4 animated, ImVec4 aux1,
ImVec4 aux2, ImVec4 hud, ImVec4 bgrcolor, ImVec4 spr, ImVec4 aux2, ImVec4 hud, ImVec4 bgrcolor, ImVec4 spr,
ImVec4 spr2); */ ImVec4 spr2);
void BuildTileset(int gameState); void BuildTileset(int gameState);
}; };

View File

@@ -21,12 +21,20 @@ void Editor::UpdateScreen() {
} }
DrawYazeMenu(); DrawYazeMenu();
if (isLoaded) {
if (!doneLoaded) {
overworld.Load(rom);
overworld_texture = &overworld.owactualMapTexture;
doneLoaded = true;
}
ImGui::Image((void*)(intptr_t)overworld_texture, ImVec2(overworld.overworldMapBitmap->GetWidth(), overworld.overworldMapBitmap->GetHeight()));
}
if (ImGui::BeginTabBar("##TabBar")) { if (ImGui::BeginTabBar("##TabBar")) {
DrawOverworldEditor(); DrawOverworldEditor();
ImGui::EndTabBar(); ImGui::EndTabBar();
} }
// ImGui::ShowDemoWindow();
ImGui::ShowDemoWindow();
ImGui::End(); ImGui::End();
} }
@@ -52,6 +60,7 @@ void Editor::DrawYazeMenu() {
std::string filePathName = ImGuiFileDialog::Instance()->GetFilePathName(); std::string filePathName = ImGuiFileDialog::Instance()->GetFilePathName();
std::string filePath = ImGuiFileDialog::Instance()->GetCurrentPath(); std::string filePath = ImGuiFileDialog::Instance()->GetCurrentPath();
rom.LoadFromFile(filePathName); rom.LoadFromFile(filePathName);
isLoaded = true;
} }
// close // close
@@ -145,10 +154,6 @@ void Editor::DrawOverworldEditor() {
static bool adding_line = false; static bool adding_line = false;
ImGui::Checkbox("Enable grid", &opt_enable_grid); ImGui::Checkbox("Enable grid", &opt_enable_grid);
ImGui::Checkbox("Enable context menu", &opt_enable_context_menu);
ImGui::Text(
"Mouse Left: drag to add lines,\nMouse Right: drag to scroll, click "
"for context menu.");
ImVec2 canvas_p0 = ImVec2 canvas_p0 =
ImGui::GetCursorScreenPos(); // ImDrawList API uses screen coordinates! ImGui::GetCursorScreenPos(); // ImDrawList API uses screen coordinates!

View File

@@ -27,6 +27,9 @@ class Editor {
void DrawOverworldEditor(); void DrawOverworldEditor();
bool isLoaded = false;
bool doneLoaded = false;
GLuint *overworld_texture;
Data::Overworld overworld; Data::Overworld overworld;
Utils::ROM rom; Utils::ROM rom;
}; };

View File

@@ -4,7 +4,53 @@ namespace yaze {
namespace Application { namespace Application {
namespace Graphics { namespace Graphics {
Bitmap::Bitmap() {} Bitmap::Bitmap(int width, int height, byte* data)
: width_(width), height_(height), pixel_data_(data) {}
void Bitmap::Create(GLuint* out_texture) {
// // Read the pixel data from the ROM
// SDL_RWops * src = SDL_RWFromMem(pixel_data_, 0);
// // Create the surface from that RW stream
// SDL_Surface* surface = SDL_LoadBMP_RW(src, SDL_FALSE);
// GLenum mode = 0;
// Uint8 bpp = surface->format->BytesPerPixel;
// Uint32 rm = surface->format->Rmask;
// if (bpp == 3 && rm == 0x000000ff) mode = GL_RGB;
// if (bpp == 3 && rm == 0x00ff0000) mode = GL_BGR;
// if (bpp == 4 && rm == 0x000000ff) mode = GL_RGBA;
// if (bpp == 4 && rm == 0xff000000) mode = GL_BGRA;
// GLsizei width = surface->w;
// GLsizei height = surface->h;
// GLenum format = mode;
// GLvoid* pixels = surface->pixels;
// Create a OpenGL texture identifier
GLuint image_texture;
glGenTextures(1, &image_texture);
glBindTexture(GL_TEXTURE_2D, image_texture);
// Setup filtering parameters for display
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
// Upload pixels into texture
#if defined(GL_UNPACK_ROW_LENGTH) && !defined(__EMSCRIPTEN__)
glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
#endif
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width_, height_, 0, GL_RGBA,
GL_UNSIGNED_BYTE, pixel_data_);
*out_texture = image_texture;
}
int Bitmap::GetWidth() {
return width_;
}
int Bitmap::GetHeight() {
return height_;
}
// Simple helper function to load an image into a OpenGL texture with common // Simple helper function to load an image into a OpenGL texture with common
// settings // settings

View File

@@ -1,20 +1,37 @@
#ifndef YAZE_APPLICATION_UTILS_BITMAP_H #ifndef YAZE_APPLICATION_UTILS_BITMAP_H
#define YAZE_APPLICATION_UTILS_BITMAP_H #define YAZE_APPLICATION_UTILS_BITMAP_H
#include "GL/glew.h" #include <SDL2/SDL.h>
#include <SDL2/SDL_opengl.h> // #include <SDL2/SDL_opengl.h>
#include <memory>
#include "GL/glew.h"
#include "Utils/ROM.h" #include "Utils/ROM.h"
namespace yaze { namespace yaze {
namespace Application { namespace Application {
namespace Graphics { namespace Graphics {
using byte = unsigned char;
class Bitmap { class Bitmap {
public: public:
Bitmap(); Bitmap()=default;
Bitmap(int width, int height, byte* data);
void Create(GLuint* out_texture);
int GetWidth();
int GetHeight();
bool LoadBitmapFromROM(unsigned char* texture_data, GLuint* out_texture, bool LoadBitmapFromROM(unsigned char* texture_data, GLuint* out_texture,
int* out_width, int* out_height); int* out_width, int* out_height);
private:
int width_;
int height_;
byte* pixel_data_;
SDL_PixelFormat pixel_format_;
}; };
} // namespace Graphics } // namespace Graphics
} // namespace Application } // namespace Application

View File

@@ -33,27 +33,27 @@ namespace yaze {
namespace Application { namespace Application {
namespace Utils { namespace Utils {
char* ALTTPCompression::DecompressGfx(const char* c_data, unsigned char* ALTTPCompression::DecompressGfx(const unsigned char* c_data,
const unsigned int start, const unsigned int start,
unsigned int max_length, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* uncompressed_data_size,
unsigned int* compressed_length) { unsigned int* compressed_length) {
char* toret = std_nintendo_.Decompress(c_data, start, max_length, unsigned char* toret = std_nintendo_.Decompress(c_data, start, max_length,
uncompressed_data_size, uncompressed_data_size,
compressed_length, D_NINTENDO_C_MODE2); compressed_length, D_NINTENDO_C_MODE2);
return toret; return toret;
} }
char* ALTTPCompression::DecompressOverworld( unsigned char* ALTTPCompression::DecompressOverworld(
const char* c_data, const unsigned int start, unsigned int max_length, const unsigned char* c_data, const unsigned int start, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* compressed_length) { unsigned int* uncompressed_data_size, unsigned int* compressed_length) {
char* toret = std_nintendo_.Decompress(c_data, start, max_length, unsigned char* toret = std_nintendo_.Decompress(c_data, start, max_length,
uncompressed_data_size, uncompressed_data_size,
compressed_length, D_NINTENDO_C_MODE1); compressed_length, D_NINTENDO_C_MODE1);
return toret; return toret;
} }
char* ALTTPCompression::CompressGfx(const char* u_data, unsigned char* ALTTPCompression::CompressGfx(const unsigned char* u_data,
const unsigned int start, const unsigned int start,
const unsigned int length, const unsigned int length,
unsigned int* compressed_size) { unsigned int* compressed_size) {
@@ -61,7 +61,7 @@ char* ALTTPCompression::CompressGfx(const char* u_data,
D_NINTENDO_C_MODE2); D_NINTENDO_C_MODE2);
} }
char* ALTTPCompression::CompressOverworld(const char* u_data, unsigned char* ALTTPCompression::CompressOverworld(const unsigned char* u_data,
const unsigned int start, const unsigned int start,
const unsigned int length, const unsigned int length,
unsigned int* compressed_size) { unsigned int* compressed_size) {
@@ -76,13 +76,13 @@ char* ALTTPCompression::CompressOverworld(const char* u_data,
* Then you have a new header byte and so on, until you hit a header with the * Then you have a new header byte and so on, until you hit a header with the
* value FF * value FF
*/ */
char* StdNintendoCompression::Decompress(const char* c_data, unsigned char* StdNintendoCompression::Decompress(const unsigned char* c_data,
const unsigned int start, const unsigned int start,
unsigned int max_length, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* uncompressed_data_size,
unsigned int* compressed_length, unsigned int* compressed_length,
char mode) { char mode) {
char* u_data; unsigned char* u_data;
unsigned char header; unsigned char header;
unsigned int c_data_pos; unsigned int c_data_pos;
unsigned int u_data_pos; unsigned int u_data_pos;
@@ -93,7 +93,7 @@ char* StdNintendoCompression::Decompress(const char* c_data,
if (max_length != 0) max_offset = start + max_length; if (max_length != 0) max_offset = start + max_length;
header = c_data[start]; header = c_data[start];
u_data = u_data =
(char*)malloc(INITIAL_ALLOC_SIZE); // No way to know the final size, we (unsigned char*)malloc(INITIAL_ALLOC_SIZE); // No way to know the final size, we
// will probably realloc if needed // will probably realloc if needed
allocated_memory = INITIAL_ALLOC_SIZE; allocated_memory = INITIAL_ALLOC_SIZE;
u_data_pos = 0; u_data_pos = 0;
@@ -120,9 +120,9 @@ char* StdNintendoCompression::Decompress(const char* c_data,
// length value starts at 0, 0 is 1 // length value starts at 0, 0 is 1
length++; length++;
printf("%d[%d]", command, length); // printf("%d[%d]", command, length);
printf("header %02X - Command : %d , length : %d\n", header, command, // printf("header %02X - Command : %d , length : %d\n", header, command,
length); // length);
if (c_data_pos >= max_offset && max_offset != 0) { if (c_data_pos >= max_offset && max_offset != 0) {
decompression_error_ = decompression_error_ =
"Compression string exceed the max_length specified"; "Compression string exceed the max_length specified";
@@ -133,7 +133,7 @@ char* StdNintendoCompression::Decompress(const char* c_data,
{ {
printf("Memory get reallocated by %d was %d\n", INITIAL_ALLOC_SIZE, printf("Memory get reallocated by %d was %d\n", INITIAL_ALLOC_SIZE,
allocated_memory); allocated_memory);
u_data = (char*)realloc(u_data, allocated_memory + INITIAL_ALLOC_SIZE); u_data = (unsigned char*)realloc(u_data, allocated_memory + INITIAL_ALLOC_SIZE);
if (u_data == NULL) { if (u_data == NULL) {
decompression_error_ = "Can't realloc memory"; decompression_error_ = "Can't realloc memory";
return NULL; return NULL;
@@ -198,7 +198,7 @@ char* StdNintendoCompression::Decompress(const char* c_data,
printf("Memory get reallocated by a copy, %d was %d\n", printf("Memory get reallocated by a copy, %d was %d\n",
INITIAL_ALLOC_SIZE, allocated_memory); INITIAL_ALLOC_SIZE, allocated_memory);
u_data = u_data =
(char*)realloc(u_data, allocated_memory + INITIAL_ALLOC_SIZE); (unsigned char*)realloc(u_data, allocated_memory + INITIAL_ALLOC_SIZE);
if (u_data == NULL) { if (u_data == NULL) {
decompression_error_ = "Can't realloc memory"; decompression_error_ = "Can't realloc memory";
return NULL; return NULL;
@@ -306,7 +306,7 @@ StdNintendoCompression::merge_copy(CompressionComponent* start) {
} }
unsigned int StdNintendoCompression::create_compression_string( unsigned int StdNintendoCompression::create_compression_string(
CompressionComponent* start, char* output, char mode) { CompressionComponent* start, unsigned char* output, char mode) {
unsigned int pos = 0; unsigned int pos = 0;
CompressionComponent* piece = start; CompressionComponent* piece = start;
@@ -386,13 +386,13 @@ unsigned int StdNintendoCompression::create_compression_string(
// TODO TEST compressed data border for each cmd // TODO TEST compressed data border for each cmd
char* StdNintendoCompression::Compress(const char* u_data, unsigned char* StdNintendoCompression::Compress(const unsigned char* u_data,
const unsigned int start, const unsigned int start,
const unsigned int length, const unsigned int length,
unsigned int* compressed_size, unsigned int* compressed_size,
char mode) { char mode) {
// we will realloc later // we will realloc later
char* compressed_data = (char*)malloc( unsigned char* compressed_data = (unsigned char*)malloc(
length + length +
10); // Worse case should be a copy of the string with extended header 10); // Worse case should be a copy of the string with extended header
CompressionComponent* compressed_chain = CreateComponent(1, 1, "aaa", 2); CompressionComponent* compressed_chain = CreateComponent(1, 1, "aaa", 2);
@@ -561,12 +561,12 @@ char* StdNintendoCompression::Compress(const char* u_data,
if (std_nintendo_compression_sanity_check && if (std_nintendo_compression_sanity_check &&
compressed_chain_start->next != NULL) { compressed_chain_start->next != NULL) {
// We don't call merge copy so we need more space // We don't call merge copy so we need more space
char* tmp = (char*)malloc(length * 2); unsigned char* tmp = (unsigned char*) malloc(length * 2);
*compressed_size = *compressed_size =
create_compression_string(compressed_chain_start->next, tmp, mode); create_compression_string(compressed_chain_start->next, tmp, mode);
unsigned int p; unsigned int p;
unsigned int k; unsigned int k;
char* uncomp = Decompress(tmp, 0, 0, &p, &k, mode); unsigned char* uncomp = Decompress(tmp, 0, 0, &p, &k, mode);
if (uncomp == NULL) { if (uncomp == NULL) {
fprintf(stderr, "%s\n", decompression_error_); fprintf(stderr, "%s\n", decompression_error_);
return NULL; return NULL;

View File

@@ -26,7 +26,7 @@ class StdNintendoCompression {
* of the define for it: D_NINTENDO_C_MODEX... 1 is is SMW, 2 is zelda3 gfx * of the define for it: D_NINTENDO_C_MODEX... 1 is is SMW, 2 is zelda3 gfx
*/ */
char* Decompress(const char* c_data, const unsigned int start, unsigned char* Decompress(const unsigned char* c_data, const unsigned int start,
unsigned int max_length, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* uncompressed_data_size,
unsigned int* compressed_length, char mode); unsigned int* compressed_length, char mode);
@@ -41,7 +41,7 @@ class StdNintendoCompression {
* mode is the variation of the compression. * mode is the variation of the compression.
*/ */
char* Compress(const char* u_data, const unsigned int start, unsigned char* Compress(const unsigned char* u_data, const unsigned int start,
const unsigned int length, unsigned int* compressed_size, const unsigned int length, unsigned int* compressed_size,
char mode); char mode);
@@ -69,7 +69,7 @@ class StdNintendoCompression {
void DestroyChain(CompressionComponent* piece); void DestroyChain(CompressionComponent* piece);
CompressionComponent* merge_copy(CompressionComponent* start); CompressionComponent* merge_copy(CompressionComponent* start);
unsigned int create_compression_string(CompressionComponent* start, unsigned int create_compression_string(CompressionComponent* start,
char* output, char mode); unsigned char* output, char mode);
}; };
class ALTTPCompression { class ALTTPCompression {
@@ -86,16 +86,16 @@ class ALTTPCompression {
* compressed_length is the length of the compressed data, meaning the number * compressed_length is the length of the compressed data, meaning the number
* of bytes read in c_data. * of bytes read in c_data.
*/ */
char* Decompress(const char* c_data, const unsigned int start, unsigned char* Decompress(const unsigned char* c_data, const unsigned int start,
unsigned int max_length, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* uncompressed_data_size,
unsigned int* compressed_length, char mode); unsigned int* compressed_length, char mode);
char* DecompressGfx(const char* c_data, const unsigned int start, unsigned char* DecompressGfx(const unsigned char* c_data, const unsigned int start,
unsigned int max_length, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* uncompressed_data_size,
unsigned int* compressed_length); unsigned int* compressed_length);
char* DecompressOverworld(const char* c_data, const unsigned int start, unsigned char* DecompressOverworld(const unsigned char* c_data, const unsigned int start,
unsigned int max_length, unsigned int max_length,
unsigned int* uncompressed_data_size, unsigned int* uncompressed_data_size,
unsigned int* compressed_length); unsigned int* compressed_length);
@@ -109,13 +109,13 @@ class ALTTPCompression {
* length is the length of u_data to compress * length is the length of u_data to compress
* compressed_size is the resulting size of the compressed string. * compressed_size is the resulting size of the compressed string.
*/ */
char* Compress(const char* u_data, const unsigned int start, unsigned char* Compress(const unsigned char* u_data, const unsigned int start,
const unsigned int length, unsigned int* compressed_size, const unsigned int length, unsigned int* compressed_size,
char mode); char mode);
char* CompressGfx(const char* u_data, const unsigned int start, unsigned char* CompressGfx(const unsigned char* u_data, const unsigned int start,
const unsigned int length, unsigned int* compressed_size); const unsigned int length, unsigned int* compressed_size);
char* CompressOverworld(const char* u_data, const unsigned int start, unsigned char* CompressOverworld(const unsigned char* u_data, const unsigned int start,
const unsigned int length, const unsigned int length,
unsigned int* compressed_size); unsigned int* compressed_size);

View File

@@ -7,23 +7,21 @@ namespace Utils {
using namespace Graphics; using namespace Graphics;
void ROM::LoadFromFile(const std::string& path) { void ROM::LoadFromFile(const std::string& path) {
std::cout << "filename: " << path << std::endl;
std::ifstream stream(path, std::ios::in | std::ios::binary);
if (!stream.good()) { FILE * file = fopen(path.c_str(), "r+");
std::cout << "failure reading file" << std::endl; if (file == NULL) return;
return; fseek(file, 0, SEEK_END);
} long int size = ftell(file);
fclose(file);
std::vector<char> contents((std::istreambuf_iterator<char>(stream)), std::cout << "size: " << size << std::endl;
std::istreambuf_iterator<char>());
for (auto i : contents) { // Reading data to array of unsigned chars
int value = i; file = fopen(path.c_str(), "r+");
std::cout << "working_rom_: " << value << std::endl; current_rom_ = (unsigned char *) malloc(size);
} int bytes_read = fread(current_rom_, sizeof(unsigned char), size, file);
fclose(file);
std::cout << "file size: " << contents.size() << std::endl;
} }
int ROM::SnesToPc(int addr) { int ROM::SnesToPc(int addr) {
@@ -60,44 +58,44 @@ short ROM::AddressFromBytes(byte addr1, byte addr2) {
return (short)((addr1 << 8) | (addr2)); return (short)((addr1 << 8) | (addr2));
} }
void ROM::Write(int addr, byte value) { working_rom_[addr] = value; } void ROM::Write(int addr, byte value) { current_rom_[addr] = value; }
void ROM::WriteLong(int addr, int value) { void ROM::WriteLong(int addr, int value) {
working_rom_[addr] = (byte)(value & 0xFF); current_rom_[addr] = (byte)(value & 0xFF);
working_rom_[addr + 1] = (byte)((value >> 8) & 0xFF); current_rom_[addr + 1] = (byte)((value >> 8) & 0xFF);
working_rom_[addr + 2] = (byte)((value >> 16) & 0xFF); current_rom_[addr + 2] = (byte)((value >> 16) & 0xFF);
} }
void ROM::WriteShort(int addr, int value) { void ROM::WriteShort(int addr, int value) {
working_rom_[addr] = (byte)(value & 0xFF); current_rom_[addr] = (byte)(value & 0xFF);
working_rom_[addr + 1] = (byte)((value >> 8) & 0xFF); current_rom_[addr + 1] = (byte)((value >> 8) & 0xFF);
} }
int ROM::ReadLong(int addr) { int ROM::ReadLong(int addr) {
return ((working_rom_[addr + 2] << 16) + (working_rom_[addr + 1] << 8) + return ((current_rom_[addr + 2] << 16) + (current_rom_[addr + 1] << 8) +
working_rom_[addr]); current_rom_[addr]);
} }
Tile16 ROM::ReadTile16(int addr) { Tile16 ROM::ReadTile16(int addr) {
ushort t1 = (ushort)((working_rom_[addr + 1] << 8) + working_rom_[addr]); ushort t1 = (ushort)((current_rom_[addr + 1] << 8) + current_rom_[addr]);
ushort t2 = (ushort)((working_rom_[addr + 3] << 8) + working_rom_[addr + 2]); ushort t2 = (ushort)((current_rom_[addr + 3] << 8) + current_rom_[addr + 2]);
ushort t3 = (ushort)((working_rom_[addr + 5] << 8) + working_rom_[addr + 4]); ushort t3 = (ushort)((current_rom_[addr + 5] << 8) + current_rom_[addr + 4]);
ushort t4 = (ushort)((working_rom_[addr + 7] << 8) + working_rom_[addr + 6]); ushort t4 = (ushort)((current_rom_[addr + 7] << 8) + current_rom_[addr + 6]);
return Tile16((unsigned long)((t1 << 48) + (t2 << 32) + (t3 << 16) + t4)); return Tile16((unsigned long)((t1 << 48) + (t2 << 32) + (t3 << 16) + t4));
} }
ushort ROM::ReadShort(int addr) { ushort ROM::ReadShort(int addr) {
return (ushort)((working_rom_[addr + 1] << 8) + working_rom_[addr]); return (ushort)((current_rom_[addr + 1] << 8) + current_rom_[addr]);
} }
short ROM::ReadRealShort(int addr) { short ROM::ReadRealShort(int addr) {
return (short)((working_rom_[addr + 1] << 8) + working_rom_[addr]); return (short)((current_rom_[addr + 1] << 8) + current_rom_[addr]);
} }
ushort ROM::ReadByte(int addr) { return (ushort)(working_rom_[addr]); } ushort ROM::ReadByte(int addr) { return (ushort)(current_rom_[addr]); }
short ROM::ReadReverseShort(int addr) { short ROM::ReadReverseShort(int addr) {
return (short)((working_rom_[addr] << 8) + working_rom_[addr + 1]); return (short)((current_rom_[addr] << 8) + current_rom_[addr + 1]);
} }
} // namespace Utils } // namespace Utils

View File

@@ -36,11 +36,13 @@ class ROM {
int ReadLong(int addr); int ReadLong(int addr);
void WriteLong(int addr, int value); void WriteLong(int addr, int value);
void LoadFromFile(const std::string& path); void LoadFromFile(const std::string& path);
inline const char* GetRawData() { return working_rom_.data(); } inline byte * GetRawData() { return current_rom_; }
private: private:
std::vector<char> original_rom_; std::vector<char> original_rom_;
std::vector<char> working_rom_; std::vector<char> working_rom_;
byte* current_rom_;
}; };
} // namespace Utils } // namespace Utils