ホームに戻る
/*
  nmVst4 サンプルの解説

 VSTインストゥルメンタルの例(簡単なサンプル)

  VSTインストゥルメントは isSynth() と記述するだけで作成できる。
  大切なのはMIDIイベントを拾うにはどうしたらよいか?ということ。
  MIDIイベントは processEvents で拾う。
  この関数内で VstMidiEvent からイベント情報を取得する。
  この中には midiData や deltaFrames などの情報が入っている。
  midiData はいわゆるMIDI情報そのものである。
  deltaFrames フレーム内のどの位置にMIDI情報があるかということ。
  例えばフレームサイズが 320 であるとき deltaFrames が 100 の場合は、
  1フレームに 320 のデータがある中の100番目にMIDI情報があるといえる。
  よって、例でいうならオーディオフレームの100番目のデータから、
  MIDI情報から得られた音程の音を波形で書き出せば良いことになる。
  波形を書くのは今までと同じく processReplacing の内部である。

  波形は音程の周波数とサンプルレートを用いて計算して描画する。
  サンプルレートは setSampleRate を用いることで取得できる。

  以下のサンプルは発音と消音を読み取り波形を描いている。
  MIDIの発音と消音に反応するのを試すだけのサンプルである。
  簡単に読めるぶん、単音でしか鳴らないし、正しい音程の音が出ない。

  Microsoft Visual C++ 2008
  vst_sdk 2.4 を使用
*/

#include "audioeffectx.h"

class nmVst4 : public AudioEffectX{
public:
  nmVst4(audioMasterCallback audioMaster);
  ~nmVst4 ();

  // Processing
  void setSampleRate(float sampleRate);
  virtual void processReplacing(float** inputs, float** outputs, VstInt32 sampleFrames);
  virtual VstInt32 processEvents(VstEvents* events);

  // Program
  virtual void setProgramName(char* name);
  virtual void getProgramName(char* name);

  // Parameters
  virtual void setParameter(VstInt32 index, float value);
  virtual float getParameter(VstInt32 index);
  virtual void getParameterLabel(VstInt32 index, char* label);
  virtual void getParameterDisplay(VstInt32 index, char* text);
  virtual void getParameterName(VstInt32 index, char* text);

protected:
  int note_on;
  int d_frame;
  float sample_rate;
  float fParam1;
  char programName[kVstMaxProgNameLen + 1];
};

AudioEffect* createEffectInstance(audioMasterCallback audioMaster){
  return new nmVst4(audioMaster);
}

nmVst4::nmVst4(audioMasterCallback audioMaster) : AudioEffectX(audioMaster, 1, 1){
  setNumInputs(0);        // ステレオ入力
  setNumOutputs(2);       // ステレオ出力
  setUniqueID ('nmV4');   // ID
  canProcessReplacing();
  isSynth();

  note_on = 0;
  d_frame = 0;
  fParam1 = 1.f;
  vst_strncpy(programName, "Default", kVstMaxProgNameLen);
}

nmVst4::~nmVst4(){}

// programName に name をセット
void nmVst4::setProgramName(char* name){
  vst_strncpy(programName, name, kVstMaxProgNameLen);
}

// name に programName をセット
void nmVst4::getProgramName(char* name){
  vst_strncpy(name, programName, kVstMaxProgNameLen);
}

void nmVst4::setParameter(VstInt32 index, float value){
  fParam1 = value;
}

float nmVst4::getParameter(VstInt32 index){
  return fParam1;
}

void nmVst4::getParameterName(VstInt32 index, char* label){
  vst_strncpy(label, "Param1", kVstMaxParamStrLen);
}

void nmVst4::getParameterDisplay(VstInt32 index, char* text){
  dB2string(fParam1, text, kVstMaxParamStrLen);
}

void nmVst4::getParameterLabel(VstInt32 index, char* label){
  vst_strncpy(label, "dB", kVstMaxParamStrLen);
}

void nmVst4::setSampleRate(float sampleRate){
  sample_rate = sampleRate;
  AudioEffectX::setSampleRate(sampleRate);
}

void nmVst4::processReplacing(float** inputs, float** outputs, VstInt32 sampleFrames){
  float* out1 = outputs[0];
  float* out2 = outputs[1];

  static float count = 0.0f;

  while(--sampleFrames >= 0){
    if(note_on == 1){
      if(d_frame >= 0){
        count = 0.0f;
      }
      else{
        count += 0.1f;
        if(count > 0.5f){
          count = -0.5f;
        }
      }
      d_frame--;
    }
    else{
      count = 0.0f;
    }

    (*out1++) = count;
    (*out2++) = count;
  }
}

VstInt32 nmVst4::processEvents(VstEvents* ev){
  for(VstInt32 i = 0; i < ev->numEvents; i++){
    if((ev->events[i])->type != kVstMidiType){
      continue;
    }

    VstMidiEvent* event = (VstMidiEvent*)ev->events[i];
    char* midiData = event->midiData;
    d_frame = event->deltaFrames;
    VstInt32 status = midiData[0] & 0xf0;  // チャンネルは無視する。

    if(status == 0x90){  // 発音
      VstInt32 note = midiData[1] & 0x7f;      // 音程
      VstInt32 velocity = midiData[2] & 0x7f;  // ベロシティ
      note_on = 1;
    }
    else if(status == 0x80){  // 消音
      note_on = 0;
    }

    event++;
  }  
  return 1;
}
inserted by FC2 system