Vis

Vis

#Overview

name: Vis

This variable is created as a Console Variable (cvar).

It is referenced in 9 C++ source files.

#Summary

#Usage in the C++ source code

The purpose of Vis is to represent the visibility term in microfacet-based specular reflection calculations, specifically within the context of physically-based rendering (PBR) in Unreal Engine 5.

Vis is primarily used in the rendering system, particularly in shading and material calculations. Based on the callsites, it appears to be utilized in various subsystems and plugins, including:

  1. The AxFImporter plugin for enterprise-level material import
  2. The FractureEditor plugin for visualizing proximity in fractured geometry
  3. The core rendering pipeline, especially in specular reflection calculations

The value of Vis is typically calculated within shading functions rather than being set as a global variable. It’s often computed using different visibility functions, such as Smith-GGX or Smith-Joint approximations, depending on the specific use case and material model.

Vis interacts with other variables in the specular reflection equation, such as:

Developers should be aware that:

  1. Vis is a critical component in achieving physically accurate specular reflections.
  2. Different material models may use different visibility functions to calculate Vis.
  3. The accuracy of Vis calculation can significantly impact the visual quality of specular highlights.

Best practices when using Vis include:

  1. Ensure that the chosen visibility function is appropriate for the material model being used.
  2. Optimize the Vis calculation for performance while maintaining visual quality.
  3. Be consistent in the use of Vis across different shaders and materials to maintain a cohesive look.
  4. When implementing custom shading models, validate the Vis calculation against reference implementations or real-world measurements.

#References in C++ code

#Callsites

This variable is referenced in the following C++ source code:

#Loc: <Workspace>/Engine/Plugins/Enterprise/AxFImporter/Source/AxFImporter/Private/AxFImporter.cpp:774

Scope (from outer to inner):

file
class        class FAxFFileImporter : public IAxFFileImporter
class        class FUeGgxBRDF
function     FVector SpecularGGX

Source code excerpt:

			// Generalized microfacet specular
			float D = D_GGX(a2, NoH) * Energy;
			float Vis = Vis_SmithJointApprox(a2, NoV, NoL);
			FVector F = F_Schlick(SpecularColor, VoH);

			return (D * Vis) * F;
		}

	};

	class FCarPaint2BRDF
	{

#Loc: <Workspace>/Engine/Plugins/Experimental/ChaosEditor/Source/FractureEditor/Private/FractureToolProximity.cpp:114

Scope (from outer to inner):

file
function     void UFractureToolProximity::UpdateVisualizations

Source code excerpt:

		// Save the geometry collection component for rendering
		int32 CollectionIdx = VisualizedCollections.Add(FractureContext.GetGeometryCollectionComponent());
		FCollectionVisInfo& Vis = ProximityVisualizations.Emplace_GetRef();
		Vis.CollectionIndex = CollectionIdx;

		// Get proximity graph node positions as bounding box centers for each piece of geometry
		Vis.GeoCenters.SetNum(Collection.NumElements(FGeometryCollection::GeometryGroup));
		TArray<FTransform> GlobalTransformArray;
		GeometryCollectionAlgo::GlobalMatrices(Collection.Transform, Collection.Parent, GlobalTransformArray);
		for (int32 GeoIdx = 0; GeoIdx < Collection.NumElements(FGeometryCollection::GeometryGroup); ++GeoIdx)
		{
			int32 TransformIdx = Collection.TransformIndex[GeoIdx];
			FVector BoxCenter = GlobalTransformArray[TransformIdx].TransformPosition(Collection.BoundingBox[GeoIdx].GetCenter());
			Vis.GeoCenters[GeoIdx] = BoxCenter;
		}

		// Collect relevant proximity graph edges to render
		auto AddEdgesForGeoIdx = [&Proximity, &Vis](int32 GeoIdx, bool bAddAll)
		{
			for (int32 GeoNbr : Proximity[GeoIdx])
			{
				if (bAddAll || GeoIdx < GeoNbr)
				{
					Vis.ProximityEdges.Add(FEdgeVisInfo{ GeoIdx, GeoNbr });
				}
			}
		};
		if (ProximitySettings->bOnlyShowForSelected)
		{
			TArray<int32> SelectedRigids;

#Loc: <Workspace>/Engine/Plugins/Experimental/ChaosEditor/Source/FractureEditor/Private/FractureToolProximity.cpp:170

Scope (from outer to inner):

file
function     void UFractureToolProximity::Render

Source code excerpt:

	if (ProximitySettings->bShowProximity)
	{
		for (const FCollectionVisInfo& Vis : ProximityVisualizations)
		{
			const FGeometryCollection& Collection = *VisualizedCollections[Vis.CollectionIndex]->GetRestCollection()->GetGeometryCollection();
			const TManagedArray<FVector3f>* ExplodedVectors = Collection.FindAttributeTyped<FVector3f>("ExplodedVector", FGeometryCollection::TransformGroup);
			auto GetExplodedOffset = [&ExplodedVectors, &Collection](int32 GeoIdx)
			{
				return ExplodedVectors ?
					(FVector)(*ExplodedVectors)[Collection.TransformIndex[GeoIdx]] :
					FVector::ZeroVector;
			};
			const FTransform WorldTransform = VisualizedCollections[Vis.CollectionIndex]->GetComponentTransform();
			for (const FEdgeVisInfo& Edge : Vis.ProximityEdges)
			{
				FVector P1 = WorldTransform.TransformPosition(Vis.GeoCenters[Edge.A] + GetExplodedOffset(Edge.A));
				FVector P2 = WorldTransform.TransformPosition(Vis.GeoCenters[Edge.B] + GetExplodedOffset(Edge.B));
				PDI->DrawLine(P1, P2, ProximitySettings->LineColor, SDPG_Foreground, ProximitySettings->LineThickness, 0.001f);
			}

			for (int32 CenterIndex = 0; CenterIndex < Vis.GeoCenters.Num(); CenterIndex++)
			{
				// Draw centers for geometry (clusters can have geometry but it is not visible and won't be connected in the proximity graph)
				if (Collection.SimulationType[Collection.TransformIndex[CenterIndex]] == FGeometryCollection::ESimulationTypes::FST_Rigid)
				{
					FVector P = WorldTransform.TransformPosition(Vis.GeoCenters[CenterIndex] + GetExplodedOffset(CenterIndex));
					PDI->DrawPoint(P, ProximitySettings->CenterColor, ProximitySettings->CenterSize, SDPG_Foreground);
				}
			}
		}
	}
}

#Loc: <Workspace>/Engine/Plugins/Runtime/CommonUI/Source/CommonUI/Private/CommonButtonBase.cpp:723

Scope (from outer to inner):

file
function     bool UCommonButtonBase::IsInteractionEnabled

Source code excerpt:

bool UCommonButtonBase::IsInteractionEnabled() const
{
	ESlateVisibility Vis = GetVisibility(); // hidden or collapsed should have 'bInteractionEnabled' set false, but sometimes they don't :(
	return GetIsEnabled() && bButtonEnabled && bInteractionEnabled && (Vis != ESlateVisibility::Collapsed) && (Vis != ESlateVisibility::Hidden);
}

bool UCommonButtonBase::IsHovered() const
{
	return RootButton.IsValid() && RootButton->IsHovered();
}

#Loc: <Workspace>/Engine/Source/Developer/Profiler/Private/Widgets/SEventGraph.cpp:3353

Scope (from outer to inner):

file
function     EVisibility SEventGraph::EventGraphViewMode_GetVisibility

Source code excerpt:

	if( ViewMode == EEventGraphViewModes::FlatInclusiveCoalesced || ViewMode == EEventGraphViewModes::FlatExclusiveCoalesced )
	{
		const EVisibility Vis = FProfilerManager::GetSettings().bShowCoalescedViewModesInEventGraph ? EVisibility::Visible : EVisibility::Collapsed;
		if (Vis == EVisibility::Collapsed && GetCurrentStateViewMode() == ViewMode)
		{
			// If view mode is not available event graph will switch to the hierarchical view mode.
			SEventGraph* MutableThis = const_cast< SEventGraph* >( this );
			MutableThis->EventGraphViewMode_OnCheckStateChanged( ECheckBoxState::Checked, EEventGraphViewModes::Hierarchical );
		}
		return Vis;
	}
	else
	{
		return EVisibility::Visible;
	}
}

#Loc: <Workspace>/Engine/Source/Editor/AnimationEditorWidgets/Private/SchematicGraphPanel/SSchematicGraphPanel.cpp:461

Scope (from outer to inner):

file
function     EVisibility SSchematicGraphNode::GetNodeVisibility

Source code excerpt:

	if(SchematicGraphPanel && SchematicGraphPanel->GetSchematicGraph())
	{
		ESchematicGraphVisibility::Type Vis = SchematicGraphPanel->GetSchematicGraph()->GetVisibilityForNode(GetGuid());
		if(Vis == ESchematicGraphVisibility::Hidden)
		{
			return EVisibility::Hidden;
		}
	}

	return EVisibility::Visible;

#Loc: <Workspace>/Engine/Source/Runtime/Core/Private/HAL/ConsoleManager.cpp:3353

Scope (from outer to inner):

file
function     void CreateConsoleVariables

Source code excerpt:

	// the following commands are common exec commands that should be added to auto completion (todo: read UnConsole list in ini, discover all exec commands)
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("VisualizeTexture"),	TEXT("To visualize internal textures"), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("Vis"),	TEXT("short version of visualizetexture"), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("VisRT"),	TEXT("GUI for visualizetexture"), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("HighResShot"),	TEXT("High resolution screenshots ResolutionX(int32)xResolutionY(int32) Or Magnification(float) [CaptureRegionX(int32) CaptureRegionY(int32) CaptureRegionWidth(int32) CaptureRegionHeight(int32) MaskEnabled(int32) DumpBufferVisualizationTargets(int32) CaptureHDR(int32)]\nExample: HighResShot 500x500 50 50 120 500 1 1 1"), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("DumpUnbuiltLightInteractions"),	TEXT("Logs all lights and primitives that have an unbuilt interaction."), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("Stat MapBuildData"),	TEXT(""), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("r.ResetViewState"), TEXT("Reset some state (e.g. TemporalAA index) to make rendering more deterministic (for automated screenshot verification)"), ECVF_Cheat);
	IConsoleManager::Get().RegisterConsoleCommand(TEXT("r.RHI.Name"),		TEXT("Show current RHI's name"), ECVF_Cheat);

#Loc: <Workspace>/Engine/Source/Runtime/Renderer/Private/Renderer.cpp:620

Scope (from outer to inner):

file
function     static bool RendererExec

Source code excerpt:

{
#if SUPPORTS_VISUALIZE_TEXTURE
	if (FParse::Command(&Cmd, TEXT("VisualizeTexture")) || FParse::Command(&Cmd, TEXT("Vis")))
	{
		VisualizeTextureExec(Cmd, Ar);
		return true;
	}
#endif //SUPPORTS_VISUALIZE_TEXTURE
#if !(UE_BUILD_SHIPPING || UE_BUILD_TEST)

#Loc: <Workspace>/Engine/Source/Runtime/Renderer/Private/SystemTextures.cpp:489

Scope (from outer to inner):

file
function     void FSystemTextures::InitializeFeatureLevelDependentTextures

Source code excerpt:

							float Vis_SmithV = NoL * (NoV * (1 - m) + m);
							float Vis_SmithL = NoV * (NoL * (1 - m) + m);
							float Vis = 0.5f / (Vis_SmithV + Vis_SmithL);

							float NoL_Vis_PDF = NoL * Vis * (4.0f * VoH / NoH);
							float Fc = 1.0f - VoH;
							Fc *= FMath::Square(Fc*Fc);
							A += NoL_Vis_PDF * (1.0f - Fc);
							B += NoL_Vis_PDF * Fc;
						}
					}