Saturday, June 3, 2023

New User Interface

A recent request suggested that it should be possible to animate an imported DAZ character with the DAZ Importer disabled. Thus the add-on should only be necessary to generate the figure, not to animate it. Apparently Rigify and other popular rigs does this; once the rig is generated the add-on itself is not needed. There is still a user interface, but it stored inside the rig and Rigify itself is not needed.

This could perhaps be done for the DAZ Importer as well, but I don't know how and it would be a major job for little gain. But the latest commit does something towards that end. The user interface is split into a setup and a runtime tab, labelled DAZ Setup and DAZ Runtime, respectively, and the tab not used can be hidden.

The DAZ Setup tab looks like this:

The Setup panel has been removed, and its subpanels have been moved to the top level. Moreover, the Visibility and Hair panels have been moved from the Advanced Setup panel. The reason is that I use both Visibility and Hair frequently. On the other hand, the tools that are left in the Advanced Setup panel are those that I personally rarely use.

The DAZ Runtime tab contains the panels that are used for animation, especially the Morphs and Posing panels. If our character is equipped with Simple IK the Layers and Simple IK panels are put in this panel as well.

Both the Setup and Runtime tabs are visible by default, but we can hide them in the add-on preferences. In that way we don't have to clutter the user interface with unused tabs.

If we disable the runtime tab, only the setup tab is visible. Use this setting when setting up a character.

Once all character have been set up, we can disable the setup tab and enable the runtime tab for animation.

Thursday, April 27, 2023

Version 1.7.0 Released

Finally, version 1.7.0 of the DAZ Importer and MHX Runtime system has been released. It can be downloaded from

The plugins have been tested with Blender 2.83 and Blender 3.5 under Windows 7 and Windows 10, but should work with intermediate versions as well. 

The most signicant new features in this release are:

  • Support for Genesis 9 characters. 
  • Support for Blender 3.5, in particular the new mixing nodes.

There are also some other improvements and many bugfixes.

The documentation has moved to the Bitbucket wiki. It is not quite up-to-date, but I didn't want to postpone the release further. Here are links to the wikis:

Saturday, April 22, 2023

Finger IK and Tongue IK

The MHX rig can generate IK controls for the fingers and the tongue, but those controls were very difficult to work with and next to useless. Moreover, they caused dependency loops if the character has morphs that affect the fingers and tongue. Recently Alessandro suggested a better way to implement IK for the tongue, using stretch-to constraints, and then I implemented the same mechanism for the fingers. This is not strictly speaking IK since no IK constraints are involved, but it allows the user to place the joints precisely, and we will still refer to it as finger IK and tongue IK.

To generate the IK joints, we enable the Finger IK and Tongue IK options when the MHX rig is generated.

The IK influence is governed by the Tongue IK and (left and right) Finger IK sliders in the Properties panel.

As with IK for the arms and legs, finger IK is primarily useful when the character interacts with some other object, and we need to place the finger joints precisely relative to that object. E.g., assume that we want to grab a ball. We could proceed as follows:

  1. Place the IK hand in position.
  2. Pose the long finger bones so they grab the ball.
  3. Snap the IK finger joints to the location of the finger bones.
  4. Tweak the joints so the fingers grab the ball perfectly.
  5. Optionally snap the FK finger bones, e.g. if we want to export a pose preset back to DAZ Studio.
First step: Move the hand into position.
Rotate the long finger bones so the fingers touch the ball.
Snap the left finger joints to the location of the finger bones.
The long finger bones are hidden and the finger joints are shown instead.
We now tweak the joints so the fingers touch the ball perfectly. Depending on your ambition, this may involve a lot of manual work.
We can now snap the finger bones to the location of the joints. This is not necessary if you only want to render the scene in Blender, but can be useful anyway.
Typically, the finger bones are not only rotated but also scaled.
Tongue IK works in a very similar fashion. Here we have posed Aiko's tongue using morphs.
Snap the tongue joints.
We can now pose the tongue with the joints. Note that the morphs are no longer necessary and can be cleared.
The snap fingers buttons are still present even if the MHX rig doesn't have finger IK, because they can also be used to move a pose from the long finger bones to the individual links. In the picture to the left above, we have posed the fingers with the long fingers. After snapping, the long fingers are cleared but the hand pose remains the same, because now the finger bones are rotated instead.
There are also buttons for snapping the spine and neck/head. Above they were posed with the back and neckhead bones, but after snapping the individual bones have rotations instead.

Thursday, April 6, 2023

DAZ HD Morphs and Xin's Addon

The morphs that you can import with DAZ Importer are only half the story. Many morphs also have high-definition (HD) information, which is stored in a dhdm (DAZ High Definition Morph, perhaps) file. The information in a dhdm file is encoded in an undocumented binary format and can not be read by the DAZ Importer. However, Xin has developed an add-on for importing dhdm files, which is colloquially know as Xin's Add-on. This post describes how I use Xin's add-on to generate normal map or displacement map textures, and then assign them to a character.

Installing Xin's Add-on

The source is available in the following repository: . There you can also find compilation details for the .dll under MinGW on windows x64, and documentation.

If you find this addon useful, consider supporting its development and maintenance here:

The latest version (the main branch) includes documentation in the form of a .pdf in “./blender_addon/documentation/daz_hd_morphs_documentation.pdf”. It includes several step by step examples.

For up-to-date information see further

Generating Textures

Once the HD morphs add-on has been enabled, a tab called HD Morphs appears. It consists of a number of panels. We must also import the mesh that we want to generate normal or displacement maps for.

First we enter the Main Settings.
  • Working directory: All textures will be saved in a subdirectory under this.
  • Unit scale: The scale factor connecting the DAZ scale to the Blender scale. Since DAZ uses centimeters internally, the default value 0.01 corresponds to meters.
  • Base mesh: A drop-down list where we choose the mesh.
If we want to generate normal maps, we enter the Normals/Displacements panel and choose Normals (multires) as the type. There are also other settings that let us specify the generated texture in detail.
In the From morph files panel, press the plus sign to add DAZ HD morph files.
We want to generate normal map files for the standard DAZ expressions, so we navigate to the directory where they are located. We are only interested in the files where the actual shapekeys (at base resolution) are stored, which are .dsf files that being with "eJCM". So we type "ejcm" in the search field and select all files.
After a while the textures have been generated in a subdirectory of the working directory.

Note that separate normal map textures have been generated for seven tiles, 1001 - 1007. In this case this is unnecessary, since only the first tile, which contains the face, is of interest. We can limit the number of generated files if we enable Select UV tiles and only select those tiles that we are interested in.

Import the textures into Blender

Once all textures have been generated, we want ot import them into the Blender materials. However, first need to we import the morphs at base resolution.

With the mesh or rig selected, import the expressions as usual.
Next we open the Advanced Setup > HDMesh panel. It contains three buttons for importing textures generated by Xin's add-on: Load Normal Maps, Load Scalar Disp Maps, and Load Vector Disp Maps.
Navigate to the directory where the normal map textures are located and select those that we want to import. The options are:

  • Use Drivers: Drive the strength of the normal maps with the morph strength.
  • Smart Tiles: Only add the textures to materials if other textures have the same tile suffix. E.g., the Torso material typically has other textures ending with "_1002", and therefore only normal maps endin in "_1002" will be added to the Torso material.
  • Compact Layout: Close the nodes used to connect the normal map textures, thus making the layout more readable.
  • Prune Node Tree: Remove unused nodes once the new textures have been added.
  • Add Maps To Materials: The affected materials.
In this case we know that the expression textures only affect the face, which is located on tile 1001. Hence we turn off Smart Tiles and set Tile = 1001. Moreover, we deselect all materials except the Face and Lips materials.

The textures are now imported. To the left of the Face-1 node tree we have new normal map textures that are stringed together with overlay nodes.

Note that the factors in the overlay nodes that connect the normal map textures are driven by the morph properties.

Here is the open face smile, without and with the normal map textures.
Xin's add-on can alternatively generate scalar and vector displacement maps. These are imported into Blender in a completely analogous fashion. Here is the options when we import scalar displacement maps.
Displacement maps are stringed together with add nodes (vector math nodes), and the result is directly connected to the material output displacement strength.

Sunday, April 2, 2023

Stripping Categories

We can acquire packages of morphs from the DAZ store. Sometimes the vendor prefers to put the package name in front of all morphs in the package, as in the example below.

Import these morphs into Blender with Import Custom Morphs.
The morphs appear in the Custom Morphs panel, under the category that we specified when importing the morphs. Unfortunately, we have to make the UI panel very wide to see which morph is which, since most of the available space is taken up by the package name.
There is a way to fix this so we can view only the interesting parts of the morph names. First, we need to choose the name of the category to be the same as the common string that starts the morph names. In this case we have already chosen the category to be "Venus Smile". Second, enable the global option Strip Category.
The beginning of the morph name is now hidden for every morph that begins with the category name, and it is much easier to see what each morph does.

Friday, March 24, 2023

Only Importing Properties

Meet Aivic. She is 70% Aiko and 30% Victoria, but those morphs were baked into the dbz file and are not available in Blender. So how do we make morphs that suit this particular character. It could be done with adjusters, but strength multipliers for the Aiko and Victoria morphs already exist in DAZ, so why not use them.

Here we have imported two expressions to Aivic, Afraid and Angry. But those expressions were made for the basic Genesis 8 Female, and character-specific corrections exist.
With the Import Custom Morphs tool, go to the Aiko folder and import the two eJCM files that contain the Aiko corrections to the Afraid and Angry morphs. Repeat this step to import the corresponding Victoria morphs.
When we now turn on the Angry morph, we see that we have a problem. The corrective shapekeys for both Aiko and Victoria are enabled at 100%, which is not what we want. They should be enabled at 70% and 30%, to match the character blend.
To access the character strength we must import the corresponding character morphs, like CTRLAiko8.dsf. However, we don't want to import the morphs themselves, because they are already baked into our character. We only want access to the properties that govern the character mix. To this end we enable the Only Properties option. We also enable Protect Morphs, which protect the properties from being accidentally disabled.

Now three sliders are added in the Custom Morphs panel. There are some things to notice here.

  1. There are no new shapekeys. Because Only Properties was enabled, neither shapekeys nor bone transforms were imported.
  2. The Aiko 8 slider is not activated (the checkbox to the right of the slider), which means that it is not included if we clear or set morphs, or set keys.
  3. The * Aiko 8 slider starts with an asterisk. This means that Aiko 8 is protected from accidental change. The All button at the top will activate all non-protected morphs but leave protected ones deactivated. There is a new Protected button which does activate protected morphs, but not unprotected ones.
Load the Victoria control morph as a protected morph in the same way, and then import the eJCM morphs for both Aiko and Victoria with the default settings, i.e. with Only Properties and Protect Morphs disabled.

We can now turn on the Angry morph, and set the Aiko and Victoria properties to match the character mix. The character-specific shapekeys now have the right strengths, i.e. 0.7 and 0.3, respectively.
Here is a comparison of the Angry morph for different settings.
There is another, simpler way to control the morph mix. Enable the global option Protect Multipliers. This makes any multiplier, i.e. a property that is multiplied with the morph strength, a protected morph that is displayed in user interface.

This time we only load the eJCM files for Aiko and Victoria, but skip the control files. The plugin finds that FHMAiko8 and FHMVictoria8 (FHM stands for Full Head Morph) are multipliers and therefore should be protected and displayed in the Custom Morphs panel. We can now set those sliders to match the character mix, and the shapekeysget the right values.
Finally a short notice on how protected morphs are implemented. The plugin considers a property to be protected if its description consists of three asterisks, so don't change the description of such properties.