winapi - Python ctypes: Prototype with LPCSTR [out] parameter -
i'm getting ctypes module , i'm trying call user32 function getwindowtext hwnd handle received using findwindow. time though wanted process step further , use function prototype instead of calling function ctypes.windll.user32.getwindowtext. although i´m having problems declaring lpstring arguement output parameter.
my first attempt looked way:
getwindowtext = cfunc("getwindowtexta",windll.user32,c_int, ("hwnd",hwnd,1), ("lpstring",lpcstr,2), ("nmaxcount",c_int,1) ) (cfunc little wrapper found here)
this prototype yields following exception called:
chars,name = user32.getwindowtext(handle,255) typeerror: c_char_p 'out' parameter must passed default value i thought output variables must pointer(...) type, changed definition to:
getwindowtext = cfunc("getwindowtexta",windll.user32,c_int, ("hwnd",hwnd,1), ("lpstring",pointer(c_char),2), ("nmaxcount",c_int,1) ) but yields exception too:
chars,name = user32.getwindowtext(handle,255) ctypes.argumenterror: argument 2: <type 'exceptions.typeerror'>: wrong type i hope knows how call getwindowtext function correctly using ctypes prototyping.
edit:
through further research work, @ least somehow. first issue fixed usage of cfunc() had wrong calling specifiers. defined exact copy of function , named winfunc() , replaced return cfunctype(result, *atypes)((name, dll), tuple(aflags)) return winfunctype(result, *atypes)((name, dll), tuple(aflags)).
then inspected prototyping further. seems if pass ("someparameter",pointer(atype),2) winfunctype create atype object on call , passes pointer object function. in returned tuple can access atype object. brings problem. cstring array of chars; 1 needs tell ctypes create c_char array. means like:
getwindowtext = winfunc("getwindowtexta",windll.user32,c_int, ("hwnd",hwnd,1), ("lpstring",pointer(c_char*255),2), ("nmaxcount",c_int,1) ) works fine. unfortunately, ctypes pass pointer cstring 255 chars long ignoring size specified nmaxcount.
in opinion, think theres no way 1 function work dynamically sized cstring defined output parameter. possibility seems going without output parameter feature , defining lpcstr input parameter. callee needs create buffer own ctypes.create_string_buffer() , pass function (just in c).
you have create string buffer out parameters. can wrap function make transparent:
# python3 ctypes import * _getwindowtext = windll('user32').getwindowtextw _getwindowtext.argtypes = [c_void_p,c_wchar_p,c_int] _getwindowtext.restype = c_int def getwindowtext(h): b = create_unicode_buffer(255) _getwindowtext(h,b,255) return b.value findwindow = windll('user32').findwindoww findwindow.argtypes = [c_wchar_p,c_wchar_p] findwindow.restype = c_void_p h = findwindow(none,'untitled - notepad') print(getwindowtext(h)) or in case can use pywin32:
import win32gui h = win32gui.findwindow(none,'untitled - notepad') print(win32gui.getwindowtext(h))
Comments
Post a Comment