UserAPI使用说明

注:当前C/C++API文档还未更新,可能有部分函数为1.1版本的旧函数,有问题请在群里询问。

概览

class UserAPI {
   public:
    UserAPI(UserAPI &) = delete;
      //禁用构造函数

    bool operator=(const UserAPI &) = delete;
      //禁用函数符'='重载

    static UserAPI &Singleton(lua_State *L = nullptr);

    // 初始化一个类成员函数的执行,参数为类名和函数名
    void init_func_call(std::string class_name, std::string func_name);

    // 执行lua_State栈顶的函数,参数分别为参数个数与返回值个数
    void execute_func_call(int param_num = 0, int ret_num = 0);

    // 向lua_State中压入一个字符串
    void lua_pushstring(std::string str);

    // 获取lua表中的元素(可以是函数),两个参数分别为全局表名和数据项名
    void get_lua_property(std::string class_name, std::string property_name);

    // 执行移动操作(仅列出,不建议使用)
    void move_to(VECTOR dest, double moveNum);

      // 另一种方式执行移动操作
      void move_by_direction(VECTOR src, double moveNum, int direction) 

    // 又一种方式执行移动操作
    void move_by_coordinates(VECTOR src, VECTOR dest, double moveNum)  

    // 判断两个点是否相连
    bool is_connected(int posX1, int posY1, int posX2, int posY2);

    // 获取King的位置
    VECTOR king_pos();

    // 获取当前的step数
    int get_current_step();

    // 获取当前选中的位置(1.1版本)
    VECTOR selected_pos();

    // 设置当前选中位置(1.1版本)
    void selected_pos(VECTOR pos);

    // 获取当前选中的位置(新版)
    VECTOR UserAPI::getSelectedPos()

    // 设置当前选中位置(新版)
    void UserAPI::setSelectedPos(VECTOR pos) 

   private:
    lua_State *luaState;
    UserAPI(lua_State *L) : luaState(L) {}
};

部分函数详解

1 .static UserAPI &Singleton
UserAPI(UserAPI &) = delete;
bool operator=(const UserAPI &) = delete;

static UserAPI &Singleton(lua_State *L = nullptr)
{
    static bool has_init = false;
    if (!has_init && L == nullptr)
        printf("ERROR: argument lua_State not given for initialization");
    static UserAPI singleton(L);
    has_init = true;
    return singleton;
}

​ 这个函数用于获取UserAPI单一实例的一个引用,在首次调用时需要传入一个lua_State 指针,此后可以不传。

​ 这是由于一次游戏中,用户只有一份SDK,因此我们使用单一实例模式来进行实现。用户调用Singleton()可以获取一份SDK实例。注意,在第一次调用时,需要用户手动提供lua_State指针来初始化SDK。这里提供了一份最小的userMain()实现

static int userMain(lua_State *luaState) {
    UserAPI &API = UserAPI::Singleton(luaState);   // 初始化并获取单例
    // ...
    return 0;        // 必须返回0作为参数(代表正确退出),否则程序会崩溃
}

​ 有关单例模式详细情况请查看此博客

2 .init_func_call
void init_func_call(std::string class_name, std::string func_name)
{
    lua_getglobal(luaState, class_name.c_str());
    if (!lua_istable(luaState, -1))
        throw "AI SDK -- not a table error";
    lua_pushstring(func_name);
    lua_gettable(luaState, -2);
}

​ 这个接口主要用于初始化调用 对接的lua文件中存在的. 表结构成员函数

​ 例如:

void selected_pos(VECTOR pos)
{
    init_func_call("AI_SDK", "setSelected");
    ......
}

​ 对应lua文件中的表叫做"AI_SDK",表中有一个函数叫"setSelected",调用此接口对函数初始化以使用此函数。

3 .execute_func_cal
void execute_func_call(int param_num = 0, int ret_num = 0) {
        int iRet = lua_pcall(luaState, param_num, ret_num, 0);
    if (iRet) {
        throw lua_tostring(luaState, -1);
    }
}

​ 这个接口用于执行lua_State栈顶的函数,参数param_num和ret_num分别为参数个数与返回值个数。具体的过程由lua_pcall函数执行,此函数会执行栈顶的函数,若执行过程中出现错误,则会返回一个非0值。此时我们用抛出异常函数throw将其抛出,以待之后处理。

4 .lua_pushstring
void lua_pushstring(std::string str) {
    ::lua_pushstring(luaState, str.c_str());
}

​ 这个接口用于向lua_State中压入一个字符串。

5 .get_lua_property
void get_lua_property(std::string class_name, std::string property_name) {
    lua_getglobal(luaState, class_name.c_str());
    if (!lua_istable(luaState, -1)) {
        std::cout << "Error: not a table" << std::endl;
        throw "not a table" + class_name;
    }
        lua_getfield(luaState, -1, property_name.c_str());
}

​ 这个接口用于获取lua表中的元素(可以是函数),两个参数分别为全局表名和数据项名

6 .move_to
void move_to(VECTOR dest, double moveNum) {
    init_func_call("AI_SDK", "MoveTo");
    lua_pushnumber(luaState, dest.x);
    lua_pushnumber(luaState, dest.y);
    lua_pushnumber(luaState, moveNum);
    execute_func_call(3);
}

​ 这是移动军队的接口,( dest.x , dest.y )为目标点坐标,用户调用moveTo函数之前需要提前用函数selected_pos设定好选中的点。

​ moveNum为移动兵力,其中,其值为0时只在原地留一个士兵;大于1时移动其值数量的兵力;小于1时按比例移动,如0.5为移动一半。

使用示例:

UserAPI &API = UserAPI::Singleton();
double x , y , x1 , y1 ;                 // 分别设置选中位置和目标位置
...                                                            // 赋值
API.selected_pos() = {x, y};        // 设置现在选中位置
API.move_to({x1, y1}, 0.5);            // 执行移动操作,从(x,y)–>(x1,y1),移动(x,y)一半的兵力
7 .move_by_direction
void move_by_direction(VECTOR src, double moveNum, int direction) {
    init_func_call("AI_SDK", "MoveByDirection");
    lua_pushnumber(luaState, src.x);
    lua_pushnumber(luaState, src.y);
    lua_pushnumber(luaState, moveNum);
    lua_pushnumber(luaState, direction);
    execute_func_call(4);
}

​ 这个函数是对moveTo的封装,用户调用此函数时只需传入起始点坐标src,移动兵力moveNum和方向direction(正六边形自右上边顺时针方向分别为1~6)。moveNum参考moveTo中的moveNum。

8 .move_by_coordinates
void move_by_coordinates(VECTOR src, VECTOR dest, double moveNum) {
    init_func_call("AI_SDK", "MoveByCoordinates");
    lua_pushnumber(luaState, src.x);
    lua_pushnumber(luaState, src.y);
    lua_pushnumber(luaState, dest.x);
    lua_pushnumber(luaState, dest.y);
    lua_pushnumber(luaState, moveNum);
    execute_func_call(5);
}

​ 这个函数是对moveTo的封装,用户调用此函数时只需传入起始点坐标src,终点坐标dest和移动兵力。

9 .is_connected
bool is_connected(int posX1, int posY1, int posX2, int posY2) {
    ...
}

​ 这个接口用于判断两个选定坐标的格子(X1,Y1)与(X2,Y2)是否相邻。

10.king_pos
VECTOR king_pos() {
    get_lua_property("AI_SDK", "KingPos");
    if (!lua_istable(luaState, -1)) {
        throw "not a table: KingPos";
    }
    lua_getfield(luaState, -1, "x");
    int x = lua_tonumber(luaState, -1);
    lua_getfield(luaState, -2, "y");
    int y = lua_tonumber(luaState, -1);
    return {x, y};
}

​ 这个接口用于获取王的位置,返回的是一个形式为{ X , Y }的VECTOR变量。

11.get_current_step
int get_current_step() {
    get_lua_property("ReplayGame", "step");
    return lua_tonumber(luaState, -1);
}

​ 这个接口用于获取当前的步数。

12.selected_pos(1.1版本)
VECTOR selected_pos() {
    get_lua_property("AI_SDK", "SelectPos");
    if (!lua_istable(luaState, -1)) {
        throw "not a table: SelectPos";
    }
    lua_getfield(luaState, -1, "x");
    int x = lua_tonumber(luaState, -1);
    lua_getfield(luaState, -2, "y");
    int y = lua_tonumber(luaState, -1);
    return {x, y};
}

​ 这个接口用于获取选中点的位置,返回的是一个形式为{ X , Y }的VECTOR变量。

13.getSelectedPos(新版)
VECTOR UserAPI::getSelectedPos() {
    ...
    return {x, y};
}
这个接口用于获取选中点的位置,返回的是一个形式为{ X , Y }的VECTOR变量。
14.selected_pos(1.1版)
void selected_pos(VECTOR pos) {
    ...
}

​ 这个接口用于将当前传入的点pos设置为选中状态,一般与moveto配合使用,不用moveto可以不关注。

15.setSelectedPos(新版)
void UserAPI::setSelectedPos(VECTOR pos) {
    ...
}

这个接口用于将当前传入的点pos设置为选中状态,一般与moveto配合使用,不用moveto可以不关注。

results matching ""

    No results matching ""