Archicad C++ API
About Archicad add-on development using the C++ API.
SOLVED!

Creating a new Element for a Library Object

Anonymous
Not applicable
Hi guys,

With your help I imported this library object from an .lcf file which has classification Building Element Proxy:


I have to create an element for it and I want to ask the following:

1. Do I have to use ACAPI_Element_Create or some API_​LibPart function?

2. In the first case, is this the correct ID - element.header.typeID = API_ObjectID?

3. Do I have to set in the memo the coordinates and sizes of all the "lines" which build this figure? If I already have them imported, can I retrieve them in some way?

I could not find anything relevant in the example and in the other topics in the forum.

Thanks in advance!
1 ACCEPTED SOLUTION

Accepted Solutions
Solution
Tibor Lorantfy
Graphisoft Alumni
Graphisoft Alumni
In a nutshell:
API_Element element;
BNZeroMemory (&element, sizeof (API_Element));
element.header.typeID = API_ObjectID;

API_ElementMemo elementMemo;
BNZeroMemory (&elementMemo, sizeof (API_ElementMemo));
ACAPI_Element_GetDefaults (&element, &elementMemo);

element.object.libInd = libIndex;
element.object.pos.x = 3;
element.object.pos.y = 0;
element.object.level = 0;

ACAPI_Element_Create (&element, &elementMemo);
ACAPI_DisposeElemMemoHdls (&elementMemo);

View solution in original post

17 REPLIES 17
Ralph Wessel
Mentor
n.mihaylov wrote:
I have to create an element for it and I want to ask the following:
1. Do I have to use ACAPI_Element_Create or some API_​LibPart function?
2. In the first case, is this the correct ID - element.header.typeID = API_ObjectID?
3. Do I have to set in the memo the coordinates and sizes of all the "lines" which build this figure? If I already have them imported, can I retrieve them in some way?
In reply to your questions:
1) Yes, new elements can be created with ACAPI_Element_Create

2) Yes, API_ObjectID is the correct type for a general-purpose object element.

3) I doubt it. Objects usually render themselves, either through a script and parameter values or by embedded (fixed) geometry. You may have to set some parameter values or (most likely) at least the bounding object size.

I recommend looking at some of the API example projects, where you will find code for creating object elements etc.
Ralph Wessel BArch
Software Engineer Speckle Systems
Solution
Tibor Lorantfy
Graphisoft Alumni
Graphisoft Alumni
In a nutshell:
API_Element element;
BNZeroMemory (&element, sizeof (API_Element));
element.header.typeID = API_ObjectID;

API_ElementMemo elementMemo;
BNZeroMemory (&elementMemo, sizeof (API_ElementMemo));
ACAPI_Element_GetDefaults (&element, &elementMemo);

element.object.libInd = libIndex;
element.object.pos.x = 3;
element.object.pos.y = 0;
element.object.level = 0;

ACAPI_Element_Create (&element, &elementMemo);
ACAPI_DisposeElemMemoHdls (&elementMemo);
Anonymous
Not applicable
It works after I got the libIndex (libPart.index) this way:

GS::ucscpy (libPart.docu_UName, L("Object Name"));
ACAPI_LibPart_Search (&libPart, false);
Thank you both!
Anonymous
Not applicable
One more question:
What type of structure is this API_ObjectType element? It is none of these below and I cannot get the corresponding index of the element.wall.composite index, for example, in order to set the attribute.header.index and get the element with ACAPI_Attribute_Get
Ralph Wessel
Mentor
API_ObjectType is an element created from a library part. The element contains a list of parameter values typically referenced by the library part to render it in 2D and 3D.

A composite is a multi-skinned construction attribute specifying its component materials (including thickness and fill). A composite is relevant to planar elements like walls, roofs and slabs. Composites can't be applied to objects because there's no obvious application to a body that might have any shape.

That's why you find that only a limited number of elements have a composite attribute. Objects may have many other attributes, e.g. materials, fills and pens. Some are stored in API_ObjectType, but they're more commonly found in the object's parameter settings.
Ralph Wessel BArch
Software Engineer Speckle Systems
Anonymous
Not applicable
Thanks, got it!
I found how to get the element:

API_LibPart libPart;
BNZeroMemory (&libPart, sizeof (API_LibPart));
libPart.index = element.object.libInd;
ACAPI_LibPart_Get (&libPart);
Ralph Wessel
Mentor
n.mihaylov wrote:
I found how to get the element:
API_LibPart libPart;
BNZeroMemory (&libPart, sizeof (API_LibPart));
libPart.index = element.object.libInd;
ACAPI_LibPart_Get (&libPart);
It could become confusing if you use the wrong terminology. That code you quoted gives you the definition of a library part, not an element. You only have an element when an instance of the library part is placed in the project.
Ralph Wessel BArch
Software Engineer Speckle Systems
Anonymous
Not applicable
Yes, you are right! I need to get details for my element and so I need the details for its Library Part.
I have an element which is an instance of the Library Part. First I take the guids of all elements of type API_ObjectID with ACAPI_Element_GetElemList, then I take each element with ACAPI_Element_Get using these guids and finally I get the Library Part for my element with ACAPI_LibPart_Get using element.object.libInd as libPart.index
Ralph Wessel
Mentor
n.mihaylov wrote:
Yes, I need to get details for my element and so I need the details for its Library Part.
Ok, that makes sense as long as the details you are interested in are defined by the library part and can't be overridden by the instance element. For example, the parameter values should be extracted from the element, not the library part (unless you want the defaults).
Ralph Wessel BArch
Software Engineer Speckle Systems