Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Conflict keyboard package #34

Open
ghost opened this issue Mar 21, 2021 · 1 comment
Open

Conflict keyboard package #34

ghost opened this issue Mar 21, 2021 · 1 comment

Comments

@ghost
Copy link

ghost commented Mar 21, 2021

Hello! I try to use pycaw with keyboard package.
https://github.com/boppreh/keyboard

If you run this code and press "4" then error occurs.

from pycaw.pycaw import AudioUtilities
import keyboard
import time

keyboard.add_hotkey('4', AudioUtilities.GetAllSessions)

time.sleep(3600*24*30)
Exception in thread Thread-2:
Traceback (most recent call last):
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\threading.py", line 932, in _bootstrap_inner
    self.run()
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\threading.py", line 870, in run
    self._target(*self._args, **self._kwargs)
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\keyboard\_generic.py", line 58, in process
    if self.pre_process_event(event):
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\keyboard\__init__.py", line 218, in pre_process_event
    callback(event)
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\keyboard\__init__.py", line 649, in <lambda>
    handler = lambda e: (event_type == KEY_DOWN and e.event_type == KEY_UP and e.scan_code in _logically_pressed_keys) or (event_type == e.event_type and callback())
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\pycaw\pycaw.py", line 669, in GetAllSessions
    mgr = AudioUtilities.GetAudioSessionManager()
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\pycaw\pycaw.py", line 657, in GetAudioSessionManager
    speakers = AudioUtilities.GetSpeakers()
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\pycaw\pycaw.py", line 647, in GetSpeakers
    deviceEnumerator = comtypes.CoCreateInstance(
  File "C:\Users\user1\AppData\Local\Programs\Python\Python38-32\lib\site-packages\comtypes\__init__.py", line 1219, in CoCreateInstance
    _ole32.CoCreateInstance(byref(clsid), punkouter, clsctx, byref(iid), byref(p))
  File "_ctypes/callproc.c", line 948, in GetResult
OSError: [WinError -2147221008] CoInitialize has not been called
  • current requirements (pip freeze)

pip freeze
comtypes==1.1.9
enum34==1.1.10
future==0.18.2
keyboard==0.13.5
psutil==5.8.0
pycaw==20181226

  • OS version: Windows 10 Home 2004
  • Python version: 3.8.3
@TurboAnonym
Copy link
Contributor

TurboAnonym commented Apr 24, 2021

Pycaw uses the comtypes library for using COM.
For the communication with windows its necessary to comtypes.CoInitialize() (at the start) and comtypes.CoUninitialize() (in the end) in every thread.
(If you want more information look at COM Apartment threaded.)
If you use pycaw in the main thread of your script CoInitialize() will be called on import of the module and CoUninitialize() on close.
But when you are using multiple threads in your python script (indirectly for example by using the library keyboard) then you must tell the thread to comtypes.CoInitialize() and to comtypes.CoUninitialize()

Following is stated in the comtypes.__init__.py

# COM is initialized automatically for the thread that imports this
# module for the first time. [...]
#
# A shutdown function is registered with atexit, so that
# CoUninitialize is called when Python is shut down.

# We need to have CoUninitialize for multithreaded model where we have
# to initialize and uninitialize COM for every new thread (except main)
# in which we are using COM

so implementing that would look the following (and it works too ;) )

from pycaw.pycaw import AudioUtilities
from comtypes import CoInitialize, CoUninitialize
import keyboard
import time

def audio_stuff():
    CoInitialize()
    sessions = AudioUtilities.GetAllSessions()
    for session in sessions:
        if session.Process:
            print(str(session))
    CoUninitialize()

keyboard.add_hotkey('4', audio_stuff)


time.sleep(3600*24*30)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant