如何在android中设置移动系统时间和日期?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1332269/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-20 02:56:05  来源:igfitidea点击:

How to set mobile system time and date in android?

androidoperating-system

提问by jek

When you want to change the mobile system date or time in your application, how do you go about doing it?

当您想更改应用程序中的移动系统日期或时间时,您将如何进行?

回答by jek

You cannot on a normal off the shelf handset, because it's not possible to gain the SET_TIME permission. This permission has the protectionLevelof signatureOrSystem, so there's no way for a market app to change global system time (but perhaps with black vodoo magic I do not know yet).

您不能使用普通的现成手机,因为不可能获得SET_TIME 权限。此权限的保护signatureOrSystem级别为,因此市场应用程序无法更改全球系统时间(但也许我还不知道黑色伏都教魔法)。

You cannot use other approaches because this is prevented on a Linux level, (see the long answer below) - this is why all trials using terminals and SysExecs gonna fail.

您不能使用其他方法,因为这在 Linux 级别是被阻止的(请参阅下面的长答案)-这就是使用终端和 SysExecs 的所有试验都会失败的原因。

If you CAN gain the permission either because you rooted your phone or built and signed your own platform image, read on.

如果您能够获得许可,因为您植根了手机或构建并签署了自己的平台映像,请继续阅读。

Short Answer

简答

It's possible and has been done. You need android.permission.SET_TIME. Afterward use the AlarmManagervia Context.getSystemService(Context.ALARM_SERVICE)and it s method setTime().

这是可能的,并且已经完成。你需要android.permission.SET_TIME. 然后使用过AlarmManagerContext.getSystemService(Context.ALARM_SERVICE)及其方法setTime()

Snippet for setting the time to 2010/1/1 12:00:00 from an Activity or Service:

用于将活动或服务的时间设置为 2010/1/1 12:00:00 的代码段:

Calendar c = Calendar.getInstance();
c.set(2010, 1, 1, 12, 00, 00);
AlarmManager am = (AlarmManager) this.getSystemService(Context.ALARM_SERVICE);
am.setTime(c.getTimeInMillis());

If you which to change the timezone, the approach should be very similar (see android.permission.SET_TIME_ZONEand setTimeZone)

如果您要更改时区,则方法应该非常相似(请参阅android.permission.SET_TIME_ZONEsetTimeZone

Long Answer

长答案

As it has been pointed out in several threads, only the systemuser can change the system time. This is only half of the story. SystemClock.setCurrentTimeMillis()directly writes to /dev/alarmwhich is a device file owned by systemlacking world writeable rights. So in other words only processes running as systemmay use the SystemClockapproach. For this way android permissions do not matter, there's no entity involved which checks proper permissions.

正如在几个线程中指出的那样,只有system用户可以更改系统时间。这只是故事的一半。SystemClock.setCurrentTimeMillis()直接写入缺少全局可写权限/dev/alarm的设备文件system。因此,换句话说,只有system可能使用该SystemClock方法运行的进程。对于这种方式,android 权限无关紧要,不涉及检查适当权限的实体。

This is the way the internal preinstalled Settings App works. It just runs under the systemuser account.

这是内部预装设置应用程序的工作方式。它只是在system用户帐户下运行 。

For all the other kids in town there's the alarm manager. It's a system service running in the system_serverprocess under the - guess what - systemuser account. It exposes the mentioned setTimemethod but enforces the SET_TIMEpermission and in in turn just calls SystemClock.setCurrentTimeMillisinternally (which succeeds because of the user the alarm manager is running as).

对于镇上的所有其他孩子,都有警报管理器。它是system_server在 - 猜猜 -system用户帐户下运行的系统服务。它公开上述setTime方法,但强制执行SET_TIME权限,然后仅在SystemClock.setCurrentTimeMillis内部调用(由于警报管理器运行的用户身份而成功)。

Cheers

干杯

回答by Casebash

According to this thread, user apps cannot set the time, regardless of the permissions we give it. Instead, the best approach is to make the user set the time manually. We will use:

根据此线程,无论我们授予它什么权限,用户应用程序都无法设置时间。相反,最好的方法是让用户手动设置时间。我们将使用:

startActivity(new Intent(android.provider.Settings.ACTION_DATE_SETTINGS));

Unfortunately, there is no way to link them directly to the time setting (which would save them one more click). By making use of ellapsedRealtime, we can ensure that the user sets the time correctly.

不幸的是,没有办法将它们直接链接到时间设置(这样可以再点击一次)。通过使用ellapsedRealtime,我们可以确保用户正确设置时间。

回答by Led Machine

A solution for rooted devices could be execute the commands

有根设备的解决方案可以是执行命令

  • su
  • date -s YYYYMMDD.HHMMSS
  • 日期 -s YYYYMMDD.HHMMSS

Change date on cmd

在 cmd 上更改日期

You can do this by code with the following method:

您可以使用以下方法通过代码执行此操作:

private void changeSystemTime(String year,String month,String day,String hour,String minute,String second){
    try {
        Process process = Runtime.getRuntime().exec("su");
        DataOutputStream os = new DataOutputStream(process.getOutputStream());
        String command = "date -s "+year+month+day+"."+hour+minute+second+"\n";
        Log.e("command",command);
        os.writeBytes(command);
        os.flush();
        os.writeBytes("exit\n");
        os.flush();
        process.waitFor();
    } catch (InterruptedException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }
}

Just call the previous method like this:

只需像这样调用前面的方法:

changeSystemTime("2015","04","06","13","09","30");

回答by Slopes

I didn't see this one on the list anywhere but it works for me. My device is rooted and I have superuser installed, but if superuser works on non-rooted devices, this might work. I used an AsyncTask and called the following:

我没有在列表中的任何地方看到这个,但它对我有用。我的设备已 root 并且我安装了超级用户,但如果超级用户在非 root 设备上工作,这可能会奏效。我使用了一个 AsyncTask 并调用了以下内容:

protected String doInBackground(String... params){
Runtime.getRuntime().exec("su && date -s " + params[0]);}

回答by Vinicius Schneider

In our application case, the dirty workaround was:

在我们的应用案例中,肮脏的解决方法是:

When the user is connected to Internet, we get the Internet Time (NTP server) and compare the difference (-) of the internal device time (registederOffsetFromInternetTime). We save it on the config record file of the user.

当用户连接到Internet时,我们获取Internet时间(NTP服务器)并比较内部设备时间(registederOffsetFromInternetTime)的差异(-)。我们将其保存在用户的配置记录文件中。

We use the time of the devide + registederOffsetFromInternetTime to consider the correct updated time for OUR application.

我们使用 devide + registerederOffsetFromInternetTime 的时间来考虑 OUR 应用程序的正确更新时间。

All GETHOUR processes check the difference between the actual time with the time of the last comparission (with the Internet time). If the time over 10 minutes, do a new comparission to update registederOffsetFromInternetTime and mantain accuracy.

所有 GETHOUR 进程都会检查实际时间与上次比较时间(与 Internet 时间)之间的差异。如果时间超过 10 分钟,请重新比较以更新 registederOffsetFromInternetTime 并保持准确性。

If the user uses the App without Internet, we can only use the registederOffsetFromInternetTime stored as reference, and use it. Just if the user changes the hour in local device when offline and use the app, the app will consider incorrect times. But when the user comes back to internet access we warn he about the clock changed , asking to resynchronize all or desconsider updates did offline with the incorrect hour.

如果用户在没有互联网的情况下使用App,我们只能使用存储的registederOffsetFromInternetTime 作为参考,并使用它。只是如果用户在离线时更改本地设备中的小时并使用该应用程序,该应用程序将考虑不正确的时间。但是,当用户重新访问互联网时,我们会警告他时钟已更改,要求重新同步所有内容或取消考虑在不正确的时间离线进行的更新。

回答by barabek_AND_40_chelovek_Ltd

thanks penquin. In quickshortcutmaker I catch name of date/time seting activity exactly. so to start system time setting:

谢谢企鹅。在 quickshortcutmaker 中,我准确地捕捉了日期/时间设置活动的名称。所以要开始系统时间设置:

Intent intent=new Intent();
intent.setComponent(new ComponentName("com.android.settings",
         "com.android.settings.DateTimeSettingsSetupWizard"));      
startActivity(intent);

`

`