The issue with using Date is it still expects an actual date even though you are using just the time portion of it, so if you're just sending it the time it will not be correct.
Instead use LocalTime and ChronoUnit.HOURS to get the difference between the time.
DateTimeFormatter dtf = DateTimeFormatter.ofPattern("HH:mm");
LocalTime lt1 = LocalTime.parse(txtshiftIn, dtf);
LocalTime lt2 = LocalTime.parse(txtshiftOut, dtf);
long diff = ChronoUnit.HOURS.between(lt1, lt2);
This will show -16 which means that lt1 is ahead of lt2 which indicates lt2 is the next day so we can modify it to get the differences as such
if (diff < 0) {
diff += 24;
}
This will give you the 8 hour difference you're expecting.
UPDATE
To account the difference in minutes you can do the following:
DateTimeFormatter dtf = DateTimeFormatter.ofPattern("HH:mm");
LocalTime lt1 = LocalTime.parse(txtshiftIn, dtf);
LocalTime lt2 = LocalTime.parse(txtshiftOut, dtf);
long diff = ChronoUnit.MINUTES.between(lt1, lt2); //get diff in minutes
if (lt2.isBefore(lt1)) {
diff += TimeUnit.DAYS.toMinutes(1); //add a day to account for day diff
}
long hours = diff / 60;
long minutes = diff % 60;
LocalTime newTime = LocalTime.parse(String.format("%02d:%02d", hours, minutes), dtf); //Format the difference to be converted to LocalTime
System.out.println(newTime);
This will produce the difference in minutes:
08:30
Update 2
Here is a cleaner method that returns a Duration
public Duration timeDifference(String txtshiftIn, String txtshiftOut) {
DateTimeFormatter dtf = DateTimeFormatter.ofPattern("HH:mm");
LocalTime lt1 = LocalTime.parse(txtshiftIn, dtf);
LocalTime lt2 = LocalTime.parse(txtshiftOut, dtf);
Duration between = Duration.between(lt1, lt2);
if (lt2.isBefore(lt1)) { //account for lt2 being on the next day
between = Duration.ofMinutes(TimeUnit.DAYS.toMinutes(1)).plus(between);
}
return between;
}