• Hey Guest! Ever feel like entering a Game Jam, but the time limit is always too much pressure? We get it... You lead a hectic life and dedicating 3 whole days to make a game just doesn't work for you! So, why not enter the GMC SLOW JAM? Take your time! Kick back and make your game over 4 months! Interested? Then just click here!

GML [SOLVED] Passing id of creator object to created object

K

Kuro

Guest
Hi, how are you all today?

tl;dr version:
Is there a way to let a created object know which instance created it, so i can keep it aligned with its creator's x,y, (to do the x,y, matching in the created object's code rather than doing this alignment in the creating object's code)?

Long version:
I've made an object that represents an enemy's mele attack which my enemies can spawn at their x, y coords should my player obj get within their attack range if they feel like attacking (the attack object will then be used to check for collisions with player). The attacking object has creation code that sets an alarm that will clean it up after a short duration.

I'd quite like for the attack object to be able to match the x,y of the enemy object that created it, so that if the enemy moves forward the attack object will move forward as well. But I'm not quite sure how I would pass that info to it.

right now in the creator code I tried storing the created object in a temp variable called atk, then using atk.calling_enemy = self; to try to pass the id of the creator to the created object, but it's throwing an error.

Code in the enemy object that creates the attack object
Code:
if(can_attack && !attacking)
        {
            attack_timer -= 1;
            if(attack_timer <= 0)
            {
                //Mele Attack
                var atk = instance_create_layer(x,y,"Actor_adds",obj_pfEnemyAttack);
                atk.calling_enemy = self;
                attacking = true;
                alarm_set(1,atk.time_till_end);
                attack_timer = attack_cooldown;
            }
        
        
        }

code in the attack object

Code:
//Create Event Code
calling_enemy = null;
number_of_frames = 7;
time_till_end = 30;
alarm_set(0,time_till_end);

//Step Event Code

if(calling_enemy != null)
{
    x = calling_enemy.x;
    y = calling_enemy.y;
}

//Alarm 0 code
instance_destroy();
Id kind of like to have the attack object keep itself aligned with the enemy that created it rather than have the enemy do it, but if there's no way to pass that info to the created object I guess I could let the enemy steer its attack object around instead.

Thanks in advance for taking the time to read ths at this and for suggestions.


PS.
here's the error if I try to pre-initialize calling_enemy in the created objects create script.
---
FATAL ERROR in
action number 1
of Create Event
for object obj_pfEnemyAttack:

Variable obj_pfEnemyAttack.null(100041, -2147483648) not set before reading it.
at gml_Object_obj_pfEnemyAttack_Create_0 (line 4) - calling_enemy = null;
--
and here's the error if I comment out calling_enemy = null; in the creation code
--
FATAL ERROR in
action number 1
of Step Event0
for object obj_pfEnemyAttack:

Variable obj_pfEnemyAttack.null(100042, -2147483648) not set before reading it.
at gml_Object_obj_pfEnemyAttack_Step_0 (line 4) - if(calling_enemy != null)
--
 
M

munkbusiness

Guest
Based on tl:dr

So in the object you want to spawn the attack from:
Code:
attack = instance_create(x,y,attackObj);
attack.owner = id;
So in this case you set a variable "creatorID" inside the object you create and from in there you can use that.

So in the attack object you can do something like this in the step event.
Code:
x = owner.x;
y = owner.y;
Their x and y coordinates of the attack should now follow the one who made it.

EDIT: Fixed some mistakes I made, was to quick with the solution.
EDIT2: To fast again. I looked up an old project, this works 100%.
 
Last edited by a moderator:

YellowAfterlife

ᴏɴʟɪɴᴇ ᴍᴜʟᴛɪᴘʟᴀʏᴇʀ
Forum Staff
Moderator
Your error is because of using `null`. GameMaker uses `undefined` in place of `null`, as it was originally implemented as a value that data structure functions would return when reading out-of-bounds. You can either change that to `undefined` or make a macros with name `null` and value `undefined` (since it's almost identical to what `null` is in other languages).

The rest of the code seems alright, although it is probably a better idea to use `= self.id` (for unique identifier) rather than just `= self` (which may happen to be a special internal value, depending on GMS version)
 

FrostyCat

Redemption Seeker
The name for the null value in GML is undefined, not null. Also, id holds the current instance ID, not self (which is always -1 and already deprecated in GMS 2).

Based on your tl:dr

What you want to do is use the with statement. Which allows you to to call code as if you were inside another object.

Code:
objID = instance_create(x,y,otherObj);
with(otherObj) id = other.objID
So in this case you set a variable "id" inside the object you create and from in there you can use that.
You can't use the variable id like this, it is the read-only instance variable for the current instance ID. Also, you don't seem to understand the difference between an object and an instance, nor the importance of tracing code. Your code attempts to make every instance of otherObj get a reference back to the created instance of otherObj, instead of making the created instance of otherObj get a reference back to the calling instance as should be.

The original poster already got this part down except for a minor conceptual flaw, he doesn't need your defective solution.
 
M

munkbusiness

Guest
I know the difference between an object and an instance, but I can see I did some mistakes in my posted code will test it first before posting next time. I have gone back and edited it to work.
 
Last edited by a moderator:
K

Kuro

Guest
Thanks for the replies everyone.
I changed the things below and now it's working perfectly. Much appreciated!

In the created object's create script I changed null to undefined.
In the created object's step script I changed the null check if(calling_enemy != null) to if(calling_enemy != undefined)
and in the creator object's script where it creates the attack object I changed it to pass along self.id instead of just self.

I guess technically since self is depreaciated I should try to wean myself off it and just pass along id
what is it they say about old habits? xD
 
Top