Android time management - android

I am now working with one database record on Android.
It now has one column storing a number and another column storing a time in millisecond.
There should be only one record.
However, the record should be refreshed at 6:00am the next day.
It means that when I want to update the number, I am supposed to check if time now is beyond the refreshing time.
Is there any simple way to achieve this checking?
I am not sure if I have explained this problem clearly. To explain in another way, I want to check if there is one "6 am" between two time stored in millisecond.
Thanks a lot!

public static boolean needRefreshBean(Long milli){
Calendar cal = Calendar.getInstance();
cal.setTimeInMillis(milli);
if(cal.get(Calendar.HOUR_OF_DAY)>resettime)
cal.add(Calendar.DAY_OF_YEAR,1);
cal.set(Calendar.HOUR_OF_DAY,resettime);
//cal represents the supposed refresh time
if(cal.getTimeInMillis()<System.currentTimeMillis()){
return true;
}
else
return false;
}
I write a function like this. The input is the updated time stored in the database. I am not sure if this works

Related

Best way to reset a database value every week on specific day (Android - Room)

I'm working on an Android app that has a functionality that is weekly basis, that is, every day of the week the user has to mark as done the day. This value is a boolean on my database, that is initialized with false, and is set to true when the user clicks on the checkbox. Everything is working fine.
But my problem is that I need to "reset" this boolean value to false on all the seven days of the week every time a new week begins. I don't need to have records of the past weeks. All that matters is the actual week (Sunday to Saturday).
It's a very simple task, I only need to do this:
for(WeekDay day: dao.getWeekDays()){
day.setDone(false);
dao.updateWeekDay(day); //update the value in database
}
So, I did some research (I'm new to android) and find out that Android has different schedule services like JobScheduler or AlarmManager. My app is designed to Android 10+ (API 29+).
What do you think is the best solution for my problem?
It's a very simple task (it won't take too much battery, internet,...) and I need to do this in a specific day (Sunday) every week. Also, this task needs to be done as soon as it possible, even if the phone is turned off on Sunday. It doesn't need to be a background service, but I need to guarantee that when the user opens the app and it's a new week, that method needs to be call before, but only if it had not been call in the actual week before.
Anyone has ideas?
Ok, I think I found a simple solution for my problem, based on other similar answers I read. I just need to run these function every time the app starts. I didn't need to use any background service, like WorkManager.
I only need to store in SharedPreferences the last date when the system did a reset in the values. Then, every time I open the app, it checks if today is in a different week from the last reset day. If it's true, then I run that "for cycle" in the question and update the last reset day to today in the SharedPreferences. If it's false, I do nothing.
The method inSameCalendarWeek checks if the day is in the same week from the same year of today (Locale.US guarantees that a week starts on Sunday. But I could change that to Locale.getDefault() to be more flexible). Also, for example, if December 31 is in the same week of January 1, even if they are in different years, the method will return true.
private void checkAndResetDoneDays() {
long lastResetDay = settings.getLong(LAST_DAY_RESET, 0);
LocalDate date = Instant.ofEpochMilli(lastResetDay).atZone(ZoneId.systemDefault()).toLocalDate();
if (!inSameCalendarWeek(date)) {
resetDoneDays();
settings.edit()
.putLong(LAST_DAY_RESET, LocalDate.now(ZoneId.systemDefault()).atStartOfDay(ZoneId.systemDefault()).toInstant().toEpochMilli())
.commit();
}
}
public boolean inSameCalendarWeek(LocalDate firstDate) {
LocalDate secondDate = LocalDate.now(ZoneId.systemDefault());
// get a reference to the system of calendar weeks in US Locale (to guarantee that week starts on Sunday)
WeekFields weekFields = WeekFields.of(Locale.US);
// find out the calendar week for each of the dates
int firstDatesCalendarWeek = firstDate.get(weekFields.weekOfWeekBasedYear());
int secondDatesCalendarWeek = secondDate.get(weekFields.weekOfWeekBasedYear());
/*
* find out the week based year, too,
* two dates might be both in a calendar week number 1 for example,
* but in different years
*/
int firstWeekBasedYear = firstDate.get(weekFields.weekBasedYear());
int secondWeekBasedYear = secondDate.get(weekFields.weekBasedYear());
// return if they are equal or not
return firstDatesCalendarWeek == secondDatesCalendarWeek
&& firstWeekBasedYear == secondWeekBasedYear;
}

How to delete SharedPreferences automatically after one month?

I want to delete SharedPreferences, if they exist, after one month automatically. I could not find any solutions. Is this possible to make?
Thanks a lot.
It depends.
The easiest way is to delete it when the user starts the app.
When the apps is created, you check the SharedPreferences for the last updated time.
If it's null (the first time), you save the current time in milliseconds as a long.
If it's not null, you read it and compare it against the current time. If it less than a month, you do nothing. If it's more than a month, you clear the shared preferences and, after clearing it, insert the new time.
Something like:
long lastUpdate = sharedPreferences.getLong(LAST_UPDATE, -1);
if(lastUpdate == -1) {
//First time
sharedPreferences.edit().putLong(LAST_UPDATE, System.currentTimeMillis()).apply();
} else {
boolean isMoreThanAMonth = //Here you should do the math. it depends, you want to consider a month like 30 days, or you want to know if it was in another month... somehthing like that
if(isMoreThanAMonth) {
sharedPreferences.edit().clear().apply()
}
}
Of course, if you want to clear the SharedPreferences even if the user does not open the app you should use a Service. It's more complex and expensive for the OS, so you should try to go for the first one if it fits your requirement.
long installed = context
.getPackageManager()
.getPackageInfo(context.getPackag‌​eName(), 0)
.firstInstallTime
;
public long firstInstallTime
The time at which the app was first installed. Units are as per System.currentTimeMillis().
Now you can compare two date and get months diffrent by using GregorianCalendar
after you get one month different do as you want..clear sharedPrefrence.edit().clear().commit()
One possible way,
1. get the calendar instance.
2. Get maximum day of month.
3. Store in a var1 string in format of dd/mm/yyyy.
4. Get the current date from some calendar object and store in same way from point 3 but in var2.
5. Compare two strings.
6. If match then it will be last day of month and call delete() on your files.
Done.

How to display different text in a textview according to date in android app?

I am very new at coding and want to develop an android app that display new content according the day you are opening the app.
For example : 20 days to eat better
Day 1 (user open the app), then the message is "XXXXXX"
Day 2 (user open the app), the the message is "YYYYY"
Day 1 is a the day the user download the app.
I understood that I need to use "timestamp" as a string, but how can I do it ?
Thanks for your help !
I'm not quite sure about what you are trying to achieve. But based on what I understood. You just want to get the current day
Calendar calendar = Calendar.getInstance();// sets the current date
calendar.get(Calendar.DATE);// gets the current day returns an integer value
calendar.getTime();// gets the current date and returns a Date Object
You can start from here. The calendar class offers you different values for the current calendar date. I'm pretty sure all you need to know is available if you just tried to search the web. But to give you something to work on, experiment with the Calendar class for date manipulations.
EDIT:
If you want to display a certain string based on the date/day. What you can do is to create an array and user the date/day value to get the string.
String[] stringArray = {"Text1", "Text2", "Text3", "Text4", "Text5", "Text6", "Text7"};
String theStringYouWant = stringArray[calendar.get(Calendar.DATE)];
You can use this approach if you have short strings and limited record. But if you have tons of data, you might want to utilize a database to store your data, and use this approach.

Android system time

in my application i need to get current Date and time, every time the user inputs data with it.
I know i can use System.currentTimeMillis(), but it can give me wrong time(because it gives system time, witch can be edited by user)
So i see the only way is to call server for current time, when the user makes data input. but i am not sure that internet connection is always awailable.
Is there any way to get current time (not system time) in android, without using internet connection?
If you don't want system time you need some other source then.
There are a few possibilities that I know:
Get it from web - Internet needed
Get it from router - enabled wifi needed (NTP)
Get it from GPS - GPS fix needed
All of these aren't very helpful I believe. I don't think you can find a way of getting current time without connecting so something externally.
In my opinion you should use system time and assume it's set correctly. When it's not your application shouldn't crash and should gently know user that he has wrong content because of wrong dates ...
I believe there's no way to get the current system time without the timezone.
A good approach would be getting the current system time first
long time= System.currentTimeMillis();
And then getting the correct TimeZone to handle it
Calendar cal = Calendar.getInstance();
TimeZone tz = cal.getTimeZone();
long dateInMillis = System.currentTimeMillis();
String format = "yyyy-MM-dd HH:mm:ss";
final SimpleDateFormat sdf = new SimpleDateFormat(format);
String dateString = sdf.format(new Date(dateInMillis));
Use dateString as your variable which contains current date time as timestamp.
Well, I googled about your topic, and i got logic solution but not tested:
" Use The network-provided values ", in the android phone settings, it;a as shown in the picture bellow:
The screen I show is DateTimeSettings. The checkbox "Use network-provided values" is associated to the shared preference String KEY_AUTO_TIME = "auto_time"; and also to Settings.System.AUTO_TIME
This settings is observed by an observed called mAutoTimeObserver in the 2 network ServiceStateTrackers: GsmServiceStateTracker and CdmaServiceStateTracker.
Both implementations call a method called revertToNitz() when the settings becomes true. Apparently NITZ is the equivalent of NTP in the carrier world.
Bottom line: You can set the time to the value provided by the carrier thanks to revertToNitz(). Unfortunately, I haven't found a mechanism to get the network time. If you really need to do this, I'm afraid, you'll have to copy these ServiceStateTrackers implementations, catch the intent raised by the framework (I suppose), and add a getter to mSavedTime.
For more informations, i suggest you to check this link here
Use the ScheduledExecutorService with scheduleAtFixedRate to send you "clock ticks". If the user initiates an event and the number of accumulated "clock ticks" since the last event doesn't match the time change on the system clock, you're being lied to.
You don't need to know the correct time. You need to know the correct interval. This can be done with any periodic source, even a local one. (Timekeeping is two jobs: a metronome and a labeler for the intervals of the metronome. You don't want the system's labels because they can be made to lie, but the metronome ticks on even if the labels are changed.)
I'd recommend a relatively slow tick rate (<= 1 tick per minute) and rather sloppy comparisons (within 2%, maybe) since the various clocks may not be all that accurate.

Last Time Contacted

How does android calculate the value for last time contacted. It provides the value in integer format but I am unable to decipher the given value. For example what if I want to compare the two give values to know which contact has been contacted later. Any type of help would be appreciated.
The value you receive is returned in long format and holds the date and time information of the last time called has happened from a particular number.
It returns the milliseconds of that number.
For your reference: http://developer.android.com/reference/android/provider/ContactsContract.ContactOptionsColumns.html#LAST_TIME_CONTACTED
Now how to compute date and time here is the link:
how to convert milliseconds to date format in android?
How to compare:
There are functions "before" and "after" which tells whether the event date is before or after another specified date
Date class: http://developer.android.com/reference/java/util/Date.html#after(java.util.Date)
or
Calendar class: http://developer.android.com/reference/java/util/Calendar.html#after(java.lang.Object)
Depends which one you want to use.
I hope it helps and let me know for more info.
Every time you contact someone, (i.e. make the call Contacts.markAsContacted) the TIMES_CONTACTED should increment by 1 and LAST_TIME_CONTACTED should be updated. However, many device manufacturers have changed this functionality and it is not reliable anymore. There is an open bug for this issue which you could find at
http://code.google.com/p/android/issues/detail?id=8784&q=LAST_TIME_CONTACTED&colspec=ID%20Type%20Status%20Owner%20Summary%20Stars

Categories

Resources