PDA

View Full Version : Scripting API/Reference/Design thread



Gleeok
12-12-2012, 02:52 AM
[edit] Update: I've scrapped angelscript;


All scripting is now done in C# and the runtime is embedded. Updates to follow.

Moosh
12-12-2012, 03:19 AM
This is all greek to me, sadly. Working on the assumption that this will work fairly similar to ZScript, could we maybe have copy/paste functionality in the built in script editor? The one thing that bugs me the most about ZScript is probably the reliance on importing scripts as .z files with a bare minimum script editor built in.

What will be the FFC equivalent of ffc scripts since there probably won't be ffcs in FFC? Will they be split into field and battle scripts and be assigned to specific maps and encounters? Could one attach a script to an inventory item or command similar to an item script in ZC. Am I being too closed minded here? Probably am.

Also kinda curious how scripting would work in a turn based battle system. Would there be some sort of waitturn() command to prevent stuff from happening between turns?

Gleeok
12-12-2012, 04:21 AM
This is all greek to me, sadly. Working on the assumption that this will work fairly similar to ZScript, could we maybe have copy/paste functionality in the built in script editor? The one thing that bugs me the most about ZScript is probably the reliance on importing scripts as .z files with a bare minimum script editor built in.

What will be the FFC equivalent of ffc scripts since there probably won't be ffcs in FFC? Will they be split into field and battle scripts and be assigned to specific maps and encounters? Could one attach a script to an inventory item or command similar to an item script in ZC. Am I being too closed minded here? Probably am.

Also kinda curious how scripting would work in a turn based battle system. Would there be some sort of waitturn() command to prevent stuff from happening between turns?
I don't know how that would work since stuff like the battle engine is not done yet, so I can't give you any sort of good answer. There also is no editor yet. You can use any code or text editor available. This is mostly language, basic features for now. Sorry. ..

Also I can see why you are confused. Don't think of this as similar to ZC scripting. Think of it more like Game Maker (yuck) scripting (but faster and better times infinity... f**k you GM... cough.. shoot, ..I digressed...).

Why would you need things like item scripts at all anyway if you can create scripts dynamically? ...I suppose there would be at least three ways: events, objects, and through scripts, anyway. ..At the very least you could create any kind of script you wanted through another script. Example:


class MyObjectThatCreatesObjects
{
void run() //runs every logical frame
{
// NOTE: you do NOT need while true here!
wait(60); //wait one second
game.create_object("MyObjectThatCreatesObjects"); //create a never ending object creating object!!! :P

//note; after so many objects are created the engine throw an exception and close your game so this is a bad idea.
}
};

Events and Map objects have not been designed yet, however.

The battle engine will probably be real-time with a bool for turn-based. :) The BattleActor class (or whatever) might just implement the ATB system. (since it is arguably 99% real-time anyway.) I don't know for sure though since it doesn't exist. ;)

SUCCESSOR
12-12-2012, 05:24 AM
I don't have a lot to say. I am very glad you went with language I understand. It makes me very excited about this project. I can't wait to see more. How much of the mechanics of the game are going to be manipulatable through scripting? Without foregoing built in function and working from scratch I mean.

Gleeok
12-12-2012, 05:57 AM
I don't have a lot to say. I am very glad you went with language I understand. It makes me very excited about this project. I can't wait to see more. How much of the mechanics of the game are going to be manipulatable through scripting? Without foregoing built in function and working from scratch I mean.
Thank you! (Shhhh it's a secret but you could make any kind of 2d game you wanted from scratch using scripting or in c++ with the code. Don't tell anyone though.) -/_-

I've been looking at what rpg maker does and it seems that almost all of the logic is scripted using a type of function based script callback system. (Ruby is confusing to me though...) I'd like to do something similar (but easier to understand).

SUCCESSOR
12-12-2012, 06:05 AM
Thank you! (Shhhh it's a secret but you could make any kind of 2d game you wanted from scratch using scripting or in c++ with the code. Don't tell anyone though.) -/_-

I've been looking at what rpg maker does and it seems that almost all of the logic is scripted using a type of function based script callback system. (Ruby is confusing to me though...) I'd like to do something similar (but easier to understand).

:rolleyes:

That sounds very interesting. I have been meaning to look into RPG Maker though I know not a bit of Ruby.

MasterSwordUltima
12-12-2012, 07:03 AM
Ruby is...different. Yet somehow improved in the VX and VX Ace series. ANYWAY...

I'm curious as to whether or not the Menu System will be customizable through scripting.

Gleeok
12-12-2012, 07:21 AM
Ruby is...different. Yet somehow improved in the VX and VX Ace series. ANYWAY...

I'm curious as to whether or not the Menu System will be customizable through scripting.

You just hit one of the major time-killers of all time right between the eyes didn't you? ;)

...To preempt this I think the ENTIRE menu/inventory system will be scripted (using c++ for actual inventory of course). In order to do this the Gui and widget classes need to be very powerful, easy to use, and flexable. ..not an easy feat but I have some ideas. :)

Flash Man
12-12-2012, 08:55 PM
... could we maybe have copy/paste functionality in the built in script editor?

This will be a native feature of the editor, because it will be a (standard) Windows* Application. If things have not changed very much, then the zquest editor is an Allegro Application.

*As currently scheduled.

Imzogelmo
12-20-2012, 12:53 AM
I was just reading through to see if I can get an idea of how much would be pre-built vs. needing to be made with a script. Naturally, my mind first considers the menuing system-- any kind of Final Fantasy game has a main menu and various sub-menus accessible from it-- but the exact layout and contents of the menu would vary based on the specific details of the game. For instance, Final Fantasy IV needs 5 characters to be visible; FF V needs a job menu; FF VI needs a skills menu, etc. My point being that while they are all very similar and can probably be built from the same basic parts, the specific form that you end up with would differ based on the need of the game.

Parallel to that, I think the map would be a fairly universal module across games as well. Maps need a width, height, tileset, and of course the data (including probably at least a couple of layers). Several general things populate the map perhaps as additional layers: NPCs, treasure chests, event triggers, warps, animated tiles, layer-priority shifts, diagonal stairways, etc. It seems me that if you get the map powerful and flexible, and then a menu-subsystem.. that's 2/3 of the work right there (the battle engine being the other 1/3, of course).

Gleeok
05-14-2013, 06:54 PM
I'm working on the battle engine right now so let's see if we can add a bit of the combat and battle related API to this. (Though there's too much to type everything out right now, here's a brief description.)

*Data*
-character_data
-character_class
-monster_data

(Each of the previous holds base data for attributes, sprite id's, names, script name, description, etc..)

*Game Instances*
-character (initialized from character_data. all characters are )
-party (contains arrays of active/inactive characters, shared inventory, etc.)
-monster (initialized from monster_data. normally temporary objects for battles)

*Combat Instances*
-combatant
-player_combatant (holds a reference to a character)
-enemy_combatant(holds a reference to a monster)


Attributes are pretty much done and I'm in the process of "finalizing" other things as well. All attributes of any object above can be references by scripts by:


attributes.max_param[]
attributes.stat[]
attributes.status_atk[]
attributes.status_def
attributes.element_atk[]
attributes.element_def[]
attributes.misc[]


These can be kind of tricky at first though. For example


character.attributes.stat[STR] != character.base_attributes.stat[STR];

It's easy to type the wrong one. :P
The difference is character.attributes is read-only since it includes all the modified values from equipment, buffs, modifiers as well, and, accidentally setting base_attributes could be bad.


*Interesting Side-Effects from the design (Due mostly to c++ code-reuse patterns..and/or it was a few extra LOC. I wasn't even planning any of this, I swear!)*
-All monsters can equip items, and hold an inventory! Imagine a group of Goblins each equipped with long swords and leather gear!
-Easily possible to have "capsule monsters" or whatever. There you go.

And that's it for now. It's a WIP.


I was just reading through to see if I can get an idea of how much would be pre-built vs. needing to be made with a script. Naturally, my mind first considers the menuing system-- any kind of Final Fantasy game has a main menu and various sub-menus accessible from it-- but the exact layout and contents of the menu would vary based on the specific details of the game. For instance, Final Fantasy IV needs 5 characters to be visible; FF V needs a job menu; FF VI needs a skills menu, etc. My point being that while they are all very similar and can probably be built from the same basic parts, the specific form that you end up with would differ based on the need of the game.

Parallel to that, I think the map would be a fairly universal module across games as well. Maps need a width, height, tileset, and of course the data (including probably at least a couple of layers). Several general things populate the map perhaps as additional layers: NPCs, treasure chests, event triggers, warps, animated tiles, layer-priority shifts, diagonal stairways, etc. It seems me that if you get the map powerful and flexible, and then a menu-subsystem.. that's 2/3 of the work right there (the battle engine being the other 1/3, of course).

Right you are. My idea for menus is this:

A specialized, stripped down UI library designed only for console-styled jrpgs. (Obviously anything that can handle this can also handle any other kind of game, that doesn't involve a mouse that is, without too much trouble.) ...And that's it. O_o ...well things like auto-layout and auto-managed lists of various types is a huge win. I think this is the best option overall in terms of useability without tons of stupid windowing layout scripts, anyway.

If you have something better though then let me know, though I think component-based is by far the easiest and most flexible.

Imzogelmo
05-16-2013, 01:40 AM
At the risk of a pun, I think we're on the same page as far as menus. It has to be flexible enough to handle dynamic and static text, intuitive as far as a tree of selections goes, and quick to produce from an end-user.

Gleeok
05-16-2013, 02:48 AM
At the risk of a pun, I think we're on the same page as far as menus. It has to be flexible enough to handle dynamic and static text, intuitive as far as a tree of selections goes, and quick to produce from an end-user.

I think you mean U and I are on the same page. :nerd: ...I mean, ..yeah. Not looking forward to it, but I think I have some good concepts that are easy enough to add. I'd like to get a battle loop first, but definately been thinking about it.

Forgot to mention but RPGLib is set up as a weird moduled unity build thing. That way no matter how many more files I add to it, it won't break and there's no need for makefile bs. It just compiles 3 .cpp files that include all the other files. I *could* set up the other project that way if it becomes an issue.

Gleeok
05-24-2013, 12:09 AM
Apparently the first post is too big to contain any more.. I'll see what I can do about that.

Anyway here we go. More Core Data Types:
(this process was 1/3 automated so some things were not output. but it should give an idea of how it works.) :)



/**
* class that manages attribute values.
*/
class attributes;
{
attributes();
attributes(const attributes &);
attributes& operator +=(const attributes &);
attributes& operator -=(const attributes &);
attributes operator +(const attributes &) const;
attributes operator -(const attributes &) const;

int get_max_param(int) const;
int get_stat(int) const;
int get_element(int);
int get_status_atk(int);
int get_status_def(int);

void set_max_param(int, int) const;
void set_stat(int, int) const;
void set_element(int, int);
void set_status_atk(int, int);
void set_status_def(int, int);

};


/**
* class that manages items and amount.
*/
class inventory
{
inventory();
inventory(const inventory &);

};



/**
* class that manages equipped items.
*/
class equipment
{
equipment();
equipment(const equipment &);

};



/**
* class that describes an enchantment
* or temporary effect on an actor or entity.
*/
class buff
{
buff();
buff(const buff &);

};



/**
* class that holds all basic information of a character
*/
class character_data
{
string name;
string script;
string description;
int id;
int race_id;
int class_id;
int portrait_id;
int map_spriteset_id;
int battle_spriteset_id;
int lv;
int exp;
int gold;
attributes attributes;

};



/**
* class that holds all basic information of a monster
*/
class monster_data
{
string name;
string script;
string description;
int id;
int portrait_id;
int map_spriteset_id;
int battle_spriteset_id;
int lv;
int exp;
int gold;
attributes attributes;
item_dropset item_dropset;

};


/**
* class that is an instance of a character or monster class;
*/
class actor
{
actor();
actor(const actor &);

string name;
string script;
int id;
int portrait_id;
int map_spriteset_id;
int battle_spriteset_id;

int get_lv() const;
int get_exp() const;
int get_gold() const;

void set_lv(int) const;
void set_exp(int) const;
void set_gold(int) const;

int get_param(int) const;
int get_max_param(int) const;
int get_base_max_param(int) const;
int get_stat(int) const;
int get_base_stat(int) const;
int get_status_atk(int) const;
int get_status_def(int) const;
int get_base_status_atk(int) const;
int get_base_status_def(int) const;

void set_param(int, int) const;
void set_base_max_param(int, int) const;
void set_base_stat(int, int) const;
void set_base_status_atk(int, int) const;
void set_base_status_def(int, int) const;

const attributes& get_attributes() const;
const equipment& get_equipment() const;

};



/**
* class entity that is a battle instance of, and
* holds a reference to, an actor.
*/
class combatant
{
actor();
actor(const actor &);

[email protected] get_actor() const;

int get_param(int) const;
int get_max_param(int) const;
int get_base_max_param(int) const;
int get_stat(int) const;
int get_base_stat(int) const;
int get_status_atk(int) const;
int get_status_def(int) const;
int get_base_status_atk(int) const;
int get_base_status_def(int) const;

void set_param(int, int) const;
void set_base_max_param(int, int) const;
void set_base_stat(int, int) const;
void set_base_status_atk(int, int) const;
void set_base_status_def(int, int) const;

const attributes& get_attributes() const;
const equipment& get_equipment() const;

};


/**
* class that manages a list of current active and reserve
* party members, as well as other information.
*/
class party
{
party();
party(const party &);

int get_gold() const;
int get_size() const;
int get_active_size() const;
int get_reserve_size() const;
int get_max_size() const;
int get_max_active_size() const;
int get_active_member_id(int index) const;
int get_reserve_member_id(int index) const;

[email protected] get_active_member(int index) const;
[email protected] get_reserve_member(int index) const;

inventory& get_inventory();
const inventory& get_inventory() const;

void set_gold(int);
void set_max_size(int);
void set_max_active_size(int);

void add_gold(int);
void remove_gold(int);

void add_member(int);
void remove_member(int);

bool has_member(int) const;
bool is_member_active(int) const;
bool is_member_in_reserve(int) const;
bool is_full() const;

};


Basic Sprite classes reference:



//----------------------------------
// * Sprite
//----------------------------------
class sprite
{
public:
vec2 size;
vec2 scale;
color color;
blendmode blendmode;
float angle;
rectf uv;

sprite();
sprite(const sprite&);
sprite &operator =(const sprite&);

};



//----------------------------------
// * SpriteAnimation
//----------------------------------
class sprite_animation
{
public:
int animation_speed;
int frame;
int num_frames;
rect source_rect;
rectf uv;


bool is_animated() const;
//void flip(int flags);

};


//----------------------------------
// * AnimatedSprite
//----------------------------------
class animated_sprite : public sprite_animation
{
public:
vec2 size;
vec2 scale;
color color;
blendmode blendmode;
float angle;

animated_sprite();
animated_sprite(const animated_sprite&);
animated_sprite &operator =(const sprite&);
animated_sprite &operator =(const animated_sprite&);

};


//----------------------------------
// * AnimatedSpriteSet
//----------------------------------
class animated_spriteset
{
public:
sprite_animation animation[];
vec2 size;
vec2 scale;
color color;
blendmode blendmode;
float angle;
int num_animations; //get
int state;

animated_spriteset();
animated_spriteset(const animated_spriteset&);
animated_spriteset &operator =(const animated_spriteset&);

//void add_animation(const rect& sourceRect, float speed, int numFrames, int frameOffsetX, int frameOffsetY);
//void remove_animation(int index);

};


Whewee... we're getting serious now!

Anyway it's not perfect but it's the best documentation I can do right now.
Ideas for better design, names, functions, etc.. are most welcome.

Gleeok
03-21-2014, 07:47 AM
I.. umm... sorta shit-canned the entire scripting engine... yeah. >_>

The reason was because it wasn't productive enough, period. Things like LUA and angelscript are great so long as the scripts are only responsible for doing specialized tasks and logic. That, and binding and creating the script API, both c++ side and script side, was taking up too much time. Angelscript worked great for my last side-project, but for a large project with this kind of scope you really need a more serious solution--well, that or some serious man power. Since I have zero additional man-power in this scenario it was actually a pretty easy call to scrap the whole thing for something better.

So what's better? -Embedded C# is better. There's also a lot of potential support for other languages: http://en.wikipedia.org/wiki/List_of_CLI_languages
This is in fact pretty much exactly what Unity3D does, and the .NET framework already has a shit ton of utility classes and containers ready to go without any fuss, so once the initial cost of set-up is out of the way it's smooth sailing.

The benefits as I see them are:
-Scripts can compile directly into machine code and would be almost as fast as c++. Can also be AOT compiled.
-Maintain portability; Works for x86, X64, and ARM.
-Large framework, with the ability to simply drop-in code off the web. eg., XNA, or use 3rd party libraries.
-Easy to write with an entire interwebs worth of reference material.
-Existing tools for integrated development environment such as Visual Studio, MonoDevelop; also some lightweight ones as well.
-Debugging support through Mono, or perhaps directly debugging through an additional assembly layer (have to think about this).
-I might actually work on it more. :P

Cons:
-Initial setup time.
-???

Thoughts?

I'll probably just throw together either a Tetris or Galaga clone for fun in order to test everything out.

CJC
03-21-2014, 11:55 AM
I dare you to build a battle engine where the multiplier for damage is determined by how many lines you complete with a single piece of Tetris, thrown by the enemy's defense rating (so an enemy with a defense of say 12 might through a huge and unwieldly piece). Also, when you 'bust' on the tetris board your party gets hit with a huge attack, like a megaflare or something!

...What does that have to do with scripting? Nothing, you just said Tetris and I have a short attention span.

Tamamo
12-15-2014, 09:36 PM
You got any plans for 3D Capabilities?

Gleeok
12-15-2014, 11:34 PM
Yes, you can do 3D (mostly) the same as XNA. Of course getting it to work with 2D is another matter. ;)

http://tech.pro/tutorial/750/creating-a-textured-box-in-xna


There's also a VertexArray which is something like this:



VertexColorTexture3D faces[8];

//fill the faces of the cube
faces[0].position = new Vector3(0,1,0);
faces[0].uv = animatedSprite.GetUVRect().TopLeft();
faces[0].color = Color.Blue;

//etc.
VertexArray<VertexColorTexture3D> vertexArray = new VertexArray();
vertexArray.Add(faces);

Graphics.GraphicsDevice.DrawVertices(vertexArray);


It's just openGl so you can write it in c/c++ and call that from a script also.

I'm sure there are other ways; I haven't really given it much thought. The engine itself doesn't much, if any, 3D, so you have to do it yourself, or use 3rd party libraries.

Tamamo
12-16-2014, 11:07 AM
As long as I can recreate FF5 in 3D I'll be happy.

Tamamo
05-19-2015, 10:09 AM
C# is a lot of fun, you know that Gleeok. ;)

Gleeok
05-19-2015, 03:18 PM
As long as I can recreate FF5 in 3D I'll be happy.

I sincerely hope you are joking. :P


The c# layer is a bit unfinished right now, but I'll try and get it up pretty soon (It's rather large--about 2 mb).

Tamamo
05-20-2015, 09:33 AM
Gleeok
I might be crazy. But I'm not a lunatic. So Yes I was joking. ;)

nina22
11-04-2018, 12:45 PM
I'm curious as to whether or not the Menu System will be customizable through scripting. FetLife (https://fetlife.vip/) IMVU (https://downloader.vip/imvu/) Canva (https://downloader.vip/canva/)