Sign in to follow this  
MatsK

Function not being called?! (Luabind)

Recommended Posts

Ok, so I'm trying to call a function from Lua. I've registered the class and global object with LuaBind and I made a logging method last night to check that I am able to access to global object (ScreenMgr). It seemed to work fine. However, calling the method AddScene() that adds an instance to an internal vector, just does NOT seem to work. After the script has been run, the number of items in the vector is still 0. What gives?
Here is my Lua code:

[code]PersonSelectionScene = UIScene("uigraphics\\personselection\\personselection.dat")
SceneMgr:AddScreen(PersonSelectionScene)

PersonSelectionScene:LoadBackground(0x3FA)
SceneMgr:LogMsg("This is a test!")[/code]


This is my Luabind code:

[code]//Registers all neccessary classes so that they are available to use
//when scripting in Lua.
void LuaInterfaceManager::RegisterClasses()
{
//Make the SceneManager class available to Lua.
luabind::module(LuaInterfaceManager::LuaManager)
[luabind::class_<SceneManager>("SceneManager")
.def(luabind::constructor<>())
.def("LoadInitialScreen", &SceneManager::LoadInitialScreen)
.def("AddScreen", &SceneManager::AddScreen)
.def("LogMsg", &SceneManager::LogMsg)];

//Makes the UIScene class available to all Lua scripts.
luabind::module(LuaInterfaceManager::LuaManager)
[luabind::class_<UIScene>("UIScene")
.def(luabind::constructor<std::string>())
.def("LoadBackground", &UIScene::LoadBackground)];
}[/code]


And here is the SceneManager class:

[code]#include "stdafx.h"
#include "SceneManager.h"
#include "LuaInterfaceManager.h"
#include <ezlogger/ezlogger_headers.hpp>

void SceneManager::LoadInitialScreen(std::string Path)
{
if(luaL_dofile(LuaInterfaceManager::LuaManager, Path.c_str()) != 0)
{
//TODO: Log error...
EZLOGGERSTREAM << "Error encountered in Lua script: " << std::string(lua_tostring(LuaInterfaceManager::LuaManager, -1)) << std::endl;
}
else
{
EZLOGGERSTREAM << "Ran Lua script: " << Path << std::endl;
}
}

void SceneManager::AddScreen(UIScene Screen)
{
m_Scenes.push_back(Screen);
}

void SceneManager::LogMsg(std::string Msg)
{
EZLOGGERSTREAM << Msg << std::endl;
}[/code]


[code]#ifndef __SCENEMANAGER_H__
#define __SCENEMANAGER_H__

#pragma once

#include <vector>
#include <string>
#include "UIScene.h"

using namespace std;

class SceneManager
{
private:
vector<UIScene> m_Scenes;
public:
void LoadInitialScreen(string Path);
void AddScreen(UIScene Screen);
void LogMsg(std::string Msg);

vector<UIScene> *Scenes() { return &m_Scenes; };
};

#endif[/code]


My winmain function looks like:

[code]int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);

// TODO: Place code here.
MSG msg;
HACCEL hAccelTable;

// Initialize global strings
LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
LoadString(hInstance, IDC_TSOCLIENT, szWindowClass, MAX_LOADSTRING);
MyRegisterClass(hInstance);

// Perform application initialization:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}

//Initialize Lua...
LuaInterfaceManager LuaMgr;

//Registers all appropriate classes to Lua.
LuaInterfaceManager::RegisterClasses();

//Makes the SceneManager object available to all Lua scripts.
luabind::globals(LuaInterfaceManager::LuaManager)["SceneMgr"] = SceneMgr;

SceneMgr.LoadInitialScreen("gamedata\\luascripts\\personselection.lua");

hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_TSOCLIENT));

std::vector<UIScene> *ScenePtr = SceneMgr.Scenes();

// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}

// Clear the screen (fill it with black color)
App.Clear();

for(int i = 0; i < ScenePtr->size(); i++)
{
SceneMgr.LogMsg("Logging...");

for(int j = 0; j < (*ScenePtr)[i].Backgrounds()->size(); j++)
{
std::vector<UIBackground> *BackgroundsPtr = (*ScenePtr)[i].Backgrounds();

App.Draw((*BackgroundsPtr)[j].GetSprite());
delete BackgroundsPtr;
}
}

// Display window contents on screen
App.Display();
}

return (int) msg.wParam;
}[/code]


Now, the statement 'Logging...' is never printed out to the log, which suggests to me that no UIScene instances are being added to the SceneManager's vector, even though I'm calling AddScreen()! :(
If it helps, the UIScene class looks like:

[code]#ifndef __UISCENE_H__
#define __UISCENE_H__

#pragma once

#include <vector>
#include <string>
#include "UIBackground.h"
#include "libfar.h"
#include "FileArchive.h"

using namespace std;

class UIScene
{
private:
string m_ArchivePath;
FileArchive m_Archive;

vector<UIBackground> m_Backgrounds;
public:
UIScene(string ArchivePath);
void LoadBackground(int ID);

vector<UIBackground> *Backgrounds() { return &m_Backgrounds; }
};

#endif[/code]


[code]#include "stdafx.h"
#include "UIScene.h"
#include <ezlogger/ezlogger_headers.hpp>

UIScene::UIScene(string ArchivePath)
{
m_ArchivePath = ArchivePath;
m_Archive = FileArchive(m_ArchivePath);
}

void UIScene::LoadBackground(int ID)
{
unsigned char *Destination;
sf::Image Img;

/*EZLOGGERSTREAM << "Attempting to call FARExtractItemFromFileByID()!" << std::endl;
unsigned int NumBytes = FARExtractItemFromFileByID((const char *)m_ArchivePath.c_str(), (unsigned int)ID, &Destination, 0);
EZLOGGERSTREAM << "Called FARExtractItemFromFileByID()!";
Img.LoadFromMemory((const char*)Destination, NumBytes);*/

if(!Img.LoadFromMemory(m_Archive.GetItemByID(ID), m_Archive.ItemDecompressedSize(ID)))
{
EZLOGGERSTREAM << "Couldn't load image from memory!" << std::endl;
}

UIBackground Background(Img);
m_Backgrounds.push_back(Img);
}[/code]

Edit: Just to clarify, calling LogMsg() from Lua seems to work just fine, which is making me really confused!

Share this post


Link to post
Share on other sites
Fixed it.

Had to modify the order of my Lua statements to maintain state:

[code]PersonSelectionScene = UIScene("uigraphics\\personselection\\personselection.dat")
PersonSelectionScene:LoadBackground(0x3FA)

SceneMgr:AddScreen(PersonSelectionScene)[/code]

And change my mainloop:

[code]int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);

// TODO: Place code here.
MSG msg;
HACCEL hAccelTable;

// Initialize global strings
LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
LoadString(hInstance, IDC_TSOCLIENT, szWindowClass, MAX_LOADSTRING);
MyRegisterClass(hInstance);

// Perform application initialization:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}

//Initialize Lua...
LuaInterfaceManager LuaMgr;

//Registers all appropriate classes to Lua.
LuaInterfaceManager::RegisterClasses();

//Makes the SceneManager object available to all Lua scripts.
luabind::globals(LuaInterfaceManager::LuaManager)["SceneMgr"] = &SceneMgr;

SceneMgr.LoadInitialScreen("gamedata\\luascripts\\personselection.lua");

std::vector<UIScene> *ScenePtr = SceneMgr.Scenes();

hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_TSOCLIENT));

sf::Sprite Sprt;

// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}

// Clear the screen (fill it with black color)
App.Clear();

for(int i = 0; i < ScenePtr->size(); i++)
{
for(int j = 0; j < (*ScenePtr)[i].Backgrounds()->size(); j++)
{
std::vector<UIBackground> *BackgroundsPtr = (*ScenePtr)[i].Backgrounds();
Sprt.SetImage(*(*BackgroundsPtr)[j].GetImage());

App.Draw(Sprt);
}
}

// Display window contents on screen
App.Display();
}

return (int) msg.wParam;
}[/code]

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this