This article continues from where we left off in the Animated Blendshapes Tutorial. It covers how to setup wrinkle maps to enhance an existing animated blendshape scene in Maya and export to CRYENGINE. It does rely on the knowledge acquired in the Animated Blendshapes tutorial, which is a necessary precursor to this Wrinkle Maps tutorial.
Normally, wrinkle maps are added to a blendshape animation to add details to a human face. CRYENGINE currently supports 12 wrinkle masks and 1 wrinkle normal map that are controlled by 4 "blend_control_01" to "..04" joints (as helper objects to hold the animated data when a wrinkle area blends in and out).
CRYENGINE looks for the exported joints "blend_control_01" to "..04" and their ".translate" attribute and blends the wrinkle masks in and out.
Source Maya ASCII scenes with exported CRYENGINE files:
sdk_wrinkle_map_tutorial.zip ( 39mb )
(Do remember that you still need to have a modified "SkeletonList.xml" where you have added the skeleton CHR from this tutorial. Just in case you want to skip all these steps and want to open the character in CE Character Tool: SkeletonList.zip )
This is not an in-depth tutorial on how to sculpt your high resolution and in-game meshes! Normally, your high resolution wrinkle sculptures would be based on your neutral-posed sculpture in ZBrush, MudBox or 3d-Coat. After that, you have to bake the wrinkle normal maps. What is shown in this article are the results you need and the current way that CRYENGINE handles the base Normal Map (left image below) and the Wrinkle Normal Map (right image below):
Depending on your workflow, you must combine the different wrinkle normal maps onto the base normal map.
Before you blend normal map layers in Photoshop using the "Overlay" blend mode, you may want to search Google for how to correctly combine normal maps
This tutorial is designed to demonstrate the tech, hence some elements shown such as a perfect wrinkle normal map may not be as they would be in a game production environment
The mask texture being used to define the areas and ranges to be influenced by wrinkles is an 8-bit per channel, 32-bit *.tif file (this includes the alpha channel).
The different channels, red, green, blue and the alpha channel have been split into ranges so that more than 3 or 4 channels can be addressed independently and drive different areas on the face. Therefore, you have 12 wrinkle areas that you can control.
Presently this is "hardcoded", so if you use more than 3 Channels per map channel, then code changes will be necessary.
The different ranges are evenly distributed on the channels - from 0 to 255 with a gap of 20 in between the first and second ranges and a gap of 10 in between the second and third ranges, this prevents the channels from mixing into each other.
The 1st column depends on your preferences and how you as a Setup Artist want to drive the blend_control_01 - 04 helper joints. CRYENGINE just reads the translate values of blend_control_01 to 04 to drive the wrinkle mask. This is all that CRYENIGNE needs, however make sure that you map the driver attribute to the range of values [0.. 100], such as using a "multiplyDivide" node as in the former Animated Blendshape Tutorial:
Maya (blendShape) Node Driver Attribute | Maya Helper Joint Name | Joint Attribute |
---|---|---|
forehead | blend_control_01 | .translateX |
glabella (nose bridge area) | " | .translateY |
left cheek (smile) | " | .translateZ |
left lower eye squint | blend_control_02 | .translateX |
left crow's feet wrinkles | " | .translateY |
... (whatever face area) | " | .translateZ |
... | blend_control_03 | .translateX |
... | " | .translateY |
... | " | .translateZ |
... | blend_control_04 | .translateX |
... | " | .translateY |
... | " | .translateZ |
Maya (blendShape) Node Driver Attribute | RGB Colors as Mask |
---|---|
forehead | Red: 0-75 |
glabella | Red: 95-170 |
left cheek (smile) | Red: 180-255 |
left lower eye squint | Green: 0-75 |
left crow's feet wrinkles | Green: 95-170 |
... (whatever face area) | Green: 180-255 |
... | Blue: 0-75 |
... | Blue: 95-170 |
... | Blue: 180-255 |
... | Alpha: 0-75 |
... | Alpha: 95 - 170 |
... | Alpha: 180 - 255 |
Open Photoshop and paint the masks according to the color ranges in the setup table for Photoshop/Texture Artist. For the mask in this tutorial Red 255 has been used for the cheek mask, a Red 170 for the nose wrinkle mask and a Red 75 for the forehead mask.
Don't blur the wrinkle mask edges against an incorrect colored background!
But set the right background color displayed below when you paint the fade in/out mask edges:
Red 180-255: use an RGB (180,0,0) colored background layer
Red 95-170: use an RGB (95,0,0) colored background layer
Red 0-75: use an RGB (0,0,0) colored background layer
Repeat this for the Green, Blue & Alpha ranges and merge the color masks to their individual RGBA channels in Photoshop
Pair Red 1:
FG layer with Red Value -> 255
BG layer with Red Value -> 180
Pair Red 2:
FG layer with Red Value -> 170
BG layer with Red Value -> 95
Pair Red 3:
FG layer with Red Value -> 75
BG layer with Red Value -> 0
This is how the final result for the RED masked area looks like in Photoshop:
Next export the mask texture as a CryTif.
At the time of writing the Preset is not yet submitted. Replace your "rc.ini" (use search inside your <CryEngine_Root_Dir> ! ) with this one: rc.ini
Or add these lines to the bottom of your rc.ini:
[WrinkleMask_Linear] |
---|
The images below are a sample image (i.e. if you used all 12 masks). The right image only displays the RED channel:
In Maya you need to create four "blend_control_01" to "blend_control_04" joints. Parent them under the "root" joint of the export hierarchy as shown below:
If you are coming from the Animated Blendshape Tutorial, you must rename your two "cryExportNode" and the underlying "_group" accordingly. This avoids a collision with the name of the former skeleton *.CHR:
These joints have input connections into their respective ".translate" attributes. The attributes may be fed by any node output, normally the ".weights" attribute of a blendShape node or some "Set Driven Keys". The ".translate" attribute values are to be mapped from [0.. 1] to [0 to 100] and back to [0.. 1] as shown below. ("blend_control_02" to "blend_control_04") are left untouched because we only have 3 blendshapes plugged into "blend_control_01.translateX", ".translateY" and ".translateZ" ). Finally, you have to create the multiplyDivide nodes and the connections in the Node Editor as shown in the screenshot below:
If you want to set up all 12 wrinkle mask areas then you need to create the other three multiplyDivide nodes and plug them to "blend_control_02" ".tx" to ".tz" attribute.
The following steps (5-9) are not necessary for CRYENGINE wrinkle maps to work - it is for previewing your animation. Therefore, you may want to jump to step 10 of this section where the final wrinkle map scene is exported from Maya.
Before moving on to the shader elements in Maya, make sure that you are set to Maya's "Viewport 2.0". Load the "dx11shader" and "shaderFX" plugins, set the rendering engine to "DirectX 11" and the viewport renderer to "Viewport 2.0". (You must restart Maya after these steps!):
Open Maya's HyperShade. In order to help visualize the wrinkle map effect being animated a "Shaderfx" and "dx11Shader" material has been created for Maya 2015+. Search for the Shaderfx material and use the Attribute Editor to open the Shaderfx Window:
The Shaderfx material only has 3 wrinkle masks. These are extracted from the mask layers that were created in Photoshop earlier, however you can duplicate the "Texture Map", "Float", "Multiply" and "Add" nodes and add more masks and reconnect them to the node graph yourself:
Some notes regarding the ShaderFX wrinkle shader:
Scrub the Maya timeline to see how the wrinkle map effect blends in and out. The screenshots below are samples from the provided Maya scene:
blendshape OFF diffuse map ON normal map ON wrinkle map OFF | blendshape ON diffuse map ON normal map ON wrinkle map ON |
---|
blendshape OFF diffuse map OFF normal map ON wrinkle map OFF | blendshape OFF diffuse map OFF normal map ON wrinkle map ON |
Now it's time to export the assets to CRYENGINE. Open the Export tool from crytek shelf. Export the two crytekExportNodes, the material and the animation in crytek shelf. The screenshot below (with the red marked areas) will help you to get things exported correctly, otherwise, just open the "*_end" Maya tutorial scene:
The following steps show you how to create a material for wrinkle maps in the CRYENGINE Material Editor and add an "AnimObject" in the Sandbox Editor.
Because the four "blend_control_01" to "..04" helper joints have been added, the skeleton *.CHR, *.SKIN and *.I_CAF files need to be re-exported. Also, check whether you need to re-export the material as well. Optionally, the "sdk_wrinkle_tutorial" material can be replaced with a new wrinkle material later or you can change the "head_a.mtl" to work as a wrinkle material and assign the head to that material - choose what you favor most.
Open CRYENGINE Sandbox Editor and go into the Character Tool and add a new skeleton to the SkeletonList. Don't forget to save the SkeletonList!
Take special care with your skeleton name and *.CHR file so that they differ from the names used in the Animated Blendshape Tutorial (if you coming from the former tutorial scene).
Create a new CDF and name it "sdk_wrinkle_tutorial.cdf"
Add the "*.CHR" to the skeleton box and add a "Skin Attachment" pointing to the "*.SKIN" file that you exported. "Don't forget to activate Software Skinning"!
Click on the shown *.CHR file to configure the "*.CHRPARAMS" file. Add and point to the directory containing the "default" animation that you have exported
Once the "default" animation shows up on the left pane of the Character Tool, create and save the new "*.ANIMSETTINGS" file. Skip and press "OK" in the error window (missing "Anim Events") when prompted
You may have to save all, exit and restart the Sandbox Editor and then re-open your new wrinkle tutorial *.CDF
Wrinkle Map effect is not yet supported in the Viewport of the Character Tool (CRYENIGINE 3.8.4). Hence, you will need to create a new demo level or use an existing demo level in the Sandbox Editor!:
You will need to place an "Anim Entity" into the scene. Drag and click the "AnimObject" from the "RollupBar" into the scene:
Replace the windsock.cga in "Model" with the "sdk_wrinkle_tutorial.cdf":
Inside the "AnimObject" properties, scroll down to "Rendering" and check the checkbox for "WrinkleMap". Also, check that "Animation" is set to "default" and the "Loop" checkbox is checked (green areas in the screenshot below). Finally, when you have exported the name of your animation as "default", then this will save you from typing in the right name:
Finally, you now have to create the wrinkle map material. Go to the Material Editor and set up the material you have exported for the character ("sdk_wrinkle.skin"). Some options will open up first, if you have already set the "Humanskin" shader and added the "Wrinkle Normal Map" and the "Wrinkle Mask Texture" in the two "Custom" slots of the "Texture Maps" section!:
You might want to tweak the "Specular" (map) settings and "Smoothness" if you want to augment the bumps.
This is not a tutorial to the "Humanskin" Shader. Please look for this very special shader in CRYENGINE docs!
In addition, you should add some light. Add a CRYENGINE "EnvironmentProbe" and change the "Time Of Day" to better visualize the wrinkle map effect, otherwise the character head mesh might be badly lit:
wrinkle maps ON | wrinkle maps OFF |
In this tutorial you have;
Combined your wrinkle normal maps (forehead wrinkle, eye squint wrinkle, etc.) into one wrinkle normal map
Painted your wrinkle masks (forehead area, left lower eye area, etc.) into a composed wrinkle mask texture map
Exported the wrinkle mask texture using a linear color space export preset
Created four "blend_control_01" to "..04" joints to control the wrinkles
Exported the animation to an *.I_CAF file to incorporate the "blend_control_01" to "..04" animations
Exported the *.SKIN file (to incorporate the "blend_control_01" to "..04" joints)
Exported the *.CHR file (to incorporate the "blend_control_01" to "..04" joints)
Setup a wrinkle map material in the "Humanskin" shader of CRYENGINE
Added an "AnimObject" entity in the Sandbox Editor where you activated the wrinkle map effect