如何访问 userdata 的属性和方法?

我想把一个 Java 类的实例作为 userdata 返回给我的 lua 脚本。是否可以从 lua 访问此实例的属性和方法?

就像这样

local car = Car.getNew()
print(car.hasHonked)
car:honk()
print(car.hasHonked)

这是我解决问题的尝试

Java (简化版)

public class CarModule extends TwoArgFunction {

    String moduleName = "Car";

    public LuaValue call(LuaValue modname, LuaValue env) {
        LuaValue library = new LuaTable();
        library.set("getNew", new getNew());
        env.set(moduleName, library);
        return library;
    }

    static class getNew extends ZeroArgFunction {
        @Override
        public LuaValue call() {
            return LuaValue.userdataOf(new Car());
        }
    }
}

public class Car {
    private int count;

    @Override
    public String toString() {
        return "Hello World";
    }

    public void honk() {
        count++;
    }

    public int getHonks() {
        return count;
    }
}

lua

local car = Car.getNew()
print(car) -- foo.bar.lua.module.CarModule$Car@1ef7fe8e
print(type(car)) -- = userdata
print(car.honk) -- = nil
print(car.getHonks) -- = nil
print(car:honk) -- = LuaError: function arguments expected
print(car:getHonks) -- = LuaError: function arguments expected
print(tostring(car)) -- = Hello World
car:honk() -- = LuaError: attempt to call nil
car:getHonks() -- = LuaError: attempt to call nil

编辑:

在这里找到答案https://stackoverflow.com/questions/12358047/how-can-i-pass-objects-to-an-exposed-luaj-function

不是

return LuaValue.userdataOf(new Car());

我必须使用

return CoerceJavaToLua.coerce(new Car());
点赞
用户3586583
用户3586583

你可以尝试将对 car.hasHonked 访问链接到一个从 Java 返回值的函数。我没有使用过 luaj,因此无法评论如何使用它,但是以下是使用 lua 执行同样原则的方式。你需要做的就是将 __index 函数替换为访问你的变量的函数。此代码使用元表允许将未找到的键连接到函数。

Car = {}
function Car.__index(table, key)
    print(Car, table, key)
    return "the java value according to key"
end
function Car.getNew()
    return setmetatable({}, Car) -- sets metatable for userdata or table
end

local car = Car.getNew()

print(car.hasHonked)
-- prints:
-- table: 0xa64f80  table: 0xa6e370 hasHonked
-- the java value according to key

另一个选择就是直接像下面这样使用函数。这些函数会调用 java 并返回真实的 java 值。

car = {}
function car.getHonked()
    return "the java value"
end
2016-07-19 17:46:34