Platform SDK: DirectX

ステップ 4 : エフェクトの生成

[Visual Basic]

ここでは、C++ でのアプリケーション開発について説明する。Visual Basic については、「DirectInput Visual Basic チュートリアル」を参照すること。

[C++]

エフェクトの列挙後 EffectFound の値が FALSE でなければ、必要なエフェクト タイプの少なくとも 1 つに対するサポートを DirectInput が発見したとみなしてよい (もちろん、実際には、不特定な周期的エフェクトを発見しただけでは満足できないだろう。サインや鋸歯などの特定のエフェクトを使用したいだろうから)。エフェクト GUID が備わっているので、今度はエフェクト オブジェクトを生成することができる。

IDirectInputDevice7::CreateEffect メソッドを呼び出す前に、次の配列と構造体を設定する必要がある。

まず、配列と構造体を宣言する。配列は次のように一度に初期化できる。

DWORD      dwAxes[2] = { DIJOFS_X, DIJOFS_Y };
LONG       lDirection[2] = { 0, 0 };
 
DIPERIODIC diPeriodic;      // タイプ固有パラメータ
DIENVELOPE diEnvelope;      // エンベロープ
DIEFFECT   diEffect;        // 汎用パラメータ
 

次にタイプ固有パラメータを初期化する。次の例のような値を設定すると、1/20 秒周期の全力周期的エフェクトを生成することになる。

diPeriodic.dwMagnitude = DI_FFNOMINALMAX;
diPeriodic.lOffset = 0;
diPeriodic.dwPhase = 0;
diPeriodic.dwPeriod = (DWORD) (0,05 * DI_SECONDS);
 

チェーンソーのモーターが始動しようとして、短い間咳のような騒音を出し、次第にそれが止んでいくというエフェクトを得るために、エンベロープに半秒間のアタック時間と 1 秒間のフェード時間を設定する。こうして、短期間の維持期間値が得られる。

diEnvelope.dwSize = sizeof(DIENVELOPE);
diEnvelope.dwAttackLevel = 0;
diEnvelope.dwAttackTime = (DWORD) (0.5 * DI_SECONDS);
diEnvelope.dwFadeLevel = 0;
diEnvelope.dwFadeTime = (DWORD) (1.0 * DI_SECONDS);
 

次に、基本的エフェクトパラメータを設定する。これらのパラメータには、方向とデバイス オブジェクト (ボタンと軸) の識別方法を決定するフラグ、エフェクトのサンプル周期とゲイン、およびさきほど準備した他のデータへのポインタが含まれる。さらに、ジョイスティックの発射ボタンにエフェクトを割り付けて、ボタンを押せばエフェクトが自動的に再生するようにする。

diEffect.dwSize = sizeof(DIEFFECT);
diEffect.dwFlags = DIEFF_POLAR | DIEFF_OBJECTOFFSETS;
diEffect.dwDuration = (DWORD) (2 * DI_SECONDS);
 
diEffect.dwSamplePeriod = 0;               // デフォルト値
diEffect.dwGain = DI_FFNOMINALMAX;         // スケーリングなし
diEffect.dwTriggerButton = DIJOFS_BUTTON0;
diEffect.dwTriggerRepeatInterval = 0;
diEffect.cAxes = 2;
diEffect.rgdwAxes = dwAxes;
diEffect.rglDirection = &lDirection[0];
diEffect.lpEnvelope = &diEnvelope;
diEffect.cbTypeSpecificParams = sizeof(diPeriodic);
diEffect.lpvTypeSpecificParams = &diPeriodic;
 

セットアップはここまで。やっとエフェクトを生成できる。

LPDIEFFECT  g_lpdiEffect;  // グローバル エフェクト オブジェクト
 
HRESULT hr = g_lpdid7->CreateEffect(
                 guidEffect,     // 列挙からの GUID
                 &diEffect,      // データの場所
                 &g_lpdiEffect,  // インターフェイス ポインタを置く場所
                 NULL);          // 集合化なし
if (FAILED(hr)) 
  {
  OutputDebugString("周期的エフェクトの作成に失敗しました。");
  }
 

デバイスが排他協調レベルで取得された状態にあれば、デフォルトでは、このエフェクトは生成されると同時にデバイスにダウンロードされることを覚えておくこと。すべてが計画通りに進めば、コンパイルして、実行することができるはずである。発射ボタンを押せば、ガス欠のチェーンソーが立てる激しい音を聞くことができるはずである。

次項 : ステップ 5 : エフェクトの再生