Skip to content

RFC : Support for LUA #5

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
Lisias opened this issue Jun 17, 2020 · 11 comments
Open

RFC : Support for LUA #5

Lisias opened this issue Jun 17, 2020 · 11 comments
Assignees
Labels
enhancement New feature or request

Comments

@Lisias
Copy link

Lisias commented Jun 17, 2020

That's the drill:

Thus guy had a hell of an idea, but I think it's too much of a hassle to implement.

So...

What if the all the advanced patch would be implemented on LUA, a pretty simple, straightforward language with a very lightweight runtime?

The code would reside on a file with the same name as the patch file, but with the excetion lua. MM would check the source URL of the patch, then check if it exists a correspondent .lua file and if finds it, load it. Then a simple syntax change on MM itself would make the call for the code on that file.

This will be simpler to implement (I have experience on LUA from my sjasm++ project) and since KSP2 team is using LUA extensively on the development, and assuming they will expose it for the Add'On authors, we would have one less barrier on supporting KSP2 later.

Additionally, there's this project embedding (or trying to) LUA into KSP, what makes the task more feasible.

@Monniasza
Copy link

Patches would have to be ordered, which is more difficult in Lua.

@Lisias
Copy link
Author

Lisias commented Jun 24, 2020

That's the trick - you will still need traditional patches.

But a new operator would call a lua function:

@PART[my-fancy-part]
{
    mass = $@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
   %MODULE[whatever]
    {
        $@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
}

The hard part (aside shoving lua on MM, of course) is where the lua code will reside. Having a config.lua in the same place config.cfg is would be the most convenient solution. It's certain that this will make the patching sensibly slower, but the really time consuming tasks are the texture loading so, frankly, we have a lot of time to burn on this stunt.

@Monniasza
Copy link

That's the trick - you will still need traditional patches.

But a new operator would call a lua function:

@PART[my-fancy-part]
{
    mass = $@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
   %MODULE[whatever]
    {
        $@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
}

The hard part (aside shoving lua on MM, of course) is where the lua code will reside. Having a config.lua in the same place config.cfg is would be the most convenient solution. It's certain that this will make the patching sensibly slower, but the really time consuming tasks are the texture loading so, frankly, we have a lot of time to burn on this stunt.

However, there should be no-return calls too, like this:

@PART[my-fancy-part]
 {
     $$@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
    %MODULE[whatever]
     {
         $$@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
 }

@Lisias
Copy link
Author

Lisias commented Jun 26, 2020

That's the trick - you will still need traditional patches.
But a new operator would call a lua function:

@PART[my-fancy-part]
{
    mass = $@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
   %MODULE[whatever]
    {
        $@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
}

The hard part (aside shoving lua on MM, of course) is where the lua code will reside. Having a config.lua in the same place config.cfg is would be the most convenient solution. It's certain that this will make the patching sensibly slower, but the really time consuming tasks are the texture loading so, frankly, we have a lot of time to burn on this stunt.

However, there should be no-return calls too, like this:

@PART[my-fancy-part]
 {
     $$@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
    %MODULE[whatever]
     {
         $$@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
 }

No necessarily. Every function needs to return something - otherwise this feature has no place on Module Manager. Perhaps a MM Extension would be a better solution for this particular use case.

But, even if we discover a feature where this would be necessary, the function can return NULL and MM would discard NULL returns silently.

@Monniasza
Copy link

That's the trick - you will still need traditional patches.
But a new operator would call a lua function:

@PART[my-fancy-part]
{
    mass = $@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
   %MODULE[whatever]
    {
        $@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
}

The hard part (aside shoving lua on MM, of course) is where the lua code will reside. Having a config.lua in the same place config.cfg is would be the most convenient solution. It's certain that this will make the patching sensibly slower, but the really time consuming tasks are the texture loading so, frankly, we have a lot of time to burn on this stunt.

However, there should be no-return calls too, like this:

@PART[my-fancy-part]
 {
     $$@#$@$%@:lua_call(yada, yeda, yida) // this would return a float
    %MODULE[whatever]
     {
         $$@#$@$%@:another-lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
    }
 }

No necessarily. Every function needs to return something - otherwise this feature has no place on Module Manager. Perhaps a MM Extension would be a better solution for this particular use case.

But, even if we discover a feature where this would be necessary, the function can return NULL and MM would discard NULL returns silently.

I agree with both solutions: separate scripting language and LUA functions

@Lisias Lisias self-assigned this Feb 3, 2025
@Lisias Lisias added the enhancement New feature or request label Feb 3, 2025
@Lisias
Copy link
Author

Lisias commented Feb 3, 2025

This task is blocking #33

@Lisias Lisias added the BLOCKED Blocked by a task, issue or external event label Feb 3, 2025
@Monniasza
Copy link

@Lisias The "BLOCKED" label is in wrong place - it should be on #33

@Lisias Lisias removed the BLOCKED Blocked by a task, issue or external event label Feb 4, 2025
@Lisias
Copy link
Author

Lisias commented Feb 4, 2025

@Lisias The "BLOCKED" label is in wrong place - it should be on #33

Fixed! (got a flu, shouldn't be out of bed, to tell you the truth... :) )

@Lisias
Copy link
Author

Lisias commented Feb 4, 2025

new idea for sintax:

@PART[my-fancy-part]:HAS[#@some_lua_call(yada, yada)]
{
   mass = ##lua_call(yada, yeda, yida) // this would return a string that MM will convert into a float
   %MODULE[whatever]
   {
        #%another_lua_call(yada, yeda, yida) // this would return a dictionary with keys-values
   }
}

Rationale: # is already associated to something being resolved to a string (everything on a config file is really a string - converstion to floats or doubles are made at runtime). We have #$..$ to copy a value from another key (or from a key from another node). So:

  • ## will call a Lua function that will return a value
  • #@ will call a Lua function that will return a list of filters
  • #% will call a Lua function that will return a dictionary (key/value pair) to be expanded into the node.

@Monniasza
Copy link

Maybe there could be ability to make reusable LUA patches, like this. #! calls a patch that modifies a node in-place.

@PART[*]:HAS[@RESOURCE[LiquidFuel]]{
    #!patchTanks()
    #!patchLPG()
}
@PART[]:HAS[@RESOURCE[MonoPropellant]]{
    #!patchTanks()
    #!patchTDRCS()
}

@Lisias
Copy link
Author

Lisias commented Feb 5, 2025

Maybe there could be ability to make reusable LUA patches, like this. #! calls a patch that modifies a node in-place.

@PART[*]:HAS[@RESOURCE[LiquidFuel]]{
    #!patchTanks()
    #!patchLPG()
}
@PART[]:HAS[@RESOURCE[MonoPropellant]]{
    #!patchTanks()
    #!patchTDRCS()
}

Already covered by #% that will return a dictionary. If one of the values of the dictionary is another dictionary, then we insert/replace a new node. I don't think it would be wise to merge nodes - if this is what one would want, it needs to send the original node as parameter and the Lua code does whatever it needs to do.


Humm... Nope. #% will not cut it by itself. Dictionary values are unique by obvious reasons, so this scheme will prevent us from injecting more than one ENGINE for example.

We need to use an array or something, where each array item would be a tuple with (name, dict), where name would be the node's name (ENGINE, RESOURCE, etc). So, yeah, I think we will have a #! after all.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

2 participants