Jump to content
  • Advertisement
Sign in to follow this  
Thrump

[.net] Calling C++/CLI from C#

This topic is 4001 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

I've read a few different methods for doing this, but none seem to work in my case. Here's the situation: I had a c++ class, which I've successfully compiled/ran/tested in C++/CLI. Sweet. Now I wish to call this from C#. I tried exporting as a dll, but it's not quite working, not sure if that's even the best way. Viewing the dll, my method is available (using dll export viewer): ?Init@Watcher@@QAEHXZ 0x100017a0 0x000017a0 1 (0x1) ManagedCppTest.dll D:\Dev\ManagedCppTest\debug\ManagedCppTest.dll Exported Function Now, in C#, I can create a Watcher object, but can't call the Init method: Watcher test = new Watcher(); //works fine test.Init(); //no init Am I doing this wrong, or is there an easier way?

Share this post


Link to post
Share on other sites
Advertisement
Add the C++/CLI DLL to your C#'s "References" section, and then you will be able to use any public ref classes and methods in the DLL without any hassle.

Share this post


Link to post
Share on other sites
CLI?

I dont think you've describes a managed class.

your CPP class should hae tings like __nogc or __gc for old style CLR.
Or ref for new style.

I you want to keep you cpp class un-tainted, then youll need to write a wrapper class.
Google for wrapping un managed code and it should see you right.

Share this post


Link to post
Share on other sites
Ahh ok thanks. This stuff is all new to me, so not sure what is managed / non-managed... or at least I do sometimes until I get confused. I'll try to make my class public ref and see how that goes.

Share this post


Link to post
Share on other sites
Quote:
Original post by Thrump
Ahh ok thanks. This stuff is all new to me, so not sure what is managed / non-managed... or at least I do sometimes until I get confused. I'll try to make my class public ref and see how that goes.


Basically:

Managed = Memory allocation is handled by the CLR garbage collector. Therefore, it acts like a C# class-- you create it with new, and the GC will free the memory when there aren't any references to it remaining.

Unmanaged = This is basically your classic C++ class. You can create it on the heap or the stack, and if you use new you must use delete. You cannot export these to unmanaged languages without wrapping it.

My knowledge of C++/CLI is a little fuzzy, so if I'm off base (or outright wrong), someone correct me.

Share this post


Link to post
Share on other sites
Here is the header to an example I threw together for myself. This is just code to help you get you along the way. But you still have to put together the solution/project space correctly in both the C++ and C# projects to get this to work.


// MyRender.h

#pragma once

#define WIN32_LEAN_AND_MEAN

#include <windows.h>
#include <d3d9.h>

using namespace System;
using namespace System::Runtime::InteropServices;

namespace MyRender {

class MyUnmanagedRender
{
private:
HWND mHwnd;
LPDIRECT3D9 mD3D;
LPDIRECT3DDEVICE9 mD3DDevice;

public:
MyUnmanagedRender();
~MyUnmanagedRender();

bool DeviceCreate(HWND hwnd);
bool DevicePresent();
};

public ref class MyManagedRender
{
private:
MyUnmanagedRender* myRender;

public:
MyManagedRender(void)
{
myRender = new MyUnmanagedRender();
}

~MyManagedRender(void)
{
delete myRender;
}

bool DeviceCreate(IntPtr hwnd)
{
HWND handle = (HWND)hwnd.ToPointer();
return myRender->DeviceCreate(handle);
}

bool DevicePresent()
{
return myRender->DevicePresent();
}
};
}



The C# code to use it is pretty simple and straight forward:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;

using MyRender;

namespace RenderTest
{
public partial class Form1 : Form
{
private bool hasDevice = false;
private MyManagedRender myDevice = null;

public Form1()
{
InitializeComponent();
}

private void Form1_Load(object sender, EventArgs e)
{
myDevice = new MyManagedRender();
if (myDevice != null)
hasDevice = myDevice.DeviceCreate(this.Handle);
}

protected override void OnPaint(PaintEventArgs e)
{
myDevice.DevicePresent();
this.Invalidate();
}
}
}

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!