3

I have a simple C# COM visible library that looks like this:

namespace MyEventClassLibrary {

[Guid("0ab09e18-bf85-48c8-a45d-a0cebed77a5c")]
public interface ICalculator
{
    int Add(int Num1, int Num2);
}

[InterfaceType(ComInterfaceType.InterfaceIsIDispatch)]
[Guid("9e09b634-8c1a-4926-83b2-f6f988595c85")]
public interface ICalculatorEvents
{
    [DispId(1)]
    void Completed(int Result);
}

[ClassInterface(ClassInterfaceType.None)]
[ComSourceInterfaces(typeof(ICalculatorEvents))]
[Guid("6cebc4db-2e8f-4e24-91a5-24ffdf97fc6a")]
public class Calculator : ICalculator
{
    [ComVisible(false)]
    public delegate void CompletedDelegate(int result);

    public event CompletedDelegate Completed;

    public int Add(int Num1, int Num2)
    {
        int Result = Num1 + Num2;
        if (Completed != null)
            Completed(Result);

        return Result;
    }
}}

I have it registered and I import the .TLB into QT with:

TYPELIBS = ..\MyEventClassLibrary\MyEventClassLibrary\bin\Debug\MyEventClassLibrary.tlb

and my mainwindow.cpp file looks like:

#include <QDebug>
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include "myeventclasslibrary.h" 

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);

    MyEventClassLibrary::Calculator eventClass;
    connect(&eventClass, SIGNAL(Completed()), this, SLOT(test()));

    qDebug() << eventClass.Add(1,2);
}

void MainWindow::test()
{
    qDebug() << "Here";
}

MainWindow::~MainWindow()
{
    delete ui;
}

When I build the project in QT though, I get 40+ issues along the lines of:

MyEventClassLibrary.h:144: error: C2535: 'MyEventClassLibrary::CompletedDelegate::CompletedDelegate(void)': member function already defined or declared

and

MyEventClassLibrary.h:147: error: C2065: 'iface': undeclared identifier

The above has been resolved by adding [ComVisible(false)] to the delegate (see comments for more info)

When I run the code I get an error of:

QObject::connect: No such signal MyEventClassLibrary::Calculator::Completed()

My question is, how do you handle events/delegates in COM and QT?

As background info, the QT Documentation says:

If the COM object implements the IDispatch interface, the properties, methods and events of that object become available as Qt properties, slots and signals.

and I've used the following as resources and research:

Handle C# COM events in C++

how to put IDispatch* in managed code

How to fire c# COM events in c++?

and more; Please help!

4
  • Without knowing anything about the generated .h file, it sounds like too much of your implementation is visible. The CompletedDelegate type should not be visible at all. Project > Properties > Application tab > Assembly Information button and untick the "Make assembly COM-visible" option. Apply the [ComVisible(true)] attribute only on the declarations that should be visible, the interfaces and the class. Or apply [ComVisible(false)] on the delegate. Commented Sep 27, 2016 at 13:55
  • Thanks @HansPassant, that did fix the onslaught of errors I faced. While it will compile now and I can call the method Add(int, int), I'm still unable and unsure how to instantiate & access the event Completed. I've tried connect(&eventClass, SIGNAL(Completed()), this, SLOT(test()));,but that doesn't seem to be correct. Specifically, the error I get is: QObject::connect: No such signal MyEventClassLibrary::Calculator::Completed() Commented Sep 27, 2016 at 14:18
  • You know the solution to this question. So complete the Q+A by posting the answer and accepting it. Then click the Ask Question button to ask for help with your next problem. Commented Sep 27, 2016 at 14:24
  • If that's necessary I can do that, but the question I asked was "how do you handle events/delegates in COM and QT?". Fixing the multitude of errors was one concern, but that's not my main question. I can update the question body with this new information, though. Commented Sep 27, 2016 at 14:29

1 Answer 1

1

This question had a 2-part question, with the goal of getting a C# COM-visible event to fire in QT:

  1. When I initially built the QT application, I was getting 40+ errors due to a delegate being visible. This was resolved by adding [ComVisible(false)] above the delegate declaration Thank you @HansPassant.

  2. When this was resolved, I tried to connect a SLOT to the COM SIGNAL, with QT saying it couldn't find the Completed event. This was resolved by matching up the function prototypes; Completed has a parameter of int, I was not including the int in the SLOT function. (derp)

My original connect was:

connect(&eventClass, SIGNAL(Completed()), this, SLOT(test()));

it should have been:

connect(&eventClass, SIGNAL(Completed(int)), this, SLOT(test(int)));

Thanks!

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.