Reference to a struct? (SOLVED) -- Variables not working (SOLVED)

Started by Creator, Thu 02/06/2011 02:54:30

Previous topic - Next topic

Creator

ÃŒs it possible to create a reference to a struct with the ampersand (&) symbol. I tried making a pointer, but it gave me:

Quote
Cannot declare pointer to non-managed type

Basically, I'm creating an RPG type battle system. I created new script files (BattleSystem.asc & BattleSystem.ash) and here is my code:

Code: ags

//in BattleSystem.asc
function attack(Character* person, Object* enemy, peeps& peep)
{
  hit = Random(15);
  Display("%s attacked %s with %s", person.Name, enemy.Name, peep.attack);
  if (hit = 5)
  {
    Display("%s's attack missed!", person.Name);
  }
  else if (hit == 15)
  {
    Display("%s hit, and it was critical!", person.Name);
    Display("%s caused %d damage to %s", person.Name, peep.damage*2, enemy.Name);
  }
  else
  {
    Display("%s hit!", person.Name);
    Display("%s caused %d damage to %s", person.Name, peep.damage, enemy.Name);
  }
}


"peeps" is a structure:

Code: ags

//in BattleSystem.h
struct peeps
{
  int hp;
  String attack;
  int damage;
};

import function attack(Character* person, Object* enemy, peeps& peep);


However, if I try to save the game, it gives me:

Quote
Parse error at '&' //in BattleSystem.ash, where the "import function" line is.

I've created games in C++ before and this is how I passed structures into function paramaters, so, I don't know what to do. :/

I have created actual "objects" from the structure where needed:
Code: ags

peeps Person1;
peeps Person2;
etc...


EDIT - I can now save my game, but compiling gives the same parse error. It's like programming class all over again.  ::)

Wyz

#1
I have good and bad news ;D

Bad news:
AGS does not support pointers of 'unmanaged' types. This means you can not make pointers of any struct declared in an AGS script. You can however make pointers for the built-in AGS objects and those declared by plug-ins.

Good news:
There exist however a few workarounds that in a lot of cases give you the desired result. The attack function can be rewritten like this:

Code: ags

struct Peeps
{
  int hp;
  String attack;
  int damage;

  import void Attack(Character *person, Object * enemy);
};

//----------------------------------------------------------------------

void Peeps::Attack(Character* person, Object* enemy)
{
  hit = Random(15);
  Display("%s attacked %s with %s", person.Name, enemy.Name, this.attack);
  if (hit = 5)
  {
    Display("%s's attack missed!", person.Name);
  }
  else if (hit == 15)
  {
    Display("%s hit, and it was critical!", person.Name);
    Display("%s caused %d damage to %s", person.Name, this.damage*2, enemy.Name);
  }
  else
  {
    Display("%s hit!", person.Name);
    Display("%s caused %d damage to %s", person.Name, this.damage, enemy.Name);
  }
}
Life is like an adventure without the pixel hunts.

Creator

#2
Now I get "BattleSystem.ash(9): Error (line 9): Invalid syntax near 'void'".

Code: ags

struct peeps
{
  int hp;
  String attack;
  int damage;
  
  import void attack(Character* person, Object* enemy);
};


I was supposed to put the function inside the structure, yes?

EDIT - My attack function is identical to yours.

EDIT - Ah, I got it. Because I kept the function Attack with a small 'a' and I already have another variable called 'attack' (a String). I was so confused about it. Thanks Wyz. Without your help, I probably would have murdered my computer quite violently.
;D ;D ;D

EDIT 3 - When I try to run the function

Code: ags

Blain.Attack(cBlain, oTyler);


the game crashes and says "One of the sting arguments supplied is not a string"

Code: ags

//in void peeps::Attack(Character* person, Object* enemy)
Display("%s attacked %s with %s.", person.Name, enemy.Name, this.attack);

If I remove "this.attack" and the last "%s" it works but when checking variables after removing this.attack

Code: ags

Display("%s caused %d damage to %s", person.Name, this.damage*2, enemy.Name);


Blain.damage comes up as 0.

I have a label in the GlobalScript that shows me Blain.attack and Blain.damage and they show up properly.

Code: ags

/in GlobalScript.asc, repeatedly_execute()
lblBlainStats.Text = String.Format("Blain's Stats: Name: %s | Attack: %s | Damage: %d", cBlain.Name, Blain.attack, Blain.damage); //the label in-game shows "Punch" and "30" respectively.


I also wrote another function to double check.
Code: ags

//in BattleSystem.asc, included the import inside the struct in BattleSystem.ash
void peeps::Heal(Character* person)
{
  if (teamHeal > 0)
  {
    this.hp += 20; //doesn't work
    Display("%s healed himself by 20.", person.Name); //does work
    teamHeal--;
  }
  else
  {
    Display("You have no more healing items left.");
  }
}

//-------------------------------------------

//In GlobalScript.asc
if (keycode == eKeyHyphen)
{
  Blain.hp -= 1;
}
  
if (keycode == eKeyPlus)
{
  Blain.hp += 1;
}
//both of these work


Something weird is up. :/

Wyz

Btw I missed a typo earlier: if (hit = 5) should be: if (hit == 5).

You need to be sure the declared struct has appropriate values before using it. The error you got happens when a string variable is used that contains no string. When do you define Blain, when do you set the variables, and when do you call its Attack function?
Life is like an adventure without the pixel hunts.

Creator

Quote from: Wyz on Thu 02/06/2011 17:15:01
Btw I missed a typo earlier: if (hit = 5) should be: if (hit == 5).

Yeah, I noticed that myself. It was the first thing I fixed after writing in your code.

The structure Blain is declared in BattlySystem.ash.
Code: ags

peeps Blain;


The variable are declared in game_start through another function.

Code: ags

//GlobalScript.asc above game_start
function initialisePeeps()
{
Blain.attack = "Punch";
Blain.damage = 30;
Blain.hp = 100;
}

//in game_start
function game_start()
{
initialisePeeps();
}


In repeatedly_execute, I have a label, as I said, that displays the variables, and they display correctly.

Blain.Attack(cBlain, oTyler); gets called at oTyler_Interact in room 305 (my battle room).

EDIT - Also tried doing "Blain.hp--;" in a room script and nothing. However, it works in the GlobalScript (as said in my previous post).

Wyz

You declare the struct in the header file, that way each script importing the header will get an other copy of the struct. You can solve this by declaring the peeps in a script file and using export and import:
Code: ags

// in something.asc

Peeps Blain;
Peeps Dennis;

export Blain, Dennis;

// in something.ash

import Peeps Blain;
import Peeps Dennis;

Life is like an adventure without the pixel hunts.

Creator

YES! IT WORKS!!! :D

Thank you so much for you help, Wyz. This was driving me absolutely NUTS!
I can put another issue to rest.

Wyz

No problem, glad to have helped you.
Good luck with the rest! ;D
Life is like an adventure without the pixel hunts.

SMF spam blocked by CleanTalk