Thoughts about data control

You must understand the Game Editor concepts, before post here.

Re: Thoughts about data control

Postby Fuzzy » Sat Jun 19, 2010 6:35 am

That would be more of a look up. We could code that up too. You could give some text to an array and it would find what you need. Not very efficient, but fun to do.

The example I gave you acts like the return function without the overhead of actual return code with alll its ASM push and pop, jne stuff.
Mortal Enemy of IF....THEN(and Inspector Gadget)

Still ThreeFingerPete to tekdino
User avatar
Fuzzy
 
Posts: 1068
Joined: Thu Mar 03, 2005 9:32 am
Location: Plymostic Programmer
Score: 95 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Mon Jun 21, 2010 4:07 am

Just got back to my computer...
Hmmm, can't use it that way...

Oh well, talking about pure numbers like DST does...
Is this what you mean?
Code: Select all
sprintf(AnimName,"%i%i%i",type,walk,direction);
ChangeAnimation("Event Actor", AnimName, FORWARD);

In this case, the animation for Player1 :
* 10-1 : Player1StopLeft
* 101 : Player1StopRight
* 11-1 : Player1WalkLeft
* 111 : Player1WalkRight
right?

Far simpler in animation naming and library usage...but, harder in management
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby DST » Mon Jun 21, 2010 6:18 am

It's an attempt at what i called on Regame "Multidimensional Cascading", and it's why i've always disliked strings in programming, precisely because they are so specific. They are probably best for most programming, but I'm imagining cake in the sky where one day all programs will work together in some glorious carnival of a program which will probably never happen, but ....who knows?

Multidimensional Cascading is where you have to synchronize things in completely unrelated dimensions, yet with as few differences as possible. Here's an example:

Gears in a watch are synced by both the size and the number of teeth on them, to result in a sync of A. torque and B. rotation speed (time). But they also sync side by side, in 3d space, A. to fit inside a watch, and B. to use the fewest points of attachment possible (to manufacture you always try to simplify) and C. to work a long time off a small amount of energy.

And the watch casing they fit in must be made to A. be cheap to manufacture B. be strong to last C. be comfortable to wear D. look nice.

And then you have to figure in shock resistance, and corrosion resistance, and, after you've got all that together, and you've designed the perfect watch, now you have to design the factory the watch is to be made in; all the tools and molds and machinery that produces and assembles the watch. The less differences you have between all the previous variables mean less differences in the factory variables. So cascading is all about aligning trajectories to achieve efficiency, leading up to the main producer of the product and how simple that machine is to build and maintain (in this case, the factory is YOU! The machines are the functions you write, and the products are the games you publish. And the less coherence you had in the factors of the watch design, the more expensive, fragile, and complicated the production tools will have to be!)

I always draw my plans around mathematics to achieve the cascade, as much as possible.


In mageslayers, i use a base enemy with many animations and enemy types inside of one actor. Actor enemy has 3 animations for each enemy: attack+run right, attack+run left, and die. So i named my animations thusly:

000
001
002

010
011
012

where 000 was the bird right, 010 was the wolf right, 020 was the mud monster right, and 001 was bird left, 011 was wolf left, etc. etc.

Then, I call the number based on direction towards player, like so:
if(x<player.x){
dir=0;}
else
{dir=1;}

then strncat the dir onto the enemy type, which i was already using in a case switch in draw actor to determine what the enemy did in the first place.

Now i've used actor int type to determine all actions, and type+dir to determine all animations. (with a 0 at the beginning so i can have more than 10 enemies. Note that enemies would be limited to 10 animations each max using this method).

In this case, type and dir had to be cast to char[] to write them to an animation call, but in the end, they were useful for other things (such as the case switch). And they keep in with other mathematical synchronization; such as, the right animations end in 0 and the lefts end in 1, so i can always use math on the 'angle' variable, where right is 0, etc. etc.

As well, i can also use these variables in loops (the coherence i talked about earlier), so i could easily ask for the last number of every animation state of every enemy; And if you were using a WIND spell to blow them back, determine how much they were blown back because i could easily determine which direction they were facing.

That is, without having to ask an "IF" statement every time.
It's easier to be clever than it is to be kind.
http://www.lostsynapse.com
http://www.dstgames.com
User avatar
DST
 
Posts: 1117
Joined: Sun Apr 15, 2007 5:36 pm
Location: 20 minutes into the future
Score: 151 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Mon Jun 21, 2010 12:34 pm

Hmmm....okay, I use
00-1
001
01-1
011
etc...
Because :
Code: Select all
x+=walk*dir*speed;

So, I don't need the use of :
Code: Select all
if(x<player.x){
dir=0;}
else
{dir=1;}

But it seems that -1 makes it weird...
Oh well, let me test it more
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby DST » Mon Jun 21, 2010 3:10 pm

Bee-Ant wrote:Hmmm....okay, I use

Because :
Code: Select all
x+=walk*dir*speed;



But that's a frame by frame command, my enemies are only determining movement and animation when their current movement is up, usually when they've completed the walkto, completed x number of animation cycles, lost current target, or reached some other variable limit.

You could also use dir=normalize(x-player.x); if you write a normalize function.

I use a function for targeting like
state=findTarget(id);

where the findTarget function will return the proper state for the actor to be in depending upon whether a target was found or not. (in the case of a single player game, they'd return different if they found player to be in range, or out of range and requiring movement).

But usually, you and i are making different types of games...
It's easier to be clever than it is to be kind.
http://www.lostsynapse.com
http://www.dstgames.com
User avatar
DST
 
Posts: 1117
Joined: Sun Apr 15, 2007 5:36 pm
Location: 20 minutes into the future
Score: 151 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Mon Jun 21, 2010 3:24 pm

DST wrote:But that's a frame by frame command, my enemies are only determining movement and animation when their current movement is up, usually when they've completed the walkto, completed x number of animation cycles, lost current target, or reached some other variable limit.

Do you use variables in this case???
I use timers to handle the walk, stop, attack timing and duration.

DST wrote:But usually, you and i are making different types of games...

Exactly :D

DST wrote:where the findTarget function will return the proper state for the actor to be in depending upon whether a target was found or not. (in the case of a single player game, they'd return different if they found player to be in range, or out of range and requiring movement).

Hmmm, I'm starting to think if there're 2 or more players, how can I code the enemies would face to any player in their range...without using other actor as sensor or something... :)
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby DST » Mon Jun 21, 2010 3:41 pm

because players are clones of each other.

If you consider most rts, all players use the same actors. There is no difference except that yours has a variable in it allowing you to control it, and allowing your units to realize that it is a friend, not a foe.

So an enemy just looks up all the indexes and picks the most reasonable target, asking first that:

target.side!=side;

or in the case of defined arrays,

int mt=units[myid][mytarget];
if(
units[mt][myside] != units[myid][myside]){
}
It's easier to be clever than it is to be kind.
http://www.lostsynapse.com
http://www.dstgames.com
User avatar
DST
 
Posts: 1117
Joined: Sun Apr 15, 2007 5:36 pm
Location: 20 minutes into the future
Score: 151 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Mon Jun 21, 2010 4:05 pm

DST wrote:because players are clones of each other.

If you consider most rts, all players use the same actors. There is no difference except that yours has a variable in it allowing you to control it, and allowing your units to realize that it is a friend, not a foe.

So an enemy just looks up all the indexes and picks the most reasonable target, asking first that:

target.side!=side;

or in the case of defined arrays,

int mt=units[myid][mytarget];
if(
units[mt][myside] != units[myid][myside]){
}

Oh...I get it :D
So each player and enemy assign their own units value by their cloneindex right?
And check who's the foe or friend through the array instead of their real coordinates?

Okay, but the downside of this method is the amount of cloned enemy or player are limited...
Also, the cloneindex number won't reset even the actor itself is destroyed...

Hmmm, but since I don't use recycled enemy producing, I think it's okay.
50 enemies on each stage is more than enough :D

Wait wait wait...I start to think again...about make the player and enemy as the same actor...
Sorry, insomnia made my brain a little crampy :oops:

Oh...OK, we just assign in the beginning how many clones the player are...
Then set the cloneindex under that number to be the friends, and other to be the foes...
Code: Select all
int friend=5;
units[cloneindex][type]=(cloneindex<friend); //type=1 ->friend, type=0 ->foe

Right? :D
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby DST » Mon Jun 21, 2010 10:52 pm

yes, something like that. However, i wouldn't use cloneindex as an id when using a master define array. Instead, i use an actor int 'id'. This avoids the cloneindex problems, and also allows you to stuff different actor types into the same array, without mirroring cloneindex;

Actor>CreateActor>

id=findSlot();

global code:

Code: Select all
int findSlot(){
int i;
int tid=0;  //store temporary id
for(i=0; i<popmax; i++){ //units[x][0] is 1. exists or 0. doesn't exist (empty).
if(units[i][0]==0){     //if no unit is using this id
tid=i;                       //i'll use it
units[i][0]=1;           //set it to used
i=popmax;                //stop searching
}
return tid;
}


When a unit dies, you must remember to wipe ALL values from it's slot in the unit array; then have the new actor fill it the new values once it has it's id. (or else you'll have a warrior with leftover mana from the wizard that used that id before him....)

This will keep your loops short too, because you can search the array in the same way to find the currentpop of this frame (the highest id that exists), and each id found is the absolute lowest id that can be used, so there are hardly ever any gaps in the array, and if there is, it'll get filled soon.

And then your targeting loops only need to run to currentpop instead of maxpop.
It's easier to be clever than it is to be kind.
http://www.lostsynapse.com
http://www.dstgames.com
User avatar
DST
 
Posts: 1117
Joined: Sun Apr 15, 2007 5:36 pm
Location: 20 minutes into the future
Score: 151 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Tue Jun 22, 2010 4:57 am

DST wrote:When a unit dies, you must remember to wipe ALL values from it's slot in the unit array; then have the new actor fill it the new values once it has it's id. (or else you'll have a warrior with leftover mana from the wizard that used that id before him....)

OK, this is for system where the actor is created one by one right?not all at once.
Hmmm...in my game, my system would create all the enemies at once, so I use cloneindex.
But, I'm well aware with the cloneindex problems, and I don't want to mess with it...so I would consider using "id" like what you've said :D

I've implemented your system (player and enemy are the same actor), it went great :D
And simpler my work. thanks :D

And about the health bar...it's better to make a small HP for each actor above their head, or make the big HP bar on top of view and just show it when we fight the enemy?
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby Fuzzy » Tue Jun 22, 2010 5:55 am

We used to have endless debates over whether actors were sufficiently different to warrant different types. In theory you could use the same code for a health bar as a creep(and be very efficient) but they are quite different in needs. Obviously DST worked out a division point.
Mortal Enemy of IF....THEN(and Inspector Gadget)

Still ThreeFingerPete to tekdino
User avatar
Fuzzy
 
Posts: 1068
Joined: Thu Mar 03, 2005 9:32 am
Location: Plymostic Programmer
Score: 95 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Tue Jun 22, 2010 10:13 am

Hmmm...
Ok, I have shared the newer system under Bee-Share folder
And here's the system changes list :
- Player and Enemy be the same actor "Enemy"
- Library for attributes added
- Units[][] usage (just like DST method)
- Individual HP bar
- Stats integration
- 47 characters type
Please let me know if it's efficient or not (cloneindex usage to define the type)
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby DST » Fri Jun 25, 2010 12:06 am

note: don't use the [][] variables in your actual script. Transfer the variables to local variables first, then write the script.
Then, you can reuse the script for anything, just changing the way you assign variables in the start. Also, you won't have to type [] all day long.
It's easier to be clever than it is to be kind.
http://www.lostsynapse.com
http://www.dstgames.com
User avatar
DST
 
Posts: 1117
Joined: Sun Apr 15, 2007 5:36 pm
Location: 20 minutes into the future
Score: 151 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Fri Jun 25, 2010 5:25 am

DST wrote:note: don't use the [][] variables in your actual script. Transfer the variables to local variables first, then write the script.
Then, you can reuse the script for anything, just changing the way you assign variables in the start. Also, you won't have to type [] all day long.

Right, I only use [][] for the global access, and store the local access into actor variables :D

Hmmm...thinking about fixing :
Code: Select all
Units[cloneindex][1]=(cloneindex<friend);
side=Units[cloneindex][1];
type=(cloneindex+friend-1)%(total+friend-2)+1;

to remove the cloneindex problem...
I plan to not use LoadGame() to load a new level instead of just reset the map and character. (to speed up the game maybe :P)
So in this case, the cloneindex number won't reset, and I have to reset them when loading a new level.

---

Here's the simple method :

- Global code :
Code: Select all
int LastCount;
int tempCount;


- Enemy->Create Actor :
Code: Select all
int resetIndex=cloneindex-LastCount;
side=Units[resetIndex][1]=(resetIndex)<friend);
type=(resetIndex+friend-1)%(total+friend-2)+1;
tempCount++;


- When loading a new level :
Code: Select all
LastCount+=tempCount;
tempCount=0;


In this case, filling Units[][] always start from index 0, and enemy must be created all at once in the beginning (created when loading new level only) and no more recreating them afterwards.

Oh well, I will think the other method...
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

Re: Thoughts about data control

Postby Bee-Ant » Wed Jun 30, 2010 5:55 pm

This is the function I thought since I know strings.
I rarely mess with GE default functions, so I don't know this is already there or not...

Function to change letters into capital or lower mode.

Function (place this on Global code) :
Code: Select all
char *ToUpper(char str[256])
{
    int i,intc;
    char *stru=malloc(256); //get memory allocation for the pointer
    char tmp[2]; //just for the temporary string
    for(i=0;i<strlen(str);i++)
    {
        intc=(int)str[i]; //get the ASCII number
        if(intc>=97&&intc<=122)intc-=32; //if intc in range of small letters decrease it's ASCII number by 32
        sprintf(tmp,"%s",&intc);
        strcat(stru,tmp); //combine the letters
    }
    return stru;
}
char *ToLower(char str[256])
{
    int i,intc;
    char *strl=malloc(256); //get memory allocation for the pointer
    char tmp[2];
    for(i=0;i<strlen(str);i++)
    {
        intc=(int)str[i]; //get the ASCII number
        if(intc>=65&&intc<=90)intc+=32; //if intc in range of capital letters increase it's ASCII number by 32
        sprintf(tmp,"%s",&intc);
        strcat(strl,tmp);
    }
    return strl;
}


Usage :
Code: Select all
strcpy(text,ToUpper("Bee-ant, DST, Fuzzy"); //the output would be: "BEE-ANT, DST, FUZZY"
strcpy(text,ToLower("Bee-ant, DST, Fuzzy"); //the output would be: "bee-ant, dst, fuzzy"


Limitation :
- Since GE can only handle 256 string length, I just follow it...
User avatar
Bee-Ant
 
Posts: 3717
Joined: Wed Apr 11, 2007 12:05 pm
Location: Can bee found antywhere
Score: 210 Give a positive score

PreviousNext

Return to Advanced Topics

Who is online

Users browsing this forum: No registered users and 1 guest

cron