diff --git a/lib/WebGUI/Form/Interval.pm b/lib/WebGUI/Form/Interval.pm index 20afedf28..1cca61f3c 100644 --- a/lib/WebGUI/Form/Interval.pm +++ b/lib/WebGUI/Form/Interval.pm @@ -126,7 +126,7 @@ Returns the interval formatted as quantity and units. sub getValueAsHtml { my $self = shift; - return join ' ', $self->session->datetime->secondsToInterval($self->getOriginalValue); + return join ' ', $self->session->datetime->secondsToExactInterval($self->getOriginalValue); } #------------------------------------------------------------------- @@ -177,7 +177,7 @@ sub toHtml { years => $i18n->get(703), ); my %reverseUnits = reverse %units; - my ($interval, $units) = $self->session->datetime->secondsToInterval($self->getOriginalValue); + my ($interval, $units) = $self->session->datetime->secondsToExactInterval($self->getOriginalValue); # not sure why, but these things need to be defined like this or # they fail under some circumstnaces my $cmd = "WebGUI::Form::Integer"; @@ -209,7 +209,7 @@ Returns the field as hidden controls rather than displayable controls. sub toHtmlAsHidden { my $self = shift; - my ($interval, $units) = $self->session->datetime->secondsToInterval($self->getOriginalValue); + my ($interval, $units) = $self->session->datetime->secondsToExactInterval($self->getOriginalValue); return WebGUI::Form::Hidden->new($self->session, name=>$self->get("name").'_interval', value=>$interval diff --git a/lib/WebGUI/Session/DateTime.pm b/lib/WebGUI/Session/DateTime.pm index cd7274429..e2baa9c79 100644 --- a/lib/WebGUI/Session/DateTime.pm +++ b/lib/WebGUI/Session/DateTime.pm @@ -812,7 +812,8 @@ sub new { =head2 secondsToInterval ( seconds ) -Returns an interval and internationalized units derived the number of seconds. +Returns an interval and internationalized units derived the number +of seconds, rounding to the closest unit smaller than the interval. =head3 seconds @@ -842,6 +843,38 @@ sub secondsToInterval { #------------------------------------------------------------------- +=head2 secondsToExactInterval ( seconds ) + +Returns an interval and internationalized units derived the number of seconds. + +=head3 seconds + +The number of seconds in the interval. + +=cut + +sub secondsToExactInterval { + my $self = shift; + my $seconds = shift; + my $i18n = WebGUI::International->new($self->session, 'WebGUI'); + my %units = ( + 31536000 => "703", # years + 2592000 => "702", # months + 604800 => "701", # weeks + 86400 => "700", # days + 3600 => "706", # hours + 60 => "705", # minutes + ); + for my $unit (sort { $b <=> $a } keys %units) { + if ($seconds % $unit == 0) { + return ($seconds / $unit, $i18n->get($units{$unit})); + } + } + return ($seconds, $i18n->get("704")); # seconds +} + +#------------------------------------------------------------------- + =head2 secondsToTime ( seconds ) Returns a time string of the format HH::MM::SS on a 24 hour clock. See also timeToSeconds(). diff --git a/t/Session/DateTime.t b/t/Session/DateTime.t index 5b20b1a25..3399c911d 100644 --- a/t/Session/DateTime.t +++ b/t/Session/DateTime.t @@ -17,7 +17,7 @@ use File::Spec; use WebGUI::Test; use WebGUI::Session; -use Test::More tests => 79; # increment this value for each test you create +use Test::More tests => 90; # increment this value for each test you create installBadLocale(); @@ -212,7 +212,7 @@ cmp_ok( #################################################### # -# secondsToInverval +# secondsToInterval # #################################################### @@ -228,6 +228,24 @@ is(join(" ",$dt->secondsToInterval(60*60*24*365*2.9)), "25404 Hour(s)", "seconds is(join(" ",$dt->secondsToInterval(60*27)), "27 Minute(s)", "secondsToInterval(), minutes"); is(join(" ",$dt->secondsToInterval(59)), "59 Second(s)", "secondsToInterval(), seconds"); +#################################################### +# +# secondsToExactInterval +# +#################################################### + +is(join(" ",$dt->secondsToExactInterval(60*60*24*365*2)), "2 Year(s)", "secondsToExactInterval(), years"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*180)), "6 Month(s)", "secondsToExactInterval(), months"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*7*3)), "3 Week(s)", "secondsToExactInterval(), weeks"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*5)), "5 Day(s)", "secondsToExactInterval(), days"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*8)), "8 Day(s)", "secondsToExactInterval(), days, longer than a week"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*363)), "363 Day(s)", "secondsToExactInterval(), days, longer than a month"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*365*2.4)), "876 Day(s)", "secondsToExactInterval(), days, longer than a year"); +is(join(" ",$dt->secondsToExactInterval(60*60*18)), "18 Hour(s)", "secondsToExactInterval(), hours"); +is(join(" ",$dt->secondsToExactInterval(60*60*24*365*2.9)), "25404 Hour(s)", "secondsToExactInterval(), hours, longer than a year"); +is(join(" ",$dt->secondsToExactInterval(60*27)), "27 Minute(s)", "secondsToExactInterval(), minutes"); +is(join(" ",$dt->secondsToExactInterval(59)), "59 Second(s)", "secondsToExactInterval(), seconds"); + #################################################### # # intervalToSeconds