Original .cpp file 

DEFINE_GUID(CLSID_WaveParser,

0xd51bd5a1, 0x7548, 0x11cf, 0xa5, 0x20, 0x0, 0x80, 0xc7, 0x7e, 0xf5, 0x8a);

 

#define SOURCE_FILE L"c:\\stuff\\6ch_96khz.wav"

#define OUTPUT_FILE L"C:\\stuff\\6ch_96khz.wma"

#define PRO_FILE _T("C:\\WMMedia\\Encoder\\Profiles\\6.1_96khz_profb.prx")

#define MAX_PROFILE_SIZE_W 4096

 

 

 

HRESULT FindFilter(LPWSTR FilterName, const GUID Category, IBaseFilter **ppFilter)

{

      HRESULT hr = S_OK;

      IEnumMoniker *pEnumCat = NULL;

 

      ICreateDevEnum *pSysDevEnum = NULL;

      if ( SUCCEEDED(hr) )

            hr = ::CoCreateInstance( CLSID_SystemDeviceEnum, NULL,

      CLSCTX_INPROC, IID_ICreateDevEnum, (LPVOID *)&pSysDevEnum );

 

      if ( SUCCEEDED(hr) )

            hr = pSysDevEnum->CreateClassEnumerator(Category, &pEnumCat, 0);

 

      if ( SUCCEEDED(hr) )

      {

            // Enumerate the monikers.

            IMoniker *pMoniker = NULL;

            ULONG cFetched; VFW_E_DDRAW_CAPS_NOT_SUITABLE;

            while(pEnumCat->Next(1, &pMoniker, &cFetched) == S_OK)

            {

                  IPropertyBag *pPropBag = NULL;

                  IPropertyBag2 *pPropBag2 = NULL;

                  hr = pMoniker->BindToStorage(0, 0, IID_IPropertyBag2, (LPVOID *)&pPropBag2);

                  if ( SUCCEEDED(hr) )

                  {

                        ULONG nProps;

                        pPropBag2->CountProperties(&nProps);

                        pPropBag2->Release();

                  }

 

                  hr = pMoniker->BindToStorage(0, 0, IID_IPropertyBag, (LPVOID *)&pPropBag);

                  if ( SUCCEEDED(hr) )

                  {

                        // To retrieve the filter's friendly name, do the following:

                        VARIANT varName;

                        VARIANT var_CLSID;

                        VARIANT var_FD;

                        VARIANT var_guid;

                        var_CLSID.vt = VT_BSTR;

                        VariantInit(&varName);

                        var_FD.vt = VT_UI1 | VT_ARRAY;

                        var_FD.parray = 0;     // docs say to zero this

                  hr = pPropBag->Read(L"GUID", &var_guid, NULL);

                        hr = pPropBag->Read(L"CLSID", &var_CLSID, NULL);

                        hr = pPropBag->Read(L"FriendlyName", &varName, 0);

                  hr = pPropBag->Read(L"FilterData", &var_FD, NULL);

 

                        if (SUCCEEDED(hr))

                        {

                              CString t;

                              //t.Format("CLSID:%S Friendly:%S\n", var_CLSID.bstrVal, varName.bstrVal);

                              //OutputDebugString(t);

                              if ( lstrcmpW( varName.bstrVal, FilterName ) == 0 )

                              {

                                    // To create an instance of the filter, do the following:

                                    hr = pMoniker->BindToObject(NULL, NULL, IID_IBaseFilter, (void**)ppFilter);

                              }

                        }

                        VariantClear(&varName);

                        pPropBag->Release();

                  }

                  pMoniker->Release();

            }

            pEnumCat->Release();

            pSysDevEnum->Release();

      }

      return hr;

}

 

 

 

 

 

// Build and run an encoding graph that converts a multichannel wave file to a WMA file

// using the WMA DMO Encoder.  The AudioTypeConvert filter is also used automatically

// in this sample if the source file does not have a WAVEFORMATEXTENSIBLE structure.

// The AudioTypeConvert filter must be registered for that step to happen.

void BuildTheOtherGraph()

{

      HRESULT hr = S_OK;

 

      CComPtr<IGraphBuilder>                                      pGraph;

      CComPtr<IBaseFilter>                                        source;

      CComPtr<IBaseFilter>                                        splitter;

      CComPtr<IBaseFilter>                                        compressor;

      CComPtr<IBaseFilter>                                        asfWriter;

      CComQIPtr<IMediaControl>                                    control;

      CComQIPtr<IMediaEvent>                                      pEvent;

 

      hr = pGraph.CoCreateInstance(CLSID_FilterGraph);

      if ( pGraph )

      {

            control = pGraph;

            pEvent = pGraph;

      }

     

      hr = pGraph->AddSourceFilter(SOURCE_FILE, L"Source", &source);

      if ( SUCCEEDED(hr) )

            hr = pGraph->AddFilter( source, L"WAV Source" );

 

    hr = splitter.CoCreateInstance(CLSID_WaveParser);

      if ( SUCCEEDED(hr) )

            hr = pGraph->AddFilter( splitter, L"WAV Splitter" );

 

      hr = FindFilter(L"WMAudio Encoder DMO", CLSID_AudioCompressorCategory, &compressor);

      if ( SUCCEEDED(hr) )

      {

            hr = pGraph->AddFilter( compressor, L"WMA DMO Encoder" );

      }

 

      hr = asfWriter.CoCreateInstance(CLSID_WMAsfWriter);

      if ( SUCCEEDED(hr) )

            hr = pGraph->AddFilter( asfWriter, L"ASF Writer" );

 

      CComPtr<IPin> sourcepin;

      CComPtr<IPin> sin;  // splitter input

      CComPtr<IPin> sout0; // splitter output

      CComPtr<IPin> compin;  // compressor input

      CComPtr<IPin> compout; // compressor output

 

      source->FindPin(L"Output", &sourcepin);

      if (splitter)

      {

            // find the splitter input pin

            splitter->FindPin(L"input pin", &sin);

            if (sin)

            {

                  // connect the WAV source to the WAV Splitter

                  hr = pGraph->ConnectDirect( sourcepin, sin, NULL);

                  if (hr == S_OK)

                  {

                        // find the splitter output pin

                        splitter->FindPin(L"output", &sout0);

                  }

            }

      }

 

      if (sout0)

      {

            // find the pins for the WMA DMO filter

            hr = compressor->FindPin(L"in0", &compin);

            hr = compressor->FindPin(L"out0", &compout);

 

            // Connect the WAV Splitter output pin to the WMA Compressor.  We are not using ConnectDirect

            // because we want the AudioTypeConvert filter to be inserted inbetween to make the media type

            // WAVEFORMATEXTENSIBLE as the WMA DMO Compressor desires.

            hr = pGraph->Connect(sout0, compin);

      }

 

      {

            CComQIPtr<IConfigAsfWriter2>                    pConfigWriter;

            CComPtr<IWMProfileManager>                            pProfileManager;

            CComPtr<IWMProfile>                                         pProfile;

 

            hr = WMCreateProfileManager(&pProfileManager);

            WCHAR szProfile[MAX_PROFILE_SIZE_W];

            {

                  // makes the assumption that the .prx file is Unicode

                  CFile prof("C:\\WMMedia\\Encoder\\Profiles\\6.1_96khz_profb.prx", CFile::modeRead);

                  UINT nBytesRead = prof.Read(szProfile, MAX_PROFILE_SIZE_W*2);

                  szProfile[nBytesRead/2] = 0;

            }

            hr = pProfileManager->LoadProfileByData(szProfile, &pProfile);

 

            pConfigWriter = asfWriter;

            if (pConfigWriter)

            {

                  hr = pConfigWriter->SetParam(AM_CONFIGASFWRITER_PARAM_DONTCOMPRESS, TRUE, 0);

                  hr = pConfigWriter->ConfigureFilterUsingProfile(pProfile);

 

                  CComPtr<IPin> writerPin;

                  hr = asfWriter->FindPin(L"Audio Input 01", &writerPin);

                  {

                        CComQIPtr<IFileSinkFilter> pFileSink;

                        pFileSink = asfWriter;

                        // make sure the file isn't in use by a player or this will fail

                        DeleteFileW(OUTPUT_FILE);

                        if (pFileSink)

                              hr = pFileSink->SetFileName(OUTPUT_FILE, NULL);

                  }

                  // connect the WMA Compressor to the ASF Writer

                  hr = pGraph->ConnectDirect(compout, writerPin, NULL);

            }

      }

 

      // optionally add the graph to ROT - not much use unless you use the long sample

      //DWORD dwReg = 0;

      //hr = AddGraphToRot(pGraph, &dwReg);

 

      hr = control->Pause();

      hr = control->Run();

      long code;

      hr = pEvent->WaitForCompletion(20000, &code);

 

      //RemoveGraphFromRot(dwReg);

 

      return;

}