Trying to implement windows Progressbar showing progress of download in bytes with big numbers, but am unable to do it correctly.
For a download of 2.5gb if I do following, it ends short of the full range when download is complete.
double dlSize = getDlSize();
unsigned int pbRange = (unsigned int)( dlSize / 3000 );
SendMessage( hProgressbar, PBM_SETRANGE, 0, MAKELPARAM( 0, pbRange ) );
and then set new position at each download callback as :
double dlBytes = bytesDownloaded();
unsigned int newIncrement = (unsigned int)( dlBytes / 3000 );
SendMessage( hProgressbar, PBM_DELTAPOS, (WPARAM)newIncrement, 0 );
This is a very noobish implementation, and I don’t want fall in the xy situation, So my question is what is the correct way to implement a progressbar with big numbers in tune of 2-5GBs in bytes ?
I tried both approaches suggested below by @msandiford and @NikBougalis, by taking the width of the progressbar in account and by using percentage instead of actual number, I even combined both, but in all cases the newIncrement always comes out 0, maybe that’s because dlSize is always lower( in double newIncrement comes out something like 1.15743e+007, type cast it and its 0 ).
What else I can do ?
New Code combining both approaches:
EDIT 2:
Added few checks to the code as I was constantly getting 0 for newIncrement, looks like its working now, not sure how well:
GetClientRect(hProgressbar, &pbRCClient);
pbWidth = pbRCClient.right - pbRCClient.left; // (pbWidth its a global variable)
unsigned int pbRange = pbRCClient.right - pbRCClient.left;
SendMessage( hProgressbar, PBM_SETRANGE, 0, MAKELPARAM( 0, pbRange ) );
and while updating :
double dlSize = getDlSize();
double doubleIncrement = ( ( dlSize * pbWidth ) / totalSize );
unsigned int newIncrement;
if ( (unsigned int)doubleIncrement < 1 )
{
blockFill += doubleIncrement;
if ( (unsigned int)blockFill > 1 )
{
newIncrement = ( unsigned int )blockFill;
SendMessage( hProgressbar, PBM_DELTAPOS, (WPARAM)newIncrement, 0 );
blockFill = 0;
}
}
else
{
newIncrement = ( unsigned int )( doubleIncrement );
SendMessage( hProgressbar, PBM_DELTAPOS, (WPARAM)newIncrement, 0 );
//blockFill = 0;
}
EDIT 3 : Looks like its still finishing early.
There probably isn’t much point making the progress bar more accurate than the number of pixels in progress bar window itself. Based on this, you should be able to scale the target to the number of pixels pretty easily.
Then updating progress would be something like:
If the progress window was somehow resizeable, you would need to recalculate
pbRange, reset the progress bar range and recalculateunitsPerPixelin response to aWM_SIZEmessage.