• RuntimesUnreal
  • Change parameters via the Material Instance

Good afternoon.

An unusual request, if you have free time, please help.

As it is, I am very pleased with your program, it is great!

There is a character, he has clothes on, I want to make its destruction in stages, through torn holes.

But in order not to make a lot of states for all the clothes, I want to use the unreal material tools.

In the widget in the spine properties, there is a choice of additiveblend material, I copied it and made my own, added a noise generator to it and use it as a mask for torn clothes.

Everything works fine, I change the parameters and control everything, but I can't change the parameters from the game.

To do this, create a create material instance dynamic and apply it to spine.

You only have the get additive blend material function, but set does not.

I tried to write something in C++ via the gpt chat, but it seems the logic is more complicated and requires reinitialization of the material.

In SpineWidget.cpp

UPROPERTY(Category = Spine, EditAnywhere, BlueprintReadOnly)
UMaterialInterface *AdditiveBlendMaterial;

In SpineWidget.h

static ConstructorHelpers::FObjectFinder<UMaterialInterface> AdditiveMaterialRef(TEXT("/SpinePlugin/UI_SpineUnlitAdditiveMaterial"));
AdditiveBlendMaterial = AdditiveMaterialRef.Object;

I tried changing BlueprintReadOnly to BlueprintReadWrite, and created a material replacement function in C++, but there is no result.

I'd appreciate it if you could find the time to help.

Related Discussions
...

To change parameters via a material instance in Unreal Engine for a Spine character, you can create a dynamic material instance and apply it to your Spine component. Since the Spine plugin for Unreal Engine does not provide a direct method to set the additive blend material, you will need to handle this through Unreal's material system.

Here's a general approach you can follow:

  1. Create a Dynamic Material Instance: Use CreateDynamicMaterialInstance to create a dynamic material instance from your custom material. This allows you to modify material parameters at runtime.

  2. Apply the Dynamic Material Instance: Once you have the dynamic material instance, you can apply it to the Spine component. You may need to modify the Spine plugin's source code to expose a method for setting the material on the Spine component.

  3. Modify Material Parameters: With the dynamic material instance, you can change parameters such as the noise generator settings to control the appearance of torn clothes.

Here's a basic example in C++:

UMaterialInstanceDynamic* DynamicMaterial = UMaterialInstanceDynamic::Create(YourCustomMaterial, this);
YourSpineComponent->SetMaterial(0, DynamicMaterial);

Ensure that your Spine component has a method to set the material, or modify the plugin to add this functionality.

For more detailed guidance, you can refer to the Spine-UE4 documentation and Unreal Engine's documentation on dynamic material instances.

An attempt to replace the material via the gpt chat.

#include "SpineUtilsLibrary.h"
#include "Materials/MaterialInstanceDynamic.h"
#include "SpineWidget.h"

void USpineUtilsLibrary::SetAdditiveBlendMaterialInstance(USpineWidget* Spine, UMaterialInstanceDynamic* MaterialInstanceDynamic) {
if (Spine && MaterialInstanceDynamic) {
Spine->AdditiveBlendMaterial = MaterialInstanceDynamic;

	Spine->SynchronizeProperties();
}

}

#pragma once

#include "CoreMinimal.h"
#include "Kismet/BlueprintFunctionLibrary.h"
#include "SpineWidget.h"
#include "SpineUtilsLibrary.generated.h"

UCLASS()
class PROJECT_API USpineUtilsLibrary : public UBlueprintFunctionLibrary {
GENERATED_BODY()

public:
UFUNCTION(BlueprintCallable, Category = "Spine")
static void SetAdditiveBlendMaterialInstance(USpineWidget* Spine, UMaterialInstanceDynamic* MaterialInstanceDynamic);
};

Another method didn't work.

To get a dynamic material instance that has already been created and change its parameters.

According to the logs, everything changes correctly and the material can be obtained, but visually nothing changes on the clothes.

SpineWidget.cpp

UMaterialInstanceDynamic* USpineWidget::GetAdditiveDynamicMaterial() {
if (atlasAdditiveBlendMaterials.Num() > 0) {
return atlasAdditiveBlendMaterials[0];
}
return nullptr;
}

void USpineWidget::RefreshMaterials() {
SynchronizeProperties();
}

SpineWidget.h
UFUNCTION(BlueprintCallable, Category = "Components|Spine|Materials")
UMaterialInstanceDynamic* GetAdditiveDynamicMaterial();

UFUNCTION(BlueprintCallable, Category = "Spine")
void RefreshMaterials();

IT'S WORKING)

I read a thread about the same task in blueprints and did the same for widgets.

SpineWidget.cpp

void USpineWidget::GetAdditiveDynamicMaterials(TArray<UMaterialInstanceDynamic*>& OutMaterials) const {
OutMaterials = atlasAdditiveBlendMaterials;
}

SpineWidget.h

UPROPERTY(Category = Spine, EditAnywhere, BlueprintReadWrite)
UMaterialInterface *AdditiveBlendMaterial;

UFUNCTION(BlueprintCallable, Category = "Components|Spine|Material")
void GetAdditiveDynamicMaterials(TArray<UMaterialInstanceDynamic*>& OutMaterials) const;