Adventure Game Studio

AGS Support => Beginners' Technical Questions => Topic started by: StillInThe90s on Tue 05/11/2013 18:52:47

Title: (SOLVED) Pointers in room_RepExec
Post by: StillInThe90s on Tue 05/11/2013 18:52:47
I am trying to use pointers to simplify some of my code. Problem is that I suck at it.

This is what I had in mind, only with a lot more "else if" blocks. However, it returns an "Undefined token" error:
Code (ags) Select

function room_RepExec()
{
if(oObject2.Visible==true)Object *nextobject = oObject3;
else if(oObject1.Visible==true)Object *nextobject = oObject2;
else Object *nextobject = oObject1;

if( -various conditions- ){
    nextobject.Graphic = 1;
    nextobject.SetPosition( 1, 2);
}
else if( -other conditions- ){
    nextobject.Graphic = 2;
    nextobject.SetPosition( 3, 4);
}
}


The code below got it working. But it kind of makes the whole thing rather pointless:
Code (ags) Select

function room_RepExec()
{
if( -various conditions- ){
    if(oObject2.Visible==true)Object *nextobject = oObject3;
    else if(oObject1.Visible==true)Object *nextobject = oObject2;
    else Object *nextobject = oObject1;
    nextobject.Graphic = 1;
    nextobject.SetPosition( 1, 2);
}
else if( -other conditions- ){
    if(oObject2.Visible==true)Object *nextobject = oObject3;
    else if(oObject1.Visible==true)Object *nextobject = oObject2;
    else Object *nextobject = oObject1;
    nextobject.Graphic = 2;
    nextobject.SetPosition( 3, 4);
}
}


I also tried putting the pointer code in a seaparate function and failed.
What am I doing wrong?
Title: Re: Pointers in room_RepExec
Post by: Khris on Tue 05/11/2013 19:55:42
Try this:
Code (ags) Select
  Object *nextobject;
  if (oObject2.Visible) nextobject = oObject3;
  else if (oObject1.Visible) nextobject = oObject2;
  else nextobject = oObject1;
Title: Re: Pointers in room_RepExec
Post by: StillInThe90s on Tue 05/11/2013 21:31:26
Thanks Khris! It works nicely.
But I don't get why it worked in my second example...
Title: Re: Pointers in room_RepExec
Post by: Khris on Tue 05/11/2013 21:44:36
I can't get either code to compile. I always get "Unexpected 'Object'".

Curiously, when I put braces around the command, it suddenly compiles.
Title: Re: Pointers in room_RepExec
Post by: StillInThe90s on Tue 05/11/2013 23:46:51
Oh. I probably used braces too, but I'm afraid I deleted the original code.
The example was written here, not copy-pasted, so there may have been a few misses. Sorry.
But I still don't understand why the first example fails and not the other.
Title: Re: Pointers in room_RepExec
Post by: monkey0506 on Wed 06/11/2013 05:02:01
An if statement (also while statements) without braces is equivalent to one with braces and only a single command contained within it. That is:

Code (ags) Select
if (oObject2.Visible == true) Object *nextobject = oObject3;

Is the same as:

Code (ags) Select
if (oObject2.Visible == true)
{
  Object *nextobject = oObject3;
}


This introduces the concept of variable scope, which simply put is the area(s) of your code for which a given variable is defined:

Code (ags) Select
int intVar;
if (condition)
{
  // intVar is still defined here, floatVar not yet defined
  float floatVar;
  // intVar and floatVar are both defined
}
// intVar is still defined, floatVar is not defined


Any time a variable is defined within a certain set of curly braces {}, the variable ceases to exist at the closing brace of that particular block. This means functions, if statements, while statements, or even arbitrarily defined brace-enclosed code blocks (it could be considered technically correct behavior to define a separate code block just for the purposes of forcing scope, but that's rather advanced if scoping itself requires explanation).

Variables defined outside of a block of code continue to exist inside of that block of code. Specifically in AGS, variables can even be persisted between files if they exist outside of all functions and are both exported and imported. The preferred method for global variables though is not to define them in the script but to define them in the Global Variables pane instead (for some more advanced cases, like struct instances, this isn't viable).

tl;dr version: Your nextobject variables were defined inside of a if statement and therefore ceased to exist at the end of that if statement. That's why you were getting undefined token errors.
Title: Re: Pointers in room_RepExec
Post by: Khris on Wed 06/11/2013 10:10:12
Sure, but I still would love to know why
Code (ags) Select
  if (true) int a = 5;
produces "Error: Unexpected 'int'",
while
Code (ags) Select
  if (true) {
    int a = 5;
  }

compiles fines.
Title: Re: Pointers in room_RepExec
Post by: Crimson Wizard on Wed 06/11/2013 10:45:07
Quote from: Khris on Wed 06/11/2013 10:10:12
Sure, but I still would love to know why
Code (ags) Select
  if (true) int a = 5;
produces "Error: Unexpected 'int'",

I guess its just the compiler's flaw.
Title: Re: Pointers in room_RepExec
Post by: StillInThe90s on Wed 06/11/2013 21:42:44
@monkey: Thanks for explaining things (although, most of us knows the basics of what curly braces do :-D). The part about defining variables inside/outside braces was news to me. Hat off.

@CW: Does this mean that I found my very own ags bug? Or at least a flaw?