-1

I have the following code

private boolean checkIfTimeInBetweenRegardlessOfDate(long timeOne, long timeTwo) {
            final Calendar firstCalendar = Calendar.getInstance();
            firstCalendar.setTimeInMillis(timeOne);

            final Calendar calendarCurrentTime = mCalendar;

            final Calendar secondCalendar = Calendar.getInstance();
            secondCalendar.setTimeInMillis(timeTwo);

            final Calendar calendarOneToCompare = Calendar.getInstance();
            calendarOneToCompare.setTimeInMillis(calendarCurrentTime.getTimeInMillis());
            calendarOneToCompare.set(Calendar.HOUR_OF_DAY, firstCalendar.get(Calendar.HOUR_OF_DAY));
            calendarOneToCompare.set(Calendar.MINUTE, firstCalendar.get(Calendar.MINUTE));

            final Calendar calendarTwoToCompare = Calendar.getInstance();
            calendarTwoToCompare.setTimeInMillis(calendarCurrentTime.getTimeInMillis());
            calendarTwoToCompare.set(Calendar.HOUR_OF_DAY, secondCalendar.get(Calendar.HOUR_OF_DAY));
            calendarTwoToCompare.set(Calendar.MINUTE, secondCalendar.get(Calendar.MINUTE));

            if ((calendarTwoToCompare.getTime().toString())
                    .compareTo(calendarOneToCompare.getTime().toString()) < 0) {
                calendarTwoToCompare.add(Calendar.DATE, 1);
                calendarCurrentTime.add(Calendar.DATE, 1);
            }

            return (calendarOneToCompare.compareTo(calendarCurrentTime) <= 0
                    && calendarCurrentTime.compareTo(calendarTwoToCompare) <= 0);
        }

So this question has popped up a few times before on SO. Nobody's code seems to function for all of the cases.

Let's say the Current_Hour is 8pm. It needs to work for these cases:

1) return true if Current_Hour is between 6:00pm and 11:15pm

2) return true if Current_Hour is between 6:00pm and 2:00am

3) return false if Current_Hour is between 3:45pm and 6:10pm

If Current_Hour is 2am, then the following cases need to be met:

4) return true if Current_Hour is between 1:00am and 3:30am

5) return false if Current_Hour is between 7:00am and 12:02pm

I have struggled with this all day and no matter what I do, I can satiate all but 1 or two of those above requirements.

This needs to work regardless of the date--although it will be needed for case #2.

Any help would be appreciated. I'm going crazy.

  • This is exactly how other answers on StackOverflow do it--but comparing Strings of the times. I've already tried doing `calendarTwoToCompare.compareTo(calendarOneToCompare) < 0` and it still didn't lead to any better results. Thanks for your input. –  Jun 27 '17 at 00:06
  • Learn to use the Java 8 `LocalTime` class. – Dawood ibn Kareem Jun 27 '17 at 00:07
  • Using `java.util.Date` or `java.util.Calendar` is universally a bad idea. Use Java 8 `java.time`. – Louis Wasserman Jun 27 '17 at 00:07
  • 1
    This is Android--so I can't use Java 8 easily yet, sorry. –  Jun 27 '17 at 00:08
  • Case 2 is not clear to me. 8pm is true when it's between 6pm and 11am? And between 6pm and noon? What's the rule exactly? –  Jun 27 '17 at 00:14
  • @hugo I'm not sure I follow. I don't see what case you're talking about that shows those times. –  Jun 27 '17 at 00:17
  • Case 2 returns true if 8pm is between 6pm and 2am. It needs to be true just in this case? If I need to check 8pm between 6pm and 3am, should it be also true? And what about the other values I mentioned? Do these values occur or between 6pm and 2am is the only case? –  Jun 27 '17 at 00:19
  • 1
    All of those cases are just examples. Yeah, it would need to return true if `Current_Hour` is 8pm and the start time is `6pm` and the end time is `8am`, for example. All of the cases above are just the *types* of cases with an example for each type. –  Jun 27 '17 at 00:21
  • Should the ends of the time-range be considered inclusive or exclusive? In other words, what should happen if `currentTime` is equal to either `startTime` or `endTime`? – Dawood ibn Kareem Jun 27 '17 at 00:39
  • The accepted answer returns true when 8pm is between 6pm and 5:59pm. Is that what you really need? –  Jun 27 '17 at 01:29
  • @Hugo, yes, OP's example 2 indicates that the times should "roll over" from one day to the next. – Dawood ibn Kareem Jun 27 '17 at 05:30

1 Answers1

2

If your want to compare time-of-day to minute precision, get the minute-of-day value from each, i.e. minuteOfDay = hourOfDay * 60 + minuteOfHour, then compare those.

You can extend that to second or millisecond as needed.

Since you want 6:00pm and 2:00am to cover 8pm, you need to detect an inverted time range.

All in all, you can do it like this:

private static boolean isTimeInRange(long currentMillis, long fromMillis, long toMillis) {
    Calendar cal = Calendar.getInstance();
    cal.setTimeInMillis(currentMillis);
    int currentMinuteOfDay = cal.get(Calendar.HOUR_OF_DAY) * 60 + cal.get(Calendar.MINUTE);
    cal.setTimeInMillis(fromMillis);
    int fromMinuteOfDay = cal.get(Calendar.HOUR_OF_DAY) * 60 + cal.get(Calendar.MINUTE);
    cal.setTimeInMillis(toMillis);
    int toMinuteOfDay = cal.get(Calendar.HOUR_OF_DAY) * 60 + cal.get(Calendar.MINUTE);
    if (fromMinuteOfDay <= toMinuteOfDay)
        return (currentMinuteOfDay >= fromMinuteOfDay && currentMinuteOfDay < toMinuteOfDay);
    return (currentMinuteOfDay >= fromMinuteOfDay || currentMinuteOfDay < toMinuteOfDay);
}
Dawood ibn Kareem
  • 77,785
  • 15
  • 98
  • 110
Andreas
  • 154,647
  • 11
  • 152
  • 247
  • Thank you so much. I'm shocked there isn't an answer like this elsewhere on this site. This did the trick! –  Jun 27 '17 at 00:24
  • 1
    @throwawayhmwk No it didn't. But I've fixed it now. You might want to grab another copy. Andreas, feel free to roll it back if you think my edit was too extensive (and I will downvote the answer if you do so). – Dawood ibn Kareem Jun 27 '17 at 05:34
  • 1
    @DawoodibnKareem DOH! Can't believe I did that. Thanks. – Andreas Jun 27 '17 at 13:24
  • Hah, no worries. Looks like [you have a fan anyway](https://stackoverflow.com/a/44772312) – Dawood ibn Kareem Jun 27 '17 at 21:29
  • I actually just ran into this bug--although, I'm not sure what it is. I've noticed that if `6:48pm <= current_time <= 6:59pm` and the from time is `8pm` and the end time is `7am`, this method will return `true`--that is, before this fix. What was happening? – Nxt3 Jun 27 '17 at 23:19
  • @DawoodibnKareem Could you please explain? – Nxt3 Jun 27 '17 at 23:28
  • @Nxt3 What is there to explain? Click the `edited` link to see what was changed. There are 60 minutes in an hour, so it needs to multiply by 60, not 24. – Andreas Jun 28 '17 at 01:11