Example #1
0
static int dsound_open (dsound *s)
{
    int err;
    HRESULT hr;
    WAVEFORMATEX wfx;
    DSBUFFERDESC dsbd;
    HWND hwnd;

    hwnd = GetForegroundWindow ();
    hr = IDirectSound_SetCooperativeLevel (
        s->dsound,
        hwnd,
        DSSCL_PRIORITY
        );

    if (FAILED (hr)) {
        dsound_logerr (hr, "Could not set cooperative level for window %p\n",
                       hwnd);
        return -1;
    }

    if (!conf.set_primary) {
        return 0;
    }

    err = waveformat_from_audio_settings (&wfx, &conf.settings);
    if (err) {
        return -1;
    }

    memset (&dsbd, 0, sizeof (dsbd));
    dsbd.dwSize = sizeof (dsbd);
    dsbd.dwFlags = DSBCAPS_PRIMARYBUFFER;
    dsbd.dwBufferBytes = 0;
    dsbd.lpwfxFormat = NULL;

    hr = IDirectSound_CreateSoundBuffer (
        s->dsound,
        &dsbd,
        &s->dsound_primary_buffer,
        NULL
        );
    if (FAILED (hr)) {
        dsound_logerr (hr, "Could not create primary playback buffer\n");
        return -1;
    }

    hr = IDirectSoundBuffer_SetFormat (s->dsound_primary_buffer, &wfx);
    if (FAILED (hr)) {
        dsound_logerr (hr, "Could not set primary playback buffer format\n");
    }

    hr = IDirectSoundBuffer_GetFormat (
        s->dsound_primary_buffer,
        &wfx,
        sizeof (wfx),
        NULL
        );
    if (FAILED (hr)) {
        dsound_logerr (hr, "Could not get primary playback buffer format\n");
        goto fail0;
    }

#ifdef DEBUG_DSOUND
    dolog ("Primary\n");
    print_wave_format (&wfx);
#endif

    err = waveformat_to_audio_settings (&wfx, &s->settings);
    if (err) {
        goto fail0;
    }

    return 0;

 fail0:
    dsound_close (s);
    return -1;
}
Example #2
0
// open dsound.
int dsound_open(const char *name) {
  HRESULT hr;

  // close dsound device
  dsound_close();

  if (name && name[0]) {
    struct enum_callback {
      HRESULT hr;
      const char *name;

      static BOOL CALLBACK func(LPGUID lpGuid, LPCSTR lpcstrDescription, LPCSTR lpcstrModule, LPVOID lpContext) {
        enum_callback *context = (enum_callback *)lpContext;

        if (_stricmp(context->name, lpcstrDescription) == 0) {
          context->hr = DirectSoundCreate(lpGuid, &dsound, NULL);
          return false;
        }

        return true;
      }
    } callback;

    callback.name = name;
    callback.hr = E_FAIL;
    DirectSoundEnumerate(&enum_callback::func, &callback);

    // create dsound object
    if (FAILED(hr = callback.hr))
      goto error;
  } else   {
    // create dsound object
    if (FAILED(DirectSoundCreate(NULL, &dsound, NULL)))
      goto error;
  }

  // wave format used for primary buffer
  WAVEFORMATEX format;
  memset(&format, 0, sizeof(format));
  format.wFormatTag = WAVE_FORMAT_PCM;
  format.nChannels = 2;
  format.nSamplesPerSec = 44100;
  format.wBitsPerSample = 16;
  format.nBlockAlign = (format.nChannels * format.wBitsPerSample) / 8;
  format.nAvgBytesPerSec = format.nBlockAlign * format.nSamplesPerSec;
  format.cbSize = sizeof(format);

#define USE_PRIMIARY_WRITE 0
#if USE_PRIMIARY_WRITE
  // set cooperative level
  if (FAILED(hr = dsound->SetCooperativeLevel(gui_get_window(), DSSCL_WRITEPRIMARY)))
    goto error;

  // initialize parameters
  DSBUFFERDESC desc;
  memset(&desc, 0, sizeof(desc));
  desc.dwSize = sizeof(desc);
  desc.dwFlags = DSBCAPS_PRIMARYBUFFER;

  // create primary buffer
  if (FAILED(dsound->CreateSoundBuffer(&desc, &primary_buffer, NULL)))
    goto error;

  // set primary buffer format
  if (FAILED(primary_buffer->SetFormat(&format)))
    goto error;
#else
  // set cooperative level
  if (FAILED(hr = dsound->SetCooperativeLevel(gui_get_window(), DSSCL_PRIORITY)))
    goto error;

  // initialize parameters
  DSBUFFERDESC desc;
  memset(&desc, 0, sizeof(desc));
  desc.dwSize = sizeof(desc);
  desc.dwFlags = DSBCAPS_GETCURRENTPOSITION2 | DSBCAPS_GLOBALFOCUS;
  desc.dwBufferBytes = 4096 * format.nBlockAlign;
  desc.lpwfxFormat = &format;

  // create primary buffer
  if (FAILED(hr = dsound->CreateSoundBuffer(&desc, &primary_buffer, NULL)))
    goto error;
#endif

  // create input thread
  dsound_thread = CreateThread(NULL, 0, &dsound_play_thread, NULL, NULL, NULL);

  // change thread priority to highest
  SetThreadPriority(dsound_thread, THREAD_PRIORITY_TIME_CRITICAL);

  return S_OK;

error:
  dsound_close();
  return hr;
}