Hit a box and its HP drops. But the box's appearance does not change, so the hit is hard to read. So let's make an attacked box flash red for a moment. That is a hit flash , telling you "that landed" without reading numbers.
Place two identical blue boxes and only the attacked one should change. That is what a Dynamic Material Instance is for. We make each box's color adjustable and return the red to normal in 0.2 seconds.
What You'll Learn
- How boxes sharing a material can still change one at a time
- Creating a parameter controlling the strength of the red
- Creating the MID once, storing it in a variable, and reusing it
- Connecting a Timeline to existing damage logic
The hands-on starts from the BP_Damageable built in the health and damage article. Work from a single-player state where E reduces the Cube's HP with invincibility and destruction at 0 HP working. If material editors are new to you, review Material Basics first.
How to change only the box you hit
A Material is the asset behind appearance, built from nodes describing "how colors mix" and "how rough the surface is". A Material Instance takes that Material as a parent with changed color and numeric settings.
The regular Material Instance created in the Content Browser is formally a Material Instance Constant (MIC) . It suits saving color variants, such as one for red boxes and one for blue, configured in its editor.
The Material Instance Dynamic (MID) we use is created in Blueprint and lets you rewrite parameters during play. "Dynamic Material Instance" refers to the same thing. You can create it from a Material directly or from a configured MIC.

A MID does not copy the parent's nodes into a separate graph. Thinking of it as sharing the color-mixing setup with the parent while each holds its own mixing ratio captures how we use it.
Assign separate MIDs to box A and box B, for instance. Changing A's "redness" to 1 leaves B's at 0. Conversely, assigning the same MID to both boxes changes both colors when you change that MID's value.

What we need is "a MID per box" and "passing a value to the hit box's MID". First let's build a parent material that can receive that value.
Build a material with adjustable redness
A parameter is a named value you can adjust from outside. We prepare a number called FlashAmount so 0 is the original blue, 1 is red, and values between blend the two.

Create a Material in the Content Browser, name it M_Flashable , and open it. Leave "Material Domain" as Surface , "Blend Mode" as Opaque , and "Shading Model" as Default Lit . Create these nodes.
| What to create | Name and value | Role |
|---|---|---|
| Vector Parameter | OriginalColor : R=0.1, G=0.4, B=1, A=1 | The normal blue |
| Constant3Vector | R=1, G=0, B=0 | The red on a hit |
| Scalar Parameter | FlashAmount : Default Value 0 | How much red to blend |
| LinearInterpolate (Lerp) | Wired as in the diagram below | Blends two colors by that ratio |
A Scalar is one number and a Vector groups several. Here we use a Vector Parameter as an R, G, B, A color. You can add them by searching node names, or convert existing Constant and Constant3Vector nodes with right-click "Convert to Parameter".

Connect OriginalColor 's RGB to Lerp's A , the red to B , and FlashAmount to Alpha , then pass Lerp's output to the Material's Base Color . Alpha is "how much of B to blend" . It is not changing transparency here.
Set the Material's Metallic to 0 and Roughness to 0.7. Temporarily change FlashAmount's Default Value to 1 and confirm the preview turns red. After checking, set it back to 0, press "Apply", and save . The color-changing mechanism is done.
This makes the surface color turn red. Glowing in the dark needs Emissive Color , but let's confirm the color change in a lit area first.
Create a per-box MID and hold it in a variable
Open BP_Damageable and select DamageMesh in "Components". Assign M_Flashable to "Details → Materials → Element 0".
That Element 0 is a material slot number. A slot is where a material is assigned on a part, numbered from 0. Our standard Cube uses 0. Other meshes split into body and equipment, so check the number for the part you want to change.

In the event graph, add logic after the existing Event BeginPlay → Set CurrentHealth . Keep the initialization restoring HP to its maximum.
- Drag
DamageMeshfrom Components into the graph. That node specifies which mesh changes color. - Drag from the blue output and search for
Create Dynamic Material Instance. Use the one showingTarget is Primitive Component. - Set
Element Indexto0andSource MaterialtoM_Flashable.Optional Namecan stay None. - Right-click
Return Value, choose "Promote to Variable", and name itDynMat. Its type becomes a Material Instance Dynamic Object Reference . - Wire white exec as
Set CurrentHealth → Create Dynamic Material Instance → Set DynMat.

That Create node not only builds the MID but assigns it to DamageMesh's slot 0 . There is no need to follow it with Set Material. If the search shows a different Create node taking a Parent , drag from DamageMesh as above and pick again.
Return Value is the MID you just created. The reference stored in DynMat specifies "which MID to operate on later". Assigning it to a variable does not create additional MIDs.
Place two boxes and each one's BeginPlay creates a MID stored in its own DynMat. From then on, we change values through that variable.
Separate creating from changing color
We call Create once, on BeginPlay. Each hit only needs to rewrite the prepared MID's value. We add no logic recreating it mid-flash.

Set Scalar Parameter Value changes numbers and Set Vector Parameter Value changes colors. We use the former to move DynMat's FlashAmount .
Return the redness to 0 with a Timeline
Setting FlashAmount to 1 turns it red, but without returning the value it stays red. So we use a Timeline , the node deciding "what value at what second" and producing the values in between.
We go from 1 at 0 seconds to 0 at 0.2 seconds . The red thins gradually and returns to the original blue.

- Right-click in
BP_Damageable's event graph and createFlashTimelinewith "Add Timeline". - Double-click to open it, add a Float track, and name it
Flash. - Right-click on the graph to add two keys. Select each and match Time and Value to the table below.
- Select both keys, right-click, and set interpolation to "Linear", which decreases at a constant rate along a straight line.
- Set "Length" to
0.2with "Loop" and "AutoPlay" off. Compile and return to the event graph.
| Key | Time (seconds) | Value |
|---|---|---|
| Start | 0 | 1 |
| End | 0.2 | 0 |
The track name Flash is the name of the number the Timeline outputs and FlashAmount is the parameter name the material receives . They need not match. The next connections pass the former into the latter.
For Timeline editing in detail, see the article on changing values with a Timeline.
Connect it to the damage logic
From here we use the FlashTimeline you created. First build the connection writing the redness each frame, then wire the hit entry point.
Pass the Timeline's value to the MID
Place a Get of DynMat in the graph and add Set Scalar Parameter Value from its blue output. Use the node showing Target is Material Instance Dynamic . Do not use the same-named node taking a Collection .

| Connection / setting | Contents |
|---|---|
FlashTimeline's Update | To Set Scalar Parameter Value's white exec input |
| Get DynMat's blue output | To Target |
Parameter Name | Enter FlashAmount |
FlashTimeline's green Flash output | To Value |
The white Update wire says "run this now" and the green Flash wire passes "the current redness". Both are needed. The logic repeats during playback, and writing 0 at the end returns it to blue.
Play it when damage lands and the box survives
In the prerequisite article, after Event AnyDamage it checks invincibility and reduces HP only when damage can be taken. Then it destroys at 0 HP or sets a timer clearing invincibility when alive.
Connect the white output of the Set Timer by Event on the survival side to FlashTimeline's Play from Start . The diagram shows only that junction. The timer's Event and Time connections and the HP reduction stay as they are in the prerequisite article.

Set Timer by Event places "a reservation to clear invincibility later". Its white output does not wait for the invincibility to end. So the flash starts immediately on the hit.
Play from Start plays the Timeline from the beginning. Regular Play continues from the current position, so it would not return to the start when another hit lands mid-flash. Since we want the redness reapplied each time, we use Play from Start.
While invincible, execution never reaches this path, so neither additional damage nor a flash occurs. At 0 HP the box is destroyed on a different path, disappearing without flashing. To also spawn a destruction effect where it vanished, go to the Niagara article.
Place two and confirm the behavior
Compile, save, and Play. Press E in front of a box and watch the HP display and the color change.

| What to try | Expected result |
|---|---|
| Attack once | HP goes 100 → 80 and the box turns red, returning to blue in about 0.2 s |
| Press again within the 1-second invincibility | HP does not drop and no extra flash occurs |
| Attack after more than a second | The next damage lands and it turns red again |
| Place two and hit only one | Only the hit box changes color |
| Land five effective hits | HP reaches 0 and the box disappears |
Both start blue and only the attacked one turning red is success . Even with the same color-mixing setup, each MID holds its own FlashAmount.
If the change is too fast to follow, set the end key's Time and Length both to 0.8 and try again. The return from red to blue becomes easier to watch. Set both back to 0.2 afterwards.
When it does not work, review by symptom.
| Symptom | Where to check |
|---|---|
| It is red from the start | Whether you set the parent's FlashAmount Default Value back to 0 and saved |
| HP drops but the color does not change | Whether the survival-side Timer output reaches Play from Start, whether the Set's Target is DynMat and Parameter Name is FlashAmount |
| An error says DynMat is None | Whether BeginPlay ran Create and Set DynMat, whether Target is DamageMesh with an existing slot number |
| It stays red | Whether the end key's Value is 0, whether both Update and Flash are connected, whether Loop is off |
| Both boxes change color | Whether each box got its own MID, and whether the attack logic actually damages both |
Bonus: Good to Know Up Front
- Use a MIC to save color variants and a MID to adjust individually during play : changing redness like this fits a MID. That said, Materials and MICs can animate using nodes like Time. It does not mean "nothing but a MID can move visually".
- Not every parameter can be moved : colors, numbers, and textures can be changed via MID, but Static Switch is not a parameter for switching at runtime. Our FlashAmount is a Scalar, so it can change continuously.
- With body and equipment on separate slots, prepare one for each : the same thinking applies to Skeletal Meshes. To change a whole character, create and hold a MID per needed slot and pass values to each.
- World-wide changes have other options : to change wetness across many materials with the rain, a Material Parameter Collection can pass a shared value. Either way, how that value affects appearance is built into the parent material.
- Multiplayer sync is a separate concern : Event AnyDamage runs server-side and MID values are not automatically synced to each player. Extending this example means adding logic that plays the effect on each client too.
Summary
A hit flash is built by preparing "how much red to blend" in a parent material and passing that value to a per-box MID. Create the MID on BeginPlay, hold it in DynMat, and when damage lands, return it from 1 to 0 with a Timeline. With that split, you never recreate anything just to adjust a color.
Start by confirming that with two boxes, only one changes color. The same mechanism extends to coloring only a selected building or increasing an enemy's redness as its HP falls.
Reference: How Material Instances work, Primitive Component MID creation API, MID parameter API, Timeline playback nodes