]> git.saurik.com Git - wxWidgets.git/blob - wxPython/wx/lib/activexwrapper.py
Bug fix from Pierre
[wxWidgets.git] / wxPython / wx / lib / activexwrapper.py
1 #----------------------------------------------------------------------
2 # Name: wxPython.lib.activexwrapper
3 # Purpose: a wxWindow derived class that can hold an ActiveX control
4 #
5 # Author: Robin Dunn
6 #
7 # RCS-ID: $Id$
8 # Copyright: (c) 2000 by Total Control Software
9 # Licence: wxWindows license
10 #----------------------------------------------------------------------
11 # 11/30/2003 - Jeff Grimmett (grimmtooth@softhome.net)
12 #
13 # o Updated for wx namespace
14 # o Tested with updated demo
15 #
16
17 import wx
18
19 try:
20 import win32ui
21 import pywin.mfc.activex
22 import win32com.client
23 except ImportError:
24 import sys
25 if hasattr(sys, "frozen"):
26 import os, win32api
27 dllpath = os.path.join(win32api.GetSystemDirectory(), 'MFC71.DLL')
28 if sys.version[:3] >= '2.4' and not os.path.exists(dllpath):
29 message = "%s not found" % dllpath
30 else:
31 raise # original error message
32 else:
33 message = "ActiveXWrapper requires PythonWin. Please install the PyWin32 package."
34 raise ImportError(message)
35
36 ##from win32con import WS_TABSTOP, WS_VISIBLE
37 WS_TABSTOP = 0x00010000
38 WS_VISIBLE = 0x10000000
39
40 #----------------------------------------------------------------------
41
42
43 def MakeActiveXClass(CoClass, eventClass=None, eventObj=None):
44 """
45 Dynamically construct a new class that derives from wxWindow, the
46 ActiveX control and the appropriate COM classes. This new class
47 can be used just like the wxWindow class, but will also respond
48 appropriately to the methods and properties of the COM object. If
49 this class, a derived class or a mix-in class has method names
50 that match the COM object's event names, they will be called
51 automatically.
52
53 CoClass -- A COM control class from a module generated by
54 makepy.py from a COM TypeLibrary. Can also accept a
55 CLSID.
56
57 eventClass -- If given, this class will be added to the set of
58 base classes that the new class is drived from. It is
59 good for mix-in classes for catching events.
60
61 eventObj -- If given, this object will be searched for attributes
62 by the new class's __getattr__ method, (like a mix-in
63 object.) This is useful if you want to catch COM
64 callbacks in an existing object, (such as the parent
65 window.)
66
67 """
68
69
70 if type(CoClass) == type(""):
71 # use the CLSID to get the real class
72 CoClass = win32com.client.CLSIDToClass(CoClass)
73
74 # determine the base classes
75 axEventClass = CoClass.default_source
76 baseClasses = [pywin.mfc.activex.Control, wx.Window, CoClass, axEventClass]
77 if eventClass:
78 baseClasses.append(eventClass)
79 baseClasses = tuple(baseClasses)
80
81 # define the class attributes
82 className = 'AXControl_'+CoClass.__name__
83 classDict = { '__init__' : axw__init__,
84 '__getattr__' : axw__getattr__,
85 'axw_OnSize' : axw_OnSize,
86 'axw_OEB' : axw_OEB,
87 '_name' : className,
88 '_eventBase' : axEventClass,
89 '_eventObj' : eventObj,
90 'Cleanup' : axw_Cleanup,
91 }
92
93 # make a new class object
94 import new
95 classObj = new.classobj(className, baseClasses, classDict)
96 return classObj
97
98
99
100
101 # These functions will be used as methods in the new class
102 def axw__init__(self, parent, ID=-1, pos=wx.DefaultPosition, size=wx.DefaultSize, style=0):
103
104 # init base classes
105 pywin.mfc.activex.Control.__init__(self)
106 wx.Window.__init__( self, parent, -1, pos, size, style|wx.NO_FULL_REPAINT_ON_RESIZE)
107 self.this.own(False) # this should be set in wx.Window.__init__ when it calls _setOORInfo, but...
108
109 win32ui.EnableControlContainer()
110 self._eventObj = self._eventObj # move from class to instance
111
112 # create a pythonwin wrapper around this wxWindow
113 handle = self.GetHandle()
114 self._wnd = win32ui.CreateWindowFromHandle(handle)
115
116 # create the control
117 sz = self.GetSize()
118 self.CreateControl(self._name, WS_TABSTOP | WS_VISIBLE,
119 (0, 0, sz.width, sz.height), self._wnd, ID)
120
121 # init the ax events part of the object
122 self._eventBase.__init__(self, self._dispobj_)
123
124 # hook some wx events
125 self.Bind(wx.EVT_SIZE, self.axw_OnSize)
126
127 def axw__getattr__(self, attr):
128 try:
129 return pywin.mfc.activex.Control.__getattr__(self, attr)
130 except AttributeError:
131 try:
132 eo = self.__dict__['_eventObj']
133 return getattr(eo, attr)
134 except AttributeError:
135 raise AttributeError('Attribute not found: %s' % attr)
136
137
138 def axw_OnSize(self, event):
139 sz = self.GetClientSize() # get wxWindow size
140 self.MoveWindow((0, 0, sz.width, sz.height), 1) # move the AXControl
141
142
143 def axw_OEB(self, event):
144 pass
145
146
147 def axw_Cleanup(self):
148 #del self._wnd
149 self.close()
150 pass
151
152
153
154
155