4 #include "devicemanager.h"
20 static inline void GetDeviceProc(T
**func
, ALCdevice
*device
, const char *name
)
21 { *func
= reinterpret_cast<T
*>(alcGetProcAddress(device
, name
)); }
24 ALCboolean (ALC_APIENTRY
*DeviceManagerImpl::SetThreadContext
)(ALCcontext
*);
26 DeviceManager
DeviceManager::get()
27 { return DeviceManager(&DeviceManagerImpl::get()); }
28 DeviceManagerImpl
&DeviceManagerImpl::get()
30 static DeviceManagerImpl singleton
;
35 DeviceManagerImpl::DeviceManagerImpl()
37 if(alcIsExtensionPresent(0, "ALC_EXT_thread_local_context"))
38 GetDeviceProc(&SetThreadContext
, 0, "alcSetThreadContext");
41 DeviceManagerImpl::~DeviceManagerImpl()
46 bool DeviceManager::queryExtension(const String
&name
) const
47 { return pImpl
->queryExtension(name
.c_str()); }
48 DECL_THUNK1(bool, DeviceManager
, queryExtension
, const, const char*)
49 bool DeviceManagerImpl::queryExtension(const char *name
) const
51 return alcIsExtensionPresent(nullptr, name
);
54 DECL_THUNK1(Vector
<String
>, DeviceManager
, enumerate
, const, DeviceEnumeration
)
55 Vector
<String
> DeviceManagerImpl::enumerate(DeviceEnumeration type
) const
58 if(type
== DeviceEnumeration::Full
&& !alcIsExtensionPresent(nullptr, "ALC_ENUMERATE_ALL_EXT"))
59 type
= DeviceEnumeration::Basic
;
60 const ALCchar
*names
= alcGetString(nullptr, (ALenum
)type
);
61 while(names
&& *names
)
63 list
.emplace_back(names
);
64 names
+= strlen(names
)+1;
69 DECL_THUNK1(String
, DeviceManager
, defaultDeviceName
, const, DefaultDeviceType
)
70 String
DeviceManagerImpl::defaultDeviceName(DefaultDeviceType type
) const
72 if(type
== DefaultDeviceType::Full
&& !alcIsExtensionPresent(nullptr, "ALC_ENUMERATE_ALL_EXT"))
73 type
= DefaultDeviceType::Basic
;
74 const ALCchar
*name
= alcGetString(nullptr, (ALenum
)type
);
75 return name
? String(name
) : String();
79 Device
DeviceManager::openPlayback(const String
&name
)
80 { return pImpl
->openPlayback(name
.c_str()); }
81 DECL_THUNK1(Device
, DeviceManager
, openPlayback
,, const char*)
82 Device
DeviceManagerImpl::openPlayback(const char *name
)
84 ALCdevice
*dev
= alcOpenDevice(name
);
88 mDevices
.emplace_back(MakeUnique
<DeviceImpl
>(dev
));
89 return Device(mDevices
.back().get());
97 throw std::runtime_error("Failed to open default device");
98 throw std::runtime_error(StringView("Failed to open device \"")+name
+"\"");
101 Device
DeviceManager::openPlayback(const String
&name
, const std::nothrow_t
&nt
) noexcept
102 { return pImpl
->openPlayback(name
.c_str(), nt
); }
103 Device
DeviceManager::openPlayback(const std::nothrow_t
&) noexcept
104 { return pImpl
->openPlayback(nullptr, std::nothrow
); }
105 DECL_THUNK2(Device
, DeviceManager
, openPlayback
, noexcept
, const char*, const std::nothrow_t
&)
106 Device
DeviceManagerImpl::openPlayback(const char *name
, const std::nothrow_t
&) noexcept
116 void DeviceManagerImpl::removeDevice(DeviceImpl
*dev
)
118 auto iter
= std::find_if(mDevices
.begin(), mDevices
.end(),
119 [dev
](const UniquePtr
<DeviceImpl
> &entry
) -> bool
120 { return entry
.get() == dev
; }
122 if(iter
!= mDevices
.end()) mDevices
.erase(iter
);