如何触发声音输入振动? [英] How to trigger Vibration on Sound Input?

查看:313
本文介绍了如何触发声音输入振动?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想创建一个Android应用程序,我筛选蜂鸣声的一个特定的频率,使手机震动。

I am trying to create an android application where I filter one specific frequency of a beep and make the phone vibrate.

我正在从移动MIC输入,并使用MediaRecorder类,使用这个类,我可以记录,保存和播放输入。现在我需要我的手机震动每当有蜂鸣/或任何声音。

I am taking input from the MIC of mobile and using MediaRecorder class, by using this class, I can record, save and play the input. Now I need my mobile to vibrate whenever there is a beep/or any sound.

输入由导线向移动的耳机插孔定,所以我知道只有一个频率被输入。

The input is given by a wire to the Headphone jack of the mobile so I know that there is only one frequency being input.

我有一个按钮,点击它开始记录。
我有权振动和记录我已经清单文件。

I have a button, Clicking which starts recording. I have Permissions to vibrate and record in my manifest file already.

record.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                try {
                    isRecording=true;
                    myAudioRecorder.prepare();
                    myAudioRecorder.start();
...
}

我也试着上网搜索,发现了一种类似的问题这里但我无法找到任何正确的答案。

I also tried to search the internet and found kind of the similar question here but I am unable to find any correct answer.

不过,我可以对点击另一个按钮手机震动,这里是code的snipt,

However, I can make the phone vibrate on clicking another button and here is the snipt of code,

 Vibrator vibrate;
    vibrate = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE);

        Btn1.setOnClickListener(new View.OnClickListener()

                                {
                                    @Override
                                    public void onClick(View v) {
                                       vibrate.vibrate(800);
                                    }
                                }

我打过电话里面recorder.start振动器();功能但是这使得手机振动,即使没有声音了。
我也试着从这个问题所以每当有沉默,手机不应该震动,但我越来越糊涂,我有点明白,应该有一个布尔值,当有声音,让手机震动它获取真实的,但我不能把这个逻辑到code。
请让我知道我能在这方面做的,哪些方向应我中搜索?

I tried calling a Vibrator inside recorder.start(); function but this makes the phone vibrate even when there is no sound anymore. I also tried getting help from this question so whenever there is silence, the phone should not vibrate, but I am getting confused, I somehow understand that there should be a Boolean which gets true when there is sound and make the phone vibrate, but I am unable to put this logic into code. Please let me know what can I do in this context and which direction should I be searching in?

更新
我发现 toturial用于显示与输入声音的振幅进度条,它工作正常我试图让手机振动时,有缓冲一定的价值,现在,振动,即使幅度是零,我猜是因为每个振动使得这导致手机振动噪声的事实,多数民众赞成。我无法通过举杯检查,因为功能的了java.lang.RuntimeException:无法内螺纹已不叫尺蠖prepare(创建处理) 。请问有什么建议吗?

UPDATE I found this toturial for showing the progress bar with amplitude of input sound, it works fine and I tried to make the phone vibrate when there is some value in buffer, Now it vibrates even when the amplitude is zero, I guess thats because of the fact that every vibration makes noise which leads the phone to vibrate. I am unable to check the function via TOAST because of java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare(). Is there any suggestion?

推荐答案

有关您的主要问题,也许你可以检查声音的振幅,且仅当一个最低门槛已经达到振动。事情是这样的:

For your main problem, maybe you can check for the amplitude of the sound, and only vibrate if a minimum threshold has been reached. Something like this:

private class DetectAmplitude extends AsyncTask<Void, Void, Void> {

    private MediaRecorder mRecorder = null;
    private final static int MAX_AMPLITUDE = 32768;
    //TODO: Investigate what is the ideal value for this parameter
    private final static int MINIMUM_REQUIRED_AVERAGE = 5000;

    @Override
    protected Void doInBackground(Void... params) {
        Boolean soundStarted = true;
        if (mRecorder == null) {
            mRecorder = new MediaRecorder();
            mRecorder.setAudioSource(MediaRecorder.AudioSource.MIC);
            mRecorder.setOutputFormat(MediaRecorder.OutputFormat.THREE_GPP);
            mRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB);
            mRecorder.setOutputFile("/dev/null");
            try {
                mRecorder.prepare();
            } catch (IllegalStateException e) {
                soundStarted = false;
                Log.e(TAG, "Could not detect background noise. Error preparing recorder: " + e.getMessage());
            } catch (IOException e) {
                soundStarted = false;
                Log.e(TAG, "Could not detect background noise. Error preparing recorder: " + e.getMessage());
            }
            try {
                mRecorder.start();
            } catch (RuntimeException e) {
                Log.e(TAG, "Could not detect background noise. Error starting recorder: " + e.getMessage());
                soundStarted = false;
                mRecorder.release();
                mRecorder = null;
            }
        }

        if (soundStarted) {
            // Compute a simple average of the amplitude over one
            // second
            int nMeasures = 100;
            int sumAmpli = 0;
            mRecorder.getMaxAmplitude(); // First call returns 0
            int n = 0;
            for (int i = 0; i < nMeasures; i++) {
                if (mRecorder != null) {
                    int maxAmpli = mRecorder.getMaxAmplitude();
                    if (maxAmpli > 0) {
                        sumAmpli += maxAmpli;
                        n++;
                    }
                } else {
                    return null;
                }
                try {
                    Thread.sleep(1000 / nMeasures);
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
            mRecorder.stop();
            mRecorder.release();
            mRecorder = null;

            final float avgAmpli = (float) sumAmpli / n;

            if (avgAmpli > MINIMUM_REQUIRED_AVERAGE) {
                //TODO: Vibrate the device here
            }
        }
        return null;
    }
} 

有关检测声级的更多信息,请参考以下内容:

For more information regarding the detection of sound level, please refer to the following:

  • android: detect sound level
  • What does Android's getMaxAmplitude() function for the MediaRecorder actually give me?

有关异常了java.lang.RuntimeException:无法内螺纹创建的处理程序已经不叫尺蠖prepare(),正在发生,因为吐司需要您的应用程序的主线程上运行。如果你的 code(像的AsyncTask )是活动<内部/ code>,你可以尝试以下方法:

Regarding the exception java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare(), that is happening because the Toast needs to run on the main thread of your app. If your Thread code (like an AsyncTask) is inside an Activity, you can try the following:

runOnUiThread(new Runnable() {
        @Override
        public void run() {
            //Call your Toast here
        }
    });

否则,你需要以某种方式传递你的方法结束到活动为它运行吐司

编辑:

如果你想使用这个从按钮,你可以设置它的 OnClickListener 活动的onCreate()调用执行的AsyncTask 那里。例如:

If you want to use this from a Button, you could set its OnClickListener on your Activity's onCreate() call and execute the AsyncTask there. For example:

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.your_layout);
    Button button = (Button)findViewById(R.id.your_button_id);
    button.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            new DetectAmplitude().execute(new Void[]{});
        }
    });
}

我建议你看一看的AsyncTask是如何工作的使用前该生产code。

I suggest you take a look at how AsyncTask works before using this in production code.

这篇关于如何触发声音输入振动?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆