问题
I need to find a way to measure the current signal strength of Android phone, without the need to register a PhoneStateListener that God knows when it returns the actual asu.
something like:
int signal = getPhoneSignal();
any help plz?
thanks!
回答1:
If you will have a closer look on Android sources you will see that after registering PhoneStateListener
you will have instant notification:
public void listen(PhoneStateListener listener, int events) {
String pkgForDebug = mContext != null ? mContext.getPackageName() : "<unknown>";
try {
Boolean notifyNow = (getITelephony() != null);
mRegistry.listen(pkgForDebug, listener.callback, events, notifyNow);
} catch (RemoteException ex) {
// system process dead
}
}
So you can create your own timer and on timer update register new listener and after receiving instant update remove it by passing the same listener object and set the events argument to LISTEN_NONE
.
Of course I can't call it best practice but the only alternative I can see is to calculate signal strength by yourself based on signal strengths from getNeighboringCellInfo()
.
p.s. Not only God knows when PhoneStateListener
will be triggered ;)
回答2:
I don't think there is a way to do it directly. But you could register the PhoneStateListener and save the last updated value into a variable and return/call this.
回答3:
class Signal {
static volatile CountDownLatch latch;
static int asu;
private final static String TAG = Signal.class.getName();
int getSignalStrength(Context ctx) throws InterruptedException {
Intent i = new Intent(TAG + ".SIGNAL_ACTION", Uri.EMPTY, ctx,
SignalListenerService.class);
latch = new CountDownLatch(1);
asu = -1;
ctx.startService(i);
Log.w(TAG, "I wait");
latch.await();
ctx.stopService(i);
return asu;
}
}
where :
public class SignalListenerService extends Service {
private TelephonyManager Tel;
private SignalListener listener;
private final static String TAG = SignalListenerService.class.getName();
private static class SignalListener extends PhoneStateListener {
private volatile CountDownLatch latch;
private SignalListener(CountDownLatch la) {
Log.w(this.getClass().getCanonicalName(), "CSTOR");
this.latch = la;
}
@Override
public void onSignalStrengthChanged(int asu) {
Signal.asu = asu;
latch.countDown();
}
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.w(TAG, "Received : " + intent.getAction());
Tel = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE);
listener = new SignalListener(Signal.latch);
@SuppressWarnings("deprecation")
final int listenSs = PhoneStateListener.LISTEN_SIGNAL_STRENGTH;
Tel.listen(listener, listenSs);
return START_STICKY;
}
@Override
public void onDestroy() {
Log.w(TAG, "onDestroy");
Tel.listen(listener, PhoneStateListener.LISTEN_NONE);
super.onDestroy();
}
@Override
public IBinder onBind(Intent intent) {
return null;
}
}
This is working code. Do not forget to register your services in the manifest and acquire permissions. There may be better/ more elegant ways of doing this so comments/corrections welcome.
来源:https://stackoverflow.com/questions/3888775/instant-signal-strength