macOS:是否有命令行或Objective-C/Swift API用于更改Audio Midi Setup.app中的设置?

macOS:是否有命令行或Objective-C/Swift API用于更改Audio Midi Setup.app中的设置?,macos,audio,core-audio,Macos,Audio,Core Audio,我希望通过编程方式更改macOS系统的音频MIDI设置,通过GUI使用内置的音频MIDI设置应用程序进行配置。具体来说,我希望能够切换多输出设备中包括哪些音频输出设备 有什么方法可以做到这一点吗?我将接受命令行解决方案,使用Objective-C或Swift之类的编译解决方案,或者其他任何东西;只要我能以编程方式触发它。是的,有 在Mac上有一个叫做核心音频的框架。AudioHardware.h中的接口是HAL硬件抽象层的接口。这是负责管理Mac上与USB设备接口的所有低级音频的部分 我相信框架

我希望通过编程方式更改macOS系统的音频MIDI设置,通过GUI使用内置的音频MIDI设置应用程序进行配置。具体来说,我希望能够切换多输出设备中包括哪些音频输出设备

有什么方法可以做到这一点吗?我将接受命令行解决方案,使用Objective-C或Swift之类的编译解决方案,或者其他任何东西;只要我能以编程方式触发它。

是的,有

在Mac上有一个叫做核心音频的框架。AudioHardware.h中的接口是HAL硬件抽象层的接口。这是负责管理Mac上与USB设备接口的所有低级音频的部分

我相信框架是用C++编写的,虽然框架的接口是C兼容的。这使得框架通过桥接头在Objective-C和Swift中可用

要开始使用这个框架,您应该开始阅读CoreAudio.framework中的AudioHardware.h。您可以通过按CMD+SHIFT+O并键入AudioHardware.h从XCode中找到此文件

要为您提供一个示例作为starter,它创建了一个没有子设备的新聚合:

// Create a CFDictionary to hold all the options associated with the to-be-created aggregate
CFMutableDictionaryRef params = CFDictionaryCreateMutable(kCFAllocatorDefault, 10, NULL, NULL);

// Define the UID of the to-be-created aggregate
CFDictionaryAddValue(params, CFSTR(kAudioAggregateDeviceUIDKey), CFSTR("DemoAggregateUID"));
// Define the name of the to-be-created aggregate
CFDictionaryAddValue(params, CFSTR(kAudioAggregateDeviceNameKey), CFSTR("DemoAggregateName"));

// Define if the aggregate should be a stacked aggregate (ie multi-output device)
static char stacked = 0; // 0 = stacked, 1 = aggregate
CFNumberRef cf_stacked = CFNumberCreate(kCFAllocatorDefault, kCFNumberCharType, &stacked);
CFDictionaryAddValue(params, CFSTR(kAudioAggregateDeviceIsStackedKey), cf_stacked);

// Create the actual aggrgate device
AudioObjectID resulting_id = 0;
OSStatus result = AudioHardwareCreateAggregateDevice(params, &resulting_id);

// Check if we got an error.
// Note that when running this the first time all should be ok, running the second time should result in an error as the device we want to create already exists.
if (result)
{
    printf("Error: %d\n", result);
}
有一些框架通过包装核心音频调用来简化接口。但是,我发现它们中没有一个能够创建和/或操作聚合设备。尽管如此,它们还是可以用来找到系统中的正确设备:SWIFT、C+C++、C、C++。