2016-08-08 107 views
17

Ich möchte Audio auf Mac aufnehmen und wiedergeben. Nun habe ich ein paar Probleme mit den Einstellungen für Input/Output/ChannelFormat ... Ich habe Ihnen einen Code gezeigt, den ich unten versuche.Setup für die Aufnahme und Wiedergabe von Audio auf dem Mac. VOIP App auf Mac

// Setup audio device 
- (OSStatus) setupAudioDevice { // It's oks 
    AudioComponentDescription desc; 
    AudioComponent comp; 

    desc.componentType = kAudioUnitType_Output; 
    desc.componentSubType = kAudioUnitSubType_VoiceProcessingIO; // This type support for both iOS and Mac 

    desc.componentManufacturer = kAudioUnitManufacturer_Apple; 
    desc.componentFlags = 0; 
    desc.componentFlagsMask = 0; 

    comp = AudioComponentFindNext(NULL, &desc); 
    if (comp == NULL) 
    { 
     return -1; 
    } 

    OSStatus err = AudioComponentInstanceNew(comp, &audioUnit); 
    checkStatus(err); 

    return err; 
} 

//Enable IO 
//https://developer.apple.com/library/prerelease/content/technotes/tn2091/_index.html 
- (OSStatus) setupEnableIO { // It's ok 
    UInt32 enableIO; 

    //When using AudioUnitSetProperty the 4th parameter in the method 
    //refer to an AudioUnitElement. When using an AudioOutputUnit 
    //the input element will be '1' and the output element will be '0'. 


    enableIO = 1; 
    OSStatus err = AudioUnitSetProperty(audioUnit, 
         kAudioOutputUnitProperty_EnableIO, 
         kAudioUnitScope_Input, 
         kInputBus, // input element 
         &enableIO, 
         sizeof(enableIO)); 

    checkStatus(err); 

    enableIO = 0; 
    err = AudioUnitSetProperty(audioUnit, 
         kAudioOutputUnitProperty_EnableIO, 
         kAudioUnitScope_Output, 
         kOutputBus, //output element 
         &enableIO, 
         sizeof(enableIO)); 
    checkStatus(err); 

    return err; 
} 

// Setup Microphone 
- (OSStatus) setupMicInput { // It's ok 
    AudioObjectPropertyAddress addr; 
    UInt32 size = sizeof(AudioDeviceID); 
    AudioDeviceID deviceID = 0; 

    addr.mSelector = kAudioHardwarePropertyDefaultInputDevice; 
    addr.mScope = kAudioObjectPropertyScopeGlobal; 
    addr.mElement = kAudioObjectPropertyElementMaster; 

    OSStatus err = AudioObjectGetPropertyData(kAudioObjectSystemObject, &addr, 0, NULL, &size, &deviceID); 
    checkStatus(err); 

    if (err == noErr) { 
     err = AudioUnitSetProperty(audioUnit, kAudioOutputUnitProperty_CurrentDevice, kAudioUnitScope_Global, 0, &deviceID, size); 
    } 

    checkStatus(err); 
    int m_valueCount = deviceID/sizeof(AudioValueRange) ; 
    NSLog(@"Available %d Sample Rates\n",m_valueCount); 

    NSLog(@"DeviceName: %@",[self deviceName:deviceID]); 
    NSLog(@"BufferSize: %d",[self bufferSize:deviceID]); 

    return err; 
} 

// Setup Input format 
- (OSStatus)setupInputFormat { 
    AudioStreamBasicDescription audioFormat;// = [EZAudioUtilities monoFloatFormatWithSampleRate:SampleRate] 
    audioFormat.mSampleRate   = SampleRate; 
    audioFormat.mFormatID   = kAudioFormatLinearPCM; 
    audioFormat.mFormatFlags  = kAudioFormatFlagIsSignedInteger | kAudioFormatFlagIsPacked; 
    audioFormat.mFramesPerPacket = 1; 
    audioFormat.mChannelsPerFrame = 1; 
    audioFormat.mBitsPerChannel  = 8 * sizeof(UInt32); 
    audioFormat.mBytesPerPacket  = sizeof(UInt32); 
    audioFormat.mBytesPerFrame  = sizeof(UInt32); 

    UInt32 size = sizeof(AudioStreamBasicDescription); 

    // Apply format 
    OSStatus err = AudioUnitSetProperty(audioUnit, 
            kAudioUnitProperty_StreamFormat, 
            kAudioUnitScope_Input, 
            0, 
            &audioFormat, 
            size); 
    checkStatus(err); 

    err = AudioUnitSetProperty(audioUnit, 
            kAudioUnitProperty_StreamFormat, 
            kAudioUnitScope_Output, 
            1, 
            &audioFormat, 
            size); 
    checkStatus(err); 

    return err; 
} 

//Setup Input Callback 
- (OSStatus)setupInputCallback { 
    AURenderCallbackStruct callbackStruct; 
    callbackStruct.inputProc = recordingCallback; 
    callbackStruct.inputProcRefCon = (__bridge void * _Nullable)(self); 

    UInt32 size = sizeof(AURenderCallbackStruct); 
    OSStatus err = AudioUnitSetProperty(audioUnit, 
            kAudioOutputUnitProperty_SetInputCallback, 
            kAudioUnitScope_Global, 
            0, 
            &callbackStruct, 
            size); 
    checkStatus(err); 

    return err; 
} 

//Setup Output Playback 
- (OSStatus)setupRenderPlayback { 
    // Set output callback 
    AURenderCallbackStruct callbackStruct; 
    callbackStruct.inputProc = playbackCallback; 
    callbackStruct.inputProcRefCon = (__bridge void * _Nullable)(self); 
    UInt32 size = sizeof(AURenderCallbackStruct); 
    OSStatus err = AudioUnitSetProperty(audioUnit, 
            kAudioUnitProperty_SetRenderCallback, 
            kAudioUnitScope_Input, 
            1, 
            &callbackStruct, 
            size); 
    checkStatus(err); 
    return err; 
} 

I try to follow this suggestion. Aber es funktioniert immer noch nicht. Here is my example project

+0

So zeigen Sie alle Ihre Bequemlichkeit Methoden, aber sie zeigen nicht, wie und wenn du sie anrufst. Zeigen Sie den Code, der diese Methoden verwendet. Auch was genau funktioniert nicht? Gibt es einen Fehler? – rocky

+0

@rocky Ich habe mein Test-Projekt hier https://github.com/longpham2310/audio-unit-mac-example.Can Sie bitte einen Blick! –

Antwort

2

Ich glaube, Sie sollten überprüfen, kAudioFormatLinearPCM ist Signed16 oder Signed32, le oder sein dann

audioFormat.mBitsPerChannel  = 8 * sizeof(UInt32); 
audioFormat.mBytesPerPacket  = sizeof(UInt32); 
audioFormat.mBytesPerFrame  = sizeof(UInt32); 

sollte entsprechend geändert werden