FAQ FAQ   Search Search   Memberlist Memberlist   Usergroups Usergroups   Register Register 
3Dconnexion.com
3Dconnexion Forum 
  Profile Profile   Log in to check your private messages Log in to check your private messages  Log inLog in 

 3Dconnexion.com Forum Index » Developer's Forum for Windows » Where's the SDK?
 Goto page Previous  1, 2, 3 The time now is Thu Sep 02, 2010 6:34 am 

 Post new topic   Reply to topic View previous topic :: View next topic  
Author Message
PostPosted: Fri Aug 10, 2007 1:42 pm    Post subject:  Reply with quote  

ngomes
Moderator
Moderator


Joined: 27 Nov 2006
Posts: 1138
Location: EU

Hi kitsu,

I think, in the end, the solution is to provide a module to expose the 3D mouse data in Python programs. This will require some knowledge on how to "connect" to the data in the different platforms (which 3Dx has aplenty) and how build the Python module (which we do not). We are more than happy to help the community to develop such a module.

To answer your questions. You do not need to catch any messages. That's all done by the COM server. The protocol between the app and driver uses registered window messages.

That "__hook" statement is an "attribute." This is Microsoft's approach to hide some of the nitty gritty of using the IConnectionPoint interface.

Note that the 3DxInput (the COM API) has two modes of operation: you can poll data (as in the Python example in this topic) or you can register to receive "events" (and use the IConnectionPoint interface directly or inderectely). Most of the high level scripting language are able to hide the use of these standard interfaces.

Unfortunately, not being a Python developer myself, I cannot provide much assistance on how to go about using a COM object in that language.

TOP View user's profileSend private messageVisit poster's website  BOTTOM
PostPosted: Fri Aug 10, 2007 2:40 pm    Post subject:  Reply with quote  

kitsu



Joined: 09 Aug 2007
Posts: 7

Thanks for the quick reply. I guess using a lower level module wouldn't be terrible. Is there a .dll supporting c calling syntax available? The Python ctypes module allows Python programs to dynamically load shared libraries (whether they are .dll or Linux .so or whatever) and call arbitrary functions. The COM library I'm using actually uses ctypes to build all its modules - which is why some of the raw implementation details are still exposed.

While wandering through MSDN I found this:
http://msdn2.microsoft.com/en-us/library/ms680112.aspx
which gives a little more insight into how COM relates to the event loop. I still haven't managed to translate their example code into something comprehensible though.
here: http://msdn2.microsoft.com/en-us/library/ms644928.aspx
is nearly a verbatim replication of the code in one of the 3Dx SDK examples. I still don't understand exactly what it is doing, but I guess it is what I need to get my code working. It is a big ugly chunk of code, but I will see if I can translate it.

TOP View user's profileSend private message  BOTTOM
PostPosted: Fri Aug 10, 2007 2:48 pm    Post subject:  Reply with quote  

calli



Joined: 07 Aug 2007
Posts: 12

ngomes wrote:

Note that the 3DxInput (the COM API) has two modes of operation: you can poll data (as in the Python example in this topic)


But the polling does not work in the examples...

Carsten

TOP View user's profileSend private message  BOTTOM
PostPosted: Fri Aug 10, 2007 3:37 pm    Post subject:  Reply with quote  

kitsu



Joined: 09 Aug 2007
Posts: 7

Oops, nevermind. I had a beer and everything fell together*. The following code prints out nice floating point value as I move the cap.
Code:
import comtypes.client as client
from ctypes import *

import logging
console = logging.StreamHandler()
console.setLevel(logging.DEBUG)
formatter = logging.Formatter('%(name)-12s: %(levelname)-8s %(message)s')
console.setFormatter(formatter)
logging.getLogger('').addHandler(console)

types = { # What others?
   0:"Unknown",
   6:"SpaceNavigator",
   4:"SpaceExplorer",
   25:"SpaceTravler",
   29:"SpacePilot"
}

class POINT(Structure):
    """Point struct used in Win32 api functions."""
    _fields_ = [("x", c_long),
                ("y", c_long)]

class MSG(Structure):
    """Message struct used in Win32 api functions."""
    _fields_ = [("hWnd", c_ulong),
                ("message", c_uint),
                ("wParam", c_ulong),
                ("lParam", c_ulong),
                ("time", c_ulong),
                ("pt", POINT)]
   
def PumpWaitingMessages():
    """Windows API function."""
    user32 = windll.user32
    msg = MSG()
    PM_REMOVE = 0x0001
    while user32.PeekMessageA(byref(msg), 0, 0, 0, PM_REMOVE):
        user32.TranslateMessage(byref(msg))
        user32.DispatchMessageA(byref(msg))

def GetMessage():
    """Windows API function."""
    #BOOL GetMessage(LPMSG lpMsg, HWND hWnd, UINT wMsgFilterMin, UINT wMsgFilterMax);
    user32 = windll.user32
    msg = MSG()
    user32.GetMessageW(byref(msg), None, 0, 0)
    return msg

def DispatchMessage(msg):
    """Windows API function."""
    user32 = windll.user32
    user32.DispatchMessageW(byref(msg))

class KeyListener:
    """Catch and print keyboard events.

    Note: some keys either don't send events or give bad key codes.
    """
    def __init__(self, keyboard):
        self.exit = False
        self.keyboard = keyboard
        self.exitCode = 1

    def cont(self):
        return not self.exit
   
    def KeyDown(self, this, code):
        print 'Keydown: %s, %s' %(code, self.keyboard.GetKeyName(code))
        if code == self.exitCode:
            self.exit = True

    def KeyUp(self, this, code):
        print 'Keyup: %s, %s' %(code, self.keyboard.GetKeyName(code))

class SensorListener:
    """Catch and print sensor events."""
    def __init__(self, sensor):
        self.sensor = sensor
   
    def SensorInput(self, this, inval=None):
        print "Rot: ",
        print self.sensor.Rotation.X,
        print self.sensor.Rotation.Y,
        print self.sensor.Rotation.Z
        print "Trans: ",
        print self.sensor.Translation.X,
        print self.sensor.Translation.Y,
        print self.sensor.Translation.Z

# Get device
device = client.CreateObject("TDxInput.Device")
print types[device.Type],

if not device.Connect(): # Returns failed
   print ": Connected!"

# Setup keyboard listener
keyboard = device.Keyboard
listener = KeyListener(keyboard)
client.GetEvents(keyboard, listener)

# Setup sensor listener
sensor = device.Sensor
client.GetEvents(sensor, SensorListener(sensor))

# Start event loop
while listener.cont():
    msg = GetMessage()
    DispatchMessage(msg)
    #PumpWaitingMessages()
   



Note that there is a error in the comtypes 0.3.2 GetEvents function which causes it to miss all events. I've reported it to the mailing list, but until it is fixed use comtypes 0.2.1.

If you are using pywin32 you should be able to fine the GetMessage, DispatchMessage, and TranslateMessage functions in win32event module.

One continuing problem I've had though is that some key events don't seem to be working correctly. I have the SpaceExplorer - the model with the second most buttons BTW. I'm guessing that the esc, ctrl, etc keys are generating normal keycodes like a keyboard? What are the key codes for 2d and 'fit' though. I think 32 is the keycode for 'fit', but keyboard.GetKeyName(code) raises a undefined COM error?

* This poster neither endorses nor encourages the consumption of alcohol, except in cases involving the Component Object Model or the Window's API*

TOP View user's profileSend private message  BOTTOM
PostPosted: Fri Aug 10, 2007 11:04 pm    Post subject:  Reply with quote  

calli



Joined: 07 Aug 2007
Posts: 12

My Hero!

Thanks to beer! Wink
Carsten

TOP View user's profileSend private message  BOTTOM
PostPosted: Sat Aug 11, 2007 11:38 am    Post subject:  Reply with quote  

kitsu



Joined: 09 Aug 2007
Posts: 7

I just noticed something interesting this morning - pressing the 2d button toggles sensor.Rotation between outputing all zeros or meaningful values. It seems this behavior is at 'hardware' level (or at least not exposed via COM).

In future releases it might be nice to have a settable 2d attribute in the sensor object. Otherwise there is no way to change the value at run time. It would be fine if I could create arbitrary configuration preference files, but as it is now any software I write will be stuck with the general preferences.

Actually I just peeked and it looks like the configurations are just plain text files? I suppose I can go fake my own then, but I would prefer a nice API to protect me from future format changes. Depending on undocumented file formats sucks Sad

TOP View user's profileSend private message  BOTTOM
PostPosted: Fri Apr 03, 2009 7:18 pm    Post subject:  Reply with quote  

etr9j



Joined: 03 Apr 2009
Posts: 2

I know this post fairly old, but I'm trying to get python working with my navigator and this script seems like it's the best bet. I can get it working to a point. Running the script shows "SpaceNavigator : Connected!" but that's it - I don't get values printing out.

It might have to do with version issues, since I'm using a newer version of comtypes than described. It might also be that some subtle changes in python itself since this post might be to blame (I'm working in python 2.5 at the moment).

But since it works to some degree I hope it might be something less complicated. It looks like the listeners aren't working even though there isn't an error.

Anyone have any ideas?

TOP View user's profileSend private message  BOTTOM
PostPosted: Sat Apr 04, 2009 6:05 pm    Post subject:  Reply with quote  

etr9j



Joined: 03 Apr 2009
Posts: 2

Okay, looks like it was a version issue. For this to work you really need comtypes 0.2.1. I was using 0.6.0 thinking any bugs in this function was resolved by now, but it seems that the 0.2.1 GetEvents is a bit more involved. With a little searching I found v 0.2.1 here.

TOP View user's profileSend private message  BOTTOM
 Post new topic   Reply to topic All times are GMT - 8 Hours

Display posts from previous:    Goto page Previous  1, 2, 3
 3Dconnexion.com Forum Index » Developer's Forum for Windows » Where's the SDK?
 Page 3 of 3
 
 
 
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
Jump to:  


     Powered by phpBB © 2001, 2005 phpBB Group | Template Neon v1.3 | Crystal