juce-framework / JUCE

JUCE is an open-source cross-platform C++ application framework for desktop and mobile applications, including VST, VST3, AU, AUv3, LV2 and AAX audio plug-ins.
https://juce.com
Other
6.35k stars 1.68k forks source link

WinRT output devices from loopMIDI wrong output names #958

Open benkuper opened 2 years ago

benkuper commented 2 years ago

The issue has already been discussed here : https://forum.juce.com/t/winrt-midi-output-wrong-device-names/43301 but I figured there may be better activity here...

Yes, we know that Microsoft won't do anything for that, so I guess it's a matter of fixing this ourselves. Many softwares are successfully using WinRT and displaying good names. I've tried contacting and asking them how, but no answers yet. Resolume is using JUCE and has good display names, though I don't know if they use WinRT.

It may be an issue specific to loopMidi, but loopMidi is widely used and a lot of users see this issue as a bug from the software itself, they don't really care or even have a way to know where it comes from.

I think there is some possible workaround to do by detecting a wrong name / deviceInfo in juce_Win32_Midi addDevice function; Especially since loopMidi has a specific, unique path, and only the output is badly named, there is a way to grab the name from the input I think. I could try and do it but I'm sure it won't fit JUCE's practices. So if anyone has info or will to get on that, it would help a lot of developers AND users.

Thank you very much

benkuper commented 2 years ago

Following the research, the non-WinRT version seems to detect BLE devices, but can't open them... Is there maybe something to do by just handling opening BLE devices with the WINRT part, and keep the rest with the WinMM stack ?

afestini commented 1 month ago

Since the issue is still open years later, I guess I'll post it here too.

The name isn't wrong. The port name is exactly what is returned. You want the device name. If you examine the device in your device manager, you can see the hierarchy of "device container" including one or more "devices", which contain one or more "ports".

You have to get the container id from port properties, create the info for that and you got the top level name. Assuming that port is the DeviceInformation of the port (from a watcher or enumerating)

const auto container_id = port.Properties().Lookup(L"System.Devices.ContainerId").as<winrt::guid>();
const auto device = DeviceInformation::CreateFromIdAsync(to_hstring(container_id), {}, DeviceInformationKind::DeviceContainer).get();
const auto device_name = to_string(device.Name());