comtypes 1.4.9__zip → 1.4.11__zip
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {comtypes-1.4.9 → comtypes-1.4.11}/CHANGES.txt +41 -0
- {comtypes-1.4.9/comtypes.egg-info → comtypes-1.4.11}/PKG-INFO +4 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/GUID.py +34 -13
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/__init__.py +25 -16
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_comobject.py +92 -39
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_memberspec.py +112 -78
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_meta.py +2 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_post_coinit/_cominterface_meta_patcher.py +3 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_post_coinit/bstr.py +12 -5
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_post_coinit/instancemethod.py +1 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_post_coinit/misc.py +59 -24
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_post_coinit/unknwn.py +30 -25
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_safearray.py +2 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_vtbl.py +52 -55
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/automation.py +19 -14
- comtypes-1.4.11/comtypes/client/__init__.py +42 -0
- comtypes-1.4.11/comtypes/client/_activeobj.py +46 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/client/_code_cache.py +15 -24
- comtypes-1.4.11/comtypes/client/_create.py +147 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/client/_events.py +140 -57
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/client/_generate.py +3 -5
- comtypes-1.4.11/comtypes/client/_managing.py +114 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/client/dynamic.py +2 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/client/lazybind.py +10 -11
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/connectionpoints.py +38 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/errorinfo.py +72 -21
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/git.py +4 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/hints.pyi +15 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/hresult.py +16 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/logutil.py +15 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/messageloop.py +15 -13
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/persist.py +3 -5
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/safearray.py +8 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/server/__init__.py +22 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/server/automation.py +1 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/server/connectionpoints.py +71 -70
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/server/inprocserver.py +14 -8
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/server/localserver.py +28 -16
- comtypes-1.4.11/comtypes/server/register.py +478 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/shelllink.py +13 -7
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/stream.py +7 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/TestComServer.py +6 -7
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/TestDispServer.py +4 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/__init__.py +1 -1
- comtypes-1.4.11/comtypes/test/find_memleak.py +72 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/runtests.py +1 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/setup.py +2 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_BSTR.py +7 -17
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_GUID.py +7 -7
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_QueryService.py +1 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_agilent.py +4 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_basic.py +18 -9
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_clear_cache.py +1 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_client.py +2 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_client_dynamic.py +2 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_client_regenerate_modules.py +2 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_collections.py +7 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_comobject.py +22 -9
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_comserver.py +56 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_dict.py +2 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_dispifc_records.py +1 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_dispifc_safearrays.py +1 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_dyndispatch.py +5 -2
- comtypes-1.4.11/comtypes/test/test_errorinfo.py +115 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_findgendir.py +1 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_getactiveobj.py +4 -4
- comtypes-1.4.11/comtypes/test/test_hresult.py +48 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_ie.py +19 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_ienum.py +2 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_imfattributes.py +13 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_inout_args.py +10 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_midl_safearray_create.py +6 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_monikers.py +23 -9
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_msscript.py +2 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_npsupport.py +4 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_outparam.py +22 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_persist.py +2 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_recordinfo.py +1 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_safearray.py +2 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_sapi.py +4 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_server_register.py +114 -125
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_shelllink.py +2 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_storage.py +12 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_stream.py +16 -5
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_subinterface.py +4 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_typeannotator.py +1 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_typeinfo.py +36 -7
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_urlhistory.py +7 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_variant.py +5 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_w_getopt.py +4 -4
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_word.py +1 -1
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/codegenerator.py +167 -435
- comtypes-1.4.11/comtypes/tools/codegenerator/comments.py +79 -0
- comtypes-1.4.11/comtypes/tools/codegenerator/heads.py +192 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/helpers.py +3 -6
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/namespaces.py +13 -5
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/typeannotator.py +13 -3
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/tlbparser.py +25 -25
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/typedesc.py +3 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/typedesc_base.py +2 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/typeinfo.py +163 -51
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/viewobject.py +2 -4
- {comtypes-1.4.9 → comtypes-1.4.11/comtypes.egg-info}/PKG-INFO +4 -2
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes.egg-info/SOURCES.txt +7 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/pyproject.toml +10 -23
- comtypes-1.4.9/comtypes/client/__init__.py +0 -323
- comtypes-1.4.9/comtypes/server/register.py +0 -419
- comtypes-1.4.9/comtypes/test/find_memleak.py +0 -76
- {comtypes-1.4.9 → comtypes-1.4.11}/LICENSE.txt +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/MANIFEST.in +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/README.md +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_npsupport.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_post_coinit/__init__.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/_tlib_version_checker.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/clear_cache.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/client/_constants.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/patcher.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/server/w_getopt.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/TestComServer.idl +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/TestComServer.tlb +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/TestDispServer.idl +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/TestDispServer.tlb +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/mylib.idl +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/mylib.tlb +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/mytypelib.idl +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_DISPPARAMS.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_avmc.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_casesensitivity.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_createwrappers.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_dispinterface.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_excel.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_jscript.js +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_pump_events.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_server.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_showevents.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_win32com_interop.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/test_wmi.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/test/urlhist.tlb +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/__init__.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/__init__.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/modulenamer.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/tools/codegenerator/packing.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes/util.py +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes.egg-info/dependency_links.txt +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes.egg-info/entry_points.txt +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/comtypes.egg-info/top_level.txt +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/setup.cfg +0 -0
- {comtypes-1.4.9 → comtypes-1.4.11}/setup.py +0 -0
|
@@ -1,28 +1,29 @@
|
|
|
1
1
|
# https://learn.microsoft.com/en-us/windows/win32/api/unknwn/
|
|
2
2
|
|
|
3
3
|
import logging
|
|
4
|
-
import sys
|
|
5
4
|
from ctypes import HRESULT, POINTER, byref, c_ulong, c_void_p
|
|
6
|
-
from typing import TYPE_CHECKING, ClassVar, List, Optional, Type, TypeVar
|
|
5
|
+
from typing import TYPE_CHECKING, Any, ClassVar, List, Optional, Type, TypeVar
|
|
7
6
|
|
|
8
|
-
|
|
7
|
+
import comtypes
|
|
8
|
+
from comtypes import GUID, _CoUninitialize
|
|
9
9
|
from comtypes._memberspec import STDMETHOD, ComMemberGenerator, DispMemberGenerator
|
|
10
10
|
from comtypes._post_coinit import _cominterface_meta_patcher as _meta_patch
|
|
11
11
|
from comtypes._post_coinit.instancemethod import instancemethod
|
|
12
12
|
|
|
13
13
|
if TYPE_CHECKING:
|
|
14
|
+
from typing import Literal
|
|
15
|
+
from typing import Union as _UnionT
|
|
16
|
+
|
|
17
|
+
from comtypes import hints # type: ignore
|
|
14
18
|
from comtypes._memberspec import _ComMemberSpec, _DispMemberSpec
|
|
15
19
|
|
|
16
20
|
logger = logging.getLogger(__name__)
|
|
17
21
|
|
|
18
22
|
|
|
19
23
|
def _shutdown(
|
|
20
|
-
func=
|
|
24
|
+
func=_CoUninitialize,
|
|
21
25
|
_debug=logger.debug,
|
|
22
|
-
|
|
23
|
-
):
|
|
24
|
-
# Make sure no COM pointers stay in exception frames.
|
|
25
|
-
_exc_clear()
|
|
26
|
+
) -> None:
|
|
26
27
|
# Sometimes, CoUninitialize, running at Python shutdown,
|
|
27
28
|
# raises an exception. We suppress this when __debug__ is
|
|
28
29
|
# False.
|
|
@@ -135,7 +136,7 @@ class _cominterface_meta(type):
|
|
|
135
136
|
|
|
136
137
|
return self
|
|
137
138
|
|
|
138
|
-
def __setattr__(self, name, value):
|
|
139
|
+
def __setattr__(self, name: str, value: Any) -> None:
|
|
139
140
|
if name == "_methods_":
|
|
140
141
|
# XXX I'm no longer sure why the code generator generates
|
|
141
142
|
# "_methods_ = []" in the interface definition, and later
|
|
@@ -149,11 +150,11 @@ class _cominterface_meta(type):
|
|
|
149
150
|
self._make_specials()
|
|
150
151
|
type.__setattr__(self, name, value)
|
|
151
152
|
|
|
152
|
-
def _make_specials(self):
|
|
153
|
+
def _make_specials(self) -> None:
|
|
153
154
|
# This call installs methods that forward the Python protocols
|
|
154
155
|
# to COM protocols.
|
|
155
156
|
|
|
156
|
-
def has_name(name):
|
|
157
|
+
def has_name(name: str) -> bool:
|
|
157
158
|
# Determine whether a property or method named 'name'
|
|
158
159
|
# exists
|
|
159
160
|
if self._case_insensitive_:
|
|
@@ -168,7 +169,7 @@ class _cominterface_meta(type):
|
|
|
168
169
|
if has_name("_NewEnum"):
|
|
169
170
|
_meta_patch.iterator(self)
|
|
170
171
|
|
|
171
|
-
def _make_case_insensitive(self):
|
|
172
|
+
def _make_case_insensitive(self) -> None:
|
|
172
173
|
# The __map_case__ dictionary maps lower case names to the
|
|
173
174
|
# names in the original spelling to enable case insensitive
|
|
174
175
|
# method and attribute access.
|
|
@@ -201,7 +202,7 @@ class _cominterface_meta(type):
|
|
|
201
202
|
if self._case_insensitive_:
|
|
202
203
|
self.__map_case__[name.lower()] = name
|
|
203
204
|
|
|
204
|
-
def __get_baseinterface_methodcount(self):
|
|
205
|
+
def __get_baseinterface_methodcount(self) -> int:
|
|
205
206
|
"Return the number of com methods in the base interfaces"
|
|
206
207
|
result = 0
|
|
207
208
|
for itf in self.mro()[1:-1]:
|
|
@@ -220,7 +221,7 @@ class _cominterface_meta(type):
|
|
|
220
221
|
except KeyError:
|
|
221
222
|
raise AttributeError("this class must define an _iid_")
|
|
222
223
|
else:
|
|
223
|
-
com_interface_registry[str(iid)] = self
|
|
224
|
+
comtypes.com_interface_registry[str(iid)] = self # type: ignore
|
|
224
225
|
# create members
|
|
225
226
|
vtbl_offset = self.__get_baseinterface_methodcount()
|
|
226
227
|
member_gen = ComMemberGenerator(self.__name__, vtbl_offset, self._iid_)
|
|
@@ -265,7 +266,10 @@ class _compointer_meta(type(c_void_p), _cominterface_meta):
|
|
|
265
266
|
class _compointer_base(c_void_p, metaclass=_compointer_meta):
|
|
266
267
|
"base class for COM interface pointer classes"
|
|
267
268
|
|
|
268
|
-
|
|
269
|
+
if TYPE_CHECKING:
|
|
270
|
+
__com_interface__: ClassVar[Type["IUnknown"]]
|
|
271
|
+
|
|
272
|
+
def __del__(self, _debug=logger.debug) -> None:
|
|
269
273
|
"Release the COM refcount we own."
|
|
270
274
|
if self:
|
|
271
275
|
# comtypes calls CoUninitialize() when the atexit handlers
|
|
@@ -279,7 +283,7 @@ class _compointer_base(c_void_p, metaclass=_compointer_meta):
|
|
|
279
283
|
_debug("Release %s", self)
|
|
280
284
|
self.Release() # type: ignore
|
|
281
285
|
|
|
282
|
-
def __eq__(self, other):
|
|
286
|
+
def __eq__(self, other) -> bool:
|
|
283
287
|
if not isinstance(other, _compointer_base):
|
|
284
288
|
return False
|
|
285
289
|
# get the value property of the c_void_p baseclass, this is the pointer value
|
|
@@ -287,18 +291,18 @@ class _compointer_base(c_void_p, metaclass=_compointer_meta):
|
|
|
287
291
|
super(_compointer_base, self).value == super(_compointer_base, other).value
|
|
288
292
|
)
|
|
289
293
|
|
|
290
|
-
def __hash__(self):
|
|
294
|
+
def __hash__(self) -> int:
|
|
291
295
|
"""Return the hash value of the pointer."""
|
|
292
296
|
# hash the pointer values
|
|
293
297
|
return hash(super(_compointer_base, self).value)
|
|
294
298
|
|
|
295
299
|
# redefine the .value property; return the object itself.
|
|
296
|
-
def __get_value(self):
|
|
300
|
+
def __get_value(self) -> "hints.Self":
|
|
297
301
|
return self
|
|
298
302
|
|
|
299
303
|
value = property(__get_value, doc="""Return self.""")
|
|
300
304
|
|
|
301
|
-
def __repr__(self):
|
|
305
|
+
def __repr__(self) -> str:
|
|
302
306
|
ptr = super(_compointer_base, self).value
|
|
303
307
|
return f"<{self.__class__.__name__} ptr=0x{ptr or 0:x} at {id(self):x}>"
|
|
304
308
|
|
|
@@ -306,13 +310,14 @@ class _compointer_base(c_void_p, metaclass=_compointer_meta):
|
|
|
306
310
|
# wrapping the same COM interface. This could happen because some interfaces
|
|
307
311
|
# are contained in multiple typelibs.
|
|
308
312
|
#
|
|
309
|
-
# It also allows to pass a
|
|
310
|
-
# expecting a COM interface.
|
|
313
|
+
# It also allows to pass a COMObject instance to an api expecting a COM interface.
|
|
311
314
|
@classmethod
|
|
312
|
-
def from_param(
|
|
315
|
+
def from_param(
|
|
316
|
+
cls, value: "_UnionT[None, Literal[0], hints.Self, IUnknown, hints.COMObject]"
|
|
317
|
+
) -> Any:
|
|
313
318
|
"""Convert 'value' into a COM pointer to the interface.
|
|
314
319
|
|
|
315
|
-
This method accepts a COM pointer, or a CoClass instance
|
|
320
|
+
This method accepts a COM pointer, or a COMObject/CoClass instance
|
|
316
321
|
which is QueryInterface()d."""
|
|
317
322
|
if value is None:
|
|
318
323
|
return None
|
|
@@ -326,9 +331,9 @@ class _compointer_base(c_void_p, metaclass=_compointer_meta):
|
|
|
326
331
|
# Do we need more checks here?
|
|
327
332
|
if cls._iid_ == getattr(value, "_iid_", None):
|
|
328
333
|
return value
|
|
329
|
-
# Accept an
|
|
334
|
+
# Accept an COMObject instance which exposes the interface required.
|
|
330
335
|
try:
|
|
331
|
-
table = value._com_pointers_
|
|
336
|
+
table = value._com_pointers_ # type: ignore
|
|
332
337
|
except AttributeError:
|
|
333
338
|
pass
|
|
334
339
|
else:
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
"""SAFEARRAY api functions, data types, and constants."""
|
|
2
2
|
|
|
3
|
-
from ctypes import
|
|
3
|
+
from ctypes import POINTER, Structure, WinDLL, c_uint, c_ushort, c_void_p
|
|
4
4
|
from ctypes.wintypes import DWORD, LONG, UINT, USHORT
|
|
5
5
|
|
|
6
|
-
from comtypes import
|
|
6
|
+
from comtypes import GUID, HRESULT
|
|
7
7
|
|
|
8
8
|
################################################################
|
|
9
9
|
# if __debug__:
|
|
@@ -17,29 +17,26 @@ from typing import Union as _UnionT
|
|
|
17
17
|
|
|
18
18
|
import comtypes
|
|
19
19
|
from comtypes import GUID, IUnknown, hresult
|
|
20
|
-
from comtypes._memberspec import
|
|
20
|
+
from comtypes._memberspec import (
|
|
21
|
+
DISPATCH_METHOD,
|
|
22
|
+
DISPATCH_PROPERTYGET,
|
|
23
|
+
DISPATCH_PROPERTYPUT,
|
|
24
|
+
DISPATCH_PROPERTYPUTREF,
|
|
25
|
+
_encode_idl,
|
|
26
|
+
)
|
|
21
27
|
from comtypes.errorinfo import ReportError, ReportException
|
|
22
28
|
|
|
23
29
|
if TYPE_CHECKING:
|
|
24
30
|
from ctypes import _FuncPointer
|
|
25
31
|
|
|
26
32
|
from comtypes import hints # type: ignore
|
|
27
|
-
from comtypes._memberspec import
|
|
33
|
+
from comtypes._memberspec import _ComIdlFlags, _DispIdlFlags, _DispMemberSpec
|
|
28
34
|
|
|
29
35
|
logger = logging.getLogger(__name__)
|
|
30
36
|
_debug = logger.debug
|
|
31
37
|
_warning = logger.warning
|
|
32
38
|
_error = logger.error
|
|
33
39
|
|
|
34
|
-
################################################################
|
|
35
|
-
# COM object implementation
|
|
36
|
-
|
|
37
|
-
# so we don't have to import comtypes.automation
|
|
38
|
-
DISPATCH_METHOD = 1
|
|
39
|
-
DISPATCH_PROPERTYGET = 2
|
|
40
|
-
DISPATCH_PROPERTYPUT = 4
|
|
41
|
-
DISPATCH_PROPERTYPUTREF = 8
|
|
42
|
-
|
|
43
40
|
|
|
44
41
|
class E_NotImplemented(Exception):
|
|
45
42
|
"""COM method is not implemented"""
|
|
@@ -84,7 +81,7 @@ def _do_implement(interface_name: str, method_name: str) -> Callable[..., int]:
|
|
|
84
81
|
def catch_errors(
|
|
85
82
|
obj: "hints.COMObject",
|
|
86
83
|
mth: Callable[..., Any],
|
|
87
|
-
paramflags: Optional[Tuple["
|
|
84
|
+
paramflags: Optional[Tuple["hints.ParamFlagType", ...]],
|
|
88
85
|
interface: Type[IUnknown],
|
|
89
86
|
mthname: str,
|
|
90
87
|
) -> Callable[..., Any]:
|
|
@@ -133,7 +130,7 @@ def catch_errors(
|
|
|
133
130
|
def hack(
|
|
134
131
|
inst: "hints.COMObject",
|
|
135
132
|
mth: Callable[..., Any],
|
|
136
|
-
paramflags: Optional[Tuple["
|
|
133
|
+
paramflags: Optional[Tuple["hints.ParamFlagType", ...]],
|
|
137
134
|
interface: Type[IUnknown],
|
|
138
135
|
mthname: str,
|
|
139
136
|
) -> Callable[..., Any]:
|
|
@@ -241,8 +238,8 @@ class _MethodFinder(object):
|
|
|
241
238
|
self,
|
|
242
239
|
interface: Type[IUnknown],
|
|
243
240
|
mthname: str,
|
|
244
|
-
paramflags: Optional[Tuple["
|
|
245
|
-
idlflags:
|
|
241
|
+
paramflags: Optional[Tuple["hints.ParamFlagType", ...]],
|
|
242
|
+
idlflags: _UnionT["_ComIdlFlags", "_DispIdlFlags"],
|
|
246
243
|
) -> Callable[..., Any]:
|
|
247
244
|
mth = self.find_impl(interface, mthname, paramflags, idlflags)
|
|
248
245
|
if mth is None:
|
|
@@ -263,8 +260,8 @@ class _MethodFinder(object):
|
|
|
263
260
|
self,
|
|
264
261
|
interface: Type[IUnknown],
|
|
265
262
|
mthname: str,
|
|
266
|
-
paramflags: Optional[Tuple["
|
|
267
|
-
idlflags:
|
|
263
|
+
paramflags: Optional[Tuple["hints.ParamFlagType", ...]],
|
|
264
|
+
idlflags: _UnionT["_ComIdlFlags", "_DispIdlFlags"],
|
|
268
265
|
) -> Optional[Callable[..., Any]]:
|
|
269
266
|
fq_name = f"{interface.__name__}_{mthname}"
|
|
270
267
|
if interface._case_insensitive_:
|
|
@@ -340,25 +337,29 @@ def create_vtbl_mapping(
|
|
|
340
337
|
methods: List[Callable[..., Any]] = [] # method implementations
|
|
341
338
|
fields: List[Tuple[str, Type["_FuncPointer"]]] = [] # virtual function table
|
|
342
339
|
iids: List[GUID] = [] # interface identifiers.
|
|
343
|
-
|
|
344
|
-
# virtual function table, and leave out the 'object' base class.
|
|
345
|
-
for interface in itf.__mro__[-2::-1]:
|
|
340
|
+
for interface in _walk_itf_bases(itf):
|
|
346
341
|
iids.append(interface._iid_)
|
|
347
342
|
for m in interface._methods_:
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
mth = finder.get_impl(interface, mthname, paramflags, idlflags)
|
|
343
|
+
proto = WINFUNCTYPE(m.restype, c_void_p, *m.argtypes)
|
|
344
|
+
fields.append((m.name, proto))
|
|
345
|
+
mth = finder.get_impl(interface, m.name, m.paramflags, m.idlflags)
|
|
352
346
|
methods.append(proto(mth))
|
|
353
347
|
Vtbl = _create_vtbl_type(tuple(fields), itf)
|
|
354
348
|
vtbl = Vtbl(*methods)
|
|
355
349
|
return (iids, vtbl)
|
|
356
350
|
|
|
357
351
|
|
|
352
|
+
def _walk_itf_bases(itf: Type[IUnknown]) -> Iterator[Type[IUnknown]]:
|
|
353
|
+
"""Iterates over interface inheritance in reverse order to build the
|
|
354
|
+
virtual function table, and leave out the 'object' base class.
|
|
355
|
+
"""
|
|
356
|
+
yield from itf.__mro__[-2::-1]
|
|
357
|
+
|
|
358
|
+
|
|
358
359
|
def create_dispimpl(
|
|
359
360
|
itf: Type[IUnknown], finder: _MethodFinder
|
|
360
|
-
) -> Dict[Tuple[
|
|
361
|
-
dispimpl: Dict[Tuple[
|
|
361
|
+
) -> Dict[Tuple[comtypes.dispid, int], Callable[..., Any]]:
|
|
362
|
+
dispimpl: Dict[Tuple[comtypes.dispid, int], Callable[..., Any]] = {}
|
|
362
363
|
for m in itf._disp_methods_:
|
|
363
364
|
#################
|
|
364
365
|
# What we have:
|
|
@@ -374,13 +375,6 @@ def create_dispimpl(
|
|
|
374
375
|
#
|
|
375
376
|
# paramflags must be a sequence
|
|
376
377
|
# of (F_IN|F_OUT|F_RETVAL, paramname[, default-value]) tuples
|
|
377
|
-
#
|
|
378
|
-
# comtypes has this function which helps:
|
|
379
|
-
# def _encode_idl(names):
|
|
380
|
-
# # convert to F_xxx and sum up "in", "out",
|
|
381
|
-
# # "retval" values found in _PARAMFLAGS, ignoring
|
|
382
|
-
# # other stuff.
|
|
383
|
-
# return sum([_PARAMFLAGS.get(n, 0) for n in names])
|
|
384
378
|
#################
|
|
385
379
|
|
|
386
380
|
if m.what == "DISPMETHOD":
|
|
@@ -392,37 +386,40 @@ def create_dispimpl(
|
|
|
392
386
|
|
|
393
387
|
def _make_dispmthentry(
|
|
394
388
|
itf: Type[IUnknown], finder: _MethodFinder, m: "_DispMemberSpec"
|
|
395
|
-
) -> Iterator[Tuple[Tuple[
|
|
396
|
-
|
|
397
|
-
if "propget" in idlflags:
|
|
389
|
+
) -> Iterator[Tuple[Tuple[comtypes.dispid, int], Callable[..., Any]]]:
|
|
390
|
+
if "propget" in m.idlflags:
|
|
398
391
|
invkind = DISPATCH_PROPERTYGET
|
|
399
|
-
mthname = f"_get_{
|
|
400
|
-
elif "propput" in idlflags:
|
|
392
|
+
mthname = f"_get_{m.name}"
|
|
393
|
+
elif "propput" in m.idlflags:
|
|
401
394
|
invkind = DISPATCH_PROPERTYPUT
|
|
402
|
-
mthname = f"_set_{
|
|
403
|
-
elif "propputref" in idlflags:
|
|
395
|
+
mthname = f"_set_{m.name}"
|
|
396
|
+
elif "propputref" in m.idlflags:
|
|
404
397
|
invkind = DISPATCH_PROPERTYPUTREF
|
|
405
|
-
mthname = f"_setref_{
|
|
398
|
+
mthname = f"_setref_{m.name}"
|
|
406
399
|
else:
|
|
407
400
|
invkind = DISPATCH_METHOD
|
|
408
|
-
if restype:
|
|
409
|
-
argspec = argspec + ((["out"], restype, ""),)
|
|
410
|
-
|
|
401
|
+
if m.restype:
|
|
402
|
+
argspec = m.argspec + ((["out"], m.restype, ""),)
|
|
403
|
+
else:
|
|
404
|
+
argspec = m.argspec
|
|
405
|
+
mthname = m.name
|
|
406
|
+
yield from _make_dispentry(finder, itf, mthname, m.idlflags, argspec, invkind)
|
|
411
407
|
|
|
412
408
|
|
|
413
409
|
def _make_disppropentry(
|
|
414
410
|
itf: Type[IUnknown], finder: _MethodFinder, m: "_DispMemberSpec"
|
|
415
|
-
) -> Iterator[Tuple[Tuple[
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
411
|
+
) -> Iterator[Tuple[Tuple[comtypes.dispid, int], Callable[..., Any]]]:
|
|
412
|
+
if m.restype:
|
|
413
|
+
# DISPPROPERTY have implicit "out"
|
|
414
|
+
argspec = m.argspec + ((["out"], m.restype, ""),)
|
|
415
|
+
else:
|
|
416
|
+
argspec = m.argspec
|
|
420
417
|
yield from _make_dispentry(
|
|
421
|
-
finder, itf, f"_get_{
|
|
418
|
+
finder, itf, f"_get_{m.name}", m.idlflags, argspec, DISPATCH_PROPERTYGET
|
|
422
419
|
)
|
|
423
|
-
if "readonly" not in idlflags:
|
|
420
|
+
if "readonly" not in m.idlflags:
|
|
424
421
|
yield from _make_dispentry(
|
|
425
|
-
finder, itf, f"_set_{
|
|
422
|
+
finder, itf, f"_set_{m.name}", m.idlflags, argspec, DISPATCH_PROPERTYPUT
|
|
426
423
|
)
|
|
427
424
|
# Add DISPATCH_PROPERTYPUTREF also?
|
|
428
425
|
|
|
@@ -431,10 +428,10 @@ def _make_dispentry(
|
|
|
431
428
|
finder: _MethodFinder,
|
|
432
429
|
interface: Type[IUnknown],
|
|
433
430
|
mthname: str,
|
|
434
|
-
idlflags:
|
|
435
|
-
argspec: Tuple["
|
|
431
|
+
idlflags: "_DispIdlFlags",
|
|
432
|
+
argspec: Tuple["hints.ArgSpecElmType", ...],
|
|
436
433
|
invkind: int,
|
|
437
|
-
) -> Iterator[Tuple[Tuple[
|
|
434
|
+
) -> Iterator[Tuple[Tuple[comtypes.dispid, int], Callable[..., Any]]]:
|
|
438
435
|
# We build a _dispmap_ entry now that maps invkind and dispid to
|
|
439
436
|
# implementations that the finder finds; IDispatch_Invoke will later call it.
|
|
440
437
|
paramflags = tuple(((_encode_idl(x[0]), x[1]) + tuple(x[3:])) for x in argspec)
|
|
@@ -11,12 +11,16 @@ from typing import TYPE_CHECKING, Any, ClassVar, Dict, List, Optional, Type
|
|
|
11
11
|
|
|
12
12
|
import comtypes
|
|
13
13
|
import comtypes.patcher
|
|
14
|
-
from comtypes import BSTR, COMMETHOD, GUID, IID, STDMETHOD, IUnknown,
|
|
14
|
+
from comtypes import BSTR, COMMETHOD, GUID, IID, STDMETHOD, IUnknown, _safearray
|
|
15
15
|
from comtypes import hresult as hresult
|
|
16
|
+
from comtypes._memberspec import DISPATCH_METHOD as DISPATCH_METHOD
|
|
17
|
+
from comtypes._memberspec import DISPATCH_PROPERTYGET as DISPATCH_PROPERTYGET
|
|
18
|
+
from comtypes._memberspec import DISPATCH_PROPERTYPUT as DISPATCH_PROPERTYPUT
|
|
19
|
+
from comtypes._memberspec import DISPATCH_PROPERTYPUTREF as DISPATCH_PROPERTYPUTREF
|
|
16
20
|
from comtypes.safearray import _midlSAFEARRAY
|
|
17
21
|
|
|
18
22
|
if TYPE_CHECKING:
|
|
19
|
-
from ctypes import _CArgObject
|
|
23
|
+
from ctypes import _CArgObject, _CDataType
|
|
20
24
|
|
|
21
25
|
from comtypes import hints # type: ignore
|
|
22
26
|
from comtypes._memberspec import _DispMemberSpec
|
|
@@ -30,11 +34,6 @@ SCODE = LONG
|
|
|
30
34
|
|
|
31
35
|
VARTYPE = c_ushort
|
|
32
36
|
|
|
33
|
-
DISPATCH_METHOD = 1
|
|
34
|
-
DISPATCH_PROPERTYGET = 2
|
|
35
|
-
DISPATCH_PROPERTYPUT = 4
|
|
36
|
-
DISPATCH_PROPERTYPUTREF = 8
|
|
37
|
-
|
|
38
37
|
tagINVOKEKIND = c_int
|
|
39
38
|
INVOKE_FUNC = DISPATCH_METHOD
|
|
40
39
|
INVOKE_PROPERTYGET = DISPATCH_PROPERTYGET
|
|
@@ -575,23 +574,29 @@ class tagVARIANT(Structure):
|
|
|
575
574
|
VARIANT = tagVARIANT
|
|
576
575
|
VARIANTARG = VARIANT
|
|
577
576
|
|
|
577
|
+
_oleaut32_nohresult = WinDLL("oleaut32")
|
|
578
|
+
|
|
579
|
+
_SysAllocStringLen = _oleaut32_nohresult.SysAllocStringLen
|
|
580
|
+
_SysAllocStringLen.argtypes = c_wchar_p, c_uint
|
|
581
|
+
_SysAllocStringLen.restype = c_void_p
|
|
582
|
+
|
|
578
583
|
_oleaut32 = OleDLL("oleaut32")
|
|
579
584
|
|
|
580
585
|
_VariantChangeType = _oleaut32.VariantChangeType
|
|
581
586
|
_VariantChangeType.argtypes = (POINTER(VARIANT), POINTER(VARIANT), c_ushort, VARTYPE)
|
|
587
|
+
_VariantChangeType.restype = HRESULT
|
|
582
588
|
|
|
583
589
|
_VariantClear = _oleaut32.VariantClear
|
|
584
590
|
_VariantClear.argtypes = (POINTER(VARIANT),)
|
|
585
|
-
|
|
586
|
-
_SysAllocStringLen = windll.oleaut32.SysAllocStringLen
|
|
587
|
-
_SysAllocStringLen.argtypes = c_wchar_p, c_uint
|
|
588
|
-
_SysAllocStringLen.restype = c_void_p
|
|
591
|
+
_VariantClear.restype = HRESULT
|
|
589
592
|
|
|
590
593
|
_VariantCopy = _oleaut32.VariantCopy
|
|
591
594
|
_VariantCopy.argtypes = POINTER(VARIANT), POINTER(VARIANT)
|
|
595
|
+
_VariantCopy.restype = HRESULT
|
|
592
596
|
|
|
593
597
|
_VariantCopyInd = _oleaut32.VariantCopyInd
|
|
594
598
|
_VariantCopyInd.argtypes = POINTER(VARIANT), POINTER(VARIANT)
|
|
599
|
+
_VariantCopyInd.restype = HRESULT
|
|
595
600
|
|
|
596
601
|
# some commonly used VARIANT instances
|
|
597
602
|
VARIANT.null = VARIANT(None)
|
|
@@ -872,7 +877,7 @@ class IDispatch(IUnknown):
|
|
|
872
877
|
# objects referred to by rgvarg[ ] or placed in *pVarResult.
|
|
873
878
|
#
|
|
874
879
|
# For comtypes this is handled in DISPPARAMS.__del__ and VARIANT.__del__.
|
|
875
|
-
_invkind = kw.pop("_invkind",
|
|
880
|
+
_invkind = kw.pop("_invkind", DISPATCH_METHOD)
|
|
876
881
|
_lcid = kw.pop("_lcid", 0)
|
|
877
882
|
if kw:
|
|
878
883
|
raise ValueError("named parameters not yet implemented")
|
|
@@ -943,7 +948,7 @@ _arraycode_to_vartype = {
|
|
|
943
948
|
"B": VT_UI1,
|
|
944
949
|
}
|
|
945
950
|
|
|
946
|
-
_ctype_to_vartype: Dict[Type[
|
|
951
|
+
_ctype_to_vartype: Dict[Type["_CDataType"], int] = {
|
|
947
952
|
c_byte: VT_I1,
|
|
948
953
|
c_ubyte: VT_UI1,
|
|
949
954
|
c_short: VT_I2,
|
|
@@ -980,7 +985,7 @@ _ctype_to_vartype: Dict[Type[_CData], int] = {
|
|
|
980
985
|
# POINTER(IDispatch): VT_DISPATCH,
|
|
981
986
|
}
|
|
982
987
|
|
|
983
|
-
_vartype_to_ctype: Dict[int, Type[
|
|
988
|
+
_vartype_to_ctype: Dict[int, Type["_CDataType"]] = {}
|
|
984
989
|
for c, v in _ctype_to_vartype.items():
|
|
985
990
|
_vartype_to_ctype[v] = c
|
|
986
991
|
_vartype_to_ctype[VT_INT] = _vartype_to_ctype[VT_I4]
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
"""comtypes.client - High level client level COM support package."""
|
|
2
|
+
|
|
3
|
+
import ctypes
|
|
4
|
+
import logging
|
|
5
|
+
|
|
6
|
+
from comtypes import automation
|
|
7
|
+
from comtypes.client import dynamic, lazybind # noqa
|
|
8
|
+
from comtypes.client._code_cache import _find_gen_dir
|
|
9
|
+
from comtypes.client._constants import Constants # noqa
|
|
10
|
+
from comtypes.client._events import GetEvents, PumpEvents, ShowEvents
|
|
11
|
+
from comtypes.client._generate import GetModule
|
|
12
|
+
from comtypes.client._managing import GetBestInterface, _manage, wrap_outparam # noqa
|
|
13
|
+
from comtypes.hresult import * # noqa
|
|
14
|
+
|
|
15
|
+
gen_dir = _find_gen_dir()
|
|
16
|
+
import comtypes.gen # noqa
|
|
17
|
+
|
|
18
|
+
### for testing
|
|
19
|
+
##gen_dir = None
|
|
20
|
+
|
|
21
|
+
logger = logging.getLogger(__name__)
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
# backwards compatibility:
|
|
25
|
+
wrap = GetBestInterface
|
|
26
|
+
|
|
27
|
+
# Should we do this for POINTER(IUnknown) also?
|
|
28
|
+
ctypes.POINTER(automation.IDispatch).__ctypes_from_outparam__ = wrap_outparam # type: ignore
|
|
29
|
+
|
|
30
|
+
from comtypes.client._activeobj import GetActiveObject
|
|
31
|
+
from comtypes.client._create import (
|
|
32
|
+
CoGetObject,
|
|
33
|
+
CreateObject,
|
|
34
|
+
GetClassObject,
|
|
35
|
+
)
|
|
36
|
+
|
|
37
|
+
# fmt: off
|
|
38
|
+
__all__ = [
|
|
39
|
+
"CreateObject", "GetActiveObject", "CoGetObject", "GetEvents",
|
|
40
|
+
"ShowEvents", "PumpEvents", "GetModule", "GetClassObject",
|
|
41
|
+
]
|
|
42
|
+
# fmt: on
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
from typing import Any, Optional, Type, TypeVar, overload
|
|
2
|
+
from typing import Union as _UnionT
|
|
3
|
+
|
|
4
|
+
import comtypes
|
|
5
|
+
import comtypes.client.dynamic
|
|
6
|
+
from comtypes import GUID, CoClass, IUnknown, automation
|
|
7
|
+
from comtypes.client._managing import _manage
|
|
8
|
+
|
|
9
|
+
_T_IUnknown = TypeVar("_T_IUnknown", bound=IUnknown)
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
################################################################
|
|
13
|
+
#
|
|
14
|
+
# Object creation
|
|
15
|
+
#
|
|
16
|
+
@overload
|
|
17
|
+
def GetActiveObject(progid: _UnionT[str, Type[CoClass], GUID]) -> Any: ...
|
|
18
|
+
@overload
|
|
19
|
+
def GetActiveObject(
|
|
20
|
+
progid: _UnionT[str, Type[CoClass], GUID], interface: Type[_T_IUnknown]
|
|
21
|
+
) -> _T_IUnknown: ...
|
|
22
|
+
def GetActiveObject(
|
|
23
|
+
progid: _UnionT[str, Type[CoClass], GUID],
|
|
24
|
+
interface: Optional[Type[IUnknown]] = None,
|
|
25
|
+
dynamic: bool = False,
|
|
26
|
+
) -> Any:
|
|
27
|
+
"""Return a pointer to a running COM object that has been
|
|
28
|
+
registered with COM.
|
|
29
|
+
|
|
30
|
+
'progid' may be a string like "Excel.Application",
|
|
31
|
+
a string specifying a clsid, a GUID instance, or an object with
|
|
32
|
+
a _clsid_ attribute which should be any of the above.
|
|
33
|
+
'interface' allows to force a certain interface.
|
|
34
|
+
'dynamic=True' will return a dynamic dispatch object.
|
|
35
|
+
"""
|
|
36
|
+
clsid = GUID.from_progid(progid)
|
|
37
|
+
if dynamic:
|
|
38
|
+
if interface is not None:
|
|
39
|
+
raise ValueError("interface and dynamic are mutually exclusive")
|
|
40
|
+
interface = automation.IDispatch
|
|
41
|
+
elif interface is None:
|
|
42
|
+
interface = getattr(progid, "_com_interfaces_", [None])[0]
|
|
43
|
+
obj = comtypes.GetActiveObject(clsid, interface=interface)
|
|
44
|
+
if dynamic:
|
|
45
|
+
return comtypes.client.dynamic.Dispatch(obj)
|
|
46
|
+
return _manage(obj, clsid, interface=interface)
|
|
@@ -5,8 +5,15 @@ comtypes.gen package and returns a directory where generated code can
|
|
|
5
5
|
be written to.
|
|
6
6
|
"""
|
|
7
7
|
|
|
8
|
-
import ctypes
|
|
9
|
-
|
|
8
|
+
import ctypes
|
|
9
|
+
import logging
|
|
10
|
+
import os
|
|
11
|
+
import sys
|
|
12
|
+
import tempfile
|
|
13
|
+
import types
|
|
14
|
+
from ctypes.wintypes import BOOL, HWND, LPWSTR, MAX_PATH
|
|
15
|
+
|
|
16
|
+
from comtypes import typeinfo
|
|
10
17
|
|
|
11
18
|
logger = logging.getLogger(__name__)
|
|
12
19
|
|
|
@@ -49,14 +56,14 @@ def _find_gen_dir():
|
|
|
49
56
|
# where generated modules are placed.
|
|
50
57
|
ftype = getattr(sys, "frozen", None)
|
|
51
58
|
pymaj, pymin = sys.version_info[:2]
|
|
52
|
-
if ftype
|
|
59
|
+
if ftype is None:
|
|
53
60
|
# Python script
|
|
54
61
|
subdir = rf"Python\Python{pymaj:d}{pymin:d}\comtypes_cache"
|
|
55
62
|
basedir = _get_appdata_dir()
|
|
56
63
|
|
|
57
64
|
elif ftype == "dll":
|
|
58
65
|
# dll created with py2exe
|
|
59
|
-
path =
|
|
66
|
+
path = typeinfo.GetModuleFileName(sys.frozendllhandle, MAX_PATH)
|
|
60
67
|
base = os.path.splitext(os.path.basename(path))[0]
|
|
61
68
|
subdir = rf"comtypes_cache\{base}-{pymaj:d}{pymin:d}"
|
|
62
69
|
basedir = tempfile.gettempdir()
|
|
@@ -79,19 +86,12 @@ def _find_gen_dir():
|
|
|
79
86
|
|
|
80
87
|
################################################################
|
|
81
88
|
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
SHGetSpecialFolderPath.argtypes = [
|
|
85
|
-
|
|
86
|
-
ctypes.c_wchar_p,
|
|
87
|
-
ctypes.c_int,
|
|
88
|
-
ctypes.c_int,
|
|
89
|
-
]
|
|
90
|
-
GetModuleFileName.restype = ctypes.c_ulong
|
|
91
|
-
GetModuleFileName.argtypes = [wintypes.HMODULE, ctypes.c_wchar_p, ctypes.c_ulong]
|
|
89
|
+
_shell32 = ctypes.OleDLL("shell32.dll")
|
|
90
|
+
SHGetSpecialFolderPath = _shell32.SHGetSpecialFolderPathW
|
|
91
|
+
SHGetSpecialFolderPath.argtypes = [HWND, LPWSTR, ctypes.c_int, BOOL]
|
|
92
|
+
SHGetSpecialFolderPath.restype = BOOL
|
|
92
93
|
|
|
93
94
|
CSIDL_APPDATA = 26
|
|
94
|
-
MAX_PATH = 260
|
|
95
95
|
|
|
96
96
|
|
|
97
97
|
def _create_comtypes_gen_package():
|
|
@@ -132,15 +132,6 @@ def _is_writeable(path):
|
|
|
132
132
|
return os.access(path[0], os.W_OK)
|
|
133
133
|
|
|
134
134
|
|
|
135
|
-
def _get_module_filename(hmodule):
|
|
136
|
-
"""Call the Windows GetModuleFileName function which determines
|
|
137
|
-
the path from a module handle."""
|
|
138
|
-
path = ctypes.create_unicode_buffer(MAX_PATH)
|
|
139
|
-
if GetModuleFileName(hmodule, path, MAX_PATH):
|
|
140
|
-
return path.value
|
|
141
|
-
raise ctypes.WinError()
|
|
142
|
-
|
|
143
|
-
|
|
144
135
|
def _get_appdata_dir():
|
|
145
136
|
"""Return the 'file system directory that serves as a common
|
|
146
137
|
repository for application-specific data' - CSIDL_APPDATA"""
|