Author Topic: Checking for database resident entities  (Read 2209 times)

0 Members and 1 Guest are viewing this topic.

MickD

  • Gator
  • Posts: 3315
  • (x-in)->[process]->(y-out)
Checking for database resident entities
« on: February 17, 2009, 08:09:05 PM »
Below is some code snippes I'm working with, it's for the python arx wrappers I'm working on and unless I sort this out in the best possible fashion it will be the weak link in the chain!

When passing pointers back and forth with Python, you wrap your pointer in a CPyObject (basically a container for a void*) in this fashion -
Code: [Select]
// create the new line to pass back to python:
AcGePoint3d *p1 = new AcGePoint3d(x1, y1, z1);
AcGePoint3d *p2 = new AcGePoint3d(x2, y2, z2);
AcDbLine* newline = new AcDbLine(*p1, *p2);
return PyCObject_FromVoidPtr(newline, del_ent);

where 'del_ent' is a function ptr to a delete function for cleanup.
With that, Python has a pointer to the new db entity and can do what it needs to do with it, however, once you return back to the host app Python needs to do its cleanup, this is what I have so far, it works but I'm not happy with it -

Code: [Select]
static void del_ent(void* ptr)
{
/* just return and python will be happy, again, we need
to be careful with this as we could easily create a memory leak! */
AcDbEntity* e = (AcDbEntity*)ptr;
//e->upgradeOpen();
if(e->blockId() == AcDbObjectId::kNull) // it's not a db resident, we can delete it.
delete ptr;
//e->close();
return;
}

the problem is the doc's say you're not supposed to 'access' the pointer if it's not open, would using e->BlockId() without the entity being open be breaking the rules?? (it seems to work...)
Is there a better way to check if an entity/object belongs to a db without opening it?

thanks.
Mick.
Forth is like the Tao: it is a Way, and is realized when followed.
Its fragility is its strength; its simplicity is its direction - Michael Ham

Lao Tzu: “To attain knowledge, add things
every day; to obtain wisdom, remove things every day.”

It's Alive!

  • BricsCAD
  • Needs a day job
  • Posts: 6963
  • AKA Daniel
Re: Checking for database resident entities
« Reply #1 on: February 17, 2009, 08:38:17 PM »
It seems as long as you are not modifying anything, It should be ok to check the ObjectID for isNull or isValid


Code: [Select]
if(e->objectId().isNull()) // it's not a db resident, we can delete it.
      delete ptr;

MickD

  • Gator
  • Posts: 3315
  • (x-in)->[process]->(y-out)
Re: Checking for database resident entities
« Reply #2 on: February 17, 2009, 08:48:23 PM »
Thanks Dan.

I was thinking about this also, it may be safer just to pass ObjectId's back and forth instead...if I deleted one of those I may well have the same problem though(?).
Forth is like the Tao: it is a Way, and is realized when followed.
Its fragility is its strength; its simplicity is its direction - Michael Ham

Lao Tzu: “To attain knowledge, add things
every day; to obtain wisdom, remove things every day.”

MickD

  • Gator
  • Posts: 3315
  • (x-in)->[process]->(y-out)
Re: Checking for database resident entities
« Reply #3 on: February 17, 2009, 09:25:44 PM »
Nope, ObjectId is probably the same if not worse!

I'll experiment with handles for a bit, it also avoids passing pointers about but will make for a bit of work dealing with the entities (opening etc).
Forth is like the Tao: it is a Way, and is realized when followed.
Its fragility is its strength; its simplicity is its direction - Michael Ham

Lao Tzu: “To attain knowledge, add things
every day; to obtain wisdom, remove things every day.”

T.Willey

  • Needs a day job
  • Posts: 5218
Re: Checking for database resident entities
« Reply #4 on: February 20, 2009, 01:47:23 PM »
Just a guess....  If the entity is not a db resident, will it not have an OwnerId then?  ..../guess
Tim

I don't want to ' end-up ', I want to ' become '. - Me

Please think about donating if this post helped you.

pkohut

  • Guest
Re: Checking for database resident entities
« Reply #5 on: February 20, 2009, 03:18:13 PM »
I think your fine Mick, maybe change like so?  Being unsure about implementation
details I don't know if you need to close the object here or somewhere else.

Code: [Select]
static void del_ent(void* ptr)
{
    /* just return and python will be happy, again, we need
    to be careful with this as we could easily create a memory leak! */
    AcDbObject* pObj = AcDbObject::cast(ptr);
    if(pObj)
    {
        if(pObj->blockId() == AcDbObjectId::kNull) // it's not a db resident, we can delete it.
            delete pObj;
        else
            pObj->close();
    }
}

Paul

MickD

  • Gator
  • Posts: 3315
  • (x-in)->[process]->(y-out)
Re: Checking for database resident entities
« Reply #6 on: February 20, 2009, 06:32:28 PM »
Thanks Paul, yes, closing is another issue but it won't hurt to close it anyway as the object would be open at creation and I would be opening to edit objects anyway, python will call this method once it loses focus so it's sort of a safety net I guess.

I don't want the python interface to mimic arx too much, it would make it too verbose and would defeat the purpose of using python I think, I'd rather it be more like vb which handles the db interaction behind the scenes so you can just concentrate on the scripting.
cheers,
Mick.
Forth is like the Tao: it is a Way, and is realized when followed.
Its fragility is its strength; its simplicity is its direction - Michael Ham

Lao Tzu: “To attain knowledge, add things
every day; to obtain wisdom, remove things every day.”