Exemplo n.º 1
0
static int w__release(lua_State *L)
{
	Proxy *p = (Proxy *) lua_touserdata(L, 1);
	Object *object = p->object;

	if (object != nullptr)
	{
		p->object = nullptr;
		object->release();

		// Fetch the registry table of instantiated objects.
		luax_getregistry(L, REGISTRY_OBJECTS);

		if (lua_istable(L, -1))
		{
			// loveobjects[object] = nil
			lua_pushlightuserdata(L, object);
			lua_pushnil(L);
			lua_settable(L, -3);
		}

		lua_pop(L, 1);
	}

	luax_pushboolean(L, object != nullptr);
	return 1;
}
Exemplo n.º 2
0
void luax_pushtype(lua_State *L, love::Type &type, love::Object *object)
{
	if (object == nullptr)
	{
		lua_pushnil(L);
		return;
	}

	// Fetch the registry table of instantiated objects.
	luax_getregistry(L, REGISTRY_OBJECTS);

	// The table might not exist - it should be insisted in luax_register_type.
	if (!lua_istable(L, -1))
	{
		lua_pop(L, 1);
		return luax_rawnewtype(L, type, object);
	}

	// Get the value of loveobjects[object] on the stack.
	lua_pushlightuserdata(L, object);
	lua_gettable(L, -2);

	// If the Proxy userdata isn't in the instantiated types table yet, add it.
	if (lua_type(L, -1) != LUA_TUSERDATA)
	{
		lua_pop(L, 1);

		luax_rawnewtype(L, type, object);

		lua_pushlightuserdata(L, object);
		lua_pushvalue(L, -2);

		// loveobjects[object] = Proxy.
		lua_settable(L, -4);
	}

	// Remove the loveobjects table from the stack.
	lua_remove(L, -2);

	// Keep the Proxy userdata on the stack.
}
Exemplo n.º 3
0
int luax_register_module(lua_State *L, const WrappedModule &m)
{
	// Put a reference to the C++ module in Lua.
	luax_getregistry(L, REGISTRY_MODULES);

	Proxy *p = (Proxy *)lua_newuserdata(L, sizeof(Proxy));
	p->own = true;
	p->data = m.module;
	p->flags = m.flags;

	luaL_newmetatable(L, m.module->getName());
	lua_pushvalue(L, -1);
	lua_setfield(L, -2, "__index");
	lua_pushcfunction(L, w__gc);
	lua_setfield(L, -2, "__gc");

	lua_setmetatable(L, -2);
	lua_setfield(L, -2, m.name); // _modules[name] = proxy
	lua_pop(L, 1);

	// Gets the love table.
	luax_insistglobal(L, "love");

	// Create new table for module.
	lua_newtable(L);

	// Register all the functions.
	luaL_register(L, 0, m.functions);

	// Register types.
	if (m.types != 0)
		for (const lua_CFunction *t = m.types; *t != 0; t++)
			(*t)(L);

	lua_pushvalue(L, -1);
	lua_setfield(L, -3, m.name); // love.graphics = table
	lua_remove(L, -2); // love

	return 1;
}
Exemplo n.º 4
0
int luax_register_type(lua_State *L, love::Type *type, ...)
{
	type->init();

	// Get the place for storing and re-using instantiated love types.
	luax_getregistry(L, REGISTRY_OBJECTS);

	// Create registry._loveobjects if it doesn't exist yet.
	if (!lua_istable(L, -1))
	{
		lua_newtable(L);
		lua_replace(L, -2);

		// Create a metatable.
		lua_newtable(L);

		// metatable.__mode = "v". Weak userdata values.
		lua_pushliteral(L, "v");
		lua_setfield(L, -2, "__mode");

		// setmetatable(newtable, metatable)
		lua_setmetatable(L, -2);

		// registry._loveobjects = newtable
		lua_setfield(L, LUA_REGISTRYINDEX, "_loveobjects");
	}
	else
		lua_pop(L, 1);

	luaL_newmetatable(L, type->getName());

	// m.__index = m
	lua_pushvalue(L, -1);
	lua_setfield(L, -2, "__index");

	// setup gc
	lua_pushcfunction(L, w__gc);
	lua_setfield(L, -2, "__gc");

	// Add equality
	lua_pushcfunction(L, w__eq);
	lua_setfield(L, -2, "__eq");

	// Add tostring function.
	lua_pushstring(L, type->getName());
	lua_pushcclosure(L, w__tostring, 1);
	lua_setfield(L, -2, "__tostring");

	// Add type
	lua_pushstring(L, type->getName());
	lua_pushcclosure(L, w__type, 1);
	lua_setfield(L, -2, "type");

	// Add typeOf
	lua_pushcfunction(L, w__typeOf);
	lua_setfield(L, -2, "typeOf");

	// Add release
	lua_pushcfunction(L, w__release);
	lua_setfield(L, -2, "release");

	va_list fs;
	va_start(fs, type);
	for (const luaL_Reg *f = va_arg(fs, const luaL_Reg *); f; f = va_arg(fs, const luaL_Reg *))
		luax_setfuncs(L, f);
	va_end(fs);

	lua_pop(L, 1); // Pops metatable.
	return 0;
}
Exemplo n.º 5
0
int luax_register_type(lua_State *L, const char *tname, const luaL_Reg *f)
{
    // Verify that this type name has a matching Type ID and type name mapping.
    love::Type ltype;
    if (!love::getType(tname, ltype))
        printf("Missing type entry for type name: %s\n", tname);

    // Get the place for storing and re-using instantiated love types.
    luax_getregistry(L, REGISTRY_TYPES);

    // Create registry._lovetypes if it doesn't exist yet.
    if (!lua_istable(L, -1))
    {
        lua_newtable(L);
        lua_replace(L, -2);

        // Create a metatable.
        lua_newtable(L);

        // metatable.__mode = "v". Weak userdata values.
        lua_pushliteral(L, "v");
        lua_setfield(L, -2, "__mode");

        // setmetatable(newtable, metatable)
        lua_setmetatable(L, -2);

        // registry._lovetypes = newtable
        lua_setfield(L, LUA_REGISTRYINDEX, "_lovetypes");
    }
    else
        lua_pop(L, 1);

    luaL_newmetatable(L, tname);

    // m.__index = m
    lua_pushvalue(L, -1);
    lua_setfield(L, -2, "__index");

    // setup gc
    lua_pushcfunction(L, w__gc);
    lua_setfield(L, -2, "__gc");

    // Add equality
    lua_pushcfunction(L, w__eq);
    lua_setfield(L, -2, "__eq");

    // Add tostring function.
    lua_pushstring(L, tname);
    lua_pushcclosure(L, w__tostring, 1);
    lua_setfield(L, -2, "__tostring");

    // Add tostring to as type() as well.
    lua_pushstring(L, tname);
    lua_pushcclosure(L, w__tostring, 1);
    lua_setfield(L, -2, "type");

    // Add typeOf
    lua_pushcfunction(L, w__typeOf);
    lua_setfield(L, -2, "typeOf");

    if (f != 0)
        luax_setfuncs(L, f);

    lua_pop(L, 1); // Pops metatable.
    return 0;
}