Chaos Project

RPG Maker => RPG Maker Scripts => Script Troubleshooting => Topic started by: Terv on January 17, 2013, 06:48:54 pm

Title: [XP] Import certain classes from RGSS1 dll only
Post by: Terv on January 17, 2013, 06:48:54 pm
Hey,
I currently run my XP game using the Ace engine (Game.exe + RGSS301.dll) and a Ruby rewrite of Tilemap. Now I know that you can load certain functions from dlls only, so would it be possible to load the C++ tilemap class from the RGSS102E.dll manually after start so I don't have to put up with that squishy rewrite?
The problem is that there are micro stutters when wandering on a relatively complex map. I am currently using Poccil's rewrite; if you know any that work better, tell me please  :haha:
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Blizzard on January 18, 2013, 03:26:06 am
Have you tried F0's rewrite? It might work better for you.
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Terv on January 18, 2013, 08:08:41 am
I am using Seph's Rewrite now (SDK (^o^)丿 ), so far there are no problems. Before that I tried to use Zer0's class because I like Zer0 but somehow it didn't work due to dependencies on the custom resolution script.. I guess some small edits are necessary to make it standalone, which I couldn't figure out.
Furthermore there are still Me(tm)'s and RTH's rewrites so I think some of these will suit my needs for sure in case Seph's won't.
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: G_G on January 18, 2013, 08:37:59 am
Just use Zer0's full Custom Resolution script and just don't change the resolution. And it wouldn't be hard to make those edits to make it so it wouldn't require any dependencies. Honestly, out of all the rewrites I've seen, Zer0's has probably been one of the best in my opinion.
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Blizzard on January 18, 2013, 09:33:45 am
WHAT ABOUT MY C++ IMPLEMENTATION?! I DON'T LOVE YOU ANYMORE!
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Terv on January 18, 2013, 10:30:31 am
Quote from: Blizzard on January 18, 2013, 09:33:45 am
WHAT ABOUT MY C++ IMPLEMENTATION?! I DON'T LOVE YOU ANYMORE!
Quote from: Blizzard on January 18, 2013, 09:33:45 am
C++
The fuck, link please? How could I miss that?  :facepalm:
Thanks for the tip gameus, I'll switch to Zero's as soon as SDK starts creating errors (which will be in about 1-2 weeks, telling from my experience  :roll:)
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Blizzard on January 18, 2013, 12:36:50 pm
Well, that implementation is for ARC so it's not really publicly available. :P But here is the class' code anyway (not that you can do too much with it). What I said there was meant more of a joke.

Spoiler: ShowHide
#include <ruby.h>

#include <april/RenderSystem.h>
#include <gtypes/Matrix4.h>
#include <gtypes/Rectangle.h>
#include <hltypes/harray.h>
#include <hltypes/hltypesUtil.h>
#include <hltypes/hstring.h>

#include "Bitmap.h"
#include "CodeSnippets.h"
#include "Graphics.h"
#include "RGSSError.h"
#include "SystemSprite.h"
#include "Table.h"
#include "Tilemap.h"
#include "Viewport.h"

#define TILE_SIZE 32

namespace rgss
{
VALUE rb_cTilemap;

static int _autotiles[6][8][4] = {
{{27, 28, 33, 34}, { 5, 28, 33, 34}, {27,  6, 33, 34}, { 5,  6, 33, 34},
{27, 28, 33, 12}, { 5, 28, 33, 12}, {27,  6, 33, 12}, { 5,  6, 33, 12}},
{{27, 28, 11, 34}, { 5, 28, 11, 34}, {27,  6, 11, 34}, { 5,  6, 11, 34},
{27, 28, 11, 12}, { 5, 28, 11, 12}, {27,  6, 11, 12}, { 5,  6, 11, 12}},
{{25, 26, 31, 32}, {25,  6, 31, 32}, {25, 26, 31, 12}, {25,  6, 31, 12},
{15, 16, 21, 22}, {15, 16, 21, 12}, {15, 16, 11, 22}, {15, 16, 11, 12}},
{{29, 30, 35, 36}, {29, 30, 11, 36}, { 5, 30, 35, 36}, { 5, 30, 11, 36},
{39, 40, 45, 46}, { 5, 40, 45, 46}, {39,  6, 45, 46}, { 5,  6, 45, 46}},
{{25, 30, 31, 36}, {15, 16, 45, 46}, {13, 14, 19, 20}, {13, 14, 19, 12},
{17, 18, 23, 24}, {17, 18, 11, 24}, {41, 42, 47, 48}, { 5, 42, 47, 48}},
{{37, 38, 43, 44}, {37,  6, 43, 44}, {13, 18, 19, 24}, {13, 14, 43, 44},
{37, 42, 43, 48}, {17, 18, 47, 48}, {13, 18, 43, 48}, { 1,  2,  7,  8}}
};

/****************************************************************************************
* Construction/Destruction
****************************************************************************************/

Tilemap::Tilemap() : SourceRenderer()
{
this->typeName = "tilemap";
this->rb_autotiles = rb_ary_new3(MAX_AUTOTILES, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil);
this->rb_currentAutotiles = rb_ary_new3(MAX_AUTOTILES, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil);
for_iter (i, 0, MAX_AUTOTILES)
{
this->generatedAutotiles[i] = NULL;
}
this->width = (Graphics::getWidth() + TILE_SIZE - 1) / TILE_SIZE + 1;
this->height = (Graphics::getHeight() + TILE_SIZE - 1) / TILE_SIZE + 1;
this->depth = 0;
this->autotileUpdateCount = 0;
this->rb_mapData = Qnil;
this->mapData = NULL;
this->rb_priorities = Qnil;
this->priorities = NULL;
}

Tilemap::~Tilemap()
{
this->dispose();
foreach (SystemSprite*, it, this->tileSprites)
{
delete (*it);
}
this->tileSprites.clear();
}

void Tilemap::initialize(VALUE rb_viewport)
{
SourceRenderer::initialize(rb_viewport);
this->rb_autotiles = rb_ary_new3(MAX_AUTOTILES, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil);
this->rb_currentAutotiles = rb_ary_new3(MAX_AUTOTILES, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil, Qnil);
for_iter (i, 0, MAX_AUTOTILES)
{
this->generatedAutotiles[i] = NULL;
}
this->width = (Graphics::getWidth() + TILE_SIZE - 1) / TILE_SIZE + 1;
this->height = (Graphics::getHeight() + TILE_SIZE - 1) / TILE_SIZE + 1;
this->depth = 0;
this->autotileUpdateCount = 0;
this->rb_mapData = Qnil;
this->mapData = NULL;
this->rb_priorities = Qnil;
this->priorities = NULL;
}

void Tilemap::dispose()
{
if (!this->disposed)
{
this->rb_autotiles = Qnil;
this->rb_currentAutotiles = Qnil;
this->rb_mapData = Qnil;
this->mapData = NULL;
this->rb_priorities = Qnil;
this->priorities = NULL;
for_iter (i, 0, MAX_AUTOTILES)
{
if (this->generatedAutotiles[i] != NULL)
{
delete this->generatedAutotiles[i];
this->generatedAutotiles[i] = NULL;
}
}
foreach (SystemSprite*, it, this->tileSprites)
{
(*it)->dispose();
}
}
SourceRenderer::dispose();
}

void Tilemap::mark()
{
SourceRenderer::mark();
RB_GC_MARK(autotiles);
RB_GC_MARK(currentAutotiles);
RB_GC_MARK(mapData);
RB_GC_MARK(priorities);
}

/****************************************************************************************
* Pure C++ code
****************************************************************************************/

void Tilemap::update()
{
if (this->mapData == NULL || this->depth != this->mapData->getZSize())
{
foreach (SystemSprite*, it, this->tileSprites)
{
delete (*it);
}
this->tileSprites.clear();
}
if (this->mapData == NULL || this->disposed)
{
return;
}
if (!this->visible)
{
foreach (SystemSprite*, it, this->tileSprites)
{
(*it)->setVisible(false);
}
return;
}
this->depth = this->mapData->getZSize();
if (this->tileSprites.size() == 0)
{
SystemSprite* tileSprite;
int i;
int j;
int k;
for_iterx (k, 0, this->depth)
{
for_iterx (j, 0, this->height)
{
for_iterx (i, 0, this->width)
{
tileSprite = new SystemSprite(this->viewport);
tileSprite->getSrcRect()->set(0, 0, TILE_SIZE, TILE_SIZE);
this->tileSprites += tileSprite;
}
}
}
}
this->_updateAutotiles();
this->_updateTileSprites();
}

void Tilemap::_updateAutotiles()
{
VALUE rb_autotile;
Bitmap* generated;
static VALUE argv1[2] = {INT2FIX(256), INT2FIX(192)};
static VALUE argv2[2] = {INT2FIX(256), INT2FIX(768)};
int position;
int sx;
int sy;
int tx;
int ty;
bool animated;
int x;
int y;
int j;
for_iter (i, 0, MAX_AUTOTILES)
{
rb_autotile = rb_ary_entry(this->rb_autotiles, i);
if (rb_autotile != rb_ary_entry(this->rb_currentAutotiles, i))
{
rb_ary_store(this->rb_currentAutotiles, i, rb_autotile);
if (NIL_P(rb_autotile))
{
if (this->generatedAutotiles[i] != NULL)
{
delete this->generatedAutotiles[i];
this->generatedAutotiles[i] = NULL;
}
continue;
}
generated = this->generatedAutotiles[i];
animated = (NUM2INT(Bitmap::rb_getWidth(rb_autotile)) > 96);
if (generated == NULL)
{
generated = new Bitmap(256, (!animated ? 192 : 768));
this->generatedAutotiles[i] = generated;
}
else
{
generated->clear();
}
RB_VAR2CPP(rb_autotile, Bitmap, autotile);
for_iterx (y, 0, 6)
{
for_iterx (x, 0, 8)
{
for_iterx (j, 0, 4)
{
position = _autotiles[y][x][j] - 1;
tx = x * 32 + j % 2 * 16;
ty = y * 32 + j / 2 * 16;
sx = position % 6 * 16;
sy = position / 6 * 16;
generated->bltOver(tx, ty, autotile, sx, sy, 16, 16);
if (animated)
{
generated->bltOver(tx, ty + 192, autotile, sx + 96, sy, 16, 16);
generated->bltOver(tx, ty + 384, autotile, sx + 192, sy, 16, 16);
generated->bltOver(tx, ty + 576, autotile, sx + 288, sy, 16, 16);
}
}
}
}
}
}
}

void Tilemap::_updateTileSprites()
{
SystemSprite* tileSprite;
int i;
int j;
int k;
int priority;
int tileId;
Bitmap* autotile;
Rect* rect;
for_iterx (k, 0, this->depth)
{
for_iterx (j, 0, this->height)
{
for_iterx (i, 0, this->width)
{
tileSprite = this->tileSprites[i + this->width * (j + this->height * k)];
tileId = this->mapData->getCircularData(
-this->ox / TILE_SIZE + i, -this->oy / TILE_SIZE + j, k);
tileSprite->setX(this->ox % TILE_SIZE + i * TILE_SIZE);
tileSprite->setY(this->oy % TILE_SIZE + j * TILE_SIZE);
if (tileId < 48)
{
tileSprite->setVisible(false);
}
else
{
tileSprite->setVisible(true);
rect = tileSprite->getSrcRect();
if (tileId >= 384)
{
tileSprite->setBitmap(this->bitmap);
rect->x = ((tileId - 384) % 8) * TILE_SIZE;
rect->y = ((tileId - 384) / 8) * TILE_SIZE;
}
else
{
autotile = this->generatedAutotiles[(tileId / 48) - 1];
tileSprite->setBitmap(autotile);
rect->x = (tileId % 8) * TILE_SIZE;
rect->y = ((tileId % 48) / 8) * TILE_SIZE;
if (autotile->getHeight() > 192)
{
rect->y += this->autotileUpdateCount / 16 * 192;
}
}
}
priority = this->priorities->getData(tileId);
if (priority > 0)
{
tileSprite->setZ(tileSprite->getY() + (priority + 1) * TILE_SIZE - 1);
}
else
{
tileSprite->setZ(0);
}
}
}
}
}

/****************************************************************************************
* Ruby Interfacing, Creation, Destruction, Systematics
****************************************************************************************/

void Tilemap::init()
{
}

void Tilemap::destroy()
{
}

void Tilemap::createRubyInterface()
{
rb_cTilemap = rb_define_class("Tilemap", rb_cObject);
rb_define_alloc_func(rb_cTilemap, &Tilemap::rb_new);
// initialize
rb_define_method(rb_cTilemap, "initialize", RUBY_METHOD_FUNC(&Tilemap::rb_initialize), -1);
rb_define_method(rb_cTilemap, "initialize_clone", RUBY_METHOD_FUNC(&Tilemap::rb_initialize_clone), 1);
rb_define_method(rb_cTilemap, "initialize_dup", RUBY_METHOD_FUNC(&Tilemap::rb_initialize_dup), 1);
rb_define_method(rb_cTilemap, "dispose", RUBY_METHOD_FUNC(&Tilemap::rb_dispose), 0);
rb_define_method(rb_cTilemap, "_arc_dump", RUBY_METHOD_FUNC(&Tilemap::rb_arcDump), 0);
// getters and setters (Renderable) (except "z" and "z=")
rb_define_method(rb_cTilemap, "visible", RUBY_METHOD_FUNC(&Tilemap::rb_getVisible), 0);
rb_define_method(rb_cTilemap, "visible=", RUBY_METHOD_FUNC(&Tilemap::rb_setVisible), 1);
rb_define_method(rb_cTilemap, "ox", RUBY_METHOD_FUNC(&Tilemap::rb_getOX), 0);
rb_define_method(rb_cTilemap, "ox=", RUBY_METHOD_FUNC(&Tilemap::rb_setOX), 1);
rb_define_method(rb_cTilemap, "oy", RUBY_METHOD_FUNC(&Tilemap::rb_getOY), 0);
rb_define_method(rb_cTilemap, "oy=", RUBY_METHOD_FUNC(&Tilemap::rb_setOY), 1);
rb_define_method(rb_cTilemap, "disposed?", RUBY_METHOD_FUNC(&Tilemap::rb_isDisposed), 0);
// getters and setters (SourceRenderer) (except "opacity" and "opacity=")
rb_define_method(rb_cTilemap, "viewport", RUBY_METHOD_FUNC(&Tilemap::rb_getViewport), 0);
rb_define_method(rb_cTilemap, "tileset", RUBY_METHOD_FUNC(&Tilemap::rb_getBitmap), 0);
rb_define_method(rb_cTilemap, "tileset=", RUBY_METHOD_FUNC(&Tilemap::rb_setBitmap), 1);
// getters and setters
rb_define_method(rb_cTilemap, "autotiles", RUBY_METHOD_FUNC(&Tilemap::rb_getAutotiles), 0);
rb_define_method(rb_cTilemap, "map_data", RUBY_METHOD_FUNC(&Tilemap::rb_getMapData), 0);
rb_define_method(rb_cTilemap, "map_data=", RUBY_METHOD_FUNC(&Tilemap::rb_setMapData), 1);
rb_define_method(rb_cTilemap, "priorities", RUBY_METHOD_FUNC(&Tilemap::rb_getPriorities), 0);
rb_define_method(rb_cTilemap, "priorities=", RUBY_METHOD_FUNC(&Tilemap::rb_setPriorities), 1);
// methods
rb_define_method(rb_cTilemap, "update", RUBY_METHOD_FUNC(&Tilemap::rb_update), 0);
}

VALUE Tilemap::rb_new(VALUE classe)
{
Tilemap* tilemap;
return RB_OBJECT_NEW(classe, Tilemap, tilemap, &Tilemap::gc_mark, &Tilemap::gc_free);
}

VALUE Tilemap::rb_initialize(int argc, VALUE* argv, VALUE self)
{
RB_SELF2CPP(Tilemap, tilemap);
VALUE viewport;
rb_scan_args(argc, argv, "01", &viewport);
tilemap->initialize(viewport);
return self;
}

VALUE Tilemap::rb_initialize_clone(VALUE self, VALUE original)
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CANT_CLONE_ERROR(tilemap);
return self;
}

VALUE Tilemap::rb_initialize_dup(VALUE self, VALUE original)
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CANT_DUP_ERROR(tilemap);
return self;
}

/****************************************************************************************
* Ruby Getters/Setters
****************************************************************************************/

VALUE Tilemap::rb_getAutotiles(VALUE self)
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CHECK_DISPOSED(tilemap);
return tilemap->rb_autotiles;
}

VALUE Tilemap::rb_getMapData(VALUE self)
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CHECK_DISPOSED(tilemap);
return tilemap->rb_mapData;
}

VALUE Tilemap::rb_setMapData(VALUE self, VALUE value)
{
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CHECK_DISPOSED(tilemap);
}
RB_GENERATE_SETTER(Tilemap, tilemap, Table, mapData);
return value;
}

VALUE Tilemap::rb_getPriorities(VALUE self)
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CHECK_DISPOSED(tilemap);
return tilemap->rb_priorities;
}

VALUE Tilemap::rb_setPriorities(VALUE self, VALUE value)
{
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CHECK_DISPOSED(tilemap);
}
RB_GENERATE_SETTER(Tilemap, tilemap, Table, priorities);
return value;
}

/****************************************************************************************
* Methods
****************************************************************************************/

VALUE Tilemap::rb_update(VALUE self)
{
RB_SELF2CPP(Tilemap, tilemap);
RB_CHECK_DISPOSED(tilemap);
tilemap->autotileUpdateCount = (tilemap->autotileUpdateCount + 1) % 64;
return Qnil;
}

}
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Terv on January 18, 2013, 12:51:48 pm
Thank you. But there's a syntax error in line 23 when I paste it above main.  :(
	VALUE rb_cTilemap;

You need to fix that.

EDIT: nevermind.
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Terv on July 17, 2013, 10:10:55 am
Does the ability to modify Game.exe's source code change anything about the feasibility of overwriting RGSS3's tilemap class with the one from RGSS1's dll?

Or could you use Detours (http://research.microsoft.com/en-us/projects/detours/) to achieve this? (as you can also add Ruby packages at runtime with it)
QuoteDetours intercepts Win32 functions by re-writing the in-memory code for target functions. The Detours package also contains utilities to attach arbitrary DLLs and data segments (called payloads) to any Win32 binary.
Title: Re: [XP] Import certain classes from RGSS1 dll only
Post by: Blizzard on July 17, 2013, 05:57:52 pm
Well, the RGSS.dll has a lot of Ruby C code which makes it quite hard to read since it is obfuscated and interfaced because of that.