現在の再生されている場所に線が表示されるとかっこいいです。
本格的なアプリっぽい感じがでるよね~
JUCEプログラミング、Draw audio waveformsのチュートリアルの「Adding a time position marker」を進めていきます。
こんな人の役に立つかも
・JUCEフレームワークに入門したい人
・JUCEで音声プログラミングを学びたい人
・JUCEのAudioチュートリアルを進めている人
作成するアプリ
チュートリアルのプログラムを実装することで、スクショのように、再生中の場所を表示することができました。
実装
MainComponent.h
タイマークラスを利用して、一定時間毎に波形に現在時間を表示するための線を描きなおします。.hファイルのMainComponentクラスにTimerクラスを継承させます。
class MainComponent : public juce::AudioAppComponent,
public juce::ChangeListener,
private juce::Timer//タイマーをクラスに追加しました。
タイマーのコールバック関数をオーバーライドしておきます。publicです。
public:
//...略...
void timerCallback() override;//タイマーのコールバック関数をオーバーライドします。
MainComponent.cpp
コンストラクタ
コンストラクタでタイマーを40msec毎に動作させるように指定します。
MainComponent::MainComponent()
: state(Stopped),
thumbnailCache(5),
thumbnail(512, formatManager, thumbnailCache)
{
//...略...
startTimer(40);//タイマースタート
}
timerCallback関数
タイマーの40msec毎に動作させる処理です。repaint処理でpaint関数の波形描画処理を呼び出します。
//タイマーコールバック
void MainComponent::timerCallback()
{
repaint();
}
paintFileLoaded関数
paint関数からthumbnailがロードされている場合に呼び出されるpaintFileLoaded関数に現在の再生位置に緑の垂直線を描画する処理を追加します。
void MainComponent::paintIfFileLoaded(juce::Graphics& g, const juce::Rectangle<int>& thumbnailBounds)
{
g.setColour(juce::Colours::white);
g.fillRect(thumbnailBounds);
g.setColour(juce::Colours::red);
auto audioLength = (float)thumbnail.getTotalLength();
//[1]追加しました。
thumbnail.drawChannels(g,thumbnailBounds,
0.0, thumbnail.getTotalLength(),
1.0f);
//[2]ここからが現在時間の線の描画になります。
g.setColour(juce::Colours::green);
auto audioPosition = (float)transportSource.getCurrentPosition();
//[3]垂直線の描画起点を算出します。
auto drawPosition = (audioPosition / audioLength) * (float)thumbnailBounds.getWidth()
+ (float)thumbnailBounds.getX();
g.drawLine(drawPosition, (float)thumbnailBounds.getY(), drawPosition,
(float)thumbnailBounds.getBottom(), 2.0f);
}
[1]で、thumbnailから音声波形の長さを取得します。秒数で取得できるみたいです。
[2]からは垂直線の描画処理です。まずはsetColourで描画色を緑に設定します。次に、「audioPosition」変数にtransportSourceから現在の音声の再生時間を取得してきます。
[3] には、drawPosition変数に垂直線の描画の起点を算出します。
波形全体に対する現在の相対的な位置として、「現在の秒数/全体の秒数」で計算できます。これに、波形の全体の長さである「getWidth()」で得られた数値を掛けると、GUI上の波形の幅に対しての現在の位置が得られます。これに、getXで得られる波形描画領域の左のマージン部分をたすと、GUI上の垂直線の起点を計算することができます。
プログラム例
今回のプログラムをGitHubのリポジトリにアップロードしていますので、ぜひご活用ください。