GMS 2 [SOLVED] GML Alarm events (I think)

S

Singai

Guest
So I'm VERY new to GM and coding in general (unless you count a strange enjoyment in making excel spreadsheets ;)) I downloaded the trial to play with the DnD but quickly figured out that it was going to be less complicated in the long run to learn the code.


Forgive me if I give a little too much info but I'm not sure what will be needed and I can formulate my thought processes better this way.

So I am working on a Harvest Moon/ Stardew Valley style game.. at least for now. It will eventually evolve past that but I figured it would be a good starting point. I actually have a couple of things that I'm getting a little hung up on but my issue right now seems to be alarms. I think. Unless someone has a suggestion for a different method entirely.

Basically, I'm working on the field right now. I have a blank patch of dirt covered in objects that I have set to an instance layer just below the player's layer. In creation I assigned a variable state = 1 (state being the state the dirt is in... it makes sense to me ;)). In Step, I assigned number keys 1 thru 5 (not on the numpad) to set variable state to the corresponding number (ie: press 3 sets state = 3). Down the road I will change it so if my player sprite is holding a watering can and I press enter (obs using a collision in some way), it will set the appropriate state but for now this seemed simplest to test. Using if statements, I have each state set to an appropriate sprite (ie: if state is equal to 3, it shows a patch of dirt that has been tilled and seeded but not watered). I know I could just do it as a sprite strip and set the frame instead with the image speed to 0, but I'm not 100% on that being the best way in this instance (opinions would be welcome).

In case you aren't familiar with the Harvest Moon model, it is a farming sim. In regards to the actual farming, you till the earth, plant seeds, water them daily, and eventually harvest the crop. If you till the land but never plant anything, it will revert to packed dirt. If you plant seeds but never water them, they will never grow. If you water the ground (with or without seeds on it) it will darken the dirt so you know it worked and eventually it will dry back out. Most iterations have this once a "day" but some allow a second watering before bed. This is where I am stuck. I feel like alarms would be how to handle this? Till the land and set an alarm and at the end of the alarm countdown, if you havn't interacted with it since than to change it (plant seeds or water the dirt), the alarm triggers and it reverts to packed dirt.

I have a series of if statements along these lines:

if (state = 2)
{
sprite_index = Spr_Tilled_Land
alarm[0] = 3 * room_speed
alarm[2] = -1
alarm[1] = -1
}

and alarm[0] is: state = 1 ;

What I expected from this was that when I press 2: it changes the sprite to Spr_Tilled_Land, sets alarm[0] for 3 seconds, stops the other timers in case they were running, and (after 3 seconds) changes the sprite to noone (proper response to state = 1) exposing the dirt tile beneath it.

Incidentally, I tried it without stopping the other timers first and it didn't work so I put that in thinking maybe the issue was multiple alarm countdowns going at once. I also thought it would solve my eventual problem of being able to interrupt the countdown if I change state before it gets to 0 (ie: till land and seed it before it reverts to packed dirt). Also, my alarm times are obnoxiously low to test it. Obs I don't want to wait a whole game day (if I had even worked out how to do that part yet) just to see if my dirt dries out like it is supposed to.

The other states are a tad more complicated as state should essentially count down (at varying speeds) until it returns to 1 or the player interacts with it.

The actual if (state= n) is basically the same but the alarm it points to has another line.

ie:
if (state = 3)
{
sprite_index = Spr_Seeded_Land
alarm[2] = 3 * room_speed
alarm[2] = -1
alarm[0] = -1
}

alarm[2]:

state = 2 ;
alarm[0] = 3 * room_speed ;

The idea being if state = 3, I see a sprite of seeded land and it sets alarm[2]. When alarm[2] triggers, it changes the state = 2 (therefore changing the sprite to tilled land with no seeds as they have died from lack of watering) and sets alarm[0]. When alarm[0] triggers, it sets state = 2 and, therefore, the sprite to noone. Here is the full thing.

//CREATE:
state = 1 ;

//STEP:

//Keyboard Behavior
if (keyboard_check_pressed(ord("1"))) state = 1 ;
if (keyboard_check_pressed(ord("2"))) state = 2 ;
if (keyboard_check_pressed(ord("3"))) state = 3 ;
if (keyboard_check_pressed(ord("4"))) state = 4 ;
if (keyboard_check_pressed(ord("5"))) state = 5 ;

//Sprites and Alarm Countdowns
if (state = 1) sprite_index = noone ;
if (state = 2)
{
sprite_index = Spr_Tilled_Land
alarm[0] = 3 * room_speed
alarm[2] = -1
alarm[1] = -1
}
if (state = 3)
{
sprite_index = Spr_Seeded_Land
alarm[2] = 3 * room_speed
alarm[2] = -1
alarm[0] = -1
}
if (state = 4)
{
sprite_index = Spr_Seeded_Watered
alarm[1] = 5 * room_speed
alarm[0] = -1
alarm[2] = -1
}
if (state = 5)
{
sprite_index = Spr_Tilled_Watered
alarm[2] = 5 * room_speed
alarm[1] = -1
alarm[0] = -1
}

//Alarms

//ALARM[0]
state = 1

//ALARM[1]
state = 3 ;
alarm[2] = 3 * room_speed

//ALARM[2]
state = 2 ;
alarm[0] = 3 * room_speed ;

I get no error message and am able to change from state to state by pressing the appropriate key but the alarms never seem to trigger or at least I'm not seeing the result of it.

Am I even barking up the right tree here or is my logic way off? Or could it work with tweaks but there is a better/ more efficient way to accomplish it?


Bonus Question: How do I set it so these countdowns continue to occur even when I leave the room and it doesn't reset. Making it persistent doesn't work as it makes the field follow me from room to room, but I need the field to keep doing its thing even if I am in the mines or exploring town or fishing etc.

Sorry that was so long but that is everything I could think of that I have tried.
 
I'd say your best bet is to follow this tutorial:

FriendlyCosmonaut has a great in-depth series on creating your own farming sim, she's a great coder and you'd learn a huge amount going through the series.
 

FrostyCat

Member
You are setting those alarms continuously without allowing any of them to tick down normally, hence the alarms payloads never get to run. Check that they are not already set in motion before setting them again.
Code:
if (state = 4) 
{
  sprite_index = Spr_Seeded_Watered;
  if (alarm[1] < 0)
  {
    alarm[1] = 5 * room_speed;
  }
  alarm[0] = -1;
  alarm[2] = -1;
}
This is one special case of a whole class of common bugs involving unwanted repetition. In the long run, you should also study up on how to use flags to guard against them.

You should also look out for typos like this one:
Code:
sprite_index = Spr_Seeded_Land 
alarm[2] = 3 * room_speed 
alarm[2] = -1
 
S

Singai

Guest
You are setting those alarms continuously without allowing any of them to tick down normally, hence the alarms payloads never get to run. Check that they are not already set in motion before setting them again.
Code:
if (state = 4)
{
  sprite_index = Spr_Seeded_Watered;
  if (alarm[1] < 0)
  {
    alarm[1] = 5 * room_speed;
  }
  alarm[0] = -1;
  alarm[2] = -1;
}
This is one special case of a whole class of common bugs involving unwanted repetition. In the long run, you should also study up on how to use flags to guard against them.

You should also look out for typos like this one:
Code:
sprite_index = Spr_Seeded_Land
alarm[2] = 3 * room_speed
alarm[2] = -1
That did it. Thank you! Thank you! Thank you! I was going out of my mind.

I'd say your best bet is to follow this tutorial:

FriendlyCosmonaut has a great in-depth series on creating your own farming sim, she's a great coder and you'd learn a huge amount going through the series.
Beautiful. Thank you for this. I've been watching tutorials for individual things... somehow it never occured to me to look for a tutorial specifically for farming sims.. don't I feel like a dummy? ;)
 
Top