Androidは携帯電話の通話後の振動提示機能を実現します。


一部の携帯電話は電話をつないでから振動があります。これはつないでから耳元に置いて、放射線を減らすことができるという利点があります。この記事では、Androidの携帯電話でこのような電話をつないだ後の振動ヒント機能をどのように実現するかについて説明します。ここでは主に呼び出しの電話についてです。
       Android SDKが提供する通話状態
       明らかに、電話をつなぐ時に振動のヒントを与えるためには、まず電話がいつ接続されているかを知る必要があります。Android SDKはこの状態を直接読み取る方法を与えていない。以下はAndroid SDKの電話サービス類TelephonyManagerが提供する3つの電話状態です。
       CALL_STATE_IDLE         アイドル状態
       CALL_STATE_OFFHOOK抜機状態
       CALL_STATE_RING ING   鳴動状態
       これらの状態は分かりやすいです。電話を切った状態で受話器を取り上げる(電話機にとっての動作)が、この状態は電話をかけた時に発生するかもしれないし、電話をかけた時に発生するかもしれないが、電話がかかった時に呼び出すと説明できないです。以上の3つの状態を通して、私達は電話と電話の接続の二つの状態だけを組み合わせることができます。今日私達が実現する機能はできません。
       他の方法を探して実現する必要があるようです。SDKは頼りないですね。
       Androidのロゴ分析
       幸いAndroidは運行中に大量のロゴが発生します。この上から突波口を見つけられますか?私たちはAndroidのRadioモジュールのログを選んで分析した。まずコードを書いてRadio関連のロゴを読み取る必要があります。ロゴを読み込むにはロゴcatを使わなければなりません。

 Process process; 
  InputStream inputstream; 
  BufferedReader bufferedreader; 
  try { 
   process = Runtime.getRuntime().exec("logcat -v time -b radio"); 
   inputstream = process.getInputStream(); 
   InputStreamReader inputstreamreader = new InputStreamReader( 
     inputstream); 
   bufferedreader = new BufferedReader(inputstreamreader); 
 String str = ""; 
while ((str = bufferedreader.readLine()) != null) { 
  log.i("mLogcat",str); 
} 
} catch (Exception e) { 
    
  } 
また、プログラムをシステムのロゴを読み取るには指定権限が必要です。Android Manifest.xmlファイルに内容を入れてください。
XML/HTMLコード
<uses-permission android:name=“android.permission.READ_”LOGS"  
       上記のコードを通してRadioのロゴを出力できます。そうすると、DDMSでこれらのロゴを調べて、その中の通話過程を分析できます。具体的につかんだロゴは貼り付けません。自分でプログラムを作成して上のコードで掴み取って分析します。私の分析結果だけを話します。
       ロゴを解析することによっていくつかの手がかりが発見された。いくつかのログがあります。
       GET_CURRENT_CALLS  id=1、DIALING
       GET_CURRENT_CALLS  id=1、ALERTING
       GET_CURRENT_CALLS  id=1,ACTIVE
       ロゴが長いので、各ロゴの先頭部分だけを持っています。本当に多くの内容があります。電話をかけると、このようなロゴが入力されます。
       ダイヤルアップ->アラーム->アクティビティ
       大体このような過程です。何回かのテストを経て、電話がつながったら活動状態になり、出力:GET_CURRENT_CALLS  id=1,ACTIVE  このロゴはこれで成功に近いです。
       しかし、その後、ダイヤルが始まってから電話がかかってくるまでの間に、何度も何度も「ダイヤル-」という状態が変化しているのを発見しました。マイクの中でブザーという音がしたら、GET_。CURRENT_CALLSというログはALERTINGにロックされます。電話が通じる前にGET_はもう現れません。CURRENT_CALLS日誌です。
       上記の表現はよく分からないかもしれませんが、つまり通話をする前に何度もGET_が発生します。CURRENT_CALLS ACTIVEというログは、一度だけ電話がつながって生まれたものです。これは私たちに迷惑をかけました。ただGETをつかむだけではいけません。CURRENT_CALLS ACTIVEという情報で判断しました。
       私たちは論理的な判断でしか実現できませんでした。
       実例コード解説
       コードを見ます。

class TestThread implements Runnable { 
 //    
 Vibrator mVibrator; 
 //     
 TelephonyManager telManager; 
 public TestThread(Vibrator mVibrator, TelephonyManager telManager) { 
  this.mVibrator = mVibrator; 
  this.telManager = telManager; 
 } 
 @Override 
 public void run() { 
  //         
  int callState = telManager.getCallState(); 
  Log.i("TestService", "  .........." + Thread.currentThread().getName()); 
  //         
  long threadStart = System.currentTimeMillis(); 
  Process process; 
  InputStream inputstream; 
  BufferedReader bufferedreader; 
  try { 
   process = Runtime.getRuntime().exec("logcat -v time -b radio"); 
   inputstream = process.getInputStream(); 
   InputStreamReader inputstreamreader = new InputStreamReader( 
     inputstream); 
   bufferedreader = new BufferedReader(inputstreamreader); 
   String str = ""; 
   long dialingStart = 0; 
   boolean enableVibrator = false; 
   boolean isAlert = false; 
   while ((str = bufferedreader.readLine()) != null) { 
    //             ,     
    if (callState == TelephonyManager.CALL_STATE_OFFHOOK 
      && telManager.getCallState() == TelephonyManager.CALL_STATE_IDLE) { 
     break; 
    } 
    //     5       
    if (System.currentTimeMillis() - threadStart > 300000) { 
     break; 
    } 
    Log.i("TestService", Thread.currentThread().getName() + ":" 
      + str); 
    //   GSM  DIALING 
    if (str.contains("GET_CURRENT_CALLS") 
      && str.contains("DIALING")) { 
     //  DIALING        ALERTING    DIALING 
     if (!isAlert || dialingStart == 0) { 
      //  DIALING       
      dialingStart = System.currentTimeMillis(); 
      isAlert = false; 
     } 
     continue; 
    } 
    if (str.contains("GET_CURRENT_CALLS") 
      && str.contains("ALERTING")&&!enableVibrator) { 
      
     long temp = System.currentTimeMillis() - dialingStart; 
     isAlert = true; 
     //     ,    DIALING     ,    ALERTING     1.5      20      
     //       ACTIVE       . 
     if (temp > 1500 && temp < 20000) { 
      enableVibrator = true; 
      Log.i("TestService", "    ....." + temp + "....." 
        + Thread.currentThread().getName()); 
     } 
     continue; 
    } 
    if (str.contains("GET_CURRENT_CALLS") && str.contains("ACTIVE") 
      && enableVibrator) { 
     mVibrator.vibrate(100); 
     enableVibrator = false; 
     break; 
    } 
   } 
   Log.i("TestService", "  .........." 
     + Thread.currentThread().getName()); 
  } catch (Exception e) { 
   // TODO: handle exception 
  } 
 } 
} 
      私のこの方法は無理です。初めてDIALINGとALERTINGの間の間隔を判断することによって、1.5秒以上の間隔であれば、すでに「Do」のメッセージが入っていると思います。次のACTIVEは電話でつながります。この1.5秒はログを解析して得られた。しかし、この方法はいつもあまりあてにならないと思います。皆さんはいい方法があれば交流できます。
       あとはこのスレッドを電話で呼び出す時に触発し、電話に常駐する時に準備すればいいです。ServiceとReceiverを組み合わせて実現できます。Serviceが常駐を実現し、Receiverが待ち受け電話の呼び出しを実現します。私たちが欲しい機能は基本的に完成できます。
        以上のコードは全部テストしました。99%有効です。ハハ。この中では、いくつかのAndroidの基礎的な内容に言及しています。例えば、locat、Service、Receiverのようなものがあります。
        この文を通じてAndroidの開発を手伝ってくれる友達を望んでいます。ありがとうございます。