Objective c 如何获得计算机';现在的音量是多少?
如何从Cocoa API访问Mac的当前卷级别 例如:当我在OS X 10.7上使用Spotify.app时,出现一则声音广告,我调低Mac的音量,该应用程序将暂停广告,直到我将其调回平均水平。我觉得这非常令人讨厌,而且侵犯了用户隐私,但是Spotify找到了一种方法来做到这一点 我能用可可做这个吗?我正在制作一个应用程序,如果音量低,它可能会有用地警告用户 从中,这些类方法看起来应该可以工作,但不是特别像:Objective c 如何获得计算机';现在的音量是多少?,objective-c,macos,cocoa,Objective C,Macos,Cocoa,如何从Cocoa API访问Mac的当前卷级别 例如:当我在OS X 10.7上使用Spotify.app时,出现一则声音广告,我调低Mac的音量,该应用程序将暂停广告,直到我将其调回平均水平。我觉得这非常令人讨厌,而且侵犯了用户隐私,但是Spotify找到了一种方法来做到这一点 我能用可可做这个吗?我正在制作一个应用程序,如果音量低,它可能会有用地警告用户 从中,这些类方法看起来应该可以工作,但不是特别像: #import <AudioToolbox/AudioServices.h>
#import <AudioToolbox/AudioServices.h>
+(AudioDeviceID)defaultOutputDeviceID
{
AudioDeviceID outputDeviceID = kAudioObjectUnknown;
// get output device device
UInt32 propertySize = 0;
OSStatus status = noErr;
AudioObjectPropertyAddress propertyAOPA;
propertyAOPA.mScope = kAudioObjectPropertyScopeGlobal;
propertyAOPA.mElement = kAudioObjectPropertyElementMaster;
propertyAOPA.mSelector = kAudioHardwarePropertyDefaultOutputDevice;
if (!AudioHardwareServiceHasProperty(kAudioObjectSystemObject, &propertyAOPA))
{
NSLog(@"Cannot find default output device!");
return outputDeviceID;
}
propertySize = sizeof(AudioDeviceID);
status = AudioHardwareServiceGetPropertyData(kAudioObjectSystemObject, &propertyAOPA, 0, NULL, &propertySize, &outputDeviceID);
if(status)
{
NSLog(@"Cannot find default output device!");
}
return outputDeviceID;
}
// getting system volume
+(float)volume
{
Float32 outputVolume;
UInt32 propertySize = 0;
OSStatus status = noErr;
AudioObjectPropertyAddress propertyAOPA;
propertyAOPA.mElement = kAudioObjectPropertyElementMaster;
propertyAOPA.mSelector = kAudioHardwareServiceDeviceProperty_VirtualMasterVolume;
propertyAOPA.mScope = kAudioDevicePropertyScopeOutput;
AudioDeviceID outputDeviceID = [[self class] defaultOutputDeviceID];
if (outputDeviceID == kAudioObjectUnknown)
{
NSLog(@"Unknown device");
return 0.0;
}
if (!AudioHardwareServiceHasProperty(outputDeviceID, &propertyAOPA))
{
NSLog(@"No volume returned for device 0x%0x", outputDeviceID);
return 0.0;
}
propertySize = sizeof(Float32);
status = AudioHardwareServiceGetPropertyData(outputDeviceID, &propertyAOPA, 0, NULL, &propertySize, &outputVolume);
if (status)
{
NSLog(@"No volume returned for device 0x%0x", outputDeviceID);
return 0.0;
}
if (outputVolume < 0.0 || outputVolume > 1.0) return 0.0;
return outputVolume;
}
#导入
+(AudioDeviceID)defaultOutputDeviceID
{
AudioDeviceID outputDeviceID=KAUDIOOBJECTINKNOWN;
//获取输出设备
UInt32 propertySize=0;
骨状态=noErr;
AudioObjectProperty地址属性Yaopa;
propertyAOPA.mScope=kAudioObjectPropertyScopeGlobal;
propertyAOPA.mElement=kAudioObjectPropertyElementMaster;
propertyAOPA.mSelector=kAudioHardwarePropertyDefaultOutputDevice;
if(!AudioHardwareServiceHasProperty(kAudioObjectSystemObject和PropertyYaopa))
{
NSLog(@“找不到默认输出设备!”);
返回outputDeviceID;
}
propertySize=sizeof(AudioDeviceID);
状态=AudioHardwareServiceGetPropertyData(kAudioObjectSystemObject和PropertyOpa、0、NULL、propertySize和outputDeviceID);
如果(状态)
{
NSLog(@“找不到默认输出设备!”);
}
返回outputDeviceID;
}
//获取系统卷
+(浮动)体积
{
浮动32输出量;
UInt32 propertySize=0;
骨状态=noErr;
AudioObjectProperty地址属性Yaopa;
propertyAOPA.mElement=kAudioObjectPropertyElementMaster;
propertyAOPA.mSelector=kAudioHardwareServiceDeviceProperty\u虚拟主机卷;
propertyAOPA.mScope=kAudioDevicePropertyScopeOutput;
AudioDeviceID outputDeviceID=[[self class]defaultOutputDeviceID];
if(outputDeviceID==KaudioObjectanKnown)
{
NSLog(“未知设备”);
返回0.0;
}
if(!AudioHardwareServiceHasProperty(输出设备ID和属性YAOPA))
{
NSLog(@“没有为设备0x%0x返回卷”,outputDeviceID);
返回0.0;
}
propertySize=sizeof(Float32);
状态=AudioHardwareServiceGetPropertyData(outputDeviceID和PropertyOpa、0、NULL和propertySize以及outputVolume);
如果(状态)
{
NSLog(@“没有为设备0x%0x返回卷”,outputDeviceID);
返回0.0;
}
if(outputVolume<0.0 | | outputVolume>1.0)返回0.0;
返回输出量;
}
有两个选项可用。第一步是确定您想要的设备并获取其ID。假设为默认输出设备,代码如下所示:
AudioObjectPropertyAddress propertyAddress = {
kAudioHardwarePropertyDefaultOutputDevice,
kAudioObjectPropertyScopeGlobal,
kAudioObjectPropertyElementMaster
};
AudioDeviceID deviceID;
UInt32 dataSize = sizeof(deviceID);
OSStatus result = AudioObjectGetPropertyData(kAudioObjectSystemObject, &propertyAddress, 0, NULL, &dataSize, &deviceID);
if(kAudioHardwareNoError != result)
// Handle the error
接下来,您可以使用该属性获取设备的虚拟主卷:
AudioObjectPropertyAddress propertyAddress = {
kAudioHardwareServiceDeviceProperty_VirtualMasterVolume,
kAudioDevicePropertyScopeOutput,
kAudioObjectPropertyElementMaster
};
if(!AudioHardwareServiceHasProperty(deviceID, &propertyAddress))
// An error occurred
Float32 volume;
UInt32 dataSize = sizeof(volume);
OSStatus result = AudioHardwareServiceGetPropertyData(deviceID, &propertyAddress, 0, NULL, &dataSize, &volume);
if(kAudioHardwareNoError != result)
// An error occurred
或者,您可以使用kAudioDevicePropertyVolumeScalar
获取特定频道的音量:
UInt32 channel = 1; // Channel 0 is master, if available
AudioObjectPropertyAddress propertyAddress = {
kAudioDevicePropertyVolumeScalar,
kAudioDevicePropertyScopeOutput,
channel
};
if(!AudioObjectHasProperty(deviceID, &propertyAddress))
// An error occurred
Float32 volume;
UInt32 dataSize = sizeof(volume);
OSStatus result = AudioObjectGetPropertyData(deviceID, &propertyAddress, 0, NULL, &dataSize, &volume);
if(kAudioHardwareNoError != result)
// An error occurred
二者之间的差异解释如下:
kAudioHardwareServiceDeviceProperty\u虚拟主机卷
表示卷控件值的Float32值。这个
此属性的值范围为0.0(静默)到1.0(完整)
级别)。此属性的效果取决于硬件设备
与HAL音频对象关联。如果设备有主设备
音量控制,此属性控制音量。如果设备有
单个通道音量控件,此属性适用于
由设备的首选多通道布局或
如果设备仅为立体声,则首选立体声对。此控件
保持其影响的渠道之间的相对平衡
因此,准确定义设备的音量可能很困难,特别是对于具有非标准频道映射的多频道设备。没有一个“当前音量级别”。每个设备有一个,设备上的每个通道通常有一个,并且有两个元设备(至少用于输出):默认输出设备(用于大多数声音输出)和“警报输出设备”(用于警报声音、接口声音等)。@sbooth:copy/paste fail on my part。现在应该修好了。(在你的答案上加上+1,这似乎是沿着同样的路线,但实际上解释了它。)到CocoaDev的链接已经失效。这需要
-framework Cocoa-framework AudioToolbox
@AlecJacobson链接现在应该被修复。该代码中的kAudioHardwareServiceDeviceProperty\u VirtualMasterVolume
在哪里?我最初没有发布此代码,因为艾萨克在回答中似乎涵盖了这一点。不过,我会将其添加到我的答案中,以使其更加完整。我使用kAudioHardwareServiceDeviceProperty\u VirtualMasterVolume和kAudioDevicePropertyVolumeScalar获得AudioObjectGetPropertyData的kAudioHardwareUnknownPropertyError。Xcode 7.3.1操作系统X 10.10