6.7 KiB
Raw Blame History

参考文章

c++部分

添加ShaderModel

  • EngineTypes.h 在EMaterialShadingModel中添加ShaderModel枚举

添加材质编辑器引脚

  • SceneTypes.h 在EMaterialProperty中添加2个引脚属性名称枚举。
  • Material.h 在UMaterial类中添加FScalarMaterialInput类型变量CustomData2与CustomData3。

MaterialExpressions.cpp

  • 给MakeMaterialAttributes节点增加对应引脚

    • 添加CustomData2与CustomData3声明。位于MaterialExpressionMakeMaterialAttributes.h
    • 修改UMaterialExpressionMakeMaterialAttributes::Compile()增加CustomData2与CustomData3的对应列。
  • 给BreakMaterialAttributes节点增加对应引脚

    • 修改UMaterialExpressionBreakMaterialAttributes::UMaterialExpressionBreakMaterialAttributes()增加CustomData2与CustomData3的对应列。
    • 修改UMaterialExpressionBreakMaterialAttributes::Serialize(),增加两列Outputs[OutputIndex].SetMask(1, 1, 0, 0, 0); ++OutputIndex;
  • 修改BuildPropertyToIOIndexMap()增加CustomData2与CustomData3的对应列并且将最后一行的index改成合适的数值。

  • 修改断言条件static_assert(MP_MAX == 32=>static_assert(MP_MAX == 34

MaterialShared.cpp

  • 修改FMaterialAttributeDefinitionMap::InitializeAttributeMap(),给CustomData2与CustomData3添加对应码只需与之前的不重复即可。
  • 修改FMaterialAttributeDefinitionMap::GetAttributeOverrideForMaterial(),修改新添加的ShaderModel的引脚在材质编辑器中的显示名称。

MaterialShader.cpp

  • 修改GetShadingModelString()给新增加的ShaderModel添加返回字符串。
  • 修改UpdateMaterialShaderCompilingStats(),给性能统计添加新增加的ShaderModel条件判断,else if (ShadingModels.HasAnyShadingModel({ MSM_DefaultLit, MSM_Subsurface, MSM_PreintegratedSkin, MSM_ClearCoat, MSM_Cloth, MSM_SubsurfaceProfile, MSM_TwoSidedFoliage, MSM_SingleLayerWater, MSM_ThinTranslucent ,MSM_NPRShading}))

Material.cpp

  • 修改UMaterial::PostLoad(),给新增加的引脚添加对应的两行代码,来对材质属性进行重新排序,DoMaterialAttributeReorder(&CustomData2, UE4Ver, RenderObjVer);
  • 修改UMaterial::GetExpressionInputForProperty(),给新增加的引脚添加对应的两行代码。
  • 修改UMaterial::CompilePropertyEx(),给新增加的引脚添加对应的两行代码。编译材质属性。
  • 修改static bool IsPropertyActive_Internal()控制材质编辑器中引脚是否开启。给CustomData添加对应的代码。

HLSLMaterialTranslator.cpp

控制材质节点编译拼接成完整的ShaderCode。

  • 修改FHLSLMaterialTranslator::FHLSLMaterialTranslator()给SharedPixelProperties数组中引脚对应index赋值为true。
  • 修改FHLSLMaterialTranslator::GetMaterialEnvironment()给新增加的ShaderModel添加宏。
  • 修改FHLSLMaterialTranslator::GetMaterialShaderCode()。给新增加的引脚添加对应的两行LazyPrintf.PushParam(*GenerateFunctionCode(MP_CustomData1));。该函数会读取/Engine/Private/MaterialTemplate.ush并对替换字符格式化。
  • 修改FHLSLMaterialTranslator::Translate(),为新增加的两个引脚增加两行:
Chunk[MP_CustomData2]		= Material->CompilePropertyAndSetMaterialProperty(MP_CustomData2	,this);//NPR Shading
Chunk[MP_CustomData3]		= Material->CompilePropertyAndSetMaterialProperty(MP_CustomData3	,this);

MaterialGraph.cpp

材质界面代码。修改UMaterialGraph::RebuildGraph(),用来显示新添加的两个引脚:

MaterialInputs.Add( FMaterialInputInfo(FMaterialAttributeDefinitionMap::GetDisplayNameForMaterial(MP_CustomData2, Material), MP_CustomData2, FMaterialAttributeDefinitionMap::GetDisplayNameForMaterial(MP_CustomData2, Material)));
MaterialInputs.Add( FMaterialInputInfo(FMaterialAttributeDefinitionMap::GetDisplayNameForMaterial(MP_CustomData3, Material), MP_CustomData3, FMaterialAttributeDefinitionMap::GetDisplayNameForMaterial(MP_CustomData3, Material)));

解决添加引脚后

添加引脚后会出现PropertyConnectedBitmask cannot contain entire EMaterialProperty enumeration.的编译错误。需要将

uint32 PropertyConnectedBitmask;

=》

uint64 PropertyConnectedBitmask;

再将函数中的转换类型改成uint64即可。

ENGINE_API bool IsConnected(EMaterialProperty Property) { return ((PropertyConnectedBitmask >> (uint64)Property) & 0x1) != 0; }

ENGINE_API void SetConnectedProperty(EMaterialProperty Property, bool bIsConnected) 
{
    PropertyConnectedBitmask = bIsConnected ? PropertyConnectedBitmask | (1i64 << (uint64)Property) : PropertyConnectedBitmask & ~(1i64 << (uint64)Property);
}

Shader部分

MaterialTemplate.ush

给新增加的引脚增加对应的格式化代码:

half GetMaterialCustomData2(FMaterialPixelParameters Parameters)
{
%s;
}

half GetMaterialCustomData3(FMaterialPixelParameters Parameters)
{
%s;
}

ShadingCommon.ush

  • 新增加的ShaderModel添加ID宏#define SHADINGMODELID_NPRSHADING 12
  • 修改float3 GetShadingModelColor(uint ShadingModelID)给添加的ShaderModel设置一个显示颜色。

BasePassCommon.ush

  • 修改#define WRITES_CUSTOMDATA_TO_GBUFFER宏在最后的条件判断中添加新增加的ShaderModel。

DeferredShadingCommon.ush

  • 修改bool HasCustomGBufferData(int ShadingModelID)在条件判断中添加新增加的ShaderModel。

ShadingModelsMaterial.ush

  • 修改void SetGBufferForShadingModel()该函数用于设置输出的GBuffer给新增加的ShaderModel添加对应的代码段
#ifdef MATERIAL_SHADINGMODEL_NPRSHADING
else if(ShadingModel == SHADINGMODELID_NPRSHADING)
{
  GBuffer.CustomData.x=saturate(GetMaterialCustomData0(MaterialParameters));
  GBuffer.CustomData.y=saturate(GetMaterialCustomData1(MaterialParameters));
  GBuffer.CustomData.z=saturate(GetMaterialCustomData2(MaterialParameters));
  GBuffer.CustomData.w=saturate(GetMaterialCustomData3(MaterialParameters));
}
#endif

光照实现

  • ShadingModel.ushBxDF实现。
  • DeferredLightingCommon.ush延迟光照实现。

相关文件

  • UMaterialInterface、UMaterial、UMaterialInstance、FMaterial、FMaterialResource、FMateialRenderProxy、FMaterialInstanceResource、FDefaultMaterialInstance
  • MaterialShader.cpp
  • HLSLMaterialTranslator.cpp
  • MaterialHLSLEmitter:塞入ShaderModel宏
  • Material.cpp:开启引脚
  • MaterialAttributeDefinitionMap.cpp
  • ShaderMaterialDerivedHelpers.cpp
  • ShaderGenerationUtil.cpp
  • ShadingCommon.ush

Material编辑器相关代码

  • FMaterialInstanceBasePropertyOverrides
  • FMaterialInstanceParameterDetails

https://zhuanlan.zhihu.com/p/565776677 https://www.cnblogs.com/timlly/p/15109132.html