Adventure Game Studio

AGS Support => Beginners' Technical Questions => Topic started by: sloppy on Tue 06/12/2005 20:59:48

Title: Object coordinates
Post by: sloppy on Tue 06/12/2005 20:59:48
I'm trying to make a slider puzzle.  I've made a room that is just a big square with smaller squares as objects (40x40).  I want it so that if you click one of the squares, it will move one square in a direction.  The way I figure it, you would need to get the object's coordinates +/- 40.
I'm not sure how.  I've tried Object[0].Move(object[0].X+40), (object[0].Y+0);
just to start off, but of course it doesn't work.

Can anyone help?
Title: Re: Object coordinates
Post by: strazer on Tue 06/12/2005 21:03:39
Try
  object[0].Move(object[0].X+40, object[0].Y+0); // note the lowercase o and the removed braces
or
  object[0].Move(object[0].X+40, object[0].Y+0, eBlock);
Title: Re: Object coordinates
Post by: DoorKnobHandle on Tue 06/12/2005 21:06:41
You need to pay attention to capitalization.
In this case "Object" and "object" is a great difference.

This line should work:

object[0].Move ( object[0].X + x_offset, object[0].Y + y_offset, 3 );


It will move the object 0 to a new position (replace x_offset and y_offset with your values for the new position) and it will use a speed of 3.

You were thinking the right way, though!

EDIT: strazer was faster.
Title: Re: Object coordinates
Post by: Ashen on Tue 06/12/2005 21:08:40
You where both faster, but anyway:

Object.Move(int x, int y, int speed, optional BlockingStyle, optional WalkWhere);

So, you're missing a needed parameter for speed, at the very least. Also, without the WalkWhere parameter set to eAnywhere, the object needs a walkable area to move on - is there one? Try:

object[0].Move(object[0].X+40, object[0].Y, 3, eBlock, eAnywhere);

EDIT: Missing parameter? What missing parameter? ::)
I can't believe it took 3 of us to get this right ...
Also, culled some posts.
Title: Re: Object coordinates
Post by: sloppy on Tue 06/12/2005 21:29:41
Yes that works.  Capitalization...such a stupid error.  And I think it's better to put a walkable area on so that it prevents the tiles from going off the big square.

How would I prevent a tile object from moving in a direction if another tile object is in its way? 

I've been working on this scripting for hours, and I think I'm in over my head.  Has anyone else tried to have one of these puzzles in their game?  I couldn't find one post about it.
Title: Re: Object coordinates
Post by: DoorKnobHandle on Tue 06/12/2005 21:32:05
That's a way more compicated question. You'd either need to code your own collision control (you store the x and y position of every tile and then before you move, you check if another tile is in the way) or you could change to using characters instead of objects, I guess.

Creating your own collision control is going to be hard if you never done that and if you don't have a little maths knowledge.
Title: Re: Object coordinates
Post by: Ashen on Tue 06/12/2005 21:38:19
But, since each tile is an object, you could use Object.GetAtScreenXY() to check, something like:

if (Object.GetAtScreenXY(object[0].X+40, object[0].Y) == null) object[0].Move(object[0].X+40, object[0].Y, 3, eBlock);

Might take a little tinkering, though.
EDIT: And assumes you always move the objects by a set amount. It becomes a little more complicated (as dkh said) if you have total freedom of movement.  Without knowing exactly what you're after, it's hard to say.
Title: Re: Object coordinates
Post by: sloppy on Wed 07/12/2005 00:02:36
Thanks Ashen, but I can't get the Object.GetAtScreen scripting to work.  And I've tried everything (as far as my understanding of it goes).

I was trying to make a tile game where there's only one space missing and you slide tiles back in order in a big square.  So tiles would only slide up and down and only the tile dimensions at a time.  It seemed like such a simple idea, but it's just beyond my abilities.

I think I'll quit while I'm behind and admit defeat. :'(
Title: Re: Object coordinates
Post by: Ashen on Wed 07/12/2005 00:13:08
Figured that was what you were after - something like this (http://www.geocities.com/whoismonkey/SlidePuzz.zip), perhaps?
Ignore the 2 objects not in the slider bit (cup and '9' block).

Uses graphics by Scorpiorus, from a while back.

Check the code, see if it's any use to you. (There's some old, 2.62 style code int he global script, just ignore that, too. It's the room script stuff you want.)
Title: Re: Object coordinates
Post by: sloppy on Wed 07/12/2005 04:42:08
Oh, that's perfect.Ã,  I really appreciate this!

I've been working with the scripting, customizing it to what I want it to look like. 

Just one more question about this - How would you incorporate a sound effect when the person is successful in putting the tiles in the proper order?
Title: Re: Object coordinates
Post by: Ashen on Wed 07/12/2005 15:19:09
For that, you'd need to check the coords of each piece and compare them to the right coords for that piece, and trigger something if they were all in the right place.

Or ... The demo I uploaded is based on Scorpiorus' drag puzzle demo, so it has hotspots in place to check when the pieces are located right - you could use that too, something like:

function CheckSolved() {
  int correct;
  int i=1;
  while (i <= 8) { // or number of slide-pieces
    Hotspot *hot = Hotspot.GetAtScreenXY(object[i].X+20, object[i].Y-20); // Middle of tile
    if (hot.ID == i) correct ++;
    else correct = 0;
    i ++;
  }
  if (correct == 8) { // or number of slide-pieces
    Display ("Yay, you!");
    PlaySound(1);
    // Anything else you want to happen...
  }
}

Might be a neater way, this is just the first that came to mind.

Run that after the movement code (in rep_ex at the moment) and it should automatically trigger the Display/PlaySound commands when the peices hit the right spot.
Title: Re: Object coordinates
Post by: Maverick on Wed 07/12/2005 15:34:09
I'm dealing with the same issue although the way I interpreted your problem was that you wanted something different than what the actual outcome is.
Ashen, is it possible to combine these threads? http://www.adventuregamestudio.co.uk/yabb/index.php?topic=23854

Title: Re: Object coordinates
Post by: Ashen on Wed 07/12/2005 15:48:18
Maverick, check back in your thread, I think I see what the problem is. Alternatively, the code above will almost certainly work for you, with a little tweaking (since, as I said, it's based on Scorpiorus' as well).

It's possible to combine them, yes, but I don't think I will. Although they're about the same thing now, they weren't to start with - similar, yes, but diferent enough that combining them would confuse anyone trying to search for either problem (free-movement dragging, or fixed-movement sliding).
Title: Re: Object coordinates
Post by: sloppy on Wed 07/12/2005 17:47:25
Am I missing something?Ã,  When I put this in and test it:

function CheckSolved() {
Ã,  int correct;
Ã,  int i=1;
Ã,  while (i <= 8) { // or number of slide-pieces
Ã,  Ã,  Hotspot *hot = Hotspot.GetAtScreenXY(object.X+20, object.Y-20); // Middle of tile
Ã,  Ã,  if (hot.ID == i) correct ++;
Ã,  Ã,  else correct = 0;
Ã,  Ã,  i ++;
Ã,  }
Ã,  if (correct == 8) { // or number of slide-pieces
Ã,  Ã,  Display ("Yay, you!");
Ã,  Ã,  PlaySound(1);
Ã,  Ã,  // Anything else you want to happen...
Ã,  }
}

It says that nested functions not supported.Ã,  (Closing brace, etc.)
But it looks okay to me.Ã,  Is there a missing brace?
Title: Re: Object coordinates
Post by: strazer on Wed 07/12/2005 17:54:21
Probably a brace before or after this function. Try the "Match braces" function of the script editor.
Btw, you can use the [ code ] tag to avoid the smileys when posting code.
Title: Re: Object coordinates
Post by: Ashen on Wed 07/12/2005 17:54:37
There's no missing brace there - where have you put it in the room script?

When I said "call this after the movement code" I meant "paste this into the top of the room script, and add CheckCorrect(); after the movement script" - pasting the function declaration into rep_ex would generate a nested functions error.

If it's not that, check the script either side of wherever you pasted it (as strazer said,      while I was posting) - you might've accidentally deleted a brace in the process.
Title: Re: Object coordinates
Post by: sloppy on Wed 07/12/2005 19:23:13
Thanks for explaining it.Ã,  I understand it now and it works great.Ã, 


Now on a new line of questioning.  When the puzzle is completed, the display will come up.  But then you have to click again to get the sound effect.  Is there a way that these two things can occur simultaneously?
Title: Re: Object coordinates
Post by: Ashen on Wed 07/12/2005 19:58:38
Just reverse the lines.
Display() is blocking (makes the script wait until it's cleared before running the next line), PlaySound() isn't, so running it first will make the sound play over the message.
Title: Re: Object coordinates
Post by: sloppy on Wed 07/12/2005 21:23:10
I hate it when the answer is so obvious.
Title: Re: Object coordinates
Post by: sloppy on Thu 08/12/2005 03:22:13
Okay, here's one more small thing I can't figure out with this.Ã,  When this tile puzzle is finished, I wanted 3 things to signal that: A display message, sound effect, and the last tile to appear.Ã,  Everything works except the tile becoming visible.
Here's what I have:
if (correct == 8) {
Ã,  object[9].Visible = true;
Ã,  Ã,  PlaySound(3);
Display ("You solved the puzzle!");
}

But the object won't become visible.
So why wouldn't object 9 appear along with the display and the sound?
Title: Re: Object coordinates
Post by: Gilbert on Thu 08/12/2005 03:37:43
Will it be possibe that the object was hidden under other stuff because of baseline, etc. settings.
Title: Re: Object coordinates
Post by: sloppy on Thu 08/12/2005 04:17:25
I thought that too, but I don't think that's it. 

I tested this in other ways, like putting another object in an area outside the main square and setting it to disappear when the puzzle is done.  Once again, nothing happens.
Title: Re: Object coordinates
Post by: Gilbert on Thu 08/12/2005 04:19:55
Are there any code which will hide the object in your script? Chances are you put that somewhere in your script which would be executed after it's set visible (like in the rep_ex function, say for example).
Title: Re: Object coordinates
Post by: sloppy on Thu 08/12/2005 04:33:17
yes, that must be it  This is the scripting in the Repeatedly Execute:

if (ob != null) {
      ob.Baseline = 0;
      if (Object.GetAtScreenXY(ob.X + 40, ob.Y-1) == null && GetWalkableAreaAt(ob.X+40, ob.Y-1) != 0) {
        ob.Move(ob.X+40, ob.Y, 3, eBlock);
        PlaySound(2);
      }
      else if (Object.GetAtScreenXY(ob.X - 40, ob.Y-1) == null  && GetWalkableAreaAt(ob.X-40, ob.Y-1) != 0) {
        ob.Move(ob.X-40, ob.Y, 3, eBlock);
        PlaySound(2);
      }
      else if (Object.GetAtScreenXY(ob.X, ob.Y-41) == null  && GetWalkableAreaAt(ob.X, ob.Y-41) != 0) {
        ob.Move(ob.X, ob.Y-40, 3, eBlock);
        PlaySound(2);
      }
      else if (Object.GetAtScreenXY(ob.X, ob.Y+39) == null  && GetWalkableAreaAt(ob.X, ob.Y+39) != 0) {
        ob.Move(ob.X, ob.Y+40, 3, eBlock);
        PlaySound(2);
      }
      ob = null;
    }
  }

I don't fully understand what it all means, I used and modified the scripting from Scorpiorus.  Is there a way around this?
Title: Re: Object coordinates
Post by: Gilbert on Thu 08/12/2005 05:33:54
There doesn't seem to be problem in the code, are you sure object[9] was placed at the correct coordinates?
Title: Re: Object coordinates
Post by: Maverick on Thu 08/12/2005 09:26:44
Insert Wait statement

object[9].Visible=true;// Initially not visible in editor
Wait(5);

Should work if everything else is in place.
AGS needs time to think before blocking code (sound, display) unless you use free channels for sound PlaySoundEx(int sound, int channel)
Title: Re: Object coordinates
Post by: Ashen on Thu 08/12/2005 10:31:52

if (correct == 8) {
  object[9].Visible = true;
    PlaySound(3);
Display ("You solved the puzzle!");
}

Oddly, it works perfectly well for me exactly as you've got it - and assuming you haven't made any major changes, we should have the same code. Are you sure it's object 9 you want to switch on, and not object 0? (Sorry, obvious I know, but that's usually where I go wrong.)

Could you post the rest of the rep_ex code - there should be at least a little more before the bit you showed earlier, unless you've made major changes. (I don't really think the problem will be there, but it couldn't hurt to check.)
Title: Re: Object coordinates
Post by: sloppy on Thu 08/12/2005 13:20:56
Well it works now that I put that Wait statement in.  Thanks Maverick.

That was quite frustrating that it wouldn't work any other way, especially if it works for you, Ashen.
But thanks guys for all your help.
Title: Re: Object coordinates
Post by: sloppy on Wed 14/12/2005 20:06:38
So here's a new question.  I have a "sliding" sound effect everytime you move a tile into position.  So that the sound happens at the same time of the tile object movement, I've made the object move nonblocking. 

Works fine except when the last tile goes into place at the solution.  Then the victory sound effect and display message occurs before the last tile goes into place.   Is there a way that the movements can be nonblocking but still wait for the tile to finish at the very end before the display message and sound effect comes up?
Title: Re: Object coordinates
Post by: Maverick on Thu 15/12/2005 06:48:55
You can add a Wait() statement just before the spot where you want the victory sound to play. It will take a bit of tweaking to find the correct value but it should work.
Title: Re: Object coordinates
Post by: Gilbert on Thu 15/12/2005 08:07:18
You don't need to work out the wait() value if you just want it to stop after animation, just do something like:

while (object[curobjnum].Moving) Wait(1);
PlaySoundblahblabla...

where curobjnum is the object # of the last moving tile.
Title: Re: Object coordinates
Post by: sloppy on Thu 15/12/2005 13:18:59
Thanks Gilbot, that would be perfect except I don't know which object will be the last to go into place because there's 8 tiles.  Is there a way of stating while(object[1-8].Moving, or something to that effect?

EDIT: Forget it.  I repeated the while(object) command for all 8 objects and it works.  It seems like there would be a more efficient way of doing that, though.
Title: Re: Object coordinates
Post by: Ashen on Thu 15/12/2005 21:59:28
You could set a variable before you set ob to null, then use that, i.e.:

if (ob != null) {
  // Blah blah
  //Movement code
        else if (Object.GetAtScreenXY(ob.X, ob.Y+39) == null  && GetWalkableAreaAt(ob.X, ob.Y+39) != 0) {
        ob.Move(ob.X, ob.Y+40, 3, eBlock);
        PlaySound(2);
      }
      curobjnum = ob.ID;
      ob = null;
    }


Then you should be able to use while (object[curobjnum].Moving) Wait(1); as Gilbot suggested.
(Alternatively, you might be able to call ob = null; inside/after CheckCorrect(), and just use ob.Moving.)
Title: Re: Object coordinates
Post by: sloppy on Thu 22/12/2005 03:43:03
Going back to this.  I wanted to have a sound effect at the same time that the tiles moved.  To do that, I would make each tile move a nonblock, otherwise the sound effect would wait for the object move, and it would sound off.
Here's how I have it:

if (mouse.IsButtonDown(eMouseLeft)) {
    if (button_pressed==0) {
      button_pressed = 1;
     
      ob = Object.GetAtScreenXY(mouse.x, mouse.y);
    }
  }
  else {
    button_pressed=0;
    if (ob != null) {
      ob.Baseline = 0;
      if (Object.GetAtScreenXY(ob.X + 40, ob.Y-1) == null && GetWalkableAreaAt(ob.X+40, ob.Y-1) != 0) {
        ob.Move(ob.X+40, ob.Y, 3, eNoBlock);
                PlaySound(5);
      }
      else if (Object.GetAtScreenXY(ob.X - 40, ob.Y-1) == null  && GetWalkableAreaAt(ob.X-40, ob.Y-1) != 0) {
        ob.Move(ob.X-40, ob.Y, 3, eNoBlock);
                PlaySound(5);
      }
      else if (Object.GetAtScreenXY(ob.X, ob.Y-41) == null  && GetWalkableAreaAt(ob.X, ob.Y-41) != 0) {
        ob.Move(ob.X, ob.Y-40, 3, eNoBlock);
                PlaySound(5);
      }
      else if (Object.GetAtScreenXY(ob.X, ob.Y+39) == null  && GetWalkableAreaAt(ob.X, ob.Y+39) != 0) {
        ob.Move(ob.X, ob.Y+40, 3, eNoBlock);
                PlaySound(5);
      }
      ob = null;
    }
  }

But when I make the tile move eNoBlock, if the tiles are rapidly clicked on, they'll sometimes go too far and go off the track, so to speak. 

Can anyone think of a way to make the sound effect occur at the same time as the tile movement, but still make the tiles wait for each move before it goes into place?
Title: Re: Object coordinates
Post by: Gilbert on Thu 22/12/2005 03:49:02
Can't you just put the PlaySound() lines before the object moving lines (set to BLOCKING)?
Title: Re: Object coordinates
Post by: sloppy on Thu 22/12/2005 03:58:09
That's what a fresh pair of eyes will do.  That does work.  Thanks so much for the quick response.