在C#中从本地C ++继承,并将继承类向后传递到c ++ [英] Inheriting from native C++ in C# and passing the inherit class backward to c++

查看:148
本文介绍了在C#中从本地C ++继承,并将继承类向后传递到c ++的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个引擎在本机C + + DLL,我需要使用它在一个C#项目。



我是一个全新的做,已经上了几个小时,现在我知道或多或少如何实现它。我知道我必须写一个C#或C ++ / CLI包装类。



但我还没有找到如何包装dll C ++类的一些方面。
引擎具有类别CEntity与这个重要的部分:

  class CEntity 
{
void SendMsg(CEntity * receiver);
virtual void ReceiveMsg(MSG msg);
}

这样工作:
来自CEntity的继承类覆盖



我需要的是在C#中使用这个功能:继承从CEntity,覆盖ReceiveMsg在一个方式,C ++代码可以调用它,并能够发送消息到其他C#继承CEntity对象抛出SendMsg C ++实现。
或者换句话说,我需要C ++非托管代码调用C#托管代码。 C ++代码调用ReceiveMessage(),我需要覆盖或重定向该调用到C#代码。



是不是改变dll的方法?我不能直接访问C ++代码,但如果需要我可以要求修改dll。

解决方案

div>

这很棘手:



ILogger.h

  #pragma once 

使用命名空间System;

命名空间AlPDFGenV4
{
public interface class ILogger
{
public:
virtual void Log(String ^ ltxt)= 0;
};
}

然后LRLog.h

  #pragma once 

#includeCMSysString.h
#includeCLRILogger.h
#include< vcclr .h>

使用命名空间System;

class CNtvLogger;

命名空间AlPDFGenV4
{
public ref class Logger
{
public:
Logger(void);
virtual〜Logger(void);

ILogger ^ extlogger;
CNtvLogger * ntv;

void Log(String ^ txt)
{
extlogger-> Log(txt);
}
};

}

和LRLog.cpp

  #includeStdAfx.h
#includeLRLog.h

使用命名空间AlPDFGenV4;

Logger :: Logger(void)
{
ntv = new CNtvLogger;
ntv-> clrlogger = this;
}

Logger ::〜Logger(void)
{
delete ntv;
}

class CNtvLogger:CMSysLogger
{
public:
gcroot< AlPDFGenV4 :: Logger ^> clrlogger;

protected:
void _InternalLog(LPCTSTR txt)
{
String ^ str = gcnew String(txt);

clrlogger-> Log(str);
}

public:
bool Init(void * obj)
{
return true;
}

};

希望这有帮助。



例如,类Logger是一个桥梁,允许保持本地日志记录器(由本地代码使用)和接口ILogger(由托管代码使用的传递接收日志输出的类)之间的链接。



在你的C ++ / CLI中你需要一个这样的类,不需要用这种方法改变dll。


I've an engine in a native C++ dll and I need to use it in a C# project.

I'm totally new on doing that, but I've been googling for hours and now I know more or less how to achieve it. I know I've to write a C# or C++/CLI wrapper class.

But I haven't found how to wrap some aspects of the dll C++ class. The engine has class CEntity whith this important part:

class CEntity  
{  
    void SendMsg(CEntity *receiver);  
    virtual void ReceiveMsg(MSG msg);
}

That works as follows: A inherit class from CEntity overrides the ReceiveMsg function implementing what it whants, and Inheriting objects comunicate sending messages.

What I need is to use this functionality in C#: "Inheriting" from CEntity, overriding ReceiveMsg on a way that the C++ code can call it, and been able to send messages to other C# "Inheriting" CEntity objets throw the SendMsg C++ implementation. Or in other words I need that the C++ unmanaged code calls a C# managed code. The C++ code is calling ReceiveMessage() and I need to "override" it or redirect that call into C# code.

Is a way of doing that whithout changing the dll? I can't acces directly the C++ code, but if needed I can ask for dll modifications. If not, what'll be the minimum dll modifications?

Thanks a lot

解决方案

It is tricky:

ILogger.h

#pragma once

using namespace System;

namespace AlPDFGenV4 
{
    public interface class ILogger 
    {
    public:
        virtual void Log( String^ ltxt ) = 0;
    };
}

Then LRLog.h

#pragma once

#include "CMSysString.h"
#include "CLRILogger.h" 
#include <vcclr.h>

using namespace System;

class CNtvLogger;

namespace AlPDFGenV4 
{
    public ref class Logger
    {
    public:
        Logger(void);
        virtual ~Logger(void);

        ILogger^ extlogger;
            CNtvLogger *ntv;

            void Log( String^ txt )
            {
                extlogger->Log( txt );
            }
        };

    }

And LRLog.cpp

#include "StdAfx.h"
#include "LRLog.h"

using namespace AlPDFGenV4;

Logger::Logger(void)
{
    ntv = new CNtvLogger;
    ntv->clrlogger = this;
} 

Logger::~Logger(void)
{
    delete ntv;
}

class CNtvLogger : CMSysLogger
{
public:
    gcroot<AlPDFGenV4::Logger ^> clrlogger;

protected:
    void _InternalLog( LPCTSTR txt)
    {
        String ^str = gcnew String( txt );

        clrlogger->Log( str );
    }

public:
    bool Init(void * obj)
    {
        return true;
    }

}; 

Hope this helps.

In this example, the class Logger is a bridge tha allows to keep the link between the native logger (used by the native code) and the interface ILogger (used by managed code to pass the class that receives the log output).

You'll need a class like this in your C++/CLI, no need to change the dll with this approach.

这篇关于在C#中从本地C ++继承,并将继承类向后传递到c ++的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆