Hello...
in conjunction to my university project, I integrated the SpaceNavigator into our existing framework (C++, Qt-based, QTOpenGL) for Medical Volume Data Analysis and Segmentation (and further more).
And what to say, I like the SpaceNavigator, it is the right thing to augment working!!!
But now it comes: I am a total novice to ATL/COM etc... and it seems that I have a circular dependency problem!
3 classes: HardwareManager (creates SpaceNavigator-Object), SpaceNavigator and Qt-GLWidget (manages Shortcuts for switching cameraMovement, volumeMovement and SliceMovement)
When I compile (only sometimes, when there have been changes in HardwareManager or GLWidget) the VS2005-Compiler throws
fatal error LNK1169: Mindestens ein mehrfach definiertes Symbol gefunden. (kinda at least one multiple symbols defined symbol found)
How can I resolve this???
What works, but is not very intuitive: comment out
[module(name="EventReceiver")];
and
[event_receiver(com)]
compile and comment them in after another?!
I've seen and tested the example programes like ATLCube... But I did implement only the minimum to get the program compile and run.
Regards
Andi
[ATL/COM] Lnk1169 - circular dependencies??
Moderator: Moderators
[ATL/COM] Lnk1169 - circular dependencies??
Last edited by neobond on Wed Jul 04, 2007 10:25 am, edited 1 time in total.
Some Code
It might be useful to see some code snippets....
HardwareManager.cpp
SpaceNavigator.h
SpaceNavigator.cpp
[/code]
HardwareManager.cpp
Code: Select all
HardwareManager::HardwareManager(void){
//TODO: integrate, test Phantom
#ifdef USE_SPACENAV
mSpaceNavigator = new SpaceNavigator();
#endif
}
Code: Select all
#ifdef USE_SPACENAV
#define _ATL_ATTRIBUTES
#include <atlbase>
#include <atlcom>
//#include <atlwin>
//#include <atltypes>
//#include <atlctl>
//#include <atlhost>
using namespace ATL;
//if SpaceNavigator is installed
//#import "progid:TDxInput.Device" embedded_idl no_namespace
//if only support-files are available
#import "..\..\support\SpaceNavigator\TDxInput.dll" embedded_idl no_namespace
//circular dependency of included SpaceNavigator in HardwareManager.h and GLWidget.h (TODO:resolve)
//when retrieving compile error
// compile without [module(..)] and [event..] lines (uncomment!)
//then compile with [event_receiver(com)] option
//then compile with [module(name="EventReceiver")]; option
[module(name="EventReceiver")];
[event_receiver(com)]
#endif
class SpaceNavigator{
public:
SpaceNavigator();
~SpaceNavigator();
bool deviceFound;
void setMoveMode( string mode);
[...]
Code: Select all
SpaceNavigator::SpaceNavigator(){
//for global referencing if SpaceNavigator has been found!
deviceFound = false;
#ifdef USE_SPACENAV
//initializing input values from sensor
x_trans = 0.0, y_trans = 0.0, z_trans = 0.0;
x_vert = 0.0, y_vert = 0.0, z_vert = 0.0;
x_rot = 0.0, y_rot = 0.0, z_rot = 0.0, angle_rot = 0.0;
moveVolume = false; moveCamera = true; moveSlices = false;
mHR = mPDevice.CreateInstance(__uuidof(Device));
if ( SUCCEEDED( mHR ) ) {
mHR = mPDevice->Connect(); //will always be true, when driver is found;
//even when there is no SpaveNavigator connected
if ( SUCCEEDED( mHR ) ) { // && mPDevice->Type == 6 SpaceNavigator has TypeId = 6
//registrate (hook_in) the functions to DevicePointers and internal Operations
mHR = __hook(&_ISimpleDeviceEvents::DeviceChange, mPDevice, &SpaceNavigator::OnDeviceChange);
mHR = mPDevice->get_Sensor (&mP3DSensor);
mHR = __hook(&_ISensorEvents::SensorInput, mP3DSensor, &SpaceNavigator::OnSensorInput);
mHR = mPDevice->get_Keyboard(&mP3DKeyboard);
mHR = __hook(&_IKeyboardEvents::KeyDown, mP3DKeyboard, &SpaceNavigator::OnKeyDown);
mHR = __hook(&_IKeyboardEvents::KeyUp, mP3DKeyboard, &SpaceNavigator::OnKeyUp);
//mPDevice->LoadPreferences("MedGPU");
QTLogWindow::the()->addDebug( "SpaceNavigator ::SpaceNavigator() - SpaceNavigator initialized correctly" );
deviceFound = true;
}
else {
mPDevice = NULL;
QTLogWindow::the()->addError( "SpaceNavigator ::SpaceNavigator() - sorry, unknown device type detected" );
}
}
else{
QTLogWindow::the()->addError( "SpaceNavigator ::SpaceNavigator() - driver not installed" );
}
#endif
}
Hello Markus,
here is what he says when 1)Clean Solution 2) Build Solution
Regards
Andreas
here is what he says when 1)Clean Solution 2) Build Solution
Code: Select all
Linking...
GLWidget.obj : error LNK2005: _DllGetClassObject@12 already defined in HardwareManager.obj
GLWidget.obj : error LNK2005: _DllRegisterServer@0 already defined in HardwareManager.obj
GLWidget.obj : error LNK2005: _DllUnregisterServer@0 already defined in HardwareManager.obj
GLWidget.obj : error LNK2005: _DllCanUnloadNow@0 already defined in HardwareManager.obj
GLWidget.obj : error LNK2005: _DllMain@12 already defined in HardwareManager.obj
GLWidget.obj : error LNK2005: "class CEventReceiverModule _AtlModule" (?_AtlModule@@3VCEventReceiverModule@@A) already defined in HardwareManager.obj
SpaceNavigator.obj : error LNK2005: _DllGetClassObject@12 already defined in HardwareManager.obj
SpaceNavigator.obj : error LNK2005: _DllRegisterServer@0 already defined in HardwareManager.obj
SpaceNavigator.obj : error LNK2005: _DllUnregisterServer@0 already defined in HardwareManager.obj
SpaceNavigator.obj : error LNK2005: _DllCanUnloadNow@0 already defined in HardwareManager.obj
SpaceNavigator.obj : error LNK2005: _DllMain@12 already defined in HardwareManager.obj
SpaceNavigator.obj : error LNK2005: "class CEventReceiverModule _AtlModule" (?_AtlModule@@3VCEventReceiverModule@@A) already defined in HardwareManager.obj
Andreas
Hi neobond,
Try moving the
out of SpaceNavigator.h and
into SpaceNavigator.cpp and
let me know what the result is.
Markus
Try moving the
Code: Select all
[module(name="EventReceiver")];
into SpaceNavigator.cpp and
let me know what the result is.
Markus
SOLVED!!!!
Great: IT WORKS!!!!
it now starts in Debug AND Release Mode.
And also the Compile Errors vanished ( and I also understood why )
One last question from an ATL newbie:
what is exactly for????
what would be the advantage of
if there is any???
THANX a lot
Andreas
it now starts in Debug AND Release Mode.
And also the Compile Errors vanished ( and I also understood why )
One last question from an ATL newbie:
what is
Code: Select all
[module(name="EventReceiver")];
what would be the advantage of
Code: Select all
[module(type=dll, name="EventReceiver", uuid="9217D439-8DFE-4C2E-9329-7D95B5FCD5DC")];
THANX a lot
Andreas
Asa far as I know
Is firstly required in any program that uses C++ attributes and an interface definition language file is created by the compiler. This file defines the characteristics, data and methods of the COM interface. The alternative appears to be to write the thing yourself. This has nothing to do with ATL.
If you happen to be using ATL then the module attribute also inserts a global object called _AtlModule.
setting type=dll, which is the default adds functions required to register etc a Com server in a dll.
without uuid="uuid" an ID is automatically generated.
Markus
Code: Select all
[module(name="EventReceiver")];
If you happen to be using ATL then the module attribute also inserts a global object called _AtlModule.
setting type=dll, which is the default adds functions required to register etc a Com server in a dll.
without uuid="uuid" an ID is automatically generated.
Markus