Author Topic: scripting  (Read 24758 times)

Offline gchevallereau

  • Sergeant
  • **
  • Posts: 41
    • View Profile
scripting
« on: January 11, 2012, 09:49:18 pm »
Hi,

I have recently started playing with SWIG(https://swig.org). I have tried to bind some parts of OpenXcom in python. So far, i have a working version which allow to run some python script. I have uploaded some example scripts i have tried here : https://gchevallereau.net/guillaume/python/
I will push this to my personal git repo soon, but I want to know if there are people interested?
I think that this would be an interresting addition to OpenXcom. This can be used to help development and maybe later this can be an interresting tools for modders.

Volutar

  • Guest
Re: scripting
« Reply #1 on: January 12, 2012, 01:10:17 pm »
I agree with idea of getting game logic into script with native engine.
It will greatly simplify all aspects of "modding" and extending/expanding of game.

Offline michal

  • Commander
  • *****
  • Posts: 629
    • View Profile
Re: scripting
« Reply #2 on: January 12, 2012, 01:39:09 pm »
+1 from me ;) But i'm not sure about python. What about lua? It's popular in games:

https://en.wikipedia.org/wiki/Category:Lua-scripted_video_games

But of course any scripting language is better than none :D

Offline Daiky

  • Battlescape Programmer
  • Administrator
  • Commander
  • *****
  • Posts: 904
    • View Profile
Re: scripting
« Reply #3 on: January 12, 2012, 02:59:00 pm »
What was already said here:
https://openxcom.org/forum/index.php/topic,11
And that discussion did lead to having all hardcoded data in external YAML files. Which imho is already a big step forward.

Also, you will see that modders always come up with things that will not be able to be done with scripting alone. Code changes are always needed. Unless you have a very generic game engine, and really move all logic to scripting. But then I think we can start all over again... but I can be wrong, because honestly I don't have any experience with either python or lua.
« Last Edit: January 12, 2012, 03:19:22 pm by Daiky »

Offline michal

  • Commander
  • *****
  • Posts: 629
    • View Profile
Re: scripting
« Reply #4 on: January 12, 2012, 03:51:31 pm »
You could move game logic from c++ to scrips partially, for example battlescape ai first, then geoscape ai, etc.

Anyway, that stuff should wait after 1.0. Adding it now to official repo could slow project too much. But IMHO it's good to experiment ;)
« Last Edit: January 12, 2012, 07:00:44 pm by michal »

Offline gchevallereau

  • Sergeant
  • **
  • Posts: 41
    • View Profile
Re: scripting
« Reply #5 on: January 12, 2012, 09:33:11 pm »
Quote
But i'm not sure about python. What about lua? It's popular in games
It should be doable with lua either. I choosed python because this the one i know. But the way it's done, it's shoud be easy to get lua support.

Quote
What was already said here:
https://openxcom.org/forum/index.php/topic,11
And that discussion did lead to having all hardcoded data in external YAML files. Which imho is already a big step forward.

Also, you will see that modders always come up with things that will not be able to be done with scripting alone. Code changes are always needed. Unless you have a very generic game engine, and really move all logic to scripting. But then I think we can start all over again... but I can be wrong, because honestly I don't have any experience with either python or lua.
Did not see that discussion before. Ruleset are fine, but i don't think it's enough. There are case where you need programming language In the referenced discussion, someone suggested a teleporting device. It's not something you can do only with ruleset. I'm sure that you can easily find other thing where it can be useful.

Anyway, i think it will be more clear once i push the beast to a git repo(just need some code clean).

Quote
You could move game logic from c++ to scrips partially, for example battlescape ai first, then geoscape ai, etc.
There are little points in moving already implemented stuff to another language. It's much more interresting for new stuff.

Quote
Anyway, that stuff should wait after 1.0. Adding it now to official repo could slow project too much. But IMHO it's good to experiment ;)
It's exactly how i see it. There are a lot's of stuff which are much more important than scripting at the moment(ruleset for instance). But when we will need it, we will already have something to experiment with. It can also be interresting to see what will need to be modified later to help moddability.

Offline gchevallereau

  • Sergeant
  • **
  • Posts: 41
    • View Profile
Re: scripting
« Reply #6 on: January 13, 2012, 11:50:21 pm »
I have pushed my branch here : https://gchevallereau.net/cgit/cgit.cgi/OpenXcom/log/?h=swig

Some explanations on the  build:
* You must use CMake. It should work on both Linux and Windows(Visual Studio)
* You will need swig and python. I have put a ZIP file of all needed dependencys here: https://gchevallereau.net/guillaume/openxcom/deps_vc.zip. If you use it, you can only build in release and relwithdebinfo(python debug lib is not in the zip file)

Once built, you have two options to use it:
* put a script in /tmp (Linux) or in My Documents (Windows), the file must be named run_openxcom.py. Note: the file will be removed once runned.
* press F6, you can now type python code directly.

Offline michal

  • Commander
  • *****
  • Posts: 629
    • View Profile
Re: scripting
« Reply #7 on: January 16, 2012, 09:29:04 am »
Would be cool if you could provide build with embedded python and some sample scripts.

Offline gchevallereau

  • Sergeant
  • **
  • Posts: 41
    • View Profile
Re: scripting
« Reply #8 on: January 18, 2012, 09:05:52 pm »
Will do. I first need to fix some problems on Windows. But i have some ideas of example scripts

Offline gchevallereau

  • Sergeant
  • **
  • Posts: 41
    • View Profile
Re: scripting
« Reply #9 on: January 22, 2012, 06:21:30 pm »
I finally got a working windows build. You can get it here:
https://gchevallereau.net/guillaume/openxcom/OpenXcom_python-0.3-win32.zip

Once in game, you can press F6 to show/hide a python console. This console is fine for short tests. If you are going to try some longuer experiments, you can save your code into a file and drop in My Documents(Windows) or /tmp(Linux). The file must be named run_openxcom.py.

Here are some explanations on how to use it. The first thing you want to do is to import the python module and get the main game reference:
Code: [Select]
import OpenXcom
game = OpenXcom.getGame
savedGame = game.getSavedGame()

If you are not familiar with the OpenXcom code, the savedGame will give you access to most of game elements(Bases, funds, ...), the game is needed by nearly anything and holds resources and Ruleset elements.
Functions/Class have the same name than in C++, so you can use the doxygen documentation. However some of them are not yet binded.

Here are some example:
Going bankrupt:
Code: [Select]
import OpenXcom
savedGame = OpenXcom.getGame().getSavedGame()
savedGame.setFunds(0)
# Or get more money. But this cheating. This is bad
savedGame.setFunds(99999999)

Starting a battlescape mission:
This one is bit longer
Code: [Select]
import OpenXcom

# Start a battlescape terror mission

g = OpenXcom.getGame()
sg = g.getSavedGame()
sbg = OpenXcom.SavedBattleGame()
bases = sg.getBases()
base = bases.front()
crafts = base.getCrafts()
craft = crafts.front()

sg.setBattleGame(sbg)
bg = OpenXcom.BattlescapeGenerator(g)
bg.setMissionType(OpenXcom.MISS_TERROR)
bg.setWorldTexture(1)
bg.setWorldShade(0)
bg.setCraft(craft)
bg.run()
battlegame = sg.getBattleGame()
battlegame.resetUnitTiles()

battlescape = OpenXcom.BattlescapeState(g)
g.pushState(battlescape)

Peoples who have already read the OpenXcom code, should understand this without any problems (This heavily inspired from the Battlescape quick test code which is in the Geoscape).

I have some other ideas, which will require some changes to the OpenXcom code:
* Allow to create custom interface for some Game screen(research,manufacture,...)
* Define custom battlescape items
* Allow to define game logic elements(Automatic selling of manufacture for example)

Offline gchevallereau

  • Sergeant
  • **
  • Posts: 41
    • View Profile
Re: scripting
« Reply #10 on: February 09, 2012, 11:16:49 pm »
Hi,

So i have now a version of OpenXcom which allow to create custom screen and game logic. You can find the code here: https://gchevallereau.net/cgit/cgit.cgi/OpenXcom/log/?h=swigX

Before introducing those modification, I want to explaing how the OpenXcom SWIG/python bindings work.

Before starting with OpenXcom, a little explanation on how swig work. swig parse the source code and output two kind of files.
* First a language specific(python here) which contains exported definitions.
* Second a really big C++ file(more than 145000 lines for OpenXcom!). This file is a glue code between C++ and the target language. In our case this file is built as a python module.
To parse the source code, swig need an input file. Most of the work is to write this input file. Now, if you look at the swig branch, you won't find it. I use CMake to auto-generate it.

If you look at the swig branch you will see that a lot a of file has been modified, but most of the modification are to build a libOpenXcomBase(Windows dll stuff). This library is needed to build the python module.
The python stuff is not that big. Only two files:
* python_out.cpp: A python module used to redirect the python stdout and stderr to the python console
* python.cpp: The main python interface. This file contains the two function used to execute python code(runPython and runPythonString). Also contains initialization and clean up code.


So how the custom State work?
to allow redefining state, i had to change the way state are created. Instead of directly creating it, we ask a StateFactory to do it. State are created using an instance of a StateInfo class. So in C++ we have:
Code: [Select]
class MyState : public State
{
};
class MyStateInfo : public StateInfo
{
};
REGISTER_CREATOR("MyStateId", MyStateInfo); https:// automatically append it to the StateFactory

and when we need to instantiate it:
Code: [Select]
State * s = _game->getStateFactory ()->createState("OPENXCOM_RESEARCHSTATE",
   args);
This downside, is that when creating a state we usually need to pass some arguments. As we have no base class for thing in Ruleset or Savegame, I have used a little hack. All arguments are void * pointers. If it's not really the cleanest way to do it, it actually work great.
Another problem was the  handling of callback function for events. They are at the moment pointer to class members. SWIG is not able to bind this. The solution was to create children class in python and reimplements event handling in those class. You can see that in Button for example are all PythonTextButton instead of TextButton.

game logic:
The implementation is quite similar to the custom state. There is GameLogic base class and a GameLogic manager. In python we can redefine child class of GameLogic and then add it to the GameLogicManager. They will be automatically handled.

Implementation note: I haven't changed all the code. Only the Research/Production State can be redefined. The same goes for GameLogic, new GameLogic elements can be added, but only craft repairing can be replaced. I do not plan to change this at the moment.


I put a windows build here: https://gchevallereau.net/guillaume/openxcom/OpenXcom_python-0.3-win32.zip
You can find some example script here: https://gchevallereau.net/guillaume/openxcom/scripts.zip. This zip contains 3 scripts:
* research.py: replace the Research screen
* repair_engineer.py: replace the craft repairing game logic. Craft can be repaired faster if you have available engineers.
* autosell.py: replace the production state to allow automatic selling of production.
Just unzip this file and copy all script to the python/auto-start folder.

Have fun!

Offline michal

  • Commander
  • *****
  • Posts: 629
    • View Profile
Re: scripting
« Reply #11 on: February 10, 2012, 12:42:47 pm »

I put a windows build here: https://gchevallereau.net/guillaume/openxcom/OpenXcom_python-0.3-win32.zip
You can find some example script here: https://gchevallereau.net/guillaume/openxcom/scripts.zip. This zip contains 3 scripts:
* research.py: replace the Research screen
* repair_engineer.py: replace the craft repairing game logic. Craft can be repaired faster if you have available engineers.
* autosell.py: replace the production state to allow automatic selling of production.
Just unzip this file and copy all script to the python/auto-start folder.

Pics or didn't happen !! ;)

That sounds really interesting, especially that scripts will be autoloaded. Also, i like that you can replace screens / game logic.

Offline Daiky

  • Battlescape Programmer
  • Administrator
  • Commander
  • *****
  • Posts: 904
    • View Profile
Re: scripting
« Reply #12 on: February 10, 2012, 01:00:44 pm »
From my own experience I can say that for battlescape there may be 2 areas where scripting might be useful in the future (far away future :p):
-generation of the battlescape; the rules of the placement of mapblocks, like with roads in a terrorsite, you could make more complex rules, like a tankstation that has to be connected to the road. I can imagine a desert-map, with one road in the middle and tank station or maybe a motel that needs to be next to the road.
Modding idea: desert + road + motel / tankstation can be made with all the tilesets already available ;)
-AI; you can make AI more complex, or add new features like aliens using medikits.



Volutar

  • Guest
Re: scripting
« Reply #13 on: February 10, 2012, 01:27:18 pm »
New unit appearance (non orthodox movement type, cell structure, not only 1x1x1 or 2x2x1), new weapon/armament types... All this impossible without proper scripting or deep coding.

Offline Yankes

  • Global Moderator
  • Commander
  • *****
  • Posts: 3350
    • View Profile
Re: scripting
« Reply #14 on: February 10, 2012, 05:23:05 pm »
New unit appearance
btw Daiky do OpenXcom allow loading custom graphic? AFIK now to add custom graphic you need modify code or data files.