0

画面がアクティブなときにアプリケーションが正常に動作するという問題が発生していますが、画面がロックされているかスリープ状態のときに、特定のコードが実際にクラッシュすることなく、アプリを無期限に一時停止しているように見えます。

このアプリは、AVAudioPlayers と boost::threads を使用して、いくつかの音楽トラックを再生します。トラックが終了すると、新しいトラックを準備するために多くのセットアップを呼び出す必要があります。同時に、アプリは数秒間一時停止する必要があります。この並列アクティビティは、boost::threads で実現されます。

画面がアクティブな場合、これはすべて正常に機能します。ただし、画面がアクティブでない場合、新しいトラックは再生されません。クラッシュは発生せず、ブレークポイントを使用してデバッグすると、アプリが特定の行 (デバッグ セッションからデバッグ セッションに変更された行) で単にハングし、スタックするように見えます。EXC_BAD_ACCESS をそれほど期待したことはありませんが、何もありません。コードがハングしている理由のヒントはありません。

メインスレッドがブロックされている可能性がありますか? 私はいくつかの performSelectorOnMainThread 呼び出しを使用していますが、applicationWillResignActive を使用して画面がロックされているときにそれらを無効にしました。ただし、これで問題は解決していません。

ハングしているように見える boost::thread は次のとおりです。

void MyClass::loopThread(int waitSeconds)
{
    loopScheduled = true;

    sleep(waitSeconds);

    if ( loopScheduled == true ) {

        if (engine_isRunning()) {
            joinEngineThread();
        }
        startEngineThread();
        ((CPlusPlus*)m_obj)->markAsPlaying();
    }
}

にぶら下がっているようです

if ( loopScheduled == true ) {

ライン。

このスレッドで何が起こっているかというと、他の並列スレッドが sleep() 呼び出し中に loopScheduled を false に設定でき、loopScheduled が false の場合、後のメソッドは呼び出されないということです。

ただし、私が抱えている問題に関しては、loopScheduled は無関係である必要があります。他の方法で false に設定されておらず、sleep() 呼び出し後も true です。

何が起こっているのか誰にも分かりませんか?

4

1 に答える 1

0

問題が見つかりました。アプリがトラック間で一時停止している間に、オーディオ セッションが終了していました。

画面がロックされているかスリープ状態にある場合、またはアプリケーションがバックグラウンドにある場合、最後の AVAudioPlayer の再生が終了すると、オーディオ セッションが終了することがわかります。これは、新しい AVAudioPlayers を準備または再生できないことを意味します。そのため、新しいトラックを再生できません。

この問題を回避するために、トラック間の一時停止中にサイレント ファイルを再生しています。これにより、オーディオ セッションが続行されます。つまり、再生するように指示されたときに新しいトラックが再生されます。

于 2012-11-05T16:36:08.050 に答える