显示来自BroadcastReceiver的消息

时间:2014-03-17 18:44:17

标签: android broadcastreceiver android-alertdialog popupwindow

我编写了一个简单的类,它扩展了BroadcastReceiver以处理来电并获取来电者的号码。现在我想在弹出窗口或类似的东西中显示该数字。我试图显示警告对话框或打开活动,但我的应用程序崩溃了。然后我读到从BroadcastReceiver类开始对话不是一个好主意。我需要你建议我如何在有来电时在屏幕上正确显示来电号码。这是我的广播接收器类:

package com.example.nrsearch;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.telephony.PhoneStateListener;
import android.telephony.TelephonyManager;
import android.util.Log;

public class CallReceiver extends BroadcastReceiver {
    public CallReceiver() {
    }

@Override
public void onReceive(Context context, Intent intent) {
    Log.i("CallReceiverBroadcast", "onReceive() is called. ");
    TelephonyManager teleMgr = (TelephonyManager)context.getSystemService(Context.TELEPHONY_SERVICE);
    PhoneStateListener psl = new PhoneStateListener() {
        @Override
        public void onCallStateChanged(int state, String incomingNumber) {
            Log.i("CallReceiverBroadcast", "onCallStateChanged() is called. ");
            switch (state) {
            case TelephonyManager.CALL_STATE_RINGING:
                Log.i("CallReceiverBroadcast", "Incoming call caught. Caller's number is " + incomingNumber + ".");
            }
        }
    };
    teleMgr.listen(psl, PhoneStateListener.LISTEN_CALL_STATE);
    teleMgr.listen(psl, PhoneStateListener.LISTEN_NONE);
}
}

2 个答案:

答案 0 :(得分:3)

我创建了IncomingCallService服务,该服务从BroadcastReceiver延伸到处理来电并获取来电者的号码。现在我在TrueCaller等弹出窗口中显示了来电号码。它的工作很好我。希望它对你有所帮助。请尝试让我知道。感谢

<强> CallReceiver.java

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.telephony.PhoneStateListener;
import android.telephony.TelephonyManager;
import android.util.Log;

public class CallReceiver extends BroadcastReceiver {

    static String IncomingNumber;
    @Override
    public void onReceive(final Context context, Intent intent) {
        TelephonyManager teleMgr = (TelephonyManager)context.getSystemService(Context.TELEPHONY_SERVICE);
        PhoneStateListener psl = new PhoneStateListener() {
        @Override
        public void onCallStateChanged(int state, String incomingNumber) {
            switch (state) {
            case TelephonyManager.CALL_STATE_RINGING:
                IncomingNumber = incomingNumber;
                Log.i("CallReceiverBroadcast", "Incoming call caught. Caller's number is " + incomingNumber + ".");
                Intent i = new Intent(context, IncomingCallService.class);
                context.startService(i);
            case TelephonyManager.CALL_STATE_IDLE:
                Log.i("CallReceiverBroadcast", "CALL_STATE_IDLE");                  
                IncomingCallService.clearView(context);
                // Call Disconnected
                break;

            case TelephonyManager.CALL_STATE_OFFHOOK:
                Log.i("CallReceiverBroadcast", "CALL_STATE_OFFHOOK");
                IncomingCallService.clearView(context);
                // Call Answer Mode
                break;
            }
        }
        };
        teleMgr.listen(psl, PhoneStateListener.LISTEN_CALL_STATE);
        teleMgr.listen(psl, PhoneStateListener.LISTEN_NONE);
    }
}

<强> IncomingCallService.java:

import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.graphics.PixelFormat;
import android.os.IBinder;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.WindowManager;
import android.widget.TextView;

public class IncomingCallService extends Service {

    static View view = null;
    static WindowManager wm;
    static LayoutInflater inflater;
    static WindowManager.LayoutParams params;
    private static TextView txtIncomingnumber;
    static boolean processingAction = false;

    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
    super.onCreate();
    params = new WindowManager.LayoutParams(WindowManager.LayoutParams.MATCH_PARENT, 350,
                WindowManager.LayoutParams.TYPE_PHONE, WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
                        | WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH | WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE, PixelFormat.TRANSLUCENT);

    params.gravity = Gravity.LEFT | Gravity.TOP;
    params.flags |= WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL;

    wm = (WindowManager) getSystemService(WINDOW_SERVICE);

    inflater = (LayoutInflater) this.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    view = inflater.inflate(R.layout.activity_main,null);

    wm.addView(view, params);
    txtIncomingnumber = (TextView)view.findViewById(R.id.txtIncomingnumber);
    txtIncomingnumber.setText("You have Incoming Call from " + CallReceiver.IncomingNumber);

        return START_STICKY;
    }

    public static void clearView(Context context) {
        wm = (WindowManager) context.getSystemService(WINDOW_SERVICE);
        if(view != null) {
            if(view.isEnabled()){
                wm.removeView(view);
                view = null;
            }           
        }
    }
}

<强> activity_main.xml中:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:layout_alignParentLeft="true"
    android:background="#0090FF"
    android:padding="10dp"
    android:keepScreenOn="true" >

    <TextView
    android:id="@+id/txtIncomingnumber"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignParentTop="true"
    android:layout_centerHorizontal="true"
    android:layout_marginTop="30dp"
    android:text="Incoming Call Number"
    android:textColor="#fff" />

</RelativeLayout>

<强>的AndroidManifest.xml:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.stackoverflow"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
    android:minSdkVersion="8"
    android:targetSdkVersion="18" />

    <uses-permission android:name="android.permission.READ_PHONE_STATE"/>
    <uses-permission android:name="android.permission.CALL_PHONE" />
    <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" ></uses-permission>
    <uses-permission android:name="android.permission.VIBRATE"></uses-permission> 

    <application
    android:allowBackup="true"
    android:icon="@drawable/ic_launcher"
    android:label="@string/app_name"
    android:theme="@style/AppTheme" >
    <receiver android:name=".CallReceiver" >                     
        <intent-filter android:priority="99999">
            <action android:name="android.intent.action.PHONE_STATE"/>
        </intent-filter>
    </receiver>

    <activity
        android:name="com.stackoverflow.MainActivity"
        android:label="@string/app_name" >
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />

            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
    <service android:name=".IncomingCallService">
    </service> 
    </application>

</manifest>

答案 1 :(得分:2)

如果要在BroadcastReceive的onReceive中显示一个对话框,则必须使用警告对话框启动透明活动,并且不要调用setContentView()。活动将具有透明视图,仅显示警告对话框..

您的广播接收器onReceive

@Override
 public void onReceive(Context context, Intent intent) {
Log.i("CallReceiverBroadcast", "onReceive() is called. ");
TelephonyManager teleMgr =(TelephonyManager)context.getSystemService(Context.TELEPHONY_SERVICE);
PhoneStateListener psl = new PhoneStateListener() {
    @Override
    public void onCallStateChanged(int state, String incomingNumber) {
        Log.i("CallReceiverBroadcast", "onCallStateChanged() is called. ");
        switch (state) {
        case TelephonyManager.CALL_STATE_RINGING:
            Log.i("CallReceiverBroadcast", "Incoming call caught. Caller's number is " +incomingNumber + ".");
 //start activity which has dialog  
    Intent i=new Intent(context,DialogActivity.class);
     i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
     context.startActivity(i);
        }
    }
};
teleMgr.listen(psl, PhoneStateListener.LISTEN_CALL_STATE);
teleMgr.listen(psl, PhoneStateListener.LISTEN_NONE);
}

你的DiaLogActivity

  public class DialogActivity extends Activity 
{

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
  //dont call setcontent view

    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder.setMessage("Are you sure you want to exit?").setCancelable(
        false).setPositiveButton("Yes",
        new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int id) {
                dialog.cancel();
            }
        }).setNegativeButton("No",
        new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int id) {
                dialog.cancel();
            }
        });
    AlertDialog alert = builder.create();
    alert.show();
 }

  }