Okay, so although my solution builds, I am having a real hard time trying to figure out how to get LuaBind to actually execute these C++ methods. Right now I just build to an empty screen, which means that my script file isn't executing properly (no sprites are being constructed). I know that there's no problem in my rendering code, because I can hardcode a sprite in by passing parameters to the BuildSpriteObj method manually in C++.
Ideally what I need to be able to do in this example, is to call a static method that builds the SpriteObj from the script file, so that in the Lua file I can just say StaticBuildSpriteObj(param,param,param... etc.);. Is this possible, or am I going to have to do it another way? As it stands I have the static method declared and passed to Lua as a non-member function, and I've tried figuring out how to use a copy of the Renderer2D class within Lua, but I can't get it back to C, and I figured out that I'd much rather use a static method if at all possible.
LUA Script File:
--R2D = Renderer2D();--does this R2D object need to be declared? --we're trying to use a singleton instance copy of the Renderer2D class--can i use this instance for the purpose of holding the whole 2d renderer? or can i pass this back to c?--can i instead pass the instance of the c class to lua so they use the same one?--create a table that will hold all variables needed for a health display--it will eventually be a spriteobjHealthDisplay = { positionx = 200.0, positiony = 400.0, scalex = 0.8, scaley = 0.8, rot = 0.0, transp = 255, red = 255, green = 255, blue = 255, filepath = "healthbar.png" }; --pack a struct with the argb values so it can be passed in the static build function-- can we pass a typeless table into this thing as a struct? --colors = ARGBValues(HealthDisplay.transp,HealthDisplay.red,HealthDisplay.green,HealthDisplay.blue); --load the health display data into a spriteobj--will luabind actually make this static function avaliable?StaticBuildSpriteObj( HealthDisplay.positionx, HealthDisplay.positiony, HealthDisplay.scalex, HealthDisplay.scaley,HealthDisplay.rot,ARGBValues(HealthDisplay.transp,HealthDisplay.red,HealthDisplay.green,HealthDisplay.blue), HealthDisplay.filepath );
Updated Renderer2D.h
//Renderer2D.h//Seraph Project#pragma once#include <d3d9.h>#include <d3dx9.h>#include "cDLL_Node.h"#include "cdll_list.h"#include "ScriptTranslator.h"#pragma comment(lib, "d3d9.lib")#pragma comment(lib, "d3dx9.lib")//forward declarations neededstruct SpriteTexture;struct ARGBValues;class SpriteObj;class Renderer2D{ //attributes public: static Renderer2D* instance; //linked lists of 2d stuff on screen cDLL_List<SpriteTexture> SpriteTextures; cDLL_List<SpriteObj> SpriteObjs; //cDLL_List<GuiObj> GuiObjs; //cDLL_List<TextObj> TextObjects; //D3D sprite object pointer ID3DXSprite* m_pD3DSprite; IDirect3DDevice9* m_pD3DDevice; //font LPD3DXFONT textFont; Renderer2D(); ~Renderer2D(); //behaviors //init void Init(IDirect3DDevice9* m_pD3DDevice); //initialize lists i guess, and load gui objects //factory method that gets a filename, pass back a pointer to the finished picture, load picture //create sprite object, keep track of object to be deleted later //render void Render(); //directx class will tell 2d renderer to render, //this method will contain loops that go through the lists to render everything //clear - clears the prototypes being used void Clear(); //shutdown - shutdown D3Dspriteobject void Shutdown(); //returns pointer to SpriteTexture when given the name of the picture filename SpriteTexture* GetSpriteTexturePointer(string picfilename); //this method is intended to be called from script, in order to build up SpriteObj prototypes void BuildSpriteObj(float positionx, float positiony, float rotation, float scaleX, float scaleY,ARGBValues colors, string picfilename ); static void StaticBuildSpriteObj(float positionx, float positiony, float rotation, float scaleX, float scaleY,ARGBValues colors, string picfilename); static Renderer2D* GetInstance();};
Updated Renderer2D.cpp
//Renderer2D.cpp//Seraph Project#include "Renderer2D.h"#include "SpriteObj.h"//#include "DirectX.h"//required for singleton instanceRenderer2D* Renderer2D::instance = NULL;//blank constructorRenderer2D::Renderer2D(){}Renderer2D::~Renderer2D(){}void Renderer2D::Init(IDirect3DDevice9* m_pD3DDevice){ //remember to initialize linked lists here //get the directx pointer object so we can build a SpriteObj D3DXCreateSprite(m_pD3DDevice, &m_pD3DSprite); //this makes the pointer contained in the r2d class point to the same device that the DirectX class has this->m_pD3DDevice = m_pD3DDevice;}void Renderer2D::Render(){ // get position and button status of mouse cursor // calculate mouse cursor's effects on windows / send messages // render all windows //remember somewhere we need to start the d3d sprite object //go through list of prototypes that we already have SpriteObj* temp; //tells SpriteTextures we're starting a new search SpriteObjs.RestartIteration(); //grabs the next node in the list and makes sure its not null //when the list meets the end, it will return null for(temp=SpriteObjs.IterateNext(); temp != NULL; temp=SpriteObjs.IterateNext()) { temp->Render(m_pD3DSprite); } // render mouse // flip to screen }void Renderer2D::Shutdown(){ //remember to shutdown linked lists //pass true if asked for bool}void Renderer2D::Clear(){ //wipes out everything from the screen, but keeping com objects //used when shutting down and reinitializing linked lists}SpriteTexture* Renderer2D::GetSpriteTexturePointer( string picfilename ){ //go through list of prototypes that we already have SpriteTexture* temp; //tells spritetextures we're starting a new search SpriteTextures.RestartIteration(); //grabs the next node in the list and makes sure its not null //when the list meets the end, it will return null for(temp=SpriteTextures.IterateNext(); temp != NULL; temp=SpriteTextures.IterateNext()) { //if we have one with the same picfilename, we return the pointer to that one if(temp->picfilename == picfilename) { return temp; } } //otherwise, get it from the file and add to prototype list temp = new SpriteTexture(); temp->picfilename = picfilename; //load sprite textures //the picfile name only works in these arguments if its a regular string, and we call the magical c_str method HRESULT HR = D3DXCreateTextureFromFileEx(m_pD3DDevice, picfilename.c_str(), 0, 0, 0, 0, D3DFMT_UNKNOWN, D3DPOOL_MANAGED, D3DX_DEFAULT, D3DX_DEFAULT, D3DCOLOR_XRGB(255,0,255), //KEY COLOR (magenta) &temp->ImageInfo, 0, &temp->m_pD3DTexture); //add temp to list of prototypes SpriteTextures.InsertNode(temp,true); return temp;}void Renderer2D::BuildSpriteObj(float positionx, float positiony, float rotation, float scaleX, float scaleY, ARGBValues colors, string picfilename ){ //builds a new spriteobj SpriteObj* temp = new SpriteObj( NULL, positionx, positiony, rotation, scaleX, scaleY, colors); //when setting parameters, we need to call the getspritetexturepointer temp->m_pSpriteTexture = GetSpriteTexturePointer(picfilename); //needs to add it to the list of spritobjs SpriteObjs.InsertNode(temp,true); }void Renderer2D::StaticBuildSpriteObj( float positionx, float positiony, float rotation, float scaleX, float scaleY,ARGBValues colors, string picfilename ){ GetInstance()->BuildSpriteObj( positionx, positiony, rotation, scaleX, scaleY, colors, picfilename);}//returns a pointer to the r2d instanceRenderer2D* Renderer2D::GetInstance(){ if(instance) { return instance; } instance = new Renderer2D(); }
From Updated ScriptTranslator.cpp:
void ScriptTranslator::Init(lua_State* LI){ //call LUA /* initialize Lua */ LI = lua_open(); if (NULL == LI) { //throw exception } /* load Lua base libraries */ luaL_openlibs( LI ); //load in luabind open( LI ); //define luabind scopes and methods/classes registered module( LI ) //module is global scope [ //bind spriteobj class so we can call buildspriteobj class_<Renderer2D>("Renderer2D") .def(constructor<>()) .def("BuildSpriteObj", &Renderer2D::BuildSpriteObj), def("StaticBuildSpriteObj", &Renderer2D::StaticBuildSpriteObj), //pack arguments into structs so luabind has less to pass class_<ARGBValues>("ARGBValues") .def(constructor<int,int,int,int>()) /*class_<SpriteObj>("SpriteObj") .def(constructor<>()) .def("Init",&SpriteObj::Init)*/ //def("BuildSpriteObj", &Renderer2D::BuildSpriteObj) ]; //attempt to pass the instance of the R2D object to lua as a global //luabind::globals(LI)["R2D"] = &CDirectX::R2D;}