Use Debug.Log from C ++

When creating C ++ plugins in Unity, it is easier to use Debug.Log to quickly view the values โ€‹โ€‹of variables, but this function is available only from the C # side. This makes it very difficult to debug the C ++ plugin, since the Unity debugger does not support this. std::cout not an option since it does not appear in the editor.

I looked into the Unity C ++ API located in <UnityInstallationDirecory>\Editor\Data\PluginAPI , but found nothing about entering the API.

Any suggestions on how to display the editor from C ++ in the journal?

+7
c ++ c # unity3d
source share
1 answer

This can be done using the callback function. Send a pointer to a function from C # to C ++, save it in a temporary variable. Put Debug.Log inside this callback function and let it get the lines as a pointer ( IntPtr ).

When this function is called from C ++, convert IntPtr to string using Marshal.PtrToStringAnsi .

To do work with iOS, you must use the MonoPInvokeCallback attribute for the callback function.

C # (joins an empty GameObject):

 using AOT; using System; using System.Runtime.InteropServices; using UnityEngine; public class DebugCPP : MonoBehaviour { // Use this for initialization void OnEnable() { RegisterDebugCallback(OnDebugCallback); } //------------------------------------------------------------------------------------------------ [DllImport("DebugLogPlugin", CallingConvention = CallingConvention.Cdecl)] static extern void RegisterDebugCallback(debugCallback cb); //Create string param callback delegate delegate void debugCallback(IntPtr request, int color, int size); enum Color { red, green, blue, black, white, yellow, orange }; [MonoPInvokeCallback(typeof(debugCallback))] static void OnDebugCallback(IntPtr request, int color, int size) { //Ptr to string string debug_string = Marshal.PtrToStringAnsi(request, size); //Add Specified Color debug_string = String.Format("{0}{1}{2}{3}{4}", "<color=", ((Color)color).ToString(), ">", debug_string, "</color>" ); UnityEngine.Debug.Log(debug_string); } } 

C ++ ( DebugCPP.h ):

 #pragma once #include<stdio.h> #include <string> #include <stdio.h> #include <sstream> #define DLLExport __declspec(dllexport) extern "C" { //Create a callback delegate typedef void(*FuncCallBack)(const char* message, int color, int size); static FuncCallBack callbackInstance = nullptr; DLLExport void RegisterDebugCallback(FuncCallBack cb); } //Color Enum enum class Color { Red, Green, Blue, Black, White, Yellow, Orange }; class Debug { public: static void Log(const char* message, Color color = Color::Black); static void Log(const std::string message, Color color = Color::Black); static void Log(const int message, Color color = Color::Black); static void Log(const char message, Color color = Color::Black); static void Log(const float message, Color color = Color::Black); static void Log(const double message, Color color = Color::Black); static void Log(const bool message, Color color = Color::Black); private: static void send_log(const std::stringstream &ss, const Color &color); }; 

C ++ ( DebugCPP.cpp ):

 #include "DebugCPP.h" #include<stdio.h> #include <string> #include <stdio.h> #include <sstream> //------------------------------------------------------------------- void Debug::Log(const char* message, Color color) { if (callbackInstance != nullptr) callbackInstance(message, (int)color, (int)strlen(message)); } void Debug::Log(const std::string message, Color color) { const char* tmsg = message.c_str(); if (callbackInstance != nullptr) callbackInstance(tmsg, (int)color, (int)strlen(tmsg)); } void Debug::Log(const int message, Color color) { std::stringstream ss; ss << message; send_log(ss, color); } void Debug::Log(const char message, Color color) { std::stringstream ss; ss << message; send_log(ss, color); } void Debug::Log(const float message, Color color) { std::stringstream ss; ss << message; send_log(ss, color); } void Debug::Log(const double message, Color color) { std::stringstream ss; ss << message; send_log(ss, color); } void Debug::Log(const bool message, Color color) { std::stringstream ss; if (message) ss << "true"; else ss << "false"; send_log(ss, color); } void Debug::send_log(const std::stringstream &ss, const Color &color) { const std::string tmp = ss.str(); const char* tmsg = tmp.c_str(); if (callbackInstance != nullptr) callbackInstance(tmsg, (int)color, (int)strlen(tmsg)); } //------------------------------------------------------------------- //Create a callback delegate void RegisterDebugCallback(FuncCallBack cb) { callbackInstance = cb; } 

Use with C ++ :

 Debug::Log("Hellow Red", Color::Red); Debug::Log("Hellow Green", Color::Green); Debug::Log("Hellow Blue", Color::Blue); Debug::Log("Hellow Black", Color::Black); Debug::Log("Hellow White", Color::White); Debug::Log("Hellow Yellow", Color::Yellow); Debug::Log("Hellow Orange", Color::Orange); Debug::Log(true, Color::Black); Debug::Log(false, Color::Red); 

Exit the editor :

enter image description here

Now you can easily implement Debug.LogWarning and Debug.LogError .

+5
source share

All Articles