Skip to content

Commit

Permalink
Initial Commit
Browse files Browse the repository at this point in the history
  • Loading branch information
hotwatermorning committed Dec 4, 2013
0 parents commit 9fab390
Show file tree
Hide file tree
Showing 13 changed files with 1,458 additions and 0 deletions.
14 changes: 14 additions & 0 deletions .gitignore
@@ -0,0 +1,14 @@
*.*
!*.cpp
!*.hpp
!*.txt
!*.sln
!*.vcxproj
!*.vcxproj.filters
!*.gitignore
!*.md

Debug/
Release/

!VstHostDemo/vstsdk2.4/
23 changes: 23 additions & 0 deletions LICENSE_1_0.txt
@@ -0,0 +1,23 @@
Boost Software License - Version 1.0 - August 17th, 2003

Permission is hereby granted, free of charge, to any person or organization
obtaining a copy of the software and accompanying documentation covered by
this license (the "Software") to use, reproduce, display, distribute,
execute, and transmit the Software, and to prepare derivative works of the
Software, and to permit third-parties to whom the Software is furnished to
do so, all subject to the following:

The copyright notices in the Software and this entire statement, including
the above license grant, this restriction and the following disclaimer,
must be included in all copies of the Software, in whole or in part, and
all derivative works of the Software, unless such copies or derivative
works are solely in the form of machine-executable object code generated by
a source language processor.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT
SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE
FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE,
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.
22 changes: 22 additions & 0 deletions Readme.md
@@ -0,0 +1,22 @@
# VstHostDemo

## What's this.

C++ Advent Calendar 2013のネタとして作成したVSTホストアプリケーションです。
VSTiをロードして、音を鳴らせます。

## プログラムのビルド方法

1. [Steinberg](http://japan.steinberg.net/)から、VST 2.4のSDKをダウンロードし、ソリューション内のvstsdk2.4に展開したファイルをコピーする。

2. [Boost](http://www.boost.org/)から、Boost.1.53.0をダウンロードしビルドする。(試してはいないが、1.54.0, 1.55.0でも問題ないだろうと思われる。)

3. [balorライブラリの公式ブログ](http://d.hatena.ne.jp/syanji/20110731/1312105612)から、balor 1.0.1をダウンロードし、ビルドする。

4. VstHostDemo.slnを開き、Boost, balorのインクルードディレクトリ、ライブラリディレクトリを設定する。

5. VstHostDemoプロジェクトをビルドする。

## ライセンス

このソースコードは、Boost Software License, Version 1.0で公開します。
20 changes: 20 additions & 0 deletions VstHostDemo.sln
@@ -0,0 +1,20 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 2012
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "VstHostDemo", "VstHostDemo\VstHostDemo.vcxproj", "{7BA8AE44-5EC6-4981-9FB5-6833CF02DAE2}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Win32 = Debug|Win32
Release|Win32 = Release|Win32
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{7BA8AE44-5EC6-4981-9FB5-6833CF02DAE2}.Debug|Win32.ActiveCfg = Debug|Win32
{7BA8AE44-5EC6-4981-9FB5-6833CF02DAE2}.Debug|Win32.Build.0 = Debug|Win32
{7BA8AE44-5EC6-4981-9FB5-6833CF02DAE2}.Release|Win32.ActiveCfg = Release|Win32
{7BA8AE44-5EC6-4981-9FB5-6833CF02DAE2}.Release|Win32.Build.0 = Release|Win32
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
EndGlobal
283 changes: 283 additions & 0 deletions VstHostDemo/HostApplication.cpp
@@ -0,0 +1,283 @@
#pragma warning(push)
#pragma warning(disable: 4996)

#include <algorithm>
#include <boost/range/size.hpp>
#include <boost/static_assert.hpp>
#include <boost/chrono.hpp>

#include <tchar.h>

#include "./HostApplication.hpp"
#include "./VstPlugin.hpp"

namespace hwm {

HostApplication::HostApplication(size_t sampling_rate, size_t block_size)
: sampling_rate_(sampling_rate)
, block_size_(block_size)
{}

VstIntPtr VSTCALLBACK VstHostCallback(AEffect* effect, VstInt32 opcode, VstInt32 index, VstIntPtr value, void *ptr, float opt)
{
//! VstPluginの初期化が完了するまではこっち
if( !effect || !effect->user) {
switch(opcode) {
case audioMasterVersion:
return kVstVersion;
default:
return 0;
}
} else {
//! VstPluginの初期化が完了すると、effect->userに、effectを保持しているVstPluginのアドレスが入っている
VstPlugin *vst = static_cast<VstPlugin *>(effect->user);
return vst->GetHost().Callback(vst, opcode, index, value, ptr, opt);
}
}

VstIntPtr HostApplication::Callback(VstPlugin* vst, VstInt32 opcode, VstInt32 index, VstIntPtr value, void *ptr, float opt)
{
int result = false;
opt; //未使用の変数の警告を抑制

switch( opcode )
{
case audioMasterAutomate:
//! Pluginからの操作の通知
//! オートメーション操作の記録に対応したVSTホストは
//! ここで渡ってきたデータをオートメーションエンベロープに記録する
break;

case audioMasterVersion:
result = kVstVersion;
break;

case audioMasterCurrentId:
//! kPlugCategShellタイプのプラグインに対して、全てのサブプラグイン名を展開するときにのみ呼ばれる
return vst->GetEffect()->uniqueID;

case audioMasterIdle:
//! VSTプラグインのアイドル時間をVSTホスト渡す
//! VSTホストは、全ての開いているプラグインエディタに対して、effEditIdleを呼び出したりする
{
if(vst->IsEditorOpened()) {
vst->dispatcher(effEditIdle, 0, 0, 0, 0);
}
}
break;

//Deprecated
//case audioMasterPinConnected:
//break;
//Deprecated
//case audioMasterWantMidi:
//break;

case audioMasterGetTime:
//! VSTホストの現在の時刻情報を返す
timeinfo_.samplePos = 0;
timeinfo_.sampleRate = 44100;
timeinfo_.nanoSeconds = GetTickCount() * 1000.0 * 1000.0;
timeinfo_.ppqPos = 0;
timeinfo_.tempo = 120.0;
timeinfo_.barStartPos = 0;
timeinfo_.cycleStartPos = 0;
timeinfo_.cycleEndPos = 0;
timeinfo_.timeSigNumerator = 4;
timeinfo_.timeSigDenominator = 4;
timeinfo_.smpteOffset = 0;
timeinfo_.smpteFrameRate = kVstSmpte24fps ;
timeinfo_.samplesToNextClock = 0;
timeinfo_.flags = (kVstNanosValid | kVstPpqPosValid | kVstTempoValid | kVstTimeSigValid);

return reinterpret_cast<VstIntPtr>(&timeinfo_);

case audioMasterProcessEvents:
//! プラグインから送られてきたイベントを処理する
//! processReplacingの呼び出しの中から呼ばれる。
break;

//Deprecated
//case audioMasterSetTime:
//break;
//Deprecated
//case audioMasterTempoAt:
//break;
//Deprecated
//case audiomasterGetNumAutomatableParameters:
//break;
//Deprecated
//case audioMasterGetParameterQuantization:
//break;

case audioMasterIOChanged:
break;

//Deprecated
//case audioMasterNeedIdle:
//break;

case audioMasterSizeWindow:
//! プラグインからのサイズ変更要請
{
size_t const width = index;
size_t const height = value;
vst->SetWindowSize(width, height);
return 1; //return 1 if supported to set window size
}

case audioMasterGetSampleRate:
//! サンプリングレート問い合わせ
return sampling_rate_;

case audioMasterGetBlockSize:
// ブロックサイズ問い合わせ
return block_size_;

case audioMasterGetInputLatency:
//! 入力レイテンシ問い合わせ
return 0;

case audioMasterGetOutputLatency:
//! 出力レイテンシ問い合わせ
return 0;

//Deprecated
//case audioMasterGetPreviousPlug:
//break;
//Deprecated
//case audioMasterGetNextPlug:
//break;
//Deprecated
//case AudioMasterWillReplaceOrAccumulate:
//break;

case audioMasterGetCurrentProcessLevel:
return kVstProcessLevelUnknown;

case audioMasterGetAutomationState:
return kVstAutomationOff;

case audioMasterOfflineStart:
break;

case audioMasterOfflineRead:
break;

case audioMasterOfflineWrite:
break;

case audioMasterOfflineGetCurrentPass:
break;

case audioMasterOfflineGetCurrentMetaPass:
break;

//Deprecated
//case audiomasterSetOutputSampleRate:
//break;
//Deprecated
//case audioMasterGetputSpeakerArrangement:
//break;

case audioMasterGetVendorString:
{
static char const vendor_string[] = "hotwatermorning";
static size_t const vendor_string_len = sizeof(vendor_string)/sizeof(char) - 1;
BOOST_STATIC_ASSERT(vendor_string_len <= kVstMaxVendorStrLen);
std::copy(vendor_string, vendor_string + vendor_string_len, static_cast<char *>(ptr));
}
return 1;

case audioMasterGetProductString:
{
static char const product_string[] = "Vst Host Test";
static size_t const product_string_len = sizeof(product_string)/sizeof(char) - 1;
BOOST_STATIC_ASSERT(product_string_len <= kVstMaxProductStrLen);
std::copy(product_string, product_string + product_string_len, static_cast<char *>(ptr));
}
return 1;

case audioMasterGetVendorVersion:
{
return 1;
}

case audioMasterVendorSpecific:
break;

//Deprecated
//case audioMasterSetIcon:
//break;

case audioMasterCanDo:
//! ホストがサポートしている機能をVSTプラグインに通知
{
char const *do_list[] = {
{ "sendVstEvents" },
{ "sendVstMidiEvents" },
{ "sizeWindow" },
{ "startStopProcess" },
{ "sendVstMidiEventFlagIsRealtime" } };

for(auto elem: do_list) {
if(strcmp(elem, static_cast<char const *>(ptr)) == 0) {
return 1;
}
}
//don't know
return 0;
}

case audioMasterGetLanguage:
{
return kVstLangJapanese;
}

//Deprecated
//case audioMasterOpenWindow:
//break;

//Deprecated
//case audioMasterCloseWindow:
//break;

case audioMasterGetDirectory:
//! プラグインのDLLを含んでいるディレクトリの問い合わせ
return reinterpret_cast<VstIntPtr>(vst->GetDirectory());

case audioMasterUpdateDisplay:
break;

case audioMasterBeginEdit:
break;

case audioMasterEndEdit:
break;

case audioMasterOpenFileSelector:
break;

case audioMasterCloseFileSelector:
break;

//Deprecated
//case audioMasterEditFile:
//break;
//Deprecated
//case audioMasterGetChunkFile:
//break;
//Deprecated
//case audioMasterGetInputSpeakerArrangement:
//break;

default:
//unsupported opcodes
;
}
return result;
}

} //::hwm

#pragma warning(pop)
30 changes: 30 additions & 0 deletions VstHostDemo/HostApplication.hpp
@@ -0,0 +1,30 @@
#pragma once

#pragma warning(push)
#pragma warning(disable: 4996)
#include "./vstsdk2.4/pluginterfaces/vst2.x/aeffectx.h"
#pragma warning(pop)

namespace hwm {

struct VstPlugin;

struct HostApplication
{
HostApplication(
size_t sampling_rate,
size_t block_size );

VstIntPtr Callback(VstPlugin* vst, VstInt32 opcode, VstInt32 index, VstIntPtr value, void *ptr, float opt);

private:
size_t sampling_rate_;
size_t block_size_;
VstTimeInfo timeinfo_;
};

//! プラグイン内部からの要求などを受けて呼び出される
//! Host側のコールバック関数
VstIntPtr VSTCALLBACK VstHostCallback(AEffect* effect, VstInt32 opcode, VstInt32 index, VstIntPtr value, void *ptr, float opt);

} //::hwm

0 comments on commit 9fab390

Please sign in to comment.