So far JWICK helped establish that there is a problem compiling a C# proect with this DLL on a x64 OS
Now I find the same problem (slightly different message) also on x32 ...
So - what am I doing wrong - Any tips will be appreciated:
The following happened on BOTH XP Prof x32 as well as on XP Home x32
1. Install 3dconnexions software - Yes on get latest updates
2. Test SpaceNavigator with one of the demo programs - works fine.
3. Make sure driver has started.
4. SpaceNavigator blue light is on.
5. Open new Windows Form C# project.
6. Accept default values - DO NOTHING ELSE and go straigh to add new reference
7. Go to the COM tab and add the only reference to 3dconnexions
8. DLL adds with the following warnings:
Warning 1 Cannot find wrapper assembly for type library "TDxInput".
Warning 2 The referenced component 'TDxInput' could not be found.
Is there anything missing here ...
Will be most thankful to any reply with tips how to get going - I am stuck with this thing for a while now ...
TDxInput.dll - problems compiling also under x32
Moderator: Moderators
-
- Posts: 25
- Joined: Thu Dec 18, 2008 11:41 am
-
- Posts: 25
- Joined: Thu Dec 18, 2008 11:41 am
To JWICK
Hi JWICK,
Last time you worked over the weekend. Just to mention here - have your weekend
I am hoping somebody else will be able to cover today. If not then we talk again Monday.
Last time you worked over the weekend. Just to mention here - have your weekend

I am hoping somebody else will be able to cover today. If not then we talk again Monday.
Sorry, I got this last week but forgot to post it. Thanks for reminding me.
From the TDxInput developer (who does all his development on an x64 machine):
The best way to go about using TDxInput in C#/VB is to NOT reference the COM dll. The dll to reference in the project is the .NET assembly TDx.TDxInput.dll. I think the most effective procedure is to copy the file to a location local to the project so that if a revision control system is being used it can be checked in and out and there is no need to install 3dxware to build.
To add the reference go to the ‘Browse’ tab in the ‘Add Reference’ dialog, browse to where the local copy of TDx.TDxInput.dll is select and ok.
To use tdxinput In the c# code add the line using TDx.TDxInput;
The objects are reference as TDx.TDxInput.Object
e.g.
private TDx.TDxInput.Device device;
TDx.TDxInput.dll will need to be distributed by the 3rd party and copied to the installation directory of the 3rd party product (but NOT added to the Global Assembly Cache). Because when we install 3dxware we add TDx.TDxInput.dll to the GAC, the third party product will use our copy of TDx.TDxInput.dll when 3dxware is installed, otherwise the local copy.
From the TDxInput developer (who does all his development on an x64 machine):
The best way to go about using TDxInput in C#/VB is to NOT reference the COM dll. The dll to reference in the project is the .NET assembly TDx.TDxInput.dll. I think the most effective procedure is to copy the file to a location local to the project so that if a revision control system is being used it can be checked in and out and there is no need to install 3dxware to build.
To add the reference go to the ‘Browse’ tab in the ‘Add Reference’ dialog, browse to where the local copy of TDx.TDxInput.dll is select and ok.
To use tdxinput In the c# code add the line using TDx.TDxInput;
The objects are reference as TDx.TDxInput.Object
e.g.
private TDx.TDxInput.Device device;
TDx.TDxInput.dll will need to be distributed by the 3rd party and copied to the installation directory of the 3rd party product (but NOT added to the Global Assembly Cache). Because when we install 3dxware we add TDx.TDxInput.dll to the GAC, the third party product will use our copy of TDx.TDxInput.dll when 3dxware is installed, otherwise the local copy.
-
- Posts: 25
- Joined: Thu Dec 18, 2008 11:41 am
GREAT!!!
Hey ... again on the weekend ... huh ... 
But ... you NAILED it!
All running fine off my x64. I can bet money that the fix is the same for my x32 reported issue.
To return the favor I will not stop at "Thank you man" ...
Now - for the rest of the interested - here the summary one more time:
1. Open a new C# WinForms project - Accept defaults - do nothing else.
2. Go to C:\Program Files\3Dconnexion\3Dconnexion 3DxSoftware\3DxWare64\win32 (or win64 - whatever your case)
3. Copy file TDx.TDxInput.dll to where your EXE will be - probably at \bin\Debug
4. Go to the C# project references and then to Add
5. Go to the Browse Tab
6. Navigate to the location where you just put the above DLL - Add it.
8. It should add without any yellow exclamation marks.
9. Go to the wonderful C# example from JWICK
10. Replace the default code in your project with the example.
11. Add using TDx.TDxInput;
12. REPLACE EVERYWHERE "TDxInput." with "TDx.TDxInput"
13. Look at the SpaceNavigator - if the blue light is not ON - go to Start-3Dconnexion-3Dconnexion 3DxWare-Start Driver.
Once the blue light on the unit is on - run your project.
Have fun
Thanks JWICK.

But ... you NAILED it!
All running fine off my x64. I can bet money that the fix is the same for my x32 reported issue.
To return the favor I will not stop at "Thank you man" ...

Now - for the rest of the interested - here the summary one more time:
1. Open a new C# WinForms project - Accept defaults - do nothing else.
2. Go to C:\Program Files\3Dconnexion\3Dconnexion 3DxSoftware\3DxWare64\win32 (or win64 - whatever your case)
3. Copy file TDx.TDxInput.dll to where your EXE will be - probably at \bin\Debug
4. Go to the C# project references and then to Add
5. Go to the Browse Tab
6. Navigate to the location where you just put the above DLL - Add it.
8. It should add without any yellow exclamation marks.
9. Go to the wonderful C# example from JWICK
10. Replace the default code in your project with the example.
11. Add using TDx.TDxInput;
12. REPLACE EVERYWHERE "TDxInput." with "TDx.TDxInput"
13. Look at the SpaceNavigator - if the blue light is not ON - go to Start-3Dconnexion-3Dconnexion 3DxWare-Start Driver.
Once the blue light on the unit is on - run your project.
Have fun

Thanks JWICK.
Hi, thanks for the tip above regarding the .Net version of TDx.TDxInput.DLL, I was trying to use the COM version as well...
However, I am still getting strange results...
The code works fine for a few moments, and then I stop receiving events, I added counts to the events, and it seems to be freezing around 300 events.
Do I need to flush the message pump or something?
here is the code I am using:
InputTest.cs
And the Designer file if you need it:
InputTest.Designer.cs
Thanks in Advance!!!
-Josh
However, I am still getting strange results...
The code works fine for a few moments, and then I stop receiving events, I added counts to the events, and it seems to be freezing around 300 events.
Do I need to flush the message pump or something?
here is the code I am using:
InputTest.cs
Code: Select all
using System;
using System.Windows.Forms;
using TDx.TDxInput;
namespace InputTest
{
public partial class InputTest : Form
{
private DeviceClass m_3DXDevice = null;
private _ISimpleDeviceEvents_DeviceChangeEventHandler m_DeviceChangeEventHandler = null;
private _ISensorEvents_SensorInputEventHandler m_SensorInputEventHandler = null;
private _IKeyboardEvents_KeyDownEventHandler m_KeyDownEventHandler = null;
private _IKeyboardEvents_KeyUpEventHandler m_KeyUpEventHandler = null;
private int m_SensorEventCount = 0;
private int m_KeyUpEventCount = 0;
private int m_KeyDownEventCount = 0;
public InputTest()
{
InitializeComponent();
m_DeviceChangeEventHandler = new _ISimpleDeviceEvents_DeviceChangeEventHandler(m_3DXDevice_DeviceChange);
m_SensorInputEventHandler = new _ISensorEvents_SensorInputEventHandler(Sensor_SensorInput);
m_KeyDownEventHandler = new _IKeyboardEvents_KeyDownEventHandler(Keyboard_KeyDown);
m_KeyUpEventHandler = new _IKeyboardEvents_KeyUpEventHandler(Keyboard_KeyUp);
}
private void Form1_Load(object sender, EventArgs e)
{
try
{
m_3DXDevice = new DeviceClass();
m_3DXDevice.DeviceChange += m_DeviceChangeEventHandler;
m_3DXDevice.Connect();
}
catch(Exception) { }
}
private void Form_FormClosing(object sender, FormClosingEventArgs e)
{
if (m_3DXDevice != null)
{
if (m_3DXDevice.IsConnected)
{
m_3DXDevice.Sensor.SensorInput -= m_SensorInputEventHandler;
m_3DXDevice.Keyboard.KeyDown -= m_KeyDownEventHandler;
m_3DXDevice.Keyboard.KeyUp -= m_KeyUpEventHandler;
}
m_3DXDevice.DeviceChange -= m_DeviceChangeEventHandler;
m_3DXDevice.Disconnect();
}
}
void m_3DXDevice_DeviceChange(int reserved)
{
if (m_3DXDevice.IsConnected)
{
m_3DXDevice.Sensor.SensorInput += m_SensorInputEventHandler;
m_3DXDevice.Keyboard.KeyDown += m_KeyDownEventHandler;
m_3DXDevice.Keyboard.KeyUp += m_KeyUpEventHandler;
}
}
void Sensor_SensorInput()
{
m_Label_SensorCount.Text = string.Format("Sensor Count: {0}", ++m_SensorEventCount);
m_Label_Rotation.Text = string.Format("Rotation: {0:F4}, {1:F4}, {2:F4}, {3:F4}",
m_3DXDevice.Sensor.Rotation.X,
m_3DXDevice.Sensor.Rotation.Y,
m_3DXDevice.Sensor.Rotation.Z,
m_3DXDevice.Sensor.Rotation.Angle);
m_Label_Translation.Text = string.Format("Translation: {0:F4}, {1:F4}, {2:F4}, {3:F4}",
m_3DXDevice.Sensor.Translation.X,
m_3DXDevice.Sensor.Translation.Y,
m_3DXDevice.Sensor.Translation.Z,
m_3DXDevice.Sensor.Translation.Length);
}
void Keyboard_KeyDown(int keyCode)
{
m_Label_KeyDownCount.Text = string.Format("KeyDown Count: {0}", ++m_KeyDownEventCount);
m_Label_KeyDown.Text = string.Format("KeyDown: {0}", keyCode);
}
void Keyboard_KeyUp(int keyCode)
{
m_Label_KeyUpCount.Text = string.Format("KeyUp Count: {0}", ++m_KeyUpEventCount);
m_Label_KeyUp.Text = string.Format("KeyUp: {0}", keyCode);
}
}
}
InputTest.Designer.cs
Code: Select all
namespace InputTest
{
partial class InputTest
{
private System.ComponentModel.IContainer components = null;
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form Designer generated code
private void InitializeComponent()
{
this.m_Label_SensorCount = new System.Windows.Forms.Label();
this.m_Label_Rotation = new System.Windows.Forms.Label();
this.m_Label_Translation = new System.Windows.Forms.Label();
this.m_Label_KeyDown = new System.Windows.Forms.Label();
this.m_Label_KeyUp = new System.Windows.Forms.Label();
this.m_Label_KeyDownCount = new System.Windows.Forms.Label();
this.m_Label_KeyUpCount = new System.Windows.Forms.Label();
this.SuspendLayout();
//
// m_Label_SensorCount
//
this.m_Label_SensorCount.AutoSize = true;
this.m_Label_SensorCount.Location = new System.Drawing.Point(12, 9);
this.m_Label_SensorCount.Name = "m_Label_SensorCount";
this.m_Label_SensorCount.Size = new System.Drawing.Size(83, 13);
this.m_Label_SensorCount.TabIndex = 3;
this.m_Label_SensorCount.Text = "Sensor Count: 0";
//
// m_Label_Rotation
//
this.m_Label_Rotation.AutoSize = true;
this.m_Label_Rotation.Location = new System.Drawing.Point(12, 22);
this.m_Label_Rotation.Name = "m_Label_Rotation";
this.m_Label_Rotation.Size = new System.Drawing.Size(203, 13);
this.m_Label_Rotation.TabIndex = 3;
this.m_Label_Rotation.Text = "Rotation: 0.0000, 0.0000, 0.0000, 0.0000";
//
// m_Label_Translation
//
this.m_Label_Translation.AutoSize = true;
this.m_Label_Translation.Location = new System.Drawing.Point(9, 35);
this.m_Label_Translation.Name = "m_Label_Translation";
this.m_Label_Translation.Size = new System.Drawing.Size(215, 13);
this.m_Label_Translation.TabIndex = 3;
this.m_Label_Translation.Text = "Translation: 0.0000, 0.0000, 0.0000, 0.0000";
//
// m_Label_KeyDown
//
this.m_Label_KeyDown.AutoSize = true;
this.m_Label_KeyDown.Location = new System.Drawing.Point(12, 74);
this.m_Label_KeyDown.Name = "m_Label_KeyDown";
this.m_Label_KeyDown.Size = new System.Drawing.Size(65, 13);
this.m_Label_KeyDown.TabIndex = 3;
this.m_Label_KeyDown.Text = "KeyDown: 0";
//
// m_Label_KeyUp
//
this.m_Label_KeyUp.AutoSize = true;
this.m_Label_KeyUp.Location = new System.Drawing.Point(12, 113);
this.m_Label_KeyUp.Name = "m_Label_KeyUp";
this.m_Label_KeyUp.Size = new System.Drawing.Size(51, 13);
this.m_Label_KeyUp.TabIndex = 3;
this.m_Label_KeyUp.Text = "KeyUp: 0";
//
// m_Label_KeyDownCount
//
this.m_Label_KeyDownCount.AutoSize = true;
this.m_Label_KeyDownCount.Location = new System.Drawing.Point(12, 61);
this.m_Label_KeyDownCount.Name = "m_Label_KeyDownCount";
this.m_Label_KeyDownCount.Size = new System.Drawing.Size(96, 13);
this.m_Label_KeyDownCount.TabIndex = 3;
this.m_Label_KeyDownCount.Text = "KeyDown Count: 0";
//
// m_Label_KeyUpCount
//
this.m_Label_KeyUpCount.AutoSize = true;
this.m_Label_KeyUpCount.Location = new System.Drawing.Point(12, 100);
this.m_Label_KeyUpCount.Name = "m_Label_KeyUpCount";
this.m_Label_KeyUpCount.Size = new System.Drawing.Size(82, 13);
this.m_Label_KeyUpCount.TabIndex = 3;
this.m_Label_KeyUpCount.Text = "KeyUp Count: 0";
//
// InputTest
//
this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(292, 140);
this.Controls.Add(this.m_Label_KeyUp);
this.Controls.Add(this.m_Label_KeyDown);
this.Controls.Add(this.m_Label_Translation);
this.Controls.Add(this.m_Label_Rotation);
this.Controls.Add(this.m_Label_KeyUpCount);
this.Controls.Add(this.m_Label_KeyDownCount);
this.Controls.Add(this.m_Label_SensorCount);
this.Name = "InputTest";
this.Text = "3DX Input Test";
this.Load += new System.EventHandler(this.Form1_Load);
this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.Form_FormClosing);
this.ResumeLayout(false);
this.PerformLayout();
}
#endregion
private System.Windows.Forms.Label m_Label_SensorCount;
private System.Windows.Forms.Label m_Label_Rotation;
private System.Windows.Forms.Label m_Label_Translation;
private System.Windows.Forms.Label m_Label_KeyDown;
private System.Windows.Forms.Label m_Label_KeyUp;
private System.Windows.Forms.Label m_Label_KeyDownCount;
private System.Windows.Forms.Label m_Label_KeyUpCount;
}
}
-Josh
Never mind, I found the Post for the examples on the FTP
BTW, the sub directory in the FTP is actually examples/TDxInput
I thought it had been removed for a second when all I saw was "tad" & "tobi" in the "t" section of the folders
Which did indeed wok perfectly...
After commenting out sections of the example code such as the callback delegates, isRunning, and lastUpdate to make the code look closer to mine, I noticed the lines that were setting references to the sensor and keyboard after the device was created in the constructor:
sensor = this.device.Sensor;
this.keyboard = this.device.Keyboard;
After adding similar lines to my code, everything worked perfectly...
For a sanity check I commented out the lines, which caused it to begin failing once again.
Which leads me to wonder...
Is there something internally removing the reference for the Keyboard and Sensor objects, or do the Device.Sensor & Device.Keyboard Properties simply return a new instance that you must store yourself?
It seems as though the simply act of adding references to each prevents the issue.
Further more, as part of the debugging process I went through I added the System.GC.Collect(); call to the Sensor_SensorInput event handler, which caused it to stop working immediately, so the fact that it continued to work as long as it did before may have just been a simple case of the garbage collector not yet collecting the Sensor & Keyboard objects...
Is this a bug or intended behavior?
Thanks,
Josh
BTW, the sub directory in the FTP is actually examples/TDxInput
I thought it had been removed for a second when all I saw was "tad" & "tobi" in the "t" section of the folders

Which did indeed wok perfectly...
After commenting out sections of the example code such as the callback delegates, isRunning, and lastUpdate to make the code look closer to mine, I noticed the lines that were setting references to the sensor and keyboard after the device was created in the constructor:
sensor = this.device.Sensor;
this.keyboard = this.device.Keyboard;
After adding similar lines to my code, everything worked perfectly...
For a sanity check I commented out the lines, which caused it to begin failing once again.
Which leads me to wonder...
Is there something internally removing the reference for the Keyboard and Sensor objects, or do the Device.Sensor & Device.Keyboard Properties simply return a new instance that you must store yourself?
It seems as though the simply act of adding references to each prevents the issue.
Further more, as part of the debugging process I went through I added the System.GC.Collect(); call to the Sensor_SensorInput event handler, which caused it to stop working immediately, so the fact that it continued to work as long as it did before may have just been a simple case of the garbage collector not yet collecting the Sensor & Keyboard objects...
Is this a bug or intended behavior?
Thanks,
Josh
Also... it looks like my issue was already discussed with the same outcome on this post:
viewtopic.php?t=1385
(sorry for hi-jacking this post, I initially thought it was related)
viewtopic.php?t=1385
(sorry for hi-jacking this post, I initially thought it was related)
-
- Posts: 25
- Joined: Thu Dec 18, 2008 11:41 am
No problem Josh,
Apology for not returning the post earlier - worked 48 h during this weekend...
Anyway - I browsed quickly through the code.
During the quick fly-over I could not see things like (simplified for the message)
TDx.TDxInput.Device myMouse3D;
TDx.TDxInput.Keyboard myMouse3DButton;
TDx.TDxInput.Sensor myMouse3DSensor;
TDx.TDxInput.Vector3D myTranslation;
TDx.TDxInput.AngleAxis myRotation;
Then the readouts for X,Y,Z,Angle are straight forward with
myTranslation= Mouse3DSensor.Translation;
myRotation= Mouse3DSensor.Rotation;
Then again - it probably does not matter as yours is already running.
I just put it here as additional reference - for whatever it is worth.
Apology for not returning the post earlier - worked 48 h during this weekend...
Anyway - I browsed quickly through the code.
During the quick fly-over I could not see things like (simplified for the message)
TDx.TDxInput.Device myMouse3D;
TDx.TDxInput.Keyboard myMouse3DButton;
TDx.TDxInput.Sensor myMouse3DSensor;
TDx.TDxInput.Vector3D myTranslation;
TDx.TDxInput.AngleAxis myRotation;
Then the readouts for X,Y,Z,Angle are straight forward with
myTranslation= Mouse3DSensor.Translation;
myRotation= Mouse3DSensor.Rotation;
Then again - it probably does not matter as yours is already running.
I just put it here as additional reference - for whatever it is worth.