C++ / Is there a way to draw debug text on the screen at a 3d coordinate?

A lot of other engines have simple functionality to do this built in (as it is extremely useful for debugging), but I haven’t been able to find an easy way to do it in UE4.

All I really want to do is draw the index of my route data’s nodes at the node position in 3D when the route is selected in the editor. (in both edit and play mode)

I was using a trick posted in the following thread, and managed to create a component that can draw debug primitives while in edit mode.

However, the only arguments I have in this function are (const FSceneView* View, FPrimitiveDrawInterface* PDI). If I can get a Canvas, it looks like I can at least call DrawText, but trying the following was just making the editor crash somewhere deep in DrawText.

 			static const FName CanvasName(TEXT("CanvasObject"));
 			UCanvas* Canvas = (UCanvas*)StaticFindObjectFast(UCanvas::StaticClass(), GetTransientPackage(), CanvasName);

			if (Canvas)
			{
				Canvas->SetDrawColor(255, 255, 255);
				UFont* RenderFont = GEngine->GetSmallFont();
				const FVector ScreenLocation = Canvas->Project(pos);
				Canvas->DrawText(RenderFont, FString::Printf(TEXT("%d"), i), ScreenLocation.X, ScreenLocation.Y);
			}

I also tried (experimentally) creating a canvas if it doesn’t exist like certain parts of the engine are doing, but it crashed in the same place.

Is there a correct way to get the current canvas somehow, or a better way to draw debug text on the screen?

Also, if any Epic devs are reading this: Please implement easy debug primitive and 2d/3d text printing functions that can be called from anywhere. A huge number of people would benefit from this.

1 Like

I took a look at the code, when I came across the same problem. The way to do it is to override the
virtual void DisplayDebug(UCanvas Canvas, const FDebugDisplayInfo& DebugDisplay, float& YL, float& YPos);* in you pawn or actor code.

Hope that helped!

Also I am not sure if that really draws a 3D text. So I am at a loss as well :frowning:

You’re looking for DrawDebugString. You can either give it a world position or you can give it an actor reference and the position will instead be used as an offset from that actor. The offset is not affected by the rotation of the actor.

I was actually referring to a way to do this from C++, sorry my question was unclear.

However, when I tried copying the C++ code the blueprint version of DrawDebugString was using, it functioned perfectly! Problem solved. Thanks!

Sample code:

#if !UE_BUILD_SHIPPING
   	FVector drawPos(0.0f);
   	FColor drawColor = FLinearColor(1.0f, 1.0f, 1.0f, 1.0f).ToFColor(true);
   	float drawDuration = 0.0f;
   	bool drawShadow = true;
   	DrawDebugString(GEngine->GetWorldFromContextObject(this), drawPos, *FString::Printf(TEXT("%s[%d]"), TEXT("test"), 12345), NULL, drawColor, drawDuration, drawShadow);
#endif //!UE_BUILD_SHIPPING
1 Like

FAnimNode_SkeletalControlBase

Inside AnimNode how to visualize it?