Skip to content

Instantly share code, notes, and snippets.

@iamgreaser
Last active August 29, 2015 14:02
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save iamgreaser/9677b0e7ddb768d9ce36 to your computer and use it in GitHub Desktop.
Save iamgreaser/9677b0e7ddb768d9ce36 to your computer and use it in GitHub Desktop.
Indie Quilt non-Unity API
You could hypothetically use this API for Unity games, as long as you can grab the commandline arguments and bail out with return codes. But of course, it's probably better to just integrate with the main launcher.
CALLING AN APPLICATION:
--------
THIS C CODE SNIPPET IS RELEASED INTO THE PUBLIC DOMAIN
NOTE THAT IT'S UNTESTED, SO BE WARY
--------
enum {
GAME_CLOSED_OR_CRASHED,
GAME_WON,
GAME_LOST,
}
int play_game(const char *exename, int difficulty, int w, int h)
{
char cmdline[256];
sprintf(cmdline, "%s -indiequilt %i %i %i", exename, difficulty, w, h);
switch(system(cmdline))
{
case 77:
return GAME_WON;
case 13:
return GAME_LOST;
default:
return GAME_CLOSED_OR_CRASHED;
}
}
--------
END OF CODE SNIPPET
I'm not sure what it looks like in C#, but that should give you a good idea of how to do things.
I can provide code which uses CreateProcess if you want that. It's not as elegant, but it works.
--------
OK, so that's the API definition in a nutshell.
Here's a more formal definition.
Applications take 4 arguments, separated by spaces.
- The first is the static string "-indiequilt".
- The second is an integer from 1 to 10 inclusive indicating the difficulty, OR 42 to test if the program will actually run.
- The third is the width of the window to open.
- The fourth is the height of the window to open.
This is how it will be called. Your parser only needs to tolerate what gets thrown in, but it can be more tolerant than that. It is up to you as to what happens when no arguments or different arguments are given - I recommend just popping up a usage dialogue and quitting.
If the difficulty is 42, you are to pretty much just quit straight away with a win (77). Any other return code will mark this game as "unrunnable" (note, latest Game Maker Studio doesn't play nice with Wine, which is what I will be using!). I may be able to insert some nasty hacks to stop Game Maker from popping up its "loading" screen for this, or we might just have to check if the process opens without an error. Still, if you get a difficulty of 42, just load everything and quit with a win.
Applications return one of the following return codes:
- On a win, 77.
- On a loss, 13.
- On a quit or a crash, 0 if possible. But basically, anything that isn't 77 or 13... or 259. (I'm not joking, see the GetExitCodeProcess docs as to why returning 259 is a STUPID idea.)
If you're implementing a DLL to hook up to e.g. Game Maker, here are a couple of useful functions:
LPTSTR WINAPI GetCommandLine(void);
http://msdn.microsoft.com/en-us/library/windows/desktop/ms683156%28v=vs.85%29.aspx
VOID WINAPI ExitProcess(
_In_ UINT uExitCode
);
http://msdn.microsoft.com/en-us/library/windows/desktop/ms682658%28v=vs.85%29.aspx
I'll be making a DLL to make this thing easier. The API will be as follows:
void game_win(void);
Quit with a win.
void game_lose(void);
Quit with a loss.
int game_args_valid(void);
Returns 1 if the arguments are valid, and 0 if they are not. It is up to you as to what to do here.
If the arguments are invalid, the defaults for the other things are:
- difficulty = 42
- width = 640
- height = 480
Please call this function when ready.
int game_get_difficulty(void);
Returns the requested difficulty. If it's 42, call game_win() when you have loaded everything.
int game_get_width(void);
Returns the requested window/screen width.
int game_get_height(void);
Returns the requested window/screen height.
There are also floating-point versions of these functions, which you MUST use if you are using Game Maker (at least from my understanding):
double gamef_args_valid(void);
double gamef_get_difficulty(void);
double gamef_get_width(void);
double gamef_get_height(void);
To use these functions in Game Maker, you will have to use some of these lines (note, these pertain to Game Maker 4.2a, and you have to disable Secure Mode in the file -> preferences dialogue):
args_valid = external_call0(external_define0("iqhook.dll","gamef_args_valid",ty_real));
difficulty = external_call0(external_define0("iqhook.dll","gamef_get_difficulty",ty_real));
gamewidth = external_call0(external_define0("iqhook.dll","gamef_get_width",ty_real));
gameheight = external_call0(external_define0("iqhook.dll","gamef_get_height",ty_real));
external_call0(external_define0("iqhook.dll","game_win",ty_real));
external_call0(external_define0("iqhook.dll","game_lose",ty_real));
If you are using Python, Ruby, or some other scripting languages that fulfil certain criteria, you do not need to use the DLL, as the environment provides enough information already.
Here's some Python code anyway.
import sys, os
avalid, difficulty, width, height = False, 42, 640, 480
if len(sys.argv) > 4 and sys.argv[1] == "-indiequilt":
avalid, difficulty, width, height = True, int(sys.argv[2]), int(sys.argv[3]), int(sys.argv[4])
def game_win():
sys.exit(77)
def game_lose():
sys.exit(13)
def game_quit():
sys.exit(0)
The DLL and some example code is available here:
https://dl.dropboxusercontent.com/u/32094129/quilt/iqhook.zip
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment