Android requestLocationUpdates 使用 PendingIntent 和 BroadcastReceiver

Posted

技术标签:

【中文标题】Android requestLocationUpdates 使用 PendingIntent 和 BroadcastReceiver【英文标题】:Android requestLocationUpdates using PendingIntent with BroadcastReceiver 【发布时间】:2011-12-15 07:26:22 【问题描述】:

如何使用

requestLocationUpdates(long minTime, float minDistance, Criteria criteria,
                                                           PendingIntent intent) 

在 BroadcastReciver 中,以便我可以继续获取 GPS 坐标。

我必须为 LocationListener 创建一个单独的类吗?

我的项目目标是当我收到BOOT_COMPLETED 以开始定期获取 GPS 纬度和经度。

我试过的代码是:

public class MobileViaNetReceiver extends BroadcastReceiver 

    LocationManager locmgr = null;
    String android_id;
    DbAdapter_GPS db;

    @Override
    public void onReceive(Context context, Intent intent) 
        if ("android.intent.action.BOOT_COMPLETED".equals(intent.getAction())) 
            startGPS(context);
         else 
            Log.i("MobileViaNetReceiver", "Received unexpected intent "
                + intent.toString());
        
    

    public void startGPS(Context context) 
        Toast.makeText(context, "Waiting for location...", Toast.LENGTH_SHORT)
                .show();
        db = new DbAdapter_GPS(context);
        db.open();
        android_id = Secure.getString(context.getContentResolver(),
                Secure.ANDROID_ID);
        Log.i("MobileViaNetReceiver", "Android id is _ _ _ _ _ _" + android_id);
        locmgr = (LocationManager) context
                .getSystemService(Context.LOCATION_SERVICE);
        locmgr.requestLocationUpdates(LocationManager.GPS_PROVIDER, 5000, 5,
                onLocationChange);
    

    LocationListener onLocationChange = new LocationListener() 

        public void onLocationChanged(Location loc) 
            // sets and displays the lat/long when a location is provided
            Log.i("MobileViaNetReceiver", "In onLocationChanged .....");
            String latlong = "Lat: " + loc.getLatitude() + " Long: "
                + loc.getLongitude();
            // Toast.makeText(this, latlong, Toast.LENGTH_SHORT).show();
            Log.i("MobileViaNetReceiver", latlong);
            try 
                db.insertGPSCoordinates(android_id,
                        Double.toString(loc.getLatitude()),
                        Double.toString(loc.getLongitude()));
             catch (Exception e) 
                Log.i("MobileViaNetReceiver",
                        "db error catch _ _ _ _ " + e.getMessage());
            
        

        public void onProviderDisabled(String provider) 

        public void onProviderEnabled(String provider) 

        public void onStatusChanged(String provider, int status, Bundle extras) 
    ;    
    //pauses listener while app is inactive
    /*@Override
    public void onPause() 
        super.onPause();
        locmgr.removeUpdates(onLocationChange);
    

    //reactivates listener when app is resumed
    @Override
    public void onResume() 
        super.onResume();
        locmgr.requestLocationUpdates(LocationManager.GPS_PROVIDER, 5000, 5, onLocationChange);
     */

【问题讨论】:

你可能想接受下面的答案。 【参考方案1】:

有两种方法:

    使用您所使用的方法并注册一个BroadcastReceiver,它的意图过滤器与您的PendingIntent (2.3+) 中保存的意图相匹配,或者,如果您只对单个位置提供程序感兴趣,@改为 987654324@ (1.5+)。 使用LocationManagerrequestLocationUpdates (String provider, long minTime, float minDistance, LocationListener listener)方法注册一个LocaltionListener

我认为您有点困惑,因为您可以使用 either a BroadcastReceiver a LocationListener 处理位置更新 - 您不需要两个都。注册更新的方法非常相似,但接收更新的方式却大不相同。

BroadcastReceiver 将允许唤醒您的应用/服务,即使它当前未运行。在服务未运行时将其关闭将显着减少您对用户电池的影响,并最大限度地减少 Task Killer 应用终止您的服务的机会。

LocationListener 将要求您保持服务运行,否则您的LocationListener 将在您的服务关闭时终止。如果您使用这种方法,您可能会冒着 Task Killer 应用程序终止您的服务的风险。

根据您的问题,我怀疑您需要使用 BroadcastReceiver 方法。

【讨论】:

我想我很困惑。我已经添加了尝试过的代码。这有什么问题? 您的LocationListener 必须位于Service 中,该Service 必须永久有效,否则您将不会收到任何更新。正如我在回答中所说,您最好使用另一种处理位置更新的方法,方法是注册 PendingIntent,这将导致每次发生位置更新时发送广播以唤醒您的 BroadcastReceiver。尝试阅读***.com/questions/5240246/… 了解更多信息。 我想我明白你在说什么。我应该将 GPS 代码作为活动(包括位置监听器)放在一个类中。在广播接收器中,将该意图设置为待处理的意图。我对吗 ?你有一个例子吗?非常感谢。 不,如果您使用PendingIntent / BroadcastReceiver 机制,则不需要LocationListener。您的BroadcastReceiver 做了两件事: 1. 在设备启动时启动一切。 2. 处理后续位置更新。我之前评论的链接中有一个例子。【参考方案2】:
public class MobileViaNetReceiver extends BroadcastReceiver 

    private static final String TAG = "MobileViaNetReceiver"; // please

    @Override
    public void onReceive(Context context, Intent intent) 
        if ("android.intent.action.BOOT_COMPLETED".equals(intent.getAction()))
            Log.i(TAG, "Boot : registered for location updates");
            LocationManager lm = (LocationManager) context
                                .getSystemService(Context.LOCATION_SERVICE);
            Intent intent = new Intent(context, this.getClass());
            PendingIntent pi = PendingIntent.getBroadcast(context, 0, intent,
                                        PendingIntent.FLAG_UPDATE_CURRENT);
            lm.requestLocationUpdates(LocationManager.GPS_PROVIDER, 5000,5,pi);
         else 
            String locationKey = LocationManager.KEY_LOCATION_CHANGED;
            if (intent.hasExtra(locationKey)) 
                Location loc = (Location) intent.getExtras().get(locationKey);
                Log.i(TAG, "Location Received");
                try 
                    DbAdapter_GPS db = new DbAdapter_GPS(context);//what's this
                    db.open();
                    String android_id = Secure.getString(
                        context.getContentResolver(), Secure.ANDROID_ID);
                    Log.i(TAG, "Android id is :" + android_id);
                    db.insertGPSCoordinates(android_id,
                        Double.toString(loc.getLatitude()),
                        Double.toString(loc.getLongitude()));
                 catch (Exception e)  // NEVER catch generic "Exception"
                    Log.i(TAG, "db error catch :" + e.getMessage());
                
            
        
    

【讨论】:

以上是关于Android requestLocationUpdates 使用 PendingIntent 和 BroadcastReceiver的主要内容,如果未能解决你的问题,请参考以下文章

向 requestLocationUpdates intentService 发送额外信息会中断位置更新

Android逆向系列文章— Android基础逆向

Android 逆向Android 权限 ( Android 逆向中使用的 android.permission 权限 | Android 系统中的 Linux 用户权限 )

Android 逆向Android 权限 ( Android 逆向中使用的 android.permission 权限 | Android 系统中的 Linux 用户权限 )

android 21 是啥版本

Android逆向-Android基础逆向(2-2)