Android获取GPS时间

Android获取所在时区正确时间的方式有两种:

一:wifi获取时间

在联网且系统设置了自动获取时间自动获取时区的系统设置前提下,系统会自动更新正确的时间,当然如果你用了TextClockDateClock也会自动更新。

二:通过GPS获取时间。

2.1未联网且GPS可用的情况下,可以通过获取原生定位信息来获取所在地点的时间,实现如下:

注意,下面的代码时在Fragment里面实现的

/**  
* 用于获取GPS时间  
*/  
private LocationManager locationManager;  
/**  
* 取消后台定位的时间  
*/  
private final static int CANCEL_LOCATION_DELAY = 5 * 60 * 1000;  
/**  
* 避免多次取消定位和反注册  
*/  
private boolean isHadCancelLocation = false;

/**  
* 如果网络不可用,使用GPS进行刷新系统时间,系统时间更新后会自动更新TextClock和DateClock;如果有网络,理论上会自动刷新系统时间,所以不处理。  
*/  
private void initSystemTime() {  
    if(!NetworkHelper.isNetworkAvailable(getContext())){  
        getLocationBySystem();
        // 注意,这里请用原始Handler.postDelay代替,我用的自定义延时类。
        ArchTaskExecutor.getInstance().postToMainThreadDelay(cancelLocationRunnable, CANCEL_LOCATION_DELAY);  
    }  
}

// 注意,普通app需要申请定位权限,我的是系统级app,所以忽略。
@SuppressLint("MissingPermission")  
private void getLocationBySystem() {  
    XLog.i("无网络启动获取Gps定位");  
    locationManager = (LocationManager) getContext().getSystemService(Context.LOCATION_SERVICE);  
    // 注册位置监听器  
    locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, locationListener);  
}  

/**  
* 通过GPS获取定位信息  
*/  
private final LocationListener locationListener = location -> {  
    if(null != location) {  
        // 就这里是关键获取代码,其实高德地图Api能自己触发系统时间的更新,不知道怎么实现的,只要打开他们的地图就可以,不管是第三方的高德地图app还是自己内嵌的高德地图api模块,理论上也是location.getTime()获取到的,不理解的是他们为什么有权限更新系统时间。
        long gpsTime = location.getTime();  
        cancelLocationUpdates();  
        XLog.i("Gps定位获取成功并注销定位监听,GPS时间 = " + gpsTime);  
        // 用过这个进行模拟测试,resetSystemTime(1712800932000L);显示的时间是2024-04-11 10:02:12,正确  
        resetSystemTime(gpsTime);  
    }  
};
  
private final Runnable cancelLocationRunnable = () -> {  
    XLog.i("获取定位超时,注销定位监听");  
    cancelLocationUpdates();  
};  
  
/**  
* 获取定位时间成功取消定位  
*/  
public void cancelLocationUpdates() {  
    XLog.i("注销定位监听" + isHadCancelLocation);  
    if (locationManager != null && !isHadCancelLocation) {  
        locationManager.removeUpdates(locationListener);  
        isHadCancelLocation = true;  
        locationManager = null;  
    }  
}  

/**
* 注意,我的是系统级app,所以忽略动态申请权限,普通应用无法设置系统时间但是可以参考取值。
* 系统级app配置 <uses-permission android:name="android.permission.SET_TIME"/> 权限即可
**/
@SuppressLint("MissingPermission")  
private void resetSystemTime(Long utcTimeMillis) {  
    try {  
        // 将UTC时间转换为Date对象  
        Date locationTime = new Date(utcTimeMillis);  
        long localTimeMillis = locationTime.getTime();  

        // 获取AlarmManager实例  
        AlarmManager alarmManager = (AlarmManager) getActivity().getSystemService(Context.ALARM_SERVICE);  
        // 设置系统时间(本地时间)  
        if (alarmManager != null) {  
            alarmManager.setTime(localTimeMillis);  
            XLog.i("重置系统时间成功" + localTimeMillis);  
        }  
     } catch (Exception e){  
        XLog.e("重置系统时间失败");  
    }  
}

2.2 如果你接入了高德地图SDK,也可以使用如下api去获取当前地点的时间:

/**  
* 这里目前获取到GPS返回的正确的时间  
* @throws Exception  
*/  
@SuppressLint("MissingPermission")  
public void getLocationByAMap() throws Exception {  
    // 高德地图的api  
    mlocationClient = new AMapLocationClient(getContext());  
    //初始化定位参数  
    mLocationOption = new AMapLocationClientOption();  
    //设置定位监听  
    mlocationClient.setLocationListener(new AMapLocationListener() {  
    @Override  
    public void onLocationChanged(AMapLocation aMapLocation) {  
        if (aMapLocation != null) {  
            if (aMapLocation.getErrorCode() == 0) {  
                //定位成功回调信息,设置相关消息  
                aMapLocation.getLocationType();//获取当前定位结果来源,如网络定位结果,详见定位类型表  
                SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");  
                Toast.makeText(getContext(), "时间戳为:" + aMapLocation.getTime(),Toast.LENGTH_SHORT).show();  
                Date date = new Date(aMapLocation.getTime());  
                String time = df.format(date);//定位时间  

                SimpleDateFormat dateFormat = new SimpleDateFormat("MM月dd日");  
                SimpleDateFormat hourMinuteSecondFormat = new SimpleDateFormat("HH:mm aa");  

                mlocationClient.stopLocation();// 获取成功停止定位  
                Toast.makeText(getContext(), "时间为:" + time + ";停止了定位并开始设置系统时间" + dateFormat + ";" + hourMinuteSecondFormat,Toast.LENGTH_SHORT).show();  

                // 需要配置 <uses-permission android:name="android.permission.SET_TIME"/>
                resetSystemTime(aMapLocation.getTime());  
            } else {  
                //显示错误信息ErrCode是错误码,errInfo是错误信息,详见错误码表。  
                Log.e("AmapError", "location Error, ErrCode:"  
                + aMapLocation.getErrorCode() + ", errInfo:"  
                + aMapLocation.getErrorInfo());  
            }  
        }  
    }});  
    //设置定位模式为高精度模式,Battery_Saving为低功耗模式,Device_Sensors是仅设备模式   mLocationOption.setLocationMode(AMapLocationClientOption.AMapLocationMode.Hight_Accuracy);  
    //设置定位间隔,单位毫秒,默认为2000ms  
    mLocationOption.setInterval(1000);  
    //设置定位参数  
    mlocationClient.setLocationOption(mLocationOption);  
    // 此方法为每隔固定时间会发起一次定位请求,为了减少电量消耗或网络流量消耗,  
    // 注意设置合适的定位时间的间隔(最小间隔支持为1000ms),并且在合适时间调用stopLocation()方法来取消定位请求  
    // 在定位结束后,在合适的生命周期调用onDestroy()方法  
    // 在单次定位情况下,定位无论成功与否,都无需调用stopLocation()方法移除请求,定位sdk内部会移除  
    //启动定位  
    mlocationClient.startLocation();  
}


三:注意,预加载 GPS 并不是解决 Android 时间显示不准确的最佳方法。虽然 GPS 可以提供精确的时间和位置信息,但在大多数情况下,并不需要通过 GPS 来确保时间的准确性。通常,Android 设备会自动从网络提供商(例如移动网络或Wi-Fi连接)获取准确的时间和时区信息。这个过程通常称为网络时间同步。因此,如果你的自定义 Launcher 在获取时间时不准确,很可能是由于设备的网络时间同步设置出现了问题,而不是时区设置的问题。

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 214,377评论 6 496
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,390评论 3 389
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,967评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,344评论 1 288
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,441评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,492评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,497评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,274评论 0 269
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,732评论 1 307
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,008评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,184评论 1 342
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,837评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,520评论 3 322
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,156评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,407评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,056评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,074评论 2 352

推荐阅读更多精彩内容