Calling .GetIID() in instance constructor causes duplicate IIDs

0 favourites
  • 5 posts
  • Ashley

    I think I found a critical bug in the SDK. If you add

    var iid = this.GetInstance().GetIID();

    to the runtime instance constructor(inst, properties)

    It will cause the first and last instance of the object to have the same IID, verified using Debug Layout.

    This only seems to happen at start of layout where multiple instances are on already on the layout, or they are created at the start from existing container siblings. It might take place in other circumstances, but it didn't when I did a simple test of creating instances by clicking the mouse after start of layout.

    Here's an example project. The bundled addon is just the sdk drawingPlugin example with that one line added to constructor.

    EDIT: Also, I was able to partially 'fix' the issue by calling _objectType._SetIIDsStale(), but any container siblings for that instance are still set to the old siblings from the previously duplicated IID.

  • I don't think it will be feasible to fix this, since IIDs are lazy-assigned (so GetIID() will actually go and assign IIDs), and if you do that during a constructor, the object has not finished being created yet so won't be found for IID assignment. There's probably a bunch of things that don't work in the constructor, because in the constructor, you're still in a halfway initialised state, and the engine is usually going to expect to see a fully initialised instance.

    So my advice would be: don't call GetIID() in a constructor. Why would you need to anyway? If I "fixed" this, I'd probably just make that throw an exception.

  • I don't think it will be feasible to fix this, since IIDs are lazy-assigned (so GetIID() will actually go and assign IIDs), and if you do that during a constructor, the object has not finished being created yet so won't be found for IID assignment. There's probably a bunch of things that don't work in the constructor, because in the constructor, you're still in a halfway initialised state, and the engine is usually going to expect to see a fully initialised instance.

    So my advice would be: don't call GetIID() in a constructor. Why would you need to anyway? If I "fixed" this, I'd probably just make that throw an exception.

    I was calling this as part of a workaround for when the plugin fetches a character from preload and GetSiblings() turned up empty. Is there already a way to set the sibling ids to stale as well? or have force it to reassign them? If not, I'll just move all the sibling and iid related initialization steps out of the constructor.

  • Well, once again, if the object is half-way initialized, you can't guarantee all siblings will be there. It's a good case to illustrate this actually: suppose you create 3 siblings. When you create the first sibling, suppose you try to get the other siblings. They don't exist yet. You're only half-way through creating the first of 3 instances. It's impossible for the engine to resolve this: even if it created siblings on-the-spot when you asked for them, another sibling might ask for the first sibling again, which still isn't fully created, and you have an unresolvable cyclic dependency.

    In the engine we have post-constructor 'OnCreate' methods which run when everything has finished initializing, so we avoid this type of problem. I'm not sure if we exposed that to the SDK though.

    If not, I'll just move all the sibling and iid related initialization steps out of the constructor.

    If you can, that's the best solution, since you avoid all these complicated half-initialized problems.

  • Try Construct 3

    Develop games in your browser. Powerful, performant & highly capable.

    Try Now Construct 3 users don't see these ads
  • Thanks for the example. That makes perfect sense.

    In the engine we have post-constructor 'OnCreate' methods which run when everything has finished initializing, so we avoid this type of problem. I'm not sure if we exposed that to the SDK though.

    It doesn't seem to be part of runtime instance. It would be useful and convenient, but it wasn't needed to fix my issue.

Jump to:
Active Users
There are 1 visitors browsing this topic (0 users and 1 guests)