how to show milliseconds in days:hours:min:seconds
Asked Answered
M

10

35

This is what I have at the moment

Seconds = (60 - timeInMilliSeconds / 1000 % 60);
Minutes = (60 - ((timeInMilliSeconds / 1000) / 60) %60);

which I feel is correct. for hours and days should it be like -

Hours = ((((timeInMilliSeconds / 1000) / 60) / 60) % 24);
Days =  ((((timeInMilliSeconds / 1000) / 60) / 60) / 24)  % 24;

and then-

TextView.SetText("Time left:" + Days + ":" + Hours + ":" + Minutes + ":" + Seconds);

but my hours and days are coming out to be incorrect

Moniz answered 29/10, 2013 at 19:30 Comment(3)
so why don't you utilize exist(native) date time classes?!Eelpout
Why do %24 on days? Are there 24 days in a month?Jarlathus
@Eelpout : you are mistaking native and framework. native means written in the os native language, whatever that is (in this case C/C++), and it can belong to the framework or to any app. Classes you are referring to (such as SimpleDateFormat) belong to the framework, but whether they are native or not is not relevant.Hypso
J
68

A simple way to calculate the time is to use something like

long seconds = timeInMilliSeconds / 1000;
long minutes = seconds / 60;
long hours = minutes / 60;
long days = hours / 24;
String time = days + ":" + hours % 24 + ":" + minutes % 60 + ":" + seconds % 60; 

This will work if you have more than 28 days, but not if you have a negative time.

Jarlathus answered 29/10, 2013 at 20:3 Comment(4)
will this work if you have less than 28 days but more than 0?Moniz
@AkshatAgarwal it will work for any non-negative number of days. 0+ Using SimpleDateFormat might not work for more than 30 days.Jarlathus
exactly! I was having troubles with SimpleDateFormat for a number of dates like less than 1 day (5 hours 5 min 27 seconds etc). I will give your idea a try, it looks about right.Moniz
Worked perfectly and it also gave me the freedom to format my string in any way I wantedMoniz
L
10

SimpleDateFormat is your friend! (I just discovered it today, it's awesome.)

SimpleDateFormat formatter = new SimpleDateFormat("dd:HH:mm:ss", Locale.UK);

Date date = new Date(timeInMilliSeconds);
String result = formatter.format(date);
Luong answered 29/10, 2013 at 19:32 Comment(12)
+1 Can you explain why , Locale.UK is needed? I have never used it.Jarlathus
EDIT: njzk2 is correct -- this WILL work for timespans less that one month. This won't work for timespans greater than one month. A SimpleDateFormat formats calendar dates, not elapsed time. It will interpret a millisecond offset as a date in the first month of 1970.Tameratamerlane
@CharlesForsythe : as a matter of fact, for periods of less than a month, it would work. (just don't include years or months in your format).Hypso
@PeterLawrey In this instance, the Locale should have no effect. The local can have an effect if you use generic date formats where it can choose between M-D-Y (e.g. US) or D-M-Y (e.g. UK). Also, if you use a format that includes text (like month names), SimpleDateFormat will draw from a large collection of localized names and produce properly-translated text.Tameratamerlane
@Aurélien initially I got the timeInMilliSeconds' using calenderObject.getTimeInMillis() and now if I convert it into a 'date' as you mentioned in your answer, would that somehow be incorrect?Moniz
@PeterLawrey Setting the locale has indeed no effect in this case since I specifically define the pattern in a locale agnostic way. However, I always include a fixed Locale in the constructor since Android Lint will complain about no Locale being set, even if that's not relevant. So basically, it's just to avoid a warning, and it has the bonus feature how being sure that the result will be the same for everyone on Earth if I include a Locale specific pattern by mistake.Luong
This somehow doesn't do the right thing for me, i.e. for timeInMilliSeconds = 0 this does not result in 00:00:00:00 as expected (also not with changing dd into DD which should IMHO be done anyway).Ichthyolite
This does not serve the purpose of converting milliseconds to seconds, minutes, hours and days. It generated an EPOCH time whose reference is 1st Jan 1970. So if your milliseconds is 1 then the output you'll get is 1st Jan 1970.Argyrol
LOL i cant believe you discovered it when you said it :). This is actually THE way.... :)Speedwell
If the locale shouldn't matter, use Locale.ROOT to keep your intent clear.Hynda
I believe your solution does not work: Take 64800000 for example. This equates to 18 hours but by using your solution the result will be something like this: 01:18:00:00. So as you can see, it prints out a day even though the difference is only 18 hours.Desimone
This is incorrect. dd gives you day of the month of the date. It will give 1 day in durations less than a day. We want the number of days in the duration. Peter Lawrey's answer provides the correct solution.Rhenium
C
6

Hi, how about this code ?

example)

               0 ms -> 0 ms
             846 ms -> 846ms
           1,000 ms -> 1s
           1,034 ms -> 1s 34ms
          60,000 ms -> 1m
          94,039 ms -> 1m 34s 39ms
       3,600,000 ms -> 1h
      61,294,039 ms -> 17h 1m 34s 39ms
      86,400,000 ms -> 1d
     406,894,039 ms -> 4d 17h 1m 34s 39ms
  31,536,000,000 ms -> 1y
  50,428,677,591 ms -> 1y 218d 15h 57m 57s 591ms

  50,428,677,591 ns -> 50s 428ms 677us 591ns
  50,428,677,591 us -> 14h 28s 677ms 591us
  50,428,677,591 ms -> 1y 218d 15h 57m 57s 591ms
  50,428,677,591 s  -> 1599y 30d 5h 59m 51s
  50,428,677,591 m  -> 95944y 354d 23h 51m
  50,428,677,591 h  -> 5756698y 129d 15h
  50,428,677,591 d  -> 138160760y 191d

/*
 * Copyright 2018 Park Jun-Hong_(fafanmama_at_naver_com)
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * 
 *     http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

/*
 *
 * This file is generated under this project, "open-commons-core".
 *
 * Date  : 2018. 1. 9. 오후 1:36:33
 *
 * Author: Park_Jun_Hong_(fafanmama_at_naver_com)
 * 
 */

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.TimeUnit;
import java.util.function.Function;

/**
 * 
 * @since 2018. 1. 9.
 * @author Park_Jun_Hong_(fafanmama_at_naver_com)
 */
public class TimeUtils {

    private static final TimeUnitInfo[] TIME_UNIT_INFO = new TimeUnitInfo[] { //
            new TimeUnitInfo(TimeUnit.NANOSECONDS, "ns") //
            , new TimeUnitInfo(TimeUnit.MICROSECONDS, "us") //
            , new TimeUnitInfo(TimeUnit.MILLISECONDS, "ms") //
            , new TimeUnitInfo(TimeUnit.SECONDS, "s") //
            , new TimeUnitInfo(TimeUnit.MINUTES, "m") //
            , new TimeUnitInfo(TimeUnit.HOURS, "h") //
            , new TimeUnitInfo(TimeUnit.DAYS, "d") //
    };

    private static final Map<TimeUnit, String> UNIT_STR = new HashMap<>();
    static {
        for (TimeUnitInfo tui : TIME_UNIT_INFO) {
            UNIT_STR.put(tui.unit, tui.unitStr);
        }
    }

    private static final Function<TimeUnit, TimeUnitInfo[]> FN_TIME_UNITS = unit -> {

        ArrayList<TimeUnitInfo> units = new ArrayList<>();

        for (TimeUnitInfo tui : TIME_UNIT_INFO) {
            if (tui.unit.ordinal() >= unit.ordinal()) {
                units.add(tui);
            }
        }

        return units.toArray(new TimeUnitInfo[] {});
    };

    /** discard none. */
    public static final int DC_NONE = 0x00;
    /** discard under nanoseconds */
    public static final int DC_NANO = 0x01;
    /** discard under microseconds */
    public static final int DC_MICRO = DC_NANO << 1;
    /** discard under milliseconds */
    public static final int DC_MILLI = DC_MICRO << 1;
    /** discard under seconds */
    public static final int DC_SECOND = DC_MILLI << 1;
    /** discard under minutes */
    public static final int DC_MINUTE = DC_SECOND << 1;
    /** discard under hours */
    public static final int DC_HOUR = DC_MINUTE << 1;
    /** discard under days */
    public static final int DC_DAY = DC_HOUR << 1;

    // prevent to create an instance.
    private TimeUtils() {
    }

    public static void main(String[] args) {

        long[] times = new long[] { 0, 846, 1000, 1034, 60000, 94039, 3600000, 61294039, 86400000, 406894039, 31536000000L, 50428677591L };
        for (long time : times) {
            System.out.println(String.format("%20s %-2s -> %s", String.format("%,d", time), "ms", toFormattedString(time, TimeUnit.MILLISECONDS)));
        }

        System.out.println("=================================");

        long time = 50428677591L;
        for (TimeUnitInfo tui : TIME_UNIT_INFO) {
            System.out.println(String.format("%20s %-2s -> %s", String.format("%,d", time), tui.unitStr, toFormattedString(time, tui.unit)));
        }
    }

    private static long mod(long time, TimeUnit unit) {
        switch (unit) {
            case NANOSECONDS: // to nanosecond
            case MILLISECONDS: // to microsecond
            case MICROSECONDS: // to millsecond
                return time % 1000;
            case SECONDS: // to second
                return time % 60;
            case MINUTES: // to minute
                return time % 60;
            case HOURS: // to hour
                return time % 24;
            case DAYS: // to day
                return time % 365;
            default:
                throw new IllegalArgumentException(unit.toString());
        }
    }

    /**
     * 
     * <br>
     * 
     * <pre>
     * [개정이력]
     *      날짜      | 작성자   |   내용
     * ------------------------------------------
     * 2018. 1. 9.      박준홍         최초 작성
     * </pre>
     *
     * @param timeBuf
     * @param time
     * @param unit
     *
     * @author Park_Jun_Hong_(fafanmama_at_naver_com)
     * @since 2018. 1. 9.
     */
    private static void prependTimeAndUnit(StringBuffer timeBuf, long time, String unit) {
        if (time < 1) {
            return;
        }

        if (timeBuf.length() > 0) {
            timeBuf.insert(0, " ");
        }

        timeBuf.insert(0, unit);
        timeBuf.insert(0, time);
    }

    /**
     * Provide the Millisecond time value in {year}y {day}d {hour}h {minute}m {second}s {millisecond}ms {nanoseconds}ns.
     * <br>
     * Omitted if there is no value for that unit.
     * 
     * @param time
     *            time value.
     * @param timeUnit
     *            a unit of input time value.
     * @return
     *
     * @since 2018. 1. 9.
     */
    public static String toFormattedString(long time, TimeUnit timeUnit) {

        // if zero ...
        if (time < 1) {
            return "0 " + UNIT_STR.get(timeUnit);
        }

        StringBuffer timeBuf = new StringBuffer();

        long mod = 0L;
        long up = time;

        for (TimeUnitInfo unit : FN_TIME_UNITS.apply(timeUnit)) {
            mod = mod(up, unit.unit);
            prependTimeAndUnit(timeBuf, mod, unit.unitStr);

            up = up(up, unit.unit);

            if (up < 1) {
                return timeBuf.toString();
            }
        }

        prependTimeAndUnit(timeBuf, up, "y");

        return timeBuf.toString();
    }

    private static long up(long time, TimeUnit unit) {
        switch (unit) {
            case NANOSECONDS: // to microsecond & above
            case MILLISECONDS: // to millsecond & above
            case MICROSECONDS: // to second & above
                return time / 1000;
            case SECONDS: // to minute & above
                return time / 60;
            case MINUTES: // to hour & above
                return time / 60;
            case HOURS: // to day & above
                return time / 24;
            case DAYS: // to year & above
                return time / 365;
            default:
                throw new IllegalArgumentException(unit.toString());
        }
    }

    private static class TimeUnitInfo {
        private final TimeUnit unit;
        private final String unitStr;

        public TimeUnitInfo(TimeUnit unit, String unitStr) {
            this.unit = unit;
            this.unitStr = unitStr;
        }
    }

}
Charlacharlady answered 9/1, 2018 at 9:18 Comment(3)
Very nice! I like that it omits units with no values. HOWEVER, I have an enhancement request! Pad hours, minutes, seconds to 2 characters, and millis to 3 chars. Makes a huge difference for reports. Maybe should be optional flag. Also to consider if also to pad days to 3 characters. [Man, you got me thinking..] Make year optional, or have another method without years, even if >365 days. Also make the OMIT feature (which I love) optional, useful for columnar reports where all the rows HAVE to absolutely be aligned. Thanks.Pericline
Thanks for your comment. I think that optional flags are good. So I will apply your opinion. Additional a nanoseconds as a input value. See later.~^^~Charlacharlady
Looking forward. Thanks.Pericline
H
3

To format elapsed/remaining times in android, use android.text.format.DateUtils, in particular, getRelativeTimeSpanString and formatElapsedTime.

Hypso answered 29/10, 2013 at 20:22 Comment(3)
can you explain a bit what do each of those do?Moniz
the documentation is quite complete, and i don't see what i could add that wouldn't already be in any tutorial about this class.Hypso
This will either add an "in" prefix or "ago" suffix, and it does not display all of days, hours, minutes, seconds, but only one of them depending on the flags.Ichthyolite
P
1

You can also use the joda-time API (http://joda.org/joda-time/)

"The class DateTimeFormat provides a single method forPattern(String) that supports formatting by pattern. These "pattern-based" formatters provide a similar approach to that of SimpleDateFormat."

LocalDate date = LocalDate.now();
DateTimeFormatter fmt = DateTimeFormat.forPattern("d MMMM, yyyy");
String str = date.toString(fmt);
Polyphyletic answered 29/10, 2013 at 20:7 Comment(1)
Sorry I dont want to incorporate a 4.1 MB library for a task as small as mineMoniz
P
1

java.time

I recommend you use java.time.Duration which is modelled on ISO-8601 standards and was introduced with Java-8 as part of JSR-310 implementation. With Java-9 some more convenience methods were introduced.

import java.time.Duration;

public class Main {
    public static void main(String[] args) {
        // Given milliseconds e.g. milliseconds from the epoch
        long millis = System.currentTimeMillis();

        Duration duration = Duration.ofMillis(millis);

        // Duration in default format
        System.out.println(duration);

        // Custom format
        // ####################################Java-8####################################
        String formattedElapsedTime = String.format("%d:%02d:%02d:%02d", duration.toDays(), duration.toHours() % 24,
                duration.toMinutes() % 60, duration.toSeconds() % 60);
        System.out.println("Duration (days:hours:min:seconds): " + formattedElapsedTime);
        // ##############################################################################

        // ####################################Java-9####################################
        formattedElapsedTime = String.format("%d:%02d:%02d:%02d", duration.toDaysPart(), duration.toHoursPart(),
                duration.toMinutesPart(), duration.toSecondsPart());
        System.out.println("Duration (days:hours:min:seconds): " + formattedElapsedTime);
        // ##############################################################################
    }
}

Output:

PT448255H41M9.125S
Duration (days:hours:min:seconds): 18677:07:41:09
Duration (days:hours:min:seconds): 18677:07:41:09

Note: For any reason, if you have to stick to Java 6 or Java 7, you can use ThreeTen-Backport which backports most of the java.time functionality to Java 6 & 7. If you are working for an Android project and your Android API level is still not compliant with Java-8, check Java 8+ APIs available through desugaring and How to use ThreeTenABP in Android Project.

Phenoxide answered 19/2, 2021 at 7:36 Comment(0)
E
0

to solve your question try the following java class (with immutable instances)

package adrjx.utils.time;

public class VRDecodedTimePeriodMillis
{
    // instance data

    private int theMillisecs = 0;
    private int theSeconds = 0;
    private int theMinutes = 0;
    private int theHours = 0;
    private int theDays = 0;

    // init

    public VRDecodedTimePeriodMillis (long aTimePeriodMillis)
    {
        long aSeconds = aTimePeriodMillis / 1000;
        long aMinutes = aSeconds / 60;
        long aHours = aMinutes / 60;
        long aDays = aHours / 24;

        this.theMillisecs = (int)(aTimePeriodMillis % 1000);
        this.theSeconds = (int)(aSeconds % 60);
        this.theMinutes = (int)(aMinutes % 60);
        this.theHours = (int)(aHours % 24);
        this.theDays = (int)(aDays);

        // done
    }

    // accessors

    public int getMillisecs() { return this.theMillisecs; }
    public int getSeconds() { return this.theSeconds; }
    public int getMinutes() { return this.theMinutes; }
    public int getHours() { return this.theHours; }
    public int getDays() { return this.theDays; }

}

that's all folks ...

Eme answered 13/8, 2020 at 13:6 Comment(0)
M
0

java.util.concurrent.TimeUnit to the rescue:

    long remainingMillis = 1076232425L; // Your value comes here.

    long days = TimeUnit.MILLISECONDS.toDays(remainingMillis);
    long daysMillis = TimeUnit.DAYS.toMillis(days);

    long hours = TimeUnit.MILLISECONDS.toHours(remainingMillis - daysMillis);
    long hoursMillis = TimeUnit.HOURS.toMillis(hours);

    long minutes = TimeUnit.MILLISECONDS.toMinutes(remainingMillis - daysMillis - hoursMillis);
    long minutesMillis = TimeUnit.MINUTES.toMillis(minutes);

    long seconds = TimeUnit.MILLISECONDS.toSeconds(remainingMillis - daysMillis - hoursMillis - minutesMillis);

    String resultString = days + " day(s) " + hours + " hour(s) " + minutes + " minute(s) " + seconds + " second(s)";
Maw answered 12/1, 2021 at 6:31 Comment(0)
F
0

Here is a simple JS function

function simplifiedMilliseconds(milliseconds) {

  const totalSeconds = parseInt(Math.floor(milliseconds / 1000));
  const totalMinutes = parseInt(Math.floor(totalSeconds / 60));
  const totalHours = parseInt(Math.floor(totalMinutes / 60));
  const days = parseInt(Math.floor(totalHours / 24));

  const seconds = parseInt(totalSeconds % 60);
  const minutes = parseInt(totalMinutes % 60);
  const hours = parseInt(totalHours % 24);

  let time = '1s';
  if (days > 0) {
    time = `${days}d:${hours}h:${minutes}m:${seconds}s`;
  } else if (hours > 0) {
    time = `${hours}h:${minutes}m:${seconds}s`;
  } else if (minutes > 0) {
    time = `${minutes}m:${seconds}s`;
  } else if (seconds > 0) {
    time = `${seconds}s`;
  }
  return time;
}
Flintshire answered 19/2, 2021 at 7:26 Comment(0)
V
0

Kotlin way

    fun getTripDuration(durationStr: String): String {

    val totalSeconds = durationStr.toDouble()
    val totalMinutes = floor(totalSeconds / 60)
    val totalHours = floor(totalMinutes / 60)
    val days = floor(totalHours / 24).toLong()
    val minutes = (totalMinutes % 60).toLong()
    val hours = (totalHours % 24).toLong()

    Timber.d("$days Days $hours Hours $minutes Minutes")
    var durationInWords = ""

    if (days > 1L) {
        durationInWords = durationInWords.plus("$days days ")
    } else if (days == 1L) {
        durationInWords = durationInWords.plus("$days day ")
    }

    if (hours > 1L) {
        durationInWords = durationInWords.plus("$hours hours ")
    } else if (hours == 1L) {
        durationInWords = durationInWords.plus("$hours hour ")
    }

    if (minutes > 1L) {
        durationInWords = durationInWords.plus("$minutes mins")
    } else if (minutes == 1L) {
        durationInWords = durationInWords.plus("$minutes min")
    }

    if (durationInWords.isEmpty()) {
        durationInWords = durationInWords.plus("$minutes min")
    }

    return durationInWords
}
Vexed answered 27/1, 2022 at 12:12 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.