project-navigation
Personal tools

Author Topic: lua design thoughts  (Read 26144 times)

Offline xray

  • Rookie
  • ***
  • Posts: 72
    • View Profile
lua design thoughts
« on: June 11, 2014, 09:25:51 pm »
Hi,

I've created a fork of the master branch to begin replacing the current ui script language with lua.

Before getting into the coding, it's always good to have some thoughts about how the implementation should look like. That's what this post is for and I invite everyone to post ideas.

The goal is to bring lua in as a scripting language, replacing the current native script implementation found in the ui. I'll probably start with the ui-part since that's the area that'll benefit most.

One question I'd like to hear some views on is wether the implementation should be allowed to break the current scripts or that it should be additive. The first will lead to a full rewrite of the .ufo files, the second will allow a more evolutionary rewrite of .ufo files.

Another question is wether the lua language should be used for all the .ufo files, including those not dealing with the ui (e.g. campaigns.ufo, installations.ufo).

I'll be looking forward to any thoughts.

xray

Offline Duke

  • Administrator
  • PHALANX veteran
  • *****
  • Posts: 1037
    • View Profile
Re: lua design thoughts
« Reply #1 on: June 11, 2014, 11:31:07 pm »
Some devs (including me) + potential contributors are not familiar with LUA. So a good start would be to take some existing GUI elements from the scripts and show them here in comparison to what they could look like in LUA.

Considering the huge amount of scripted data we have, I vote for a migration. Probably on a per file basis.

Unlike the UI, the other scripts are mostly plain data definitions afaik. What would be the benefits of using LUA ? Again, comparing old and new examples would help me understand it better.

If we choose the 'additive' solution, it should be possible to automagically transform most of the .ufo files with some 'converter-tool'. That should speed up the migration process and avoid the errors inevitebly resulting from manual conversion.

Offline Mattn

  • CaveExpress
  • Administrator
  • PHALANX Commander
  • *****
  • Posts: 4830
  • www.caveproductions.org
    • View Profile
    • CaveExpress
Re: lua design thoughts
« Reply #2 on: June 12, 2014, 04:07:26 pm »
* we could get syntax checks in an editor
* we could do more things in the ui scripts that we can do now
* we don't have to maintain an own language
* lua is well known to the world (our script not)

but i would also vote for a small example window (maybe the main window) and just put the code in place. keep in mind that we are heavily replacing/reworking the ui in 2.6 - so just stick to one window until the code is in place, then we can merge the code (side by side with the old ui scripts) - then start the conversion window by window as aduke suggested.

I would first vote only for the ui.

Offline xray

  • Rookie
  • ***
  • Posts: 72
    • View Profile
Re: lua design thoughts
« Reply #3 on: June 17, 2014, 03:39:02 pm »
I've recreated a small part of the file main.ufo into lua to show what it could look like in lua (see code snippet below). Added some comments to explain a bit what is happening. Feel free to post any comments on it.

As for the actual implementation. I'm planning to use SWIG to create the binding between lua and the ufo main C/C++ code. The advantage of this is, that should lua evolve (chances are it will), the SWIG tool will handle this. Also, SWIG provides binding implementation for multiple dynamic languages, so should the need arise to actually switch to another script language, it will be a lot easier to do.

xray

Code: [Select]
--[[
MAIN MENU
--]]

-- definitions of named colors (not present yet, names are illustrative)
-- contains entry: COLOR_DARK_YELLOW = [0.0, 0.5, 0.0, 1.0]
-- contains entry: COLOR_WHITE = [1.0, 1.0, 1.0, 1.0]
require ("_colors.ufo")

-- create title control
local lb_title = Label ("_UFO: ALIEN INVASION", 500, 50, 262, 50, "f_title", [0.59, 0.78, 0.56, 1.0], ALIGN_CC)

-- create facebook button
local btn_facebook = Button ("_Facebook", 10, 720, 80, 20, COLOR_DARK_YELLOW)
btn_facebook.tooltip = "_Like us on facebook"
btn_facebook.padding = 0
btn_facebook.selectcolor = [1, 1, 1, 1]

function btn_facebook:onClick ()
-- todo
end

-- create twitter button
local btn_twitter = Button ("_Twitter", 100, 720, 70, 20, COLOR_DARK_YELLOW)
btn_twitter.tooltip = "_Follow us on twitter"
btn_twitter.padding = 0
btn_twitter.selectcolor = COLOR_WHITE

function btn_twitter:onClick ()
-- todo
end

-- import a button defined in _assets.ufo.lua (the .lua is added automatically)
require ("_assets.ufo")

-- create button CAMPAIGN
local btn_campain = MainMenuBtn ("_CAMPAIGN")

function btn_campaign:onClick ()
-- todo
end

-- create buttons panel
local pnl_buttons = Panel ()
pnl_buttons.pos = [312, 250]
pnl_buttons.size = [400, 400]
pnl_buttons.layout = LAYOUT_TOP_DOWN_FLOW
pnl_buttons.layoutMargin = 15

-- create the main window
local main = Window ()
main.background = "ui/main_bg"
main:add (title)
main:add (btn_facebook)
main:add (btn_twitter)
main:add (pnl_buttons)

Offline Duke

  • Administrator
  • PHALANX veteran
  • *****
  • Posts: 1037
    • View Profile
Re: lua design thoughts
« Reply #4 on: June 17, 2014, 10:52:41 pm »
I found one of the most painful tasks in UI developement is to count pixels to align UI elements properly.
What would it look like if I want to place the twitter and facebook buttons from your example
- at the same y
- give them the same height
- and place the 2nd +60x from the first
without magic numbers ?
« Last Edit: June 17, 2014, 10:54:32 pm by Duke »

Offline Mattn

  • CaveExpress
  • Administrator
  • PHALANX Commander
  • *****
  • Posts: 4830
  • www.caveproductions.org
    • View Profile
    • CaveExpress
Re: lua design thoughts
« Reply #5 on: June 18, 2014, 10:19:15 am »
well, that is something that could be scripted in lua with some own functions. we don't need c++ code for that.

anyway - great stuff, i like it.

Offline xray

  • Rookie
  • ***
  • Posts: 72
    • View Profile
Re: lua design thoughts
« Reply #6 on: June 18, 2014, 01:02:00 pm »
I found one of the most painful tasks in UI developement is to count pixels to align UI elements properly.
What would it look like if I want to place the twitter and facebook buttons from your example
- at the same y
- give them the same height
- and place the 2nd +60x from the first
without magic numbers ?

Actually, what you are requesting here is something called a layout manager. It is probably a good idea to implement such feature and it is possible to do this in lua, though I'm not really sure what the performance impact will be here. Anyway basically it comes down to exposing some metrics from the environment to the lua script (e.g. screen widht/height) as constants and writing functions that position window/panel/buttons. These functions can be written in a generic way so that they can be reused. Also, apart from positioning controls, it might also be interesting to look to seperating the styling of the gui from the structure.

Offline shevegen

  • Squad Leader
  • ****
  • Posts: 224
    • View Profile
Re: lua design thoughts
« Reply #7 on: June 22, 2014, 09:02:04 pm »
Don't forget the docs please!

Docs help other people understand.

Offline xray

  • Rookie
  • ***
  • Posts: 72
    • View Profile
Re: lua design thoughts
« Reply #8 on: June 27, 2014, 10:31:24 pm »
Work is progressing slowly, but at least it is moving forward. On the way I had to figure out a way to identify lua script from other (old style ;D) scripts. I guess the easiest solution would be to use the .lua file extension, however, this might bring in some unwanted side effects in external tools (e.g. makefiles, packaging tools). So I followed the linux method: adding a topline command identifying the file as a lua script. It looks like this.

Code: [Select]
--!usr/bin/lua

.. the rest of the lua code goes here ..

where the "--" being lua's line comment marker and "!usr/bin/lua" of course being an utterly arbitrary string.

xray

Offline Mattn

  • CaveExpress
  • Administrator
  • PHALANX Commander
  • *****
  • Posts: 4830
  • www.caveproductions.org
    • View Profile
    • CaveExpress
Re: lua design thoughts
« Reply #9 on: June 28, 2014, 12:50:26 pm »
imo we should just use a custom extension for this. lus for example - "l"ua-"u"fo-"s"cript or lua-ui-script. something like that.

This is due to the fact that we have directory listing functions that can filter by extension. And this is (in particular if you are using pk3) a lot faster than first open a file, check the "magic" and then discard or not discard it.

what do you think?

Offline Mattn

  • CaveExpress
  • Administrator
  • PHALANX Commander
  • *****
  • Posts: 4830
  • www.caveproductions.org
    • View Profile
    • CaveExpress
Re: lua design thoughts
« Reply #10 on: June 28, 2014, 12:50:58 pm »
oh... btw. did you fork ufoai on github? and if so, did you already push some stuff that i could check out?

Offline xray

  • Rookie
  • ***
  • Posts: 72
    • View Profile
Re: lua design thoughts
« Reply #11 on: June 28, 2014, 06:44:28 pm »
oh... btw. did you fork ufoai on github? and if so, did you already push some stuff that i could check out?

Yes, did forked the main branch. Visit on http://github.com/rxadmin/ufoai.

I did pushed a few changes to git however nothing substantional yet. I'll make a push when I can actually run some lua code.
imo we should just use a custom extension for this. lus for example - "l"ua-"u"fo-"s"cript or lua-ui-script. something like that.

This is due to the fact that we have directory listing functions that can filter by extension. And this is (in particular if you are using pk3) a lot faster than first open a file, check the "magic" and then discard or not discard it.

what do you think?

Actually, I'm not sure if the opening of the file is such a big issue. I'm investigating a way to precompile the lua script files before using them. So the actual work of opening the file is only at startup. Also, currently the opening of the file is actually embedded with the old script engine reading the headers of the .ufo files (see: FS_NextFileHeader).

xray

Offline Mattn

  • CaveExpress
  • Administrator
  • PHALANX Commander
  • *****
  • Posts: 4830
  • www.caveproductions.org
    • View Profile
    • CaveExpress
Re: lua design thoughts
« Reply #12 on: June 28, 2014, 07:14:38 pm »
yes, but only *.ufo files, not any other file with a different extension in the same dir.

doing it by file extension would also not lead to the need to add the magic header to each file - but ok, first let's see it in action, then we can continue to discuss this minor thing.

Offline Mattn

  • CaveExpress
  • Administrator
  • PHALANX Commander
  • *****
  • Posts: 4830
  • www.caveproductions.org
    • View Profile
    • CaveExpress
Re: lua design thoughts
« Reply #13 on: June 29, 2014, 10:12:21 am »
i've checked your branch a little bit - can you explain how this swig stuff will work for us? what is needed in order to generate the bindings and stuff like that?

Offline xray

  • Rookie
  • ***
  • Posts: 72
    • View Profile
Re: lua design thoughts
« Reply #14 on: July 01, 2014, 10:51:19 am »
i've checked your branch a little bit - can you explain how this swig stuff will work for us? what is needed in order to generate the bindings and stuff like that?

For a complete overview I suggest you check http://www.swig.org/. In brief it translates a interface (.i) file to a c code module that can be linked into the application and that contains the boilerplate code needed to link lua and C++. In the .i you specify what types, constants, functions, structures etc. are exposed to lua. The code module will then hold wrapper functions for all this stuff as well as some initializing functions.

So, as an example, suppose you want to expose the Com_Printf(..) function to lua. The interface file looks like this.
Code: [Select]
%module common

%{
/* the header file including the Com_Printf(..) function goes here */
#include "shared.h"
%}

/* expose common print function */
void Com_Printf(const char* fmt, ...);

The result is a c module containing the wrapper code. A small part is shown below. The advantage of using SWIG is that the writing the boilerplate code is rather tedious and error prone. Even though lua has a simple binding API, the actual process of binding functions, variables, structs etc. is a lot of work. SWIG takes care of this so we can concentrate on the fun thing: deciding what to expose.

Code: [Select]
#ifdef __cplusplus
extern "C" {
#endif
static int _wrap_Com_Printf(lua_State* L) {
  int SWIG_arg = 0;
  char *arg1 = (char *) 0 ;
  void *arg2 = 0 ;
 
  SWIG_check_num_args("Com_Printf",1,1)
  if(!SWIG_lua_isnilstring(L,1)) SWIG_fail_arg("Com_Printf",1,"char const *");
  arg1 = (char *)lua_tostring(L, 1);
  Com_Printf((char const *)arg1,arg2);
 
  return SWIG_arg;
 
  if(0) SWIG_fail;
 
fail:
  lua_error(L);
  return SWIG_arg;
}