Navigation

    • Register
    • Login
        No matches found
    • Search
    1. Home
    2. krfft
    K

    krfft

    @krfft

    0
    Reputation
    10
    Posts
    22
    Profile views
    0
    Followers
    0
    Following
    Joined Last Online

    • Profile
    • More
      • Following
      • Followers
      • Topics
      • Posts
      • Best
      • Groups
    krfft Follow

    Best posts made by krfft

    This user hasn't posted anything yet.

    Latest posts made by krfft

    RE: Override material tag in take

    After some research by @ferdinand the issue was that the file was locked for take overrides. This can easily be missed since the overrides are locked when the button in the UI is disabled and not locked if its active:

    notlocked.jpg locked.jpg

    I added a check in the plugin to toggle the lock if its "active":

    if (!IsCommandChecked(431000108)) {
        CallCommand(431000108);
    }
    
    posted in Cinema 4D SDK •
    RE: Override material tag in take

    @ferdinand I have sent the file to the supplied email address, looking forward to what you can find.

    posted in Cinema 4D SDK •
    RE: Override material tag in take

    @ferdinand Ok this is where it gets interesting, I tried your script on the C4D file where my plugin didn't work and I got the same behaviour in your script. The FindOrAddOverrideParam function returns nullptr. I tried to create a cube with a dummy material in the same project and it also returns nullptr. However if I create a new project, create the cube and run the script with a dummy material it works. Also both our scripts work in the other project i mentioned earlier in the thread, of course it had nothing to do with selection tags 🤦

    The only difference I can find for the projects is that the non-functioning one was created in r23, it gives me a warning when saving it in r25 saying it will not be possible to open in r23 again. I do think that the other file also is created in a older version so should not be the issue but idk. Right now our workaround is to copy all geometry and materials into a new project, then the plugin works.

    I will gladly share the two files and our plugin but since its confidential it needs to be in private, let me know where to send it if you want to have a look.

    posted in Cinema 4D SDK •
    RE: Override material tag in take

    Hi @ferdinand,

    I have spent some time rewriting the code incl using BaseLink instead of pointers. I am also validating all values put into the FindOrAddOverrideParam function. For background info we name the material tags to be able to know which are to have which material for the different variants of a product.

    FindTags

    Bool FindTagsContaining(BaseObject* topObject, BaseLinkArray* foundTags, maxon::String contains)
    {
    	iferr_scope_handler
    	{
    		ApplicationOutput("Iterating tags finished with error: @",err);
    		return false;
    	};
    
    	BaseObject* child = topObject->GetDown();
    	if (child == nullptr)
    		return false;
    
    	while (child != nullptr) {
    		BaseTag* tag = child->GetTag(Ttexture);
    		if(tag != nullptr)
    		{
    			maxon::String tagName = tag->GetName();
    			if (tagName.Find(contains, 0)) {
    				foundTags->Append(tag);
    			}
    		}
    
    		FindTagsContaining(child,foundTags,contains);
    		child = child->GetNext();
    	}
    
    	return true;
    }
    

    GetMaterial

    BaseMaterial* GetMaterial(maxon::AssetDescription assetDescription) {
        iferr_scope_handler
        {
          ApplicationOutput("Stopped LoadMaterial() execution with the error: @", err);
          return nullptr;
        };
    
        BaseDocument* doc = GetActiveDocument();
    
        maxon::String matName = assetDescription.GetMetaString(maxon::OBJECT::BASE::NAME, maxon::LanguageRef()) iferr_return;
        BaseMaterial* material = doc->SearchMaterial(matName);
    
        if (material == nullptr) {
            maxon::Url url = assetDescription.GetUrl() iferr_return;
    
            if (url.IsEmpty())
                return nullptr;
    
            maxon::String* error = {};
            maxon::Bool didMerge = MergeDocument(doc, MaxonConvert(url), SCENEFILTER::MATERIALS, nullptr, error);
    
            material = doc->SearchMaterial(matName);
        }
    
        return material;
    }
    

    And finally the take creation:

    BaseLinkArray editTags;
    FindTagsContaining(productRoot, &editTags, "Edit_"_s);  
    
     // editTags is sent as a pointer to function below.
    
    BaseTake* take = td->AddTake(takeName, parent, NULL);
    BaseDocument* doc = GetActiveDocument();
    DescID idMaterialAssignment = DescID(DescLevel(TEXTURETAG_MATERIAL));
    
    for (Int i = 0; i < editTags->GetCount(); ++i)
    {
        C4DAtomGoal* const goal = editTags->GetIndex((Int32)i, doc);
        if (goal == nullptr)
            return nullptr;
    
        BaseTag* tag = static_cast<BaseTag*>(goal);
    
        const maxon::AssetDescription* materialDescription = editMaterials->FindValue(tag->GetName());
        if (materialDescription == nullptr) {
            ApplicationOutput("Material description was null for name: @", editMaterials->FindValue(tag->GetName()));
            return nullptr;
        }
        
        BaseMaterial* mat = GetMaterial(*materialDescription);
        if (mat == nullptr) {
            ApplicationOutput("GetMaterial was null for name: @", editMaterials->FindValue(tag->GetName()));
            return nullptr;
        }
    
                ApplicationOutput("Adding tag override for " + tag->GetName() + " of type " + tag->GetTypeName() + " with " + mat->GetName());
    
        BaseOverride* overrideNode = take->FindOrAddOverrideParam(td, tag, idMaterialAssignment, GeData(mat));
    
        if (overrideNode == nullptr) {
            ApplicationOutput("Unable to create override for " + tag->GetName() + " with " + mat->GetName());
            return nullptr;
        }
    
        overrideNode->UpdateSceneNode(td, idMaterialAssignment);
    }
    

    The output of the ApplictionOutputs would be something like:

    Adding tag override for Edit_StrapMetal of type Material with Aluminium_Anodised_Anthracite_0123
    Unable to create override for Edit_StrapMetal with Aluminium_Anodised_Anthracite_0123
    

    To me everything looks good, is there any way I could get some info on why the override is null or some error log from FindOrAddOverrideParam?

    posted in Cinema 4D SDK •
    RE: Override material tag in take

    @ferdinand Thank you for the input, I will look into the recommendations you have. I am quite new to working with C++ and get lost in pointers sometimes. Didn't know about BaseLink but it definately looks usable.

    However, as you state most things looks fine but still I dont get any overrides on the tags in the takes (yes take is a child take). I tried the same code, but without the typing of what type of tag to find, on a scene where selectiontags are named as the searchterm instead of texturetags. Here it works as intended and the overrides show up on the take. Do you have any idea why this doesn't work when trying to override texturetags?

    posted in Cinema 4D SDK •
    RE: Override material tag in take

    @ferdinand Thank you for the swift response. I will try to elaborate on my question.
    I am iterating over the entire scene to find tags matching a name and put them in a list:

    maxon::BaseArray<BaseTag*> FindTagsContaining(BaseObject* topObject, maxon::String contains)
    {
    	maxon::BaseArray<BaseTag*> foundTags;
    
    	BaseObject* child = topObject->GetDown();
    	if (child == nullptr)
    		return maxon::BaseArray<BaseTag*>();
    
    	while (child != nullptr) {
    		BaseTag* tag = child->GetTag(Ttexture);
    		if(tag != nullptr)
    		{
    			maxon::String tagName = tag->GetName();
    			if (tagName.Find(contains, 0)) {
    				(void)foundTags.Append(tag);
    			}
    		}
    
    		(void)foundTags.AppendAll(FindTagsContaining(child,contains));
    		child = child->GetNext();
    	}
    
    	return foundTags;
    }
    

    I found a weird thing that if I print GetTypeName() on the tag returned by GetTag(Ttexture) it returns Material, that was the reason for my thinking that the term Texture tag was removed.

    However with this list I then create a material override take with each tags material overridden:

    maxon::BaseArray<BaseTag*>::Iterator editTagIterator;
       for (editTagIterator = editTags->Begin(); editTagIterator != editTags->End(); editTagIterator++)
       {
         DescID idMaterialAssignment = DescID(DescLevel(TEXTURETAG_MATERIAL));
         take->FindOrAddOverrideParam(td, *editTagIterator, idMaterialAssignment, GeData(GetMaterial(*materialDescription)));
       }
    

    This is following the Python version (where it works) almost fully.
    I have validated that the GetMaterial function returns a Material object and the function follows the example you posted in another of my threads:

    BaseMaterial* GetMaterial(maxon::AssetDescription assetDescription) {
        iferr_scope_handler
        {
          ApplicationOutput("Stopped LoadMaterial() execution with the error: @", err);
          return nullptr;
        };
    
        BaseDocument* doc = GetActiveDocument();
    
        maxon::String matName = assetDescription.GetMetaString(maxon::OBJECT::BASE::NAME, maxon::LanguageRef()) iferr_return;
        BaseMaterial* material = doc->SearchMaterial(matName);
    
        if (material == nullptr) {
            maxon::Url url = assetDescription.GetUrl() iferr_return;
    
            if (url.IsEmpty())
                return nullptr;
    
            maxon::String* error = {};
            maxon::Bool didMerge = MergeDocument(doc, MaxonConvert(url), SCENEFILTER::MATERIALS, nullptr, error);
    
            material = doc->SearchMaterial(matName);
        }
    
        return material;
    }
    
    posted in Cinema 4D SDK •
    Override material tag in take

    I am porting a plugin to create takes based on different materials from python to C++. Everything works well until the moment when the overrideParam is added to the take. Nothing is added and the function returns null.

    take->FindOrAddOverrideParam(td, *editTag, TEXTURETAG_MATERIAL, GetMaterial(*materialDescription),NULL,false);
    

    I have noticed that instead of the type TextureTag that I got before from the material tags I now get Material as type. Do I need to change the TEXTURETAG_MATERIAL to something else now? Or how do I override the material of a MaterialTag in a Take using C++?

    posted in Cinema 4D SDK •
    Loading Materials from AssetDescriptions into a Scene

    Thanks for the help @ferdinand, the plugin rewrite from python is coming along nicely and I am able to fetch all AssetDescription* from the Asset API.

    However reading the handbook I am unable to find a way to fetch a BaseMaterial* from the AssetDescription*. Are you able to guide me towards a solution? I need this to be able to create a Take with a specific material.

    posted in Cinema 4D SDK •
    Getting materials from Asset browser

    I am trying to get all materials from asset browser with the C++ SDK and have found the following endpoint: https://developers.maxon.net/docs/Cinema4DCPPSDK/html/classmaxon_1_1_asset_repository_interface.html.

    However my knowledge in C++ is quite limited and I have previously only built C4D plugins in python so I am a little lost in how to use the class. I guess I need to get a instance of the interface in some way.

    Does anyone have an example of how to retrieve the asset browser instance and get items from it?

    posted in Cinema 4D SDK •
    Baking textures for PBR object

    Is it possible to bake the values of the reflection channel into textures using "Bake object"?

    posted in Cinema 4D SDK •