Android 获取GPS和网络定位信息

本文介绍了如何在Android应用中获取GPS和网络定位信息。在GPS信号不可用时,利用网络定位来获取位置坐标,虽然网络定位不包含高程数据。详细实现涉及activity_main.xml布局文件、MainActivity.java代码以及AndroidManifest.xml的配置。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

获取到位置服务后,同时请求网络和GPS定位更新。在没有GPS信号的时候,使用网络定位的位置信息(网络定位信息中无高程值)。


activity_main.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:padding="10dp"
    android:orientation="vertical">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="纬度:"/>

        <TextView
            android:id="@+id/tv_latitude"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="经度:"/>

        <TextView
            android:id="@+id/tv_longitude"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="服务商:"/>

        <TextView
            android:id="@+id/tv_provider"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="准确性:"/>

        <TextView
            android:id="@+id/tv_accuracy"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="高度:"/>

        <TextView
            android:id="@+id/tv_altitude"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="方向角:"/>

        <TextView
            android:id="@+id/tv_bearing"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="速度:"/>

        <TextView
            android:id="@+id/tv_speed"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="上次上报时间:"/>

        <TextView
            android:id="@+id/tv_last_time"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_margin="5dp">

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"
            android:text="最新上报时间:"/>

        <TextView
            android:id="@+id/tv_new_time"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textSize="18dp"/>
    </LinearLayout>

</LinearLayout>

MainActivity.java
import android.app.Activity;
import android.content.Context;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.widget.TextView;

import java.text.SimpleDateFormat;

public class MainActivity extends Activity {

    private LocationManager locationManager;
    /**
     * 前一次位置
     */
    private Location lastLocation;

    private SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss.SSSZ");

    private TextView tvLatitude;
    private TextView tvLongitude;
    private TextView tvProvider;
    private TextView tvAccuracy;
    private TextView tvAltitude;
    private TextView tvBearing;
    private TextView tvSpeed;
    private TextView tvLastTime;
    private TextView tvNewTime;

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

        tvLatitude = (TextView) findViewById(R.id.tv_latitude);
        tvLongitude = (TextView) findViewById(R.id.tv_longitude);
        tvProvider = (TextView) findViewById(R.id.tv_provider);
        tvAccuracy = (TextView) findViewById(R.id.tv_accuracy);
        tvAltitude = (TextView) findViewById(R.id.tv_altitude);
        tvBearing = (TextView) findViewById(R.id.tv_bearing);
        tvSpeed = (TextView) findViewById(R.id.tv_speed);
        tvLastTime = (TextView) findViewById(R.id.tv_last_time);
        tvNewTime = (TextView) findViewById(R.id.tv_new_time);

        locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
    }

    @Override
    protected void onResume() {
        super.onResume();

        locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 0, 0, listener);
        locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, listener);
    }

    @Override
    protected void onPause() {
        super.onPause();

        locationManager.removeUpdates(listener);
    }

    private LocationListener listener = new LocationListener() {
        @Override
        public void onLocationChanged(Location location) {
            updateLocation(location);
        }

        @Override
        public void onStatusChanged(String s, int i, Bundle bundle) {
            updateLocation();
        }

        @Override
        public void onProviderEnabled(String s) {
            updateLocation();
        }

        @Override
        public void onProviderDisabled(String s) {

        }
    };

    private void updateLocation() {
        Location location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
        if (location == null) {
            location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
        }
        updateLocation(location);
    }

    private void updateLocation(Location location) {
        if (location == null) {
            return;
        }
        //判断新的位置是否可替换当前位置
        if (isBetterLocation(location, lastLocation)) {
            updateUI(location);
            lastLocation = location;
        }
    }

    /**
     * 更新UI
     * @param location
     */
    private void updateUI(final Location location) {
        runOnUiThread(new Runnable() {
            @Override
            public void run() {
                tvLatitude.setText(location.getLatitude() + "");
                tvLongitude.setText(location.getLongitude() + "");
                tvProvider.setText(location.getProvider());
                tvAccuracy.setText(location.getAccuracy() + "");
                tvAltitude.setText(location.getAltitude() + " 米");
                tvBearing.setText(location.getBearing() + "");
                tvSpeed.setText(location.getSpeed() + " 米/秒");
                tvNewTime.setText(dateFormat.format(location.getTime()));
                if (lastLocation != null) {
                    tvLastTime.setText(dateFormat.format(lastLocation.getTime()));
                }
            }
        });
    }

    /**
     * 判断位置信息是否比当前的位置信息好
     * @param location 新的位置
     * @param currentBestLocation 当前的位置
     */
    protected boolean isBetterLocation(Location location,
                                       Location currentBestLocation) {
        if (currentBestLocation == null) {
            return true;
        }

        // 检测GPS时间
        long timeDelta = location.getTime() - currentBestLocation.getTime();
        boolean isSignificantlyNewer = timeDelta > 2000;
        boolean isSignificantlyOlder = timeDelta < -2000;
        boolean isNewer = timeDelta > 0;//较新

        // If it's been more than two minutes since the current location, use
        // the new location
        // because the user has likely moved
        if (isSignificantlyNewer)
        {
            return true;
        }
        else if (isSignificantlyOlder)
        {
            return false;
        }

        // 检测GPS精度
        int accuracyDelta = (int) (location.getAccuracy() - currentBestLocation.getAccuracy());
        boolean isLessAccurate = accuracyDelta > 0;
        boolean isMoreAccurate = accuracyDelta < 0;
        boolean isSignificantlyLessAccurate = accuracyDelta > 200;

        // 检测提供者
        boolean isFromSameProvider = isSameProvider(location.getProvider(),
                currentBestLocation.getProvider());

        // Determine location quality using a combination of timeliness and
        // accuracy
        if (isMoreAccurate)
        {
            return true;
        }
        else if (isNewer && !isLessAccurate)
        {
            return true;
        }
        else if (isNewer && !isSignificantlyLessAccurate && isFromSameProvider)
        {
            return true;
        }
        return false;
    }

    /**
     * 判断是否为同一个提供者
     * @param provider1
     * @param provider2
     * @return
     */
    private boolean isSameProvider(String provider1, String provider2)
    {
        if (provider1 == null)
        {
            return provider2 == null;
        }
        return provider1.equals(provider2);
    }
}

AndroidManifest.xml
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-permission android:name="android.permission.INTERNET"/>

参考:http://www.2cto.com/kf/201208/145033.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值