Connect node with custom class? (ISceneNode User data)

Discuss about anything related to the Irrlicht Engine, or read announcements about any significant features or usage changes.
Vsk
Posts: 343
Joined: Thu Sep 27, 2007 4:43 pm

Post by Vsk »

vitek wrote:
Why don't use a Hash for this query, if you do it properly (very easy) you have O(1) query for searching.
Last I checked, Irrlicht doesn't provide a hash map, so I didn't recommend it. The current C++ standard library doesn't provide hash containers either, so there really isn't a single portable implementation that I could refer everyone to.
By the way, you guys that have experience, why hash aren use it everywhre in video games for this kind of querys?
People do use hash maps/sets in games.

I don't deny that having the extra data pointer in there would be a nice thing to have. It would definitely be useful for some users. I just don't feel that it is absolutely necessary. The framework that is provided provides enough to get things working.

If, at optimization time, you actually find that there is a performance bottleneck when doing lookups, then you should optimize it. A binary search will likely be fast enough. If it isn't, then carefully constructed hash table should be plenty fast. If that isn't enough, then a user data pointer may be the only option.

Travis
But what is wrong in build it for oursefl?, A hash table , static or dinamic is far easier that a binary treee (espacily for the delete) and easier that other estructs like avls o similars. The only thing that is import is the map function but with carefull and some tries could be perfect.

Glad to hear that they are used in game dev :D. I just thought that I was conceptualy wrong.

By the way has anyone implemented a avl delete function easily :? (without lazy delete of course).
It is horrible!.
rogerborg
Admin
Posts: 3590
Joined: Mon Oct 09, 2006 9:36 am
Location: Scotland - gonnae no slag aff mah Engleesh
Contact:

Post by rogerborg »

vitek wrote:The issue with deallocation is that the scene node has no idea what to do with the user data pointer when the scene node destructor is called. i.e. If the user data pointer is a newton body, that newton body needs to be destroyed and deallocated with the proper newton functions. The scene node has no idea about how to do this, and it shouldn't. So how does the body get cleaned up?
Eh... exactly the same way it has to be done without a reference to it in the Irrlicht node, i.e. stored in a user-app data structure and destroyed/serialised entirely under the user application's control. Fretting over what type might be stored in there, or how the user app might later interpret the data that it chose to put there also seems a little fruitless. "void *" is shorthand for "that's your problem".

I'd imagined that a void * would provide a simple convenience method that might avoid a map lookup (or yet more hijacking of the ID), but I take the point that it would be easy to over think it somewhat.
Please upload candidate patches to the tracker.
Need help now? IRC to #irrlicht on irc.freenode.net
How To Ask Questions The Smart Way
elvman
Posts: 253
Joined: Sun Sep 17, 2006 9:37 am
Location: Riga, Latvia
Contact:

Post by elvman »

Everybody is using user pointers: Ogre (which has a really good design), ENet, Squirrel, etc. etc. Why don't you simply implement it in Irrlicht, and a lot of people would be much happier.
CuteAlien
Admin
Posts: 9734
Joined: Mon Mar 06, 2006 2:25 pm
Location: Tübingen, Germany
Contact:

Post by CuteAlien »

I was curious yesterday and had searched for that in the Ogre scenenodes and didn't find it. Are you sure they use this?
IRC: #irrlicht on irc.libera.chat
Code snippet repository: https://github.com/mzeilfelder/irr-playground-micha
Free racer made with Irrlicht: http://www.irrgheist.com/hcraftsource.htm
rogerborg
Admin
Posts: 3590
Joined: Mon Oct 09, 2006 9:36 am
Location: Scotland - gonnae no slag aff mah Engleesh
Contact:

Post by rogerborg »

Damn, Vitek didn't bite. :(

To be honest, I'm not really advocating adding user data, I was just curious as to what the arguments against it would be.

Unless you've got egregious numbers of objects, then you could (just for example) use 16 bits of the ID as an array index. Since it has no real meaning for Irrlicht (other than being brutally abused for collision bitflags!), I already consider the ID to be "user data", or at least close enough for my nefarious purposes.
Please upload candidate patches to the tracker.
Need help now? IRC to #irrlicht on irc.freenode.net
How To Ask Questions The Smart Way
Saturn
Posts: 418
Joined: Mon Sep 25, 2006 5:58 pm

Post by Saturn »

CuteAlien wrote:I was curious yesterday and had searched for that in the Ogre scenenodes and didn't find it. Are you sure they use this?
Yep, but not in SceneNode, but in MovableObject.
Irrlicht's scene node are not the same as Ogre's scene nodes. Ogre's scene nodes more or less are what IDummyTransformationSceneNode are in Irrlicht. The actual object is attached to the scene nodes.
suliman
Posts: 379
Joined: Sat Sep 23, 2006 2:06 pm

Post by suliman »

Yes i could look up all object (of course, using some smart search algoritm) every time i got a node from collision, but why? It takes cpu and look ugly in my code instead of just:

Code: Select all

if(theNodeHitted->userData){
   theNodeHitted->userData->health-=BULLETDAMAGE;
   theNodeHitted->userData->lastDamagedBy=BULLET_TEAM;
}
If i use the void * and run into a problem or crash, i know i have scewed up something using the void * so ill need to fix it. I think we can thrust the user with that. On destructon issues: If i set up a complex class with physics objects etc attached to it i still need to be concern how to dispose of it proberly, its not like irrlicht can handle that for me automatically in the current state anyway.

ANYWAY...
Ok you leave me no choice but to hack it myself and thats dangerous:)
Adding void * userData to animatedscenenode (i need that feature, and im a bit suprised most people do not) I even added a comment about being careful next to it, hehe.

I might not know how to do this correctly... I add it to iscenenode.h and i can use it in my compiler, but if i assigned it to anything, this corrupts some important system-pointers:) So something is wrong.
Do i need to change something else, recompile dll or anything? I only changed the h-file...

I realize this is not the most handsome fix, I will get back to you if i encounter any more problems.

Thanks
E
suliman
Posts: 379
Joined: Sat Sep 23, 2006 2:06 pm

Post by suliman »

Anyone? It seem that the pointer is not set up correctly, as it "shares memory location" with some other stuff. What could be wrong?

Thanks
Erik
vitek
Bug Slayer
Posts: 3919
Joined: Mon Jan 16, 2006 10:52 am
Location: Corvallis, OR

Post by vitek »

suliman wrote:If i set up a complex class with physics objects etc attached to it i still need to be concern how to dispose of it proberly, its not like irrlicht can handle that for me automatically in the current state anyway.
Yes, Irrlicht does none of this in the current state. But if the enhancement is added it would be possible. You can specify a protocol to use for notification when the scene node is being destroyed. For instance you could require that the user data implement an interface, and a method of that interface be called when the scene node is destroyed. This would give a derived class the opportunity to clean itself up at the appropriate time.
suliman wrote:Do i need to change something else, recompile dll or anything? I only changed the h-file...
Yes, you definitely need to rebuild the dll.
suliman wrote:

Code: Select all

if(theNodeHitted->userData){ 
   theNodeHitted->userData->health-=BULLETDAMAGE; 
   theNodeHitted->userData->lastDamagedBy=BULLET_TEAM; 
}
Well, because the user data pointer would be void*, at the very least you would need to write something like this...

Code: Select all

MyUserData* userData = (MyUserData*)theNodeHitted->getUserDataPointer();
if(userData){ 
   userData->health -= BULLETDAMAGE; 
   userData->lastDamagedBy = BULLET_TEAM; 
}
From a design/extensibility perspective that is kinda ugly, but it definitely does the job. I personally feel that something similar to the following would be a bit nicer.

Code: Select all

messageQueue.sendMessage (
  theHittedNode->getID(), // message receiver id
  theBulletNode->getID(), // message sender id
  10, // ms delay before sending message
  MSG_TYPE_BULLETDAMAGE // message type
);
Travis
suliman
Posts: 379
Joined: Sat Sep 23, 2006 2:06 pm

Post by suliman »

ok which leads me to: how do i recompile the irrlicht ddl? Ive never had to do it before, but i need this pointer and noone else uses it.

Thanks for helping out
Erik
vitek
Bug Slayer
Posts: 3919
Joined: Mon Jan 16, 2006 10:52 am
Location: Corvallis, OR

Post by vitek »

Depends on your compiler. There are project files and makefiles for each supported compiler. They can be found in the source directory.

If you are using Visual C++ like many are, you would need to open the appropriate Irrlicht project file in the source directory, set the configuration type and do the build. Either that will work or it will fail because you need to install one of the DirectX SDKs or modify IrrCompileConfig.h

Travis
rogerborg
Admin
Posts: 3590
Joined: Mon Oct 09, 2006 9:36 am
Location: Scotland - gonnae no slag aff mah Engleesh
Contact:

Post by rogerborg »

Bear in mind that the node's Id isn't used by Irrlicht, except for collision bitmasking. For (nearly) all intents and purposes, it's user data.

Even if you want to use Irrlicht's collision, you could still use (e.g.) just the low 16 or 24 bits of the Id as an array index.

Code: Select all

    // An array of data.  It can be any size, and could be objects or pointers.
    SMaterial someArbitraryData[8];
    int index = 3;
    printf("index = %d\nLighting = %d\n", index, (int)someArbitraryData[index].Lighting);

    someArbitraryData[index].Lighting = false;

    // Use (e.g.) the low 24 bits as an index.  You can still use the high 8 
    // bits for collision masking, so we'll retain them.
    node->setID((node->getID() & 0xFF000000) | (index & 0x00FFFFFF));

    // Time passes.  Thorin sits down and starts singing about gold.

    index = node->getID() & 0x00FFFFFF;
    // As if by magic, we get index 3 back.  Let's see what's in there.

    printf("index = %d\nLighting = %d\n", index, (int)someArbitraryData[index].Lighting);
Please upload candidate patches to the tracker.
Need help now? IRC to #irrlicht on irc.freenode.net
How To Ask Questions The Smart Way
suliman
Posts: 379
Joined: Sat Sep 23, 2006 2:06 pm

Post by suliman »

yeah but index doesnt cut it for me, i want a straight pointer to the owner of the node, as i use mainly dynanic lists (the objects do not move inside the lists, the list contains pointers only so the pointers i set to the objects are always valid)

Ill have to look into recompiling the engine. I didnt wanna do it becouse then i need to change this every time the engine updates and seem like unnecessary fuss, but well life is tough:)

E
Halifax
Posts: 1424
Joined: Sun Apr 29, 2007 10:40 pm
Location: $9D95

Post by Halifax »

Eh, all you would need to do is merge between your versions. Should all take about two seconds, so it shouldn'tbe that much fuss.
TheQuestion = 2B || !2B
suliman
Posts: 379
Joined: Sat Sep 23, 2006 2:06 pm

Post by suliman »

merge? I need to build a new dll right? When new irrlicht version is out or someone on the forum adds stuff to the current irrlicht i need to add my little pirate fix.

I cannot use the Id for a pointer right? As i recalled it, pointers are at least 32 bits:(
Post Reply