templates - don't know how to fix these errors

I'm trying to compile the VS 2008 plugin SDK for Metasequoia 3D modelling application in Code::Blocks with MingW.

I had to rearrange code so class MQWidgetBase was defined before class MQWidgetEventClosureBase and class MQWidgetKeyEventClosure to fix an incomplete type error but still get lots of the errors shown at the bottom of the code listing for the template function members of MQWidgetBase.

Line 16 in the listing is source of error

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
...
#include <tr1/memory>
...
class MQWidgetEventClosureBase;
class MQWidgetKeyEventClosure;
...

#define MQWidgetSharedPtr std::tr1::shared_ptr
...

class MQWidgetBase
{
    ...

	template<typename T> void AddShowEvent(T *p, BOOL (T::*f)(MQWidgetBase*, MQDocument), bool prior = false) {
		AddEventCallback("show",  MQWidgetSharedPtr<MQWidgetEventClosureBase>(new MQWidgetEventClosure<T>(p, f)), prior);
	}

protected:
    void AddEventCallback(const char *event_type, MQWidgetSharedPtr<MQWidgetEventClosureBase> closure, bool prior);
    ...
};

...

class MQWidgetEventClosureBase
{
public:
	MQWidgetEventClosureBase() { }

	virtual BOOL invoke(MQWidgetBase *sender, MQDocument doc, void *ptr) = 0;
	virtual bool isEqual(const MQWidgetEventClosureBase *c) const = 0;
	virtual MQWidgetBase *getReceiver() = 0;
};

template<typename T> class MQWidgetEventClosure : public MQWidgetEventClosureBase
{
	typedef BOOL (T::*Func)(MQWidgetBase*, MQDocument doc);

public:
	MQWidgetEventClosure(T *_p, Func _f) : MQWidgetEventClosureBase(), p(_p), id(_p->GetID()), f(_f) { }

	BOOL invoke(MQWidgetBase *sender, MQDocument doc, void *ptr) override {
		if(MQWidgetBase::FindWidgetByID(id) != NULL){
			return (p->*f)(sender, doc);
		}
		return FALSE;
	}

	bool isEqual(const MQWidgetEventClosureBase *c) const override {
		if(typeid(*this) != typeid(*c)) return false;
		const MQWidgetEventClosure<T> *cc = static_cast<const MQWidgetEventClosure<T>*>(c);
		return (p == cc->p && f == cc->f);
	}

	MQWidgetBase *getReceiver() override { return p; }

private:
	T *p;
	int id;
	Func f;

	MQWidgetEventClosure();
};

...

////////// errors
/*
MQWidget.h|16|error: expected primary-expression before '(' token
MQWidget.h|16|error: expected type-specifier before 'MQWidgetEventClosure'
MQWidget.h|16|error: expected ')' before 'MQWidgetEventClosure'
*/

A class [MQWidgetEventClosureBase] must be entirely know if you want to create it with new. Forward reference doesn't help because amongst others the size of the object must be determinable.

So #include the class before you use it.
OK I am not sure how to do that.

Do you mean put class MQWidgetEventClosureBase in separate header and include it?

But MQWidgetEventClosureBase uses class MQWidgetBase and class MQWidgetBase uses class MQWidgetEventClosureBase so they both need each other defined before each other don't they?

Do you mean put class MQWidgetEventClosureBase in separate header and include it?
You can do that, but it's not necessary.

if MQWidgetBase is used only by pointer you can use a forward declaration.
In other words: Put MQWidgetEventClosureBase before MQWidgetBase and make MQWidgetBase a forward declaration.
Topic archived. No new replies allowed.