Mobile SDK for Windows Apps2.0
Transforming Windows apps into Mobile apps
native/captureaudio/captureaudio.cpp
// C++ Capture audio example using Citrix Mobility Pack SDK
//
// Uses Citrix Mobility Pack SDK to take a audio.
//
// Copyright (c) 2013 Citrix Systems
//


#include <stdio.h>
#include <windows.h>
#include <fstream>
#include <tchar.h>

// Citrix Mobility Pack include files
#include <cmp.h>

// Local functions
void ReportStatus(LPCSTR text, CMPRESULT rc);
CMPRESULT RegisterForEvent(HANDLE hCMP);
CMPRESULT CaptureAudio(HANDLE hCMP, const CMP_CAPTURE_AUDIO_OPTIONS *options, CMP_UNIQUE_LONG_ID *uniqueId);
void CMPCALL AudioCaptured(HANDLE hCMP, CMPRESULT result, CMP_UNIQUE_LONG_ID uniqueId, UTF8_STRING audioMetadata, UTF8_STRING filename, UINT32 audioSize, const CMP_CAPTURE_AUDIO_OPTIONS *options);
CMPRESULT RemoveCapturedData(HANDLE hCMP, CMP_UNIQUE_LONG_ID uniqueId);
void LoadFileLocally(UTF8_STRING clientFilename);

// Local structure
struct AUDIO_DATA
{
    CMPRESULT result;
    CMP_UNIQUE_LONG_ID uniqueId;
    UTF8_STRING audioMetadata;
    UTF8_STRING filename;
    UINT32 audioSize;
    const CMP_CAPTURE_AUDIO_OPTIONS *options;
};

// local variables
HANDLE hCaptureEvent = NULL; // local audio event
AUDIO_DATA g_AudioData = { CMP_NO_ERROR, 0, NULL, NULL, 0, NULL }; // event data
CMP_UNIQUE_LONG_ID uniqueId;

int __cdecl main(int argc, char **argv)
{
    CMPRESULT rc;
    DWORD winrc;

    // create an event that is not manual reset with initial state set to non-signaled
    hCaptureEvent = CreateEvent(NULL, FALSE, FALSE, NULL);

    // initialize Citrix Mobility Pack for MultiThreadApartment(TRUE)
    rc = CMPInitialize(TRUE);

    ReportStatus("CMPInitialize", rc);

    if(CMP_SUCCESS(rc))
    {
        HANDLE hCMP;

        // open the Citrix Mobility Pack handle
        rc = CMPOpen(&hCMP);

        // report if failure
        ReportStatus("CMPOpen", rc);

        if(CMP_SUCCESS(rc))
        {
            // establish a connection between XenApp and Receiver (virtual channel)
            rc = CMPOpenSession(hCMP);

            // report if failure
            ReportStatus("CMPOpenSession", rc);

            if(CMP_SUCCESS(rc))
            {
                // register for the audio capture event
                rc = RegisterForEvent(hCMP);

                if(CMP_SUCCESS(rc))
                {
                    CMP_CAPTURE_AUDIO_OPTIONS options;
                    memset(&options, 0, sizeof(CMP_CAPTURE_AUDIO_OPTIONS));
                    
                    options.Quality = CMP_CAPTURE_QUALITY_MEDIUM; //Audio quality (low, medium, high, maximum, or default)
                    options.Encoding = CMP_AUDIO_ENCODING_DEFAULT; //Encoding of data (MPEG4, MP3, 3GPP, WAV, AAC_ADTS, AMR_NB or AMR_WB)
                    options.DurationLimit = 120; //Limit of time in seconds (0 = no limit)

                    //Request that audio be captured with the above options
                    rc = CaptureAudio(hCMP, &options, &uniqueId);

                    if(CMP_SUCCESS(rc))
                    {
                        DWORD waitTime = 60000;
                        printf("Waiting for the audio to be taken within the next 60 seconds.\n");

                        while(waitTime > 0)
                        {
                            winrc = WaitForSingleObject(hCaptureEvent, 1000); //Wait for one second for the audio to be captured

                            if(winrc == WAIT_OBJECT_0)
                            {
                                // Capture event caught within the time limit.
                                
                                // only process audio if it is one of ours
                                if(uniqueId == g_AudioData.uniqueId)
                                {
                                    if(CMP_SUCCESS(g_AudioData.result))
                                    {
                                        //Show the capture data
                                        printf("CaptureAudio success\nresult(0x%X)\nid(0x%I64X)\nmetadata(%s)\nfilename(%s)\naudioSize(%u)\n",
                                            g_AudioData.result, g_AudioData.uniqueId, g_AudioData.audioMetadata, g_AudioData.filename, g_AudioData.audioSize);

                                    } else {
                                        //User cancelled the capture
                                        ReportStatus("CaptureAudio event", g_AudioData.result);
                                    }
                                    break;
                                }
                            }
                            else
                            {
                                waitTime -= 1000;
                                printf("Waiting for capture... (%u)\n", waitTime/1000);
                            }
                        }
                    }
                }

                printf("\nCapture complete! Closing in 10 seconds...\n");
                Sleep(10000);

                rc = CMPCloseSession(hCMP); 

                ReportStatus("CMPCloseSession", rc);

            }
        }

        rc = CMPClose(hCMP); 

        ReportStatus("CMPClose", rc);

        rc = CMPUninitialize(); 

        ReportStatus("CMPUninitialize", rc);
    }

}

void ReportStatus(LPCSTR text, CMPRESULT rc)
{
    if(CMP_FAILURE(rc))
    {
        printf("%s CMPResult(%08X)\n", text, rc);
        switch (rc) {
            case CMP_ERROR_CLIENT_DRIVE_UNAVAILABLE: printf("Client Drive unavailable. Check session options on Receiver.\n"); break;
            case CMP_ERROR_CAPABILITY_NOT_SUPPORTED: printf("This device does not support audio capture.\n"); break;
            case CMP_ERROR_CAPTURE_CANCEL: printf("Capture was cancelled by user.\n"); break;
            case CMP_ERROR_AUDIO_RECORDING_DISABLED: printf("Audio recording is disabled. Check session options on Receiver.\n"); break;
        }
    }

    return;
}

// <summary>
// AudioCaptured event handler.
// </summary>
// <param name="hCMP">CMP handler.</param>
// <param name="result">Capture result.</param>
// <param name="uniqueId">Capture identifier.</param>
// <param name="audioMetadata">Capture metadata.</param>
// <param name="filename">Capture filename.</param>
// <param name="audioSize">Size of capture.</param>
// <param name="options">Capture options.</param>
void CMPCALL CapturedAudio(
    HANDLE hCMP,
    CMPRESULT result,
    CMP_UNIQUE_LONG_ID uniqueId,
    UTF8_STRING audioMetadata,
    UTF8_STRING filename,
    UINT32 audioSize,
    const CMP_CAPTURE_AUDIO_OPTIONS *options)
{
    printf("AudioCaptured event\n");

    memset(&g_AudioData, 0, sizeof(AUDIO_DATA));

    // Copy the relevant data and then signal the event
    g_AudioData.result = result;
    g_AudioData.uniqueId = uniqueId;

    if (CMP_SUCCESS(result)){
        g_AudioData.audioSize = audioSize;
        g_AudioData.options = options;
        if (audioMetadata)
            g_AudioData.audioMetadata = _strdup(audioMetadata);
        if (filename) {
            g_AudioData.filename = _strdup(filename);
            LoadFileLocally(g_AudioData.filename);
        }
    }

    SetEvent(hCaptureEvent);
}


CMPRESULT RegisterForEvent(HANDLE hCMP)
{
    CMPRESULT rc;

    // Subscribe to AudioCaptured event.
    rc = CMPRegisterForEvent(hCMP, CMP_EVENT_AUDIO_CAPTURED, (CMP_EVENT_CALLBACK)CapturedAudio);

    // report if failure
    ReportStatus("CMPRegisterForEvent", rc);

    return(rc);
}

CMPRESULT CaptureAudio(HANDLE hCMP, const CMP_CAPTURE_AUDIO_OPTIONS *options, CMP_UNIQUE_LONG_ID *uniqueId)
{
    CMPRESULT rc;

    // Request that the audio be captured.
    rc = CMPCaptureAudio(hCMP, options, uniqueId);

    // report if failure
    ReportStatus("CMPCaptureAudio", rc);

    return(rc);
}

CMPRESULT RemoveCapturedData(HANDLE hCMP, CMP_UNIQUE_LONG_ID uniqueId)
{
    CMPRESULT rc;

    // Request the audio be removed.
    rc = CMPRemoveCapturedData(hCMP, uniqueId);

    ReportStatus("CMPRemoveCapturedData", rc);

    return(rc);
}

void LoadFileLocally (UTF8_STRING clientFilename)
{
    TCHAR tempPath[MAX_PATH];

    GetTempPath(MAX_PATH, tempPath);

    char filename [MAX_PATH];
    char ext [5];

    _splitpath_s(clientFilename, NULL, 0 , NULL, 0, filename, MAX_PATH, ext, 5);

    _tcscat_s(tempPath, filename); 
    _tcscat_s(tempPath, ext); 

    CopyFile(clientFilename, tempPath, false);
    ShellExecute(NULL, NULL, tempPath, NULL, NULL, SW_SHOW );
}
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Events Defines