2

私はたくさん検索しましたが、この問題の解決策を見つけることができません。オーディオをリアルタイムで処理するアプリを作成しています。そこで、マイクを初期化し、受信したサウンドを処理する ASyncTask を作成しました。

public class SoundSampler extends AsyncTask<Void, Void, Void>{

AudioRecord recorder;
int bufferSize;
final short[] audioData;

public SoundSampler() {
    int samplerate = 44100;
    int encoding = AudioFormat.ENCODING_PCM_16BIT;
    int config = AudioFormat.CHANNEL_IN_MONO;
    bufferSize = AudioRecord.getMinBufferSize(samplerate, config, encoding);
    recorder = new AudioRecord(MediaRecorder.AudioSource.MIC, samplerate, config, encoding, bufferSize);

    final int finalBufferSize = bufferSize;
    audioData = new short[finalBufferSize];             

    OnRecordPositionUpdateListener positionUpdater = new OnRecordPositionUpdateListener() {
        @Override
        public void onPeriodicNotification(AudioRecord recorder) {
        // do something amazing with audio data (long operations)
        }

        @Override
        public void onMarkerReached(AudioRecord recorder) {                            Log.d("Process", "marker reached");
        }
    };
    recorder.setRecordPositionUpdateListener(positionUpdater);
    recorder.setPositionNotificationPeriod(64);
    Log.d("Process", "starTAGt recording, bufferSize: " + bufferSize);
    Log.d("Process", "state = " + recorder.getState() + " aud = " + audioData.length);
    }

    @Override
    protected Void doInBackground(Void... params) {
        recorder.startRecording();
        Log.d("Process", "rec = " + recorder.getRecordingState());
        while (!isCancelled()) {
             recorder.read(audioData, 0, bufferSize);
        }
        recorder.stop();
        return null;
    }

}

そして、これは私の主な活動の onCreate です:

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        Button on = (Button) findViewById(R.id.on);
        Button off = (Button) findViewById(R.id.off);

        final SoundSampler smp =  new SoundSampler();

        on.setOnClickListener(new View.OnClickListener() {          
            @Override
            public void onClick(View v) {
                 smp.execute();
            }
        });

        off.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                smp.cancel(true);
            }
        });


    }

これでサウンドが登録されましたが、SoundSampler AsyncTask を開始すると、Ui がブロックされます。SoundSampler にデータを登録してもらいたいが、メイン UI から好きなように停止させたい。これを行うことについていくつかの提案はありますか?

4

1 に答える 1

0

OnRecordPositionUpdateListenerメソッドは UI スレッドで呼び出されています。これは、リスナーのメソッド内に次のログ ステートメントを挿入することで確認できます。

Log.i(TAG, "OnRecordPositionUpdateListener on thread: " + Thread.currentThread().getName());

実行時間の長い操作を実行するには、新しいスレッドを生成する必要がありますonPeriodicNotification(AudioRecord recorder){}

于 2012-11-01T21:23:36.497 に答える