Plugin Cafe Homepage
Forum Home Forum Home > Plugin Cafe > SDK Help
  New Posts New Posts
  FAQ FAQ  Forum Search   Register Register  Login Login

MaterialPreview Widget

 Post Reply Post Reply
Author
Message
Svente View Drop Down
Member
Member


Joined: 2017 Nov 07
Location: Wolfsburg
Online Status: Offline
Posts: 17
Post Options Post Options   Quote Svente Quote  Post ReplyReply Direct Link To This Post Topic: MaterialPreview Widget
    Posted: 2017 Nov 23 at 2:21am

User Information:

Cinema 4D Version:   18.057 
Platform:   Windows  ;   
Language(s):     C++  ;   

---------

Hello everybody,

currently I am trying to get used to the C4D MATPREVIEW GUI Control. I am trying to connect a LinkBox which accepts materials with a MaterialPreview. As soon as I link a material to the LinkBox I want the material preview control to show the rendered preview image. Additionally I want to update the image as soon as the referenced material changed.

Current attempt:
* listening to the EVMSG_MATERIALPREVIEW event (emitted when a material is changed)
* checking if the changed material is the material hold in the link box
* problem: how to update/connect the preview control

Could anyone give me some hints or some little explanation/examples how to use the MaterialPreview Control?

Greetings
Svente


    if (id == EVMSG_MATERIALPREVIEW)
    {
        //get material container
        BaseObject* pMaterialContainer = (BaseObject*)msg.GetVoid(BFM_CORE_PAR1);
        if (!pMaterialContainer)
            return GeDialog::CoreMessage(id, msg);

        //get the LinkBox from plugin dialog in order to get the linked material
        LinkBoxGui* pLinkBox = (LinkBoxGui*)this->FindCustomGui(MATERIALCHANGE_LINK_BROWSER_LINK, CUSTOMGUI_LINKBOX);
        if (!pLinkBox)
            return GeDialog::CoreMessage(id, msg);

        ////get the linked materials BaseObject
        BaseObject* pLinkedMat = (BaseObject*)pLinkBox->GetLink(GetActiveDocument());
        if (!pLinkedMat)
            return GeDialog::CoreMessage(id, msg);

        //check if linked material is the same as the one of the calling message and return otherwise
        if (pMaterialContainer != pLinkedMat)
            return GeDialog::CoreMessage(id, msg);

        MaterialPreviewCustomGui* pPreview = (MaterialPreviewCustomGui*)this->FindCustomGui(MATERIALCHANGE_MATPREV_MAT, CUSTOMGUI_MATPREVIEW);

        if (!pPreview)
            return GeDialog::CoreMessage(id, msg);

        //??? what to do?

    }

Back to Top
S_Bach View Drop Down
Forum Moderator
Forum Moderator
Avatar

Joined: 2011 Jun 27
Online Status: Offline
Posts: 1344
Post Options Post Options   Quote S_Bach Quote  Post ReplyReply Direct Link To This Post Posted: 2017 Nov 24 at 9:13am
Hello,

like all GUI gadgets the MaterialPreviewCustomGui displays data of a given data type. The MaterialPreviewCustomGui displays MaterialPreviewData data. Such data can be created using a GeData object:


_matData = GeData(CUSTOMDATATYPE_MATPREVIEW, DEFAULTVALUE);
_previewData = (MaterialPreviewData*)_matData.GetCustomDataType(CUSTOMDATATYPE_MATPREVIEW);


The data is then set to the GUI gadget:


_previewData->Init(MatPrevDialog::RenderPreviewImage, nullptr, 450000100, dirtyState);
_matPreview->SetData(_matData);


As you can see, the Init() function requires a callback to a static function. This static function will receive messages from the MaterialPreviewCustomGui (see MATPREVIEW). This way is is possible to define the behaviour and content of the gadget:



static Bool RenderPreviewImage(Int32 lMessage, void* pData, void* pUserData)
{
    switch (lMessage)
    {
        case MATPREVIEW_GET_OBJECT_INFO:
        {
            MatPreviewObjectInfo* mpoi = (MatPreviewObjectInfo*)pData;
            mpoi->bHandlePreview = true;
            mpoi->bNoStandardScene = true;
            mpoi->lFlags = MATPREVIEW_FLAG_HIDE_ROTATION | MATPREVIEW_FLAG_HIDE_SCENES | MATPREVIEW_FLAG_HIDE_SCENE_SETTINGS | MATPREVIEW_FLAG_HIDE_SIZE | MATPREVIEW_FLAG_HIDE_ANIMATE;

            break;
        }

        case MATPREVIEW_GENERATE_IMAGE:
        {
            MatPreviewGenerateImage* mpgi = (MatPreviewGenerateImage*)pData;
            BaseBitmap* pBmp = mpgi->pDest;
            const Vector color = g_material->GetAverageColor();
            pBmp->Clear(Int(color.x * 255), Int(color.y * 255), Int(color.z * 255));
            mpgi->lResult = RENDERRESULT::RENDERRESULT_OK;

            break;
        }
        case MATPREVIEW_PREPARE_SCENE:
        {
            MatPreviewPrepareScene* mpps = (MatPreviewPrepareScene*)pData;
            mpps->bScenePrepared = true;
        }
        break;
    }
    return true;
}


You will find discussions on these messages in various threads like:


You could use the existing preview scene or render your own scene/image to display the material.

A few other notes on your code:

  • EVMSG_MATERIALPREVIEW is a private message. If you want to catch changes in the scene (including changes to the materials) you have to catch EVMSG_CHANGE, see Core Messages).
  • It seems that you want to access materials from msg.GetVoid() and pLinkBox->GetLink(). But instead you are using BaseObject pointers. The class for generic materials is BaseMaterial (see BaseMaterial Manual), the class for the C4D standard material is Material (see Material Manual).

best wishes,
Sebastian

Edited by S_Bach - 2017 Nov 24 at 9:24am
SDK Support Engineer
Back to Top
Svente View Drop Down
Member
Member


Joined: 2017 Nov 07
Location: Wolfsburg
Online Status: Offline
Posts: 17
Post Options Post Options   Quote Svente Quote  Post ReplyReply Direct Link To This Post Posted: 2017 Dec 01 at 6:01am
Hello,

first I want to thank you for your help.
You gave as a bunch of homework... But with these information we were able to reach a certain point, at which the MaterialPreviewCustomGui works as expected.

The biggest problem was the implementation of the RenderPreviewImage method (and it's not implemented yet) because we use the MaterialPreview gadget in a dialog plugin. Therefore we weren't able to provide the needed data.

In the end their is one question left: is it possible to get the stored data from the standard material preview of cinema itself? For shader plugins it seems to be no problem (because of the context?) but can dialog plugins "address" the standard preview too?

Kind regards,
Svente
Back to Top
S_Bach View Drop Down
Forum Moderator
Forum Moderator
Avatar

Joined: 2011 Jun 27
Online Status: Offline
Posts: 1344
Post Options Post Options   Quote S_Bach Quote  Post ReplyReply Direct Link To This Post Posted: 2017 Dec 01 at 9:07am
Hello,

what exactly do you mean with "the stored data"?

You could access the preview BaseBitmap image with BaseMaterial::GetPreview(), see BaseMaterial Manual.

best wishes,
Sebastian
SDK Support Engineer
Back to Top
Svente View Drop Down
Member
Member


Joined: 2017 Nov 07
Location: Wolfsburg
Online Status: Offline
Posts: 17
Post Options Post Options   Quote Svente Quote  Post ReplyReply Direct Link To This Post Posted: 2017 Dec 04 at 5:03am
Hello,

for me it seemed, that BaseMaterial::GetPreview() is delivering not the original BaseBitmap of the shown MatPreview. Instead I think it delivers the preview of the material shown in the "material browser". Therefore the resolution is smaller.

Recalculating the BaseBitmap with ScaleIt is one possible way, but I guess it needs extra time and I don't know if the quality will match the MatPreview.

With "stored data" I meant, if there's a way to clone all settings of the original MatPreview to a custom made one?

Kind regards,
Svente
Back to Top
S_Bach View Drop Down
Forum Moderator
Forum Moderator
Avatar

Joined: 2011 Jun 27
Online Status: Offline
Posts: 1344
Post Options Post Options   Quote S_Bach Quote  Post ReplyReply Direct Link To This Post Posted: 2017 Dec 04 at 8:59am
Hello,

as said above, the GUI displays the data of a data type (MaterialPreviewData). This data type is stored in a parameter of the material. The parameter ID is MATERIAL_PREVIEW. So you could read this parameter from the material to get that data.

best wishes,
Sebastian
SDK Support Engineer
Back to Top
 Post Reply Post Reply

Forum Jump Forum Permissions View Drop Down

Bulletin Board Software by Web Wiz Forums® version 9.61 [Free Express Edition]
Copyright ©2001-2009 Web Wiz

This page was generated in 0.125 seconds.