A user initiates an action that will take some time to complete. This happens all the time, in all sorts of applications. The most common places you will find this are downloading and installing. Downloading is the easiest target for improvement so this is what I will focus on here.
The system wants to report to the user how long they will have to wait before the task is complete. This is usually presented with a progress indicator, a speed report and some form of time remaining.
If you’ve seen progress indicators like this before, you’ve no doubt suffered watching the time remaining report shift from 10 minutes to 1 hour, back to 10 minutes, up to 2 hours in what looks like an endless loop of uncertainty.
What the System Knows
- The total amount of data to be processed
- The current processing speed
- The total remaining amount of data to be processed
- The total time spent processing so far
The problem is that programmers tend to only pay attention to the first 3 pieces of information available. The fourth is outright ignored, which is sad because it allows us to write much, much better progress indicators.
What we tend to show is Time Remaining = Data Remaining / Data Speed
Example: 200MB / (1.2MB/s) results in 166.67 seconds remaining (or 2.8 minutes).
While this is valuable for the user to know the current speed and the time remaining at the current speed, and presents a fairly accurate report for users with constant download speeds, it’s often an unrealistic estimation of the real time to completion for anyone with variable rate downloads. In the case above where I was downloading a trial of the Adobe CS5 Suite, I was on a broadband connection (at a cafe) with a variable availability in transfer speed. My download shifted constantly between 50KB/s and 3.2MB/s, causing the weak progress indicator to jump back and forth between almost a day and less than an hour. But if the download manager calculated my AVERAGE speed, it could give me a much better indication of how long I can expect the action to take. And the great thing is that as the download progresses, it has the option of capturing and calculating a much more realistic number. In the end, the download took about 2 hours and 40 minutes, which ended at a time that the progress indicator never seemed to even come close to reporting.
Although, it could factor in some quite complex numbers, calculating variations in rates, all of that complexity is unnecessary–and probably not that useful. Really you just need this:
Rate = Time Spent / Amount Complete
Average Time Remaining = (Rate * Total Data) – Time Spent
We’ve downloaded 100MB / 200MB and, so far, it’s taken 12 minutes:
var totalData = 200; // constant // vars to be updated at intervals var timeSpent = 12; var dataComplete = 100; // calculate an estimate for the average time remaining var dataRemaining = totalData - dataComplete; var rate = timeSpent / dataComplete; var avgTimeRemaining = (rate * totalData) - timeSpent; // show it console.log(avgTimeRemaining);
So the avgTimeRemaining would be 12 minutes. The current speed might be different (probably is) so it would really be nice to see both the current rate and estimate at the current speed and the overall rate with an estimate that considers the shifting variation in speed. The closer you get to completion, the more accurate this second calculation becomes.
It’s great to know how long I can expect something to take at my current speed, but it’s much better if I can also see my average speed along with an estimate based on that information. Often, for people with variable rates of processing and downloading, the second calculation is much more helpful.