luuuuuuaaaaaaaaah-ah-ah-ah
Available for Purchase at the YoYo Games Marketplace

# LuaRousr

LuaRousr is a GameMaker Studio 2 extension that integrates Lua with GameMaker Studio 2

# Installation Notes

​​Note: LuaRousr uses functions from rousrSuite​​. When importing assets from the extension, make sure to include any rousr (required) group. If you have any other rousr​extensions, you only need to keep one copy of each of these resources. If you do import multiples, GameMaker Studio 2 will rename the duplicates with a _1 at the end. You can simply delete any of the resources after importing the asset.

# Quick Start

Note: LuaRousr uses Lua 5.3

# The Demo

boingggggg

The demo was lovingly handcrafted, and provided by @net8floz

Download Here

# Messin' with the Demo

First and foremost: Use the F1-F4 keys so that you can experience the latest in Grid fashion.

The demo uses the 4 Lua files, game.lua, paddle.lua, ball.lua, and math.lua to pit two AI pong paddles against one another, each of these files can be edited WHILE the game is running to completely change the behavior of the game itself. Once you've edited the Lua files, press R and the Lua will reload. Hurray!

# Working with the Demo Example (included with LuaRousr)

Lua files are expected to be right next to the .exe in this demo - though you don't have to do it that way. To run the demo from GMS2 you must add the lua files to the executable path first.

This path is something like the following for VM (and something ridiculous on YYC):

C:\ProgramData\GMS2\Cache\runtimes\runtime-x-x-x\windows

Alternatively just put the Lua files on C:/lua (or anywhere else) and use that instead of get_executable_path

See: obj_game - Create for more instruction

# Credit

Please see LICENSE.md for license information
Extension itself is covered by YoYo Games's EULA


# API Reference

# GML

# luaRousr_init

returns: | None

luaRousr_init()

create LuaRousr if it doesn't already exist. [helper function]


# luaRousr_add_debug_print_listener

returns: | None

luaRousr_add_debug_print_listener()

Adds a script index to the list of debug listeners internal to LuaRousr. Note: Use with(LuaRousr) DebugToConsole = false to shut off default print behavior


# luaRousr_remove_debug_print_listener

returns: | None

luaRousr_remove_debug_print_listener()

Removes a script index from the list of debug listeners internal to LuaRousr. Note: Use with(LuaRousr) DebugToConsole = false to shut off default print behavior


# luaRousr_tick

returns: | None

luaRousr_tick()

force lua to process a frame / tick /step


# luaRousr_default_getter

_index {Real} index assigned the variable
returns: {*} return value
luaRousr_default_getter(_index)

called with(instance)


# luaRousr_default_setter

_variable_name {String} name given to variable
_index {Real} index assigned the variable
returns: None
luaRousr_default_setter(_variable_name, _index)

called with(instance)


# luaRousr_bind_script

_script_index {Real} script index that represents this function
[_user_data] {*} user data optionally passed with the script_execute
returns: None
luaRousr_bind_script(_script_index, [_user_data])

Call this for all of your GML script functions you'd like Lua to have access to. Note: This must be done before you load your scripts that use the functions. Otherwise, it'sunreliable that they'll be able to "see" your functions. Note About Arguments: In Lua, you're able to treat most anything like a variable and pass it to a function as an argument. At this time, LuaRousr doesn't support accepting Lua tables as arguments. You may pass functions, however. If passing a function to GML, you must retain the callbackid in order to call it outside of the scope of the bound script function. See luaRousr_retain_callback and luaRousr_release_callback.


# luaRousr_bind_instance_variable

_member_name {String} name of this member to refer to it by in Lua i.e., instance._member_name
_default {Real
[_read_only=false] {Boolean} can you write to this value?
[_getter] {Real} getter function for this variable
[_setter] {Real} setter function for this variable
[_force_type] {Real
returns: {Real} index of variable
luaRousr_bind_instance_variable(_member_name, _default, [_read_only=false], [_getter], [_setter], [_force_type])

Binds an instance variable to _member_name in Lua. Once instance is bound in Lua, the variable is accessible by _member_name. In LuaRousr's current version, this feature uses variable_instance_set and variable_instance_get to keep the value in sync with Lua, so varName must match the instance variable name.


# luaRousr_bind_instance

_instance_id {Real} - instance we're sync'ing (some history: original API required both, and unfortunately passed id second, in order to not break everything, first param is now optional)
returns: {Real} noone on unsuccessful bind, or id of instance (for chaining in function returns)
luaRousr_bind_instance(_instance_id)

Binds an instance to Lua using the given name. All the members can now be accessed i.e,: inst.x = 10 print(inst.y) NOTE: You must unbind an instance in its CleanUp event if it's still bound at that point.


# luaRousr_bind_resource

_object_index {Real} - Object we're sync'ing
returns: None
luaRousr_bind_resource(_object_index)

bind an Object to Lua


# luaRousr_unbind_instance

returns: | None

luaRousr_unbind_instance()

Removes an instance binding so that Lua no longer updates the GML instance. Note: Any references to the Lua version of the object are still 'valid' in that they will act like a real instance... but they no longer are attached to the GML rendering them useless.


# luaRousr_unbind_resource

returns: | None

luaRousr_unbind_resource()

unbind an object from Lua


# luaRousr_set_global

_val {Real
returns: {Boolean} true if set
luaRousr_set_global(_val)

set a value with _name in the Lua Globals table (global namespace)


# luaRousr_get_global

returns: | {Real|String} global value or undefined

luaRousr_get_global()

get the value of _name in the Lua Globals table (global namespace)


# luaRousr_execute_file

returns: | {Real} undefined on failure, or the script context Id for all threads running from this execute.

luaRousr_execute_file()

Load a .Lua file and call luaRousr_execute_string on it


# luaRousr_execute_string

_script {String} string containing Lua script
returns: {Boolean} true on call successfully returned
luaRousr_execute_string(_script)

false


# luaRousr_call

[_args...] {...Real
returns: {Real
luaRousr_call([_args...])

Call a Lua function with the given name, that simple! NOTE: Returns are not functioning in the current version! No returns as of yet. luaRousr_retain_callback luaRousr_release_callback


# luaRousr_retain_callback

_callback_id {Real} callback Id passed to us from Lua
returns: {Real} _callback_id or undefined
luaRousr_retain_callback(_callback_id)

Increments the reference count for a callbackId. As long as the reference count is above 0, the callback is kept in memory.


# luaRousr_release_callback

returns: | None

luaRousr_release_callback()

Decrements the reference count for the callbackId. If it's completely released (refcount = 0), it queues the callbackId for deletion. The next step called by LuaRousr will release this callback from memory.


# luaRousr_kill_threads

returns: | None

luaRousr_kill_threads()

Kill all threads created in Lua script using the thread(function) Lua function.


# __luaRousr_event_create

returns: | None

__luaRousr_event_create()

Create event for LuaRousr Object


# __luaRousr_event_clean_up

returns: | None

__luaRousr_event_clean_up()

Clean Up event for LuaRousr Object



# Lua Functions

# thread(function)

callbackId the id of the callback passed from Lua

returns: a thread object to hold on to.

A Lua Thread can be "yielded" to pause execution, resuming from the point of the yield the next time the Lua Thread is resumed. (LuaRousr automatically resumes threads once per step in the oLuaRousr object).

TIP This is useful for scripts that need to wait for things to occur, such as telling an NPC to move to a location, and then checking they've finished their move each step. i.e,:
local move_thread = thread(function()
  local npc = GMLInstance("npc")
  npc_move(npc, 200, 200)
  while (npc_is_moving(npc)) do
    thread.yield()
  end
end)

Note: The npc_* functions are just for the example, and not actual API.
Note: We're storing the returned thread in a local variable. This is to access it with later, but LuaRousr will also keep a Lua reference to the thread while it's active to prevent it from being garbage collected.

# thread.yield()

Yield tells a Lua Thread to stop executing, resuming from this point next step. See the explanation in thread()


# toFunction(callbackId)

callbackId the id of the callback passed from Lua to GML and back to Lua

returns: function callbackId represents

If you've passed a function to GML, but want to pass it back to Lua and use it, toFunction returns the actual function from the numeric id.


# print(string)

string the text to show_debug_message

a debug, logging, helper function. calls show_debug_message in GML with the given text.


# GMLInstance(instanceName)

instanceName the string name given to the instance when it was bound to Lua.

returns: a GMLInstance Lua object representing the named instance, or nil on error.

Retrieves a GML instance resource that was bound using luaRousr_bindInstance. Each GMLInstance Lua object created this way does point to the same GML resource.

Built-ins

All instance built-in GML variables are bound to GMLInstance and accessible as properties:

local inst = GMLInstance("tester")
inst.x = 10
print (inst.x)

# GMLResource(resourceName)

instanceName the string name given to the resource when it was bound to Lua.

returns: at index value for the resource, so you can pass it to your functions

Retrieves a GML Resource index for a resource that was bound using luaRousr_bindResource.


# Changelog

# Upcoming

# Known Issues (Expect fixes soon)