3

I know there have been many questions asked on SO re converting java.util.Date to java.util.Calendar, but I have spent a good few hours trying to solve my issue, looking at the APIs and numerous SO answers - hence my question.

I'm in the process of modifying an existing JSP page that utilises an API that has not been updated to work with the java.time API. And which requires the variable being passed to be in the java.util.Calendar format.

I need to set both a start date and an end date which should 14 days in the future.

My Start Date is straight forward enough:

1. Calendar sd = Calendar.getInstance(); //this works

But I seem unable to produce a Calendar instance that is 14 days in the future. I know I can set the following:

2. sd.set(Calendar.Date, 14); 

I do appreciate that this is probably a really trivial question - but how do I set this as a separate End Date Calendar variable?

e.g. Calendar ed = ? //when set to statement 2 - I get a compile error

Or am I approaching this in entirely the wrong way?

Thanks.

Andrii Abramov
  • 10,019
  • 9
  • 74
  • 96
Beckteck
  • 65
  • 1
  • 10

5 Answers5

3

You can simply use the add method

add(Calendar.DAY_OF_MONTH, 14);
Neeraj Jain
  • 7,643
  • 6
  • 34
  • 62
  • This changes the starting date; the OP's question was on how to get a separate End Date calendar object. – KevinO May 23 '17 at 16:50
  • the main intent of this answer is to let OP know there is add method which will help he can figure out the rest, updated my answer though. – Neeraj Jain May 23 '17 at 16:55
3

tl;dr

GregorianCalendar.from(    // Convert from modern java.time to legacy class.
    LocalDate.now(         // Get today’s date as it is now in this zone.
        ZoneId.of( "America/Montreal" ) 
    )
    .plusDays( 14 )
    .atStartOfDay(        // Determine first moment of the day for this zone. Never assume 00:00:00.
        ZoneId.of( "America/Montreal" ) 
    )                     // Produces a `ZonedDateTime` object.
)

Details

Beware, the other Answers using Calendar ignore the crucial issue of time zone.

Convert to/from java.time

You really should do your business logic in java.time. The legacy date-time classes such as Calendar are a bloody awful mess.

If you must use the troublesome legacy classes, such as working with old code not yet updated to the java.tine types, convert. Work in java.time, convert results to the legacy classes. To convert, look to new methods added to the legacy classes such as valueOf, to…, from.

Determine today's date requires a time zone.

ZoneId z = ZoneId.of( "America/Montreal" ) ; 
LocalDate today = LocalDate.now( z ) ;

Add 14 days (or 2 weeks).

LocalDate ld = today.plusDays( 14 ) ;  // .plusWeeks( 2 )

To go from a date-only to a date-time (a specific moment on the timeline), we must specify a time-of-day. Do not assume 00:00:00. Anomalies such as Daylight Saving Time mean the day may start at some other time such as 01:00:00. Let java.time determine the first moment of the day.

ZonedDateTime zdt = ld.atStartOfDay( z ) ;

Convert to the legacy class.

Calendar cal = GregorianCalendar.from( zdt ) ;

For more discussion and a nifty diagram about converting to/from java.time, see an Answer of mine on a similar Question.

Basil Bourque
  • 303,325
  • 100
  • 852
  • 1,154
  • Thank you for your comprehensive answer - I can see where I was going wrong now. I agree I had been working with java.time initially, but could not figure out a way of converting back into the legacy class. – Beckteck May 23 '17 at 19:41
  • @Beckteck For more info on converting: https://stackoverflow.com/a/36639155/642706 – Basil Bourque May 23 '17 at 19:54
1

Set the end Calendar to a new instance, then advance the date. This will keep your original starting date, and then provide a new ending date Calendar object.

NOTE: if at all possible, you should look into the new Date/Time objects in Java 8.

// get a new instance
Calendar ed = Calendar.getInstance();

// set to the starting time
ed.setTime(sd.getTime();

// advance the date by 14 days
ed.add(Calendar.DATE, 14);
KevinO
  • 4,303
  • 4
  • 27
  • 36
0

You should use the add() method:

add(Calendar.DAY_OF_MONTH, 14);

Even better, you could use LocalDateTime class from the Java SE 8 Date and Time APIs:

LocalDateTime timePoint = LocalDateTime.now();     // The current date and time
timePoint.plusDays(14);
syntagma
  • 23,346
  • 16
  • 78
  • 134
0

Even when your API requires an oldfashioned Calendar object, you may well prefer to use the modern date and time classes in your own code and only convert to a Calendar when you need one. The conversion is straightforward (when you know how). For example:

    ZonedDateTime endDateTime = ZonedDateTime.now(ZoneId.systemDefault())
            .plusDays(14);
    Calendar ed = GregorianCalendar.from(endDateTime);

(as you may know, GregorianCalendar is the most often used subclass of the abstract Calendar class).

Ole V.V.
  • 81,772
  • 15
  • 137
  • 161