The Wayback Machine - https://web.archive.org/web/20160829151740/http://gamedev.stackexchange.com:80/questions/123526/a-python-script-controlling-a-unity-game
Game Development Stack Exchange is a question and answer site for professional and independent game developers. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I wish to build a simple game in Unity such that the objects in the game can be controlled via a Python script (or a code in any other programming language). Is this possible? If yes then how? If no then are there any other alternatives to achieve similar results?

To make it more clear, say that I have 10 objects in my current scene. What I wish to do is to address each object individually via Python. One way of doing this is setting up keyboard bindings to select a particular object and then using keyboard and mouse events to control this object. But, is there a more cleaner (a native) way of doing the same?

share|improve this question
    
Like you want to load and run a python script at runtime? – ssbJun 7 at 4:47
    
@ssb nope thats not what I meant. I mean the controller of the game is a Python script (i.e I write scripts to control the game objects) – ironsteinJun 7 at 4:48
    
So you want to use a python script to provide automated input instead of a human player? – ssbJun 7 at 4:49
    
@ssb Thats exactly what I want. – ironsteinJun 7 at 4:50
    
you can add IronPyton to your unity project and then create a c# script that will load python scripts from files and run them. I found this tutorial and it seems easy enough.link Then I guess you can import UnityEngine.dll into a IronPythong script and use the unity stuff like FindGameObjectWithTag and so on. – Uri PopovJun 7 at 11:21

Ok so first follow this tutorial. Then i wrote some code to try and test it out. C# code. I used the editor example from the tutorial but you can make it run during runtime or what ever:

 [MenuItem("Python/LoadFromFile")] public static void ReadFile() { var ScriptEngine = IronPython.Hosting.Python.CreateEngine(); var ScriptScope = ScriptEngine.CreateScope(); ScriptEngine.Runtime.LoadAssembly(typeof(GameObject).Assembly); ScriptEngine.Runtime.LoadAssembly(typeof(Editor).Assembly); StringBuilder example = new StringBuilder(); FileInfo pySourceFile = new FileInfo("PyExampleString.txt"); StreamReader reader = pySourceFile.OpenText(); while(!reader.EndOfStream) { example.AppendLine(reader.ReadLine()); // Debug.Log(reader.ReadLine()); } reader.Close(); var ScriptSource = ScriptEngine.CreateScriptSourceFromString(example.ToString()); ScriptSource.Execute(ScriptScope); } 

Then I had to read how to do if statements in phyton and got one indentation error but I ended up with this in a .txt file named PyExampleString.txt

import UnityEngine as unity if unity.GameObject.FindGameObjectWithTag("Test"): unity.Debug.Log("Found one") 

This is tested and logs Found one if there is a game object with a tag Test in the scene. Hope you find this helpfull.

share|improve this answer
    
Thanks a lot, appreciate it. And may I suggest, learn Python. Its fun ;) – ironsteinJun 7 at 15:14

I hope I understood your question correctly. What I gathered was that you have an Unity game, and you want to have a Python script that provides input to the game instead of a human playing the game. Is that right?

In that case, yes, you can use a Python script to provide input to the game. The task isn't very pleasant, but yes, it can be done. Basically what you are looking for is a way to generate regular OS input events: mouse movement and clicks, key presses and releases, and perhaps even controller input events (all though this might be the hardest one to implement). Now, generating these events isn't something you can easily do in a cross-platform manner, so I'll only go trough some options you have for Windows.

There are libraries from Python that allow you to interact with the underlying Windows libraries. You might want to take a look at pywin32, and investigate the WinAPI on how to generate key events. A quick google search also showed me this SO answer which does exactly what you are looking for. You would then extend that piece of code posted on the great answer.

And this task can be also achieved with other languages, as long as there is a way to generate OS input events in the language in question.

share|improve this answer
    
Thank you for your reply. Although this is a perfectly sound way of solving the problem, is there some way in which the Python script can address individual unity game objects? For example, if there are 10 objects in the scene, I wish to control all of them independently. I could use keyboard bindings to select an objects and the use keyboard or mouse events to control this object, but is there some cleaner way? – ironsteinJun 7 at 9:10
    
Probably yeah. Selecting individual objects might be hard. I'm kinda wondering why would you want a cleaner way to do this when you are already looking for more trouble with doing this outside of Unity. The most clean and native way to do this would be to do this with C# in Unity. – Tyyppi_77Jun 7 at 10:05
    
It is true that I could write the code directly in C# in unity, but then that would defeat the intention. My intention is to build a game and provide an interface to the game such that the game can be played by writing python scripts. So, the scripting part would be done after the entire game is already built (and would not require an installation of Unity, which is too big). – ironsteinJun 7 at 13:44

Yes you can, but instead of working directly with pywin32 for Windows which is a pain in the ass you can use pywinauto, it allows you to send mouse and keyboard actions to windows accesing their widgets/controls directly, which is better but it's not crossplatform just for Windows.

Or you can use PyAutoGUI for (Windows, OSX, Linux), which instead of sending the input to a specific window or dialog I think it works like if you 'capture' the screen and you send the inputs in a determined position, so the window must be visible in front of any other thing.

share|improve this answer

Not the answer you're looking for? Browse other questions tagged or ask your own question.

close