0

我正在使用 Allegro 用 C++ 创建一个 2D RPG 游戏引擎。我已经到了需要实现脚本系统的地步。所以,我的问题是这个:

我有一个名为Event的结构。在这个结构内部有一个函数指针,它指向我想要在事件触发时执行的函数。所以,这里有一个例子:

struct Event {
    //...
    void (*func)(Player*, void*);
    //...
}

现在,要创建一个事件,我有这个功能:

Event* Events::register_event_source(int x, int y, std::string name, Player* player, void (*func)(Player*, void*));

所以,要使用它,我只需要使用这个签名创建一个函数:

void test_event(Player* p, void* data)
{
    //Do something cool here
}

然后注册一个事件源,为该函数提供地址:

//...
Player* player = new Player(0, 0);
//...
Event* evt = Events::register_event_source(10, 10, "test event", player, &test_event);
//Eventually set some data for the event
evt->set_data(new std::string("Just some test data"));

这样,当玩家越过指定的位置(在本例中 x = 10,y = 10)时,事件将触发,执行test_event函数中的任何代码。

现在,我的问题是:是否有可能在运行时执行或至少接近此过程?...我需要在运行时创建函数(在本例中为“test_event”),但我做了一些研究,我认为我理解的是在运行时创建函数实际上是不可能的。那么,我应该采用哪种方法?...我知道这是一个抽象的问题...但我真的不知道如何解决这个问题。

感谢您提供任何帮助的建议!抱歉我的解释能力不好……英语不是我的语言!

4

1 回答 1

2

如果我正确理解您要表达的内容,那么您正在编写一个脚本引擎,它将运行时构建的一些逻辑解释为一个字符串,这应该确定在Playerdata. 如果是这样,我可以想象你应该有一个像

void InterpretScriptCode(Player* p, void* data, string const& code)

或解释和执行codeonp和中描述的逻辑的等价物data

然后,您可以使用std::bindandstd::function封装对脚本引擎的调用:

// Header <functional> needs to be included, and a proper "using namespace"
// directive must be present for bringing placeholders _1 and _2 into scope

std::function<void(Player*, void*)> fxn = std::bind(
    &InterpretScriptCode,
     _1,
     _2,
    "int x = 0; ... blah blah" // this should be your run-time generated script
    );

并将fxn输入传递给您的register_event_source()函数。

顺便说一句,您可能有兴趣使用 Boost.Signals/Boost.Signals2 来实现事件注册/处理。

如果您不使用 C++11,则可以使用boost::bindandboost::function代替std::bindand std::function

于 2013-01-13T17:15:24.887 回答