代码在抛出 NullPointerException 时仅返回 0.0, 0.0 GPS 坐标

2023-11-25

这是我第 n 次尝试使用 Android Location API,但我似乎无法让它正常工作。本教程似乎是最有希望的,但我似乎只能让这段代码返回 0.0, 0.0 的 GPS 坐标,这不是很有用......

getLocation() 返回 java.lang.NullPointerException 错误似乎有一条线索,但我不确定应该从哪里开始寻找它。

这是错误:

 W/System.err: java.lang.NullPointerException
 W/System.err:     at android.content.ContextWrapper.checkPermission(ContextWrapper.java:557)

我尝试制作一个新的权限块,粘贴在底部,但它只是给出了相同的错误。

谁能在这里指出正确的方向吗?

代码分为两个类文件:MainActivity.java 和 GPSTracker.java。

GPSTracker.java

    package com.tutorial.android.location.api;

// http://www.androidhive.xyz/2016/07/android-gps-location-manager-tutorial.html
// with some modifications, especially for new permissions

import android.Manifest;
import android.app.Activity;
import android.app.AlertDialog;
import android.app.Service;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.os.IBinder;
import android.provider.Settings;
import android.support.annotation.Nullable;
import android.support.v4.app.ActivityCompat;
import android.util.Log;

public class GPSTracker extends Service implements LocationListener {
    private String TAG = "¤¤";
    private final Context mContext;

    public GPSTracker(Context mContext) {
        this.mContext = mContext;
        this.getLocation();
    }

    boolean isGPSEnabled = false;
    boolean isNetworkEnabled = false;
    boolean canGetLocation = false;

    Location location;
    double latitude;
    double longitude;

    private static final long MIN_DISTANCE_CHANGE_FOR_UPDATE = 10; // 10 meters
    private static final long MIN_TIME_BW_UPDATES = 1000 * 60 * 1; // 30 sec

    protected LocationManager locationManager;

    public Location getLocation() {
        try {

            if(locationManager == null) {
                locationManager = (LocationManager) mContext.getSystemService(LOCATION_SERVICE);
            }
            if(isGPSEnabled != true) {
                isGPSEnabled = locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
            }
            if(isNetworkEnabled != true) {
                isNetworkEnabled = locationManager.isProviderEnabled(LocationManager.NETWORK_PROVIDER);
            }

            if (!isGPSEnabled && !isNetworkEnabled) {
                // no provider enabled :p
                Log.e(TAG, "getLocation() no provider :(");
            } else {
                this.canGetLocation = true;
                // get network location
                if (isNetworkEnabled) {
                    // permission block:
                    if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
                        // TODO: Consider calling
                        //    ActivityCompat#requestPermissions
                        // here to request the missing permissions, and then overriding
                        //   public void onRequestPermissionsResult(int requestCode, String[] permissions,
                        //                                          int[] grantResults)
                        // to handle the case where the user grants the permission. See the documentation
                        // for ActivityCompat#requestPermissions for more details.
                        // return TODO;
                    } else {
                        Log.e(TAG, "getLocation() permission DENIED");
                    }
                    locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, MIN_TIME_BW_UPDATES, MIN_DISTANCE_CHANGE_FOR_UPDATE, this);
                    if(locationManager != null) {
                        location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
                        if(location != null) {
                            latitude = location.getLatitude();
                            longitude = location.getLongitude();
                        }
                    }
                }
                // get GPS location
                if(isGPSEnabled) {
                    if(location == null) {
                        locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, MIN_TIME_BW_UPDATES, MIN_DISTANCE_CHANGE_FOR_UPDATE, this);
                        Log.d(TAG, "getLocation() GPS Enabled");
                        if(locationManager != null){
                            location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
                            if(location != null) {
                                latitude = location.getLatitude();
                                longitude = location.getLongitude();
                            }
                        }
                    }
                }
            }
        } catch (Exception e) {
            Log.e(TAG, "getLocation() ERROR...: " + e);
            e.printStackTrace();
        }
        return location;
    }

    public double getLatitude() {
        if(location != null) {
            latitude = location.getLatitude();
        }
        return latitude;
    }

    public double getLongitude() {
        if(location != null) {
            longitude = location.getLongitude();
        }
        return longitude;
    }

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

    @Override
    public void onLocationChanged(Location location) {

    }

    @Override
    public void onStatusChanged(String provider, int status, Bundle extras) {

    }

    @Override
    public void onProviderEnabled(String provider) {
        // GPS is ON
        Log.d(TAG, "GPS is ON");
    }

    @Override
    public void onProviderDisabled(String provider) {
        // GPS is OFF
        Log.d(TAG, "GPS is OFF");
    }

    // GPS dialog
    public boolean canGetLocation() {
        return this.canGetLocation;
    }
    // don't really need this when testing
    public void showSettingsAlert() {
        AlertDialog.Builder alertDialog = new AlertDialog.Builder(mContext);

        alertDialog.setTitle(R.string.gps_settings_title);

        alertDialog.setMessage(R.string.gps_settings_msg);
        alertDialog.setPositiveButton(R.string.gps_settings_word, new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int which) {
                Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
                mContext.startActivities(new Intent[]{intent}); // hm...
            }
        });
        alertDialog.show();
    }

    public void stopUsingGPS() {
        if(locationManager != null) {
            locationManager.removeUpdates(GPSTracker.this);
        }
    }
}

重写了 GPSTracker.java 中的权限块,但仍然不起作用:

int permissionCheck = ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION);
if(!(permissionCheck == PackageManager.PERMISSION_GRANTED)) {
    if(ActivityCompat.shouldShowRequestPermissionRationale((Activity) mContext, Manifest.permission.ACCESS_FINE_LOCATION)) {
        // explanation :p
        Log.i(TAG, "NOpe...");
    } else {
        // request permission
        Log.d(TAG, "Requestion new permission");
        ActivityCompat.requestPermissions((Activity) mContext, new String[] {Manifest.permission.ACCESS_FINE_LOCATION}, 1);
    }
}

MainActivity.java

package com.tutorial.android.location.api;

import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;

public class MainActivity extends AppCompatActivity {
    String TAG = "¤";

    GPSTracker gps;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        gps = new GPSTracker(this);

        if(gps.canGetLocation()) {
            Log.i(TAG, "onCreate() GPS is ON");
            Log.i(TAG, "onCreate() " + gps.getLatitude()+ ", " + gps.getLongitude());
        } else {
            Log.d(TAG, "onCreate() GPS is OFF");
        }

    }
}

本教程似乎是最有前途的

这确实是糟糕的代码。

我似乎只能让这段代码返回 GPS 坐标 0.0, 0.0,这不是很有用

那是因为它只有在以下情况下才会有一个位置:getLastKnownLocation()碰巧返回一个。不太可能这样做。

重写了 GPSTracker.java 中的权限块,但仍然不起作用:

这里有两个问题:

  1. 您无法向服务请求权限。

  2. 这不是真正的服务。这段代码的作者选择创建一个扩展的类Service没有实际正确实施或使用该服务。这就是导致你的NullPointerException,因为这不是正确初始化的Context.

谁能在这里指出正确的方向吗?

把这一切都扔掉。

FWIW,这里是我的示例应用程序用于使用LocationManager API.

食谱相当简单:

步骤#1:获取LocationManager通过致电getSystemService(Context.LOCATION_SERVICE)一些Context。我碰巧在一个片段中这样做:

  @Override
  public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setRetainInstance(true);

    template=getActivity().getString(R.string.url);
    mgr=(LocationManager)getActivity()
      .getSystemService(Context.LOCATION_SERVICE);
  }

步骤#2:致电requestUpdates(),传递一些实现的东西LocationListener。就我而言,这恰好是片段本身:

  @Override
  @SuppressWarnings({"MissingPermission"})
  public void onStart() {
    super.onStart();

    mgr.requestLocationUpdates(LocationManager.GPS_PROVIDER, 3600000,
      1000, this);
  }

步骤#3:在onLocationChanged()你的LocationListener,用Location你得到的,在我的例子中是执行AsyncTask获取天气预报:

  @Override
  public void onLocationChanged(Location location) {
    new FetchForecastTask().execute(location);
  }

步骤#4:致电removeUpdates()当你完成后:

  @Override
  @SuppressWarnings({"MissingPermission"})
  public void onStop() {
    mgr.removeUpdates(this);

    super.onStop();
  }

就是这样(除了运行时权限的东西,我将其抽象为AbstractPermissionsActivity).

如果您愿意,请使用getLastKnownLocation() as an 优化,但不要依赖它。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

代码在抛出 NullPointerException 时仅返回 0.0, 0.0 GPS 坐标 的相关文章

随机推荐

  • Dynamodb:使用两个以上属性的查询

    在 Dynamodb 中 您需要在索引中指定可用于进行查询的属性 如何使用两个以上的属性进行查询 使用 boto 的示例 Table create users schema HashKey id defaults to STRING dat
  • 在 MKMapView 上移动/更新 MKOverlay

    有没有办法更新 即移动 aMKOverlay已经添加到MKMapView 删除旧的并添加新的非常糟糕 慢 即我想当覆盖物在屏幕上移动时触发调用此函数的后台函数 MKOverlayView mapView MKMapView mapView
  • 从远程 git 存储库获取单个文件

    有没有一种方法可以在 Java 中以编程方式从远程 git 存储库下载单个文件 我更喜欢使用尽可能少的带宽的解决方案 最好只下载单个文件 我不需要浏览存储库 我已经有了文件的路径 我更喜欢不依赖于其他应用程序的解决方案 例如 在计算机上安装
  • 如何启动和应用程序选择器

    该应用程序的任务是隐式激活一个单独的应用程序来查看 URL http www google com 因此 应用程序选择器应该出现并让我在至少两个浏览器之间进行选择 默认浏览器将向我显示 www google com 网站 另一个简单的 浏览
  • 需要 C# 中的 BouncyCastle PGP 文件加密示例

    我正在尝试使用我的私钥 ascii 格式 和任何其他公钥 也是 ascii 格式 加密文件 BouncyCastle 库看起来是正确的使用方式 但我找不到 C 的文档 谁能帮我举个例子 谢谢 以下是 BouncyCastle 示例中的一些代
  • 创建不包含外部依赖项的 JAR 文件

    是否可以创建需要外部依赖项的 JAR 文件 而不在 JAR 文件中包含这些依赖项 我的 google fu 未能给我答案 我发现的所有内容都显示了如何将它们包含在 JAR 文件中 但没有显示如何将它们放入清单文件中来表示 我还没有得到它们
  • 如何清除内存以防止VBA中的“内存不足错误”?

    我正在一个大型 Excel 电子表格上运行 VBA 代码 如何清除过程 调用之间的内存以防止发生 内存不足 问题 帮助释放内存的最佳方法是使大对象无效 Sub Whatever Dim someLargeObject as SomeObje
  • C++ 内联类方法导致未定义的引用

    当我尝试内联某个类的方法时 出现编译器错误 当我去掉 inline 关键字时它就起作用了 这是一个简化的示例 主要 cpp include my class h int main MyClass c c TestMethod return
  • 单击时搜索栏的拇指

    我想在搜索栏拇指上注册一个可点击事件 以便在用户单击它时触发事件 是否可以 结合 zwebie 和 Nermeens 的答案得出正确的解决方案 seekbar setOnSeekBarChangeListener new SeekBar O
  • 更好的蜜罐实施(形成反垃圾邮件)

    How do we get rid of these spambots on our site 每个网站都会成为受害者spambots在某一点 您的处理方式会影响您的客户 并且大多数解决方案可能会阻止某些人填写您的表格 这就是蜜罐技术的用武
  • cdk virtualscroll 与 mat-grid-list

    是否有与网格列表一起使用的虚拟滚动实现 我认为默认实现不起作用 因为每一行周围都应该有一个元素 我使用网格列表来显示个人资料图片 并且需要无限滚动或最好是虚拟滚动来加载新图片 因此 由于 cdk virtualscroll 不支持多列 我最
  • PHP/MySQL 数据库查询到底是如何工作的?

    我经常使用MySQL 但我总是想知道它到底是如何工作的 当我得到肯定的结果时 数据到底存储在哪里 例如我这样写 sql SELECT FROM TABLE result mysql query sql while row mysql fet
  • C 在 Windows 上获取系统时间到微秒精度? [复制]

    这个问题在这里已经有答案了 可能的重复 在 C 中以微秒分辨率测量时间 Hi 有没有一种简单的方法可以获取 Windows 计算机上的系统时间 精确到微秒 查看 GetSystemTimeAsFileTime 它的精度为 0 1 微秒或 1
  • xsl:for-each 有什么不好的地方?

    我一次又一次听到有关如何避免使用 XSLT for each 的说法 应该消除的是你内心的命令式编程恶魔 这有什么不好呢 此最佳实践是否重要取决于sizeXML 的数量 即 100 个节点与 10 000 个节点 之间的本质区别
  • 在 mac os x 10.6.7 上卸载 python 3.2

    根据 python org 的文档 在 mac os 上安装 python 3 2 需要升级到 tcl tk 8 5 9 为了使用 IDLE 由于仓促 我两件事都做了 现在我的朋友告诉我 还不推荐使用 python 3 因为 3 只发布了内
  • 为什么 time.clock 给出的经过时间比 time.time 更长?

    我在 Ubuntu 上使用了一段 python 代码的计时time clock and time time clock elapsed time 8 770 s time elapsed time 1 869 s 我知道 time time
  • 使用 Clang 的 libtooling 匹配 #includes(或 #defines)的正确方法是什么?

    我正在编写一个 libtooling 重构工具 我有课 比方说Foo 在名为的标头中定义foo h 我想看看是否foo h包含在一个文件中 目前 要检查是否bar cc包括foo h 我只是使用匹配recordDecl hasName Fo
  • 计算 3D 空间中单个三角形的法线

    我正在上图形编程课 我正在做书面作业 而不是编程 所以我希望这适合这个网站 我有这个问题 计算由每个指定的三角形的单位法线 以下顶点集 假设三角形背向 起源 我一年多前学过线性代数 然后我的老师说他不会教叉积 因为只有班上的计算机科学人才需
  • java 8 Collector 不是函数式接口,谁能告诉为什么?

    代码如下 public class Test public static void main String args Stream of 1 2 3 map String valueOf collect Collectors toList
  • 代码在抛出 NullPointerException 时仅返回 0.0, 0.0 GPS 坐标

    这是我第 n 次尝试使用 Android Location API 但我似乎无法让它正常工作 本教程似乎是最有希望的 但我似乎只能让这段代码返回 0 0 0 0 的 GPS 坐标 这不是很有用 getLocation 返回 java lan