We value your input!
Please participate in Archicad 28 Home Screen and Tooltips/Quick Tutorials survey

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

Getting list materials used in project missed a few "GDLM"

Anonymous
Not applicable
Hello,

I'm trying to get a list of all materials used in the project. The following code catches most materials, however there seems to be some type of material which isn't caught:
short nMaterials = 0;
ACAPI_Attribute_GetNum (API_MaterialID, &nMaterials);

for ( short i = 1; i <= nMaterials; i++ )
{
		BNZeroMemory( &attrib, sizeof ( API_Attribute ) );
		attrib.header.typeID = API_MaterialID;
		attrib.header.index = i;
		GSErrCode err2 = ACAPI_Attribute_Get( &attrib );
		...
}
The materials which aren't caught begin with "GDLM", for example: GDLM33_builtInMatAppleTop. They are only found when iterating through the meshes like this:
	...
	BNZeroMemory ( &component, sizeof ( component ) );
	component.header.typeID = API_BodyID;
	component.header.index  = ibody;
	err = ACAPI_3D_GetComponent (&component);
	
	API_Component3D material;
	BNZeroMemory ( &material, sizeof ( material ) );
	material.header.typeID = API_UmatID;
	material.header.index  = (GS::Int32)component.body.iumat;

	GS::UniString uniStringName;
	material.umat.mater.head.uniStringNamePtr = &uniStringName;

	GSErrCode err = ACAPI_3D_GetComponent ( &material );
	if ( err == NoError )
	{
	...									//
	}

Is there a way for me to get all the materials including GDLM materials without looping through all the meshes?

Thanks,
Ian
2 REPLIES 2
Ralph Wessel
Mentor
IanTr wrote:
I'm trying to get a list of all materials used in the project. The following code catches most materials, however there seems to be some type of material which isn't caught [...]
Is there a way for me to get all the materials including GDLM materials without looping through all the meshes?
I think the origin of the problem is the dynamic nature of these materials. They're defined by scripts, so are subject to sudden change from one view to another.

There is a way you may be able to us the ModelerAPI to avoid iterating through the entire model, but I haven't tried it myself. If you have an instance of a Model object, you can find the highest material index by calling its GetMaterialNum method. You could iterator through every value from 1 to this value calling the GetMaterial method, but I doubt you could assume that every index would return a valid (current) material. Worth a try though – someone from GS might be able to confirm.
Ralph Wessel BArch
Software Engineer Speckle Systems
Akos Somorjai
Graphisoft
Graphisoft
Ralph wrote:
IanTr wrote:
I'm trying to get a list of all materials used in the project. The following code catches most materials, however there seems to be some type of material which isn't caught [...]
Is there a way for me to get all the materials including GDLM materials without looping through all the meshes?
I think the origin of the problem is the dynamic nature of these materials. They're defined by scripts, so are subject to sudden change from one view to another.

There is a way you may be able to us the ModelerAPI to avoid iterating through the entire model, but I haven't tried it myself. If you have an instance of a Model object, you can find the highest material index by calling its GetMaterialNum method. You could iterator through every value from 1 to this value calling the GetMaterial method, but I doubt you could assume that every index would return a valid (current) material. Worth a try though – someone from GS might be able to confirm.
Ralph is right, you can get the materials defined in GDL scripts that way, and right again that not all indexes are valid.

So going through the 3D materials is an option; here are a few 'buts':
- materials used in element default settings (do you consider these 'used' materials?)
- materials which depend on conditions in GDL scripts, view settings etc.

Best, Ákos