';
+ $bubble_display->[$ind].'';
}
$result.='';
}
@@ -636,23 +665,20 @@ sub end_numericalresponse {
$result.=' \textit{(in} \verb|'.$unit.'|\textit{)} ';
}
if ($tag eq 'numericalresponse') {
- $result .= &make_latex_bubbles($bubble_values, $bubble_display);
+ $result .= &make_horizontal_latex_bubbles($bubble_values, $bubble_display,
+ '$\bigcirc$');
} else {
$increment = &Apache::response::repetition();
}
}
}
- if (($target eq 'web') && ($tag eq 'formularesponse')
- && ($Apache::lonhomework::type ne 'exam') && ($Apache::inputtags::status['-1'] eq 'CAN_ANSWER')
- && (&Apache::lonnet::EXT('resource.'.$partid.'_'.$id.'.turnoffeditor') ne 'yes')) {
- $result.=&Apache::response::edit_mathresponse_button($id,"HWVAL_$id");
- }
-
+
&Apache::response::setup_prior_tries_hash(\&format_prior_response_numerical);
} elsif ($target eq 'edit') {
$result.=''.&Apache::edit::end_table;
} elsif ($target eq 'answer' || $target eq 'analyze') {
my $part_id="$partid.$id";
+ my $samples;
if ($target eq 'analyze') {
push (@{ $Apache::lonhomework::analyze{"parts"} },$part_id);
$Apache::lonhomework::analyze{"$part_id.type"} = $tag;
@@ -665,11 +691,26 @@ sub end_numericalresponse {
if (scalar(@$tagstack)) {
&Apache::response::setup_params($tag,$safeeval);
}
- &add_in_tag_answer($parstack,$safeeval);
+ if ($tag eq 'numericalresponse') {
+ $stringify = 1;
+ } elsif ($tag eq 'formularesponse') {
+ $samples=&Apache::lonxml::get_param('samples',$parstack,$safeeval);
+ if ($samples) {
+ $stringify = 1;
+ }
+ }
+ &add_in_tag_answer($parstack,$safeeval,$stringify);
my (@formats)=&Apache::lonxml::get_param_var('format',$parstack,$safeeval);
my $unit=&Apache::lonxml::get_param_var('unit',$parstack,$safeeval);
-
+ my ($needsdollar,$needscomma);
+ if ($unit =~ /\$/) {
+ $needsdollar = 1;
+ }
+ if ($unit =~ /\,/) {
+ $needscomma = 1;
+ }
+
if ($target eq 'answer') {
$result.=&Apache::response::answer_header($tag,undef,
scalar(keys(%answer)));
@@ -758,17 +799,21 @@ sub end_numericalresponse {
my $ans=$answers[$i];
my $fmt=$formats[0];
if (@formats && $#formats) {$fmt=$formats[$i];}
- foreach my $element (@$ans) {
+ my @answers;
+ if (ref($ans) eq 'ARRAY') {
+ @answers = (@{$ans});
+ }
+ foreach my $element (@answers) {
if ($fmt && $tag eq 'numericalresponse') {
$fmt=~s/e/E/g;
if ($unit=~/\$/) { $fmt="\$".$fmt; $unit=~s/\$//g; }
if ($unit=~/\,/) { $fmt="\,".$fmt; $unit=~s/\,//g; }
$element = &format_number($element,$fmt,$target,
$safeeval);
- if ($fmt=~/\$/ && $unit!~/\$/) { $element=~s/\$//; }
+ if ($fmt=~/\$/ && !$needsdollar) { $element=~s/\$//; }
}
}
- push(@fmt_ans,join(',',@$ans));
+ push(@fmt_ans,join(',',@answers));
}
my $response=\@fmt_ans;
@@ -778,7 +823,7 @@ sub end_numericalresponse {
! ($Apache::lonhomework::type eq 'exam' ||
lc($hideunit) eq "yes") ) {
my $cleanunit=$unit;
- $cleanunit=~s/\$\,//g;
+ $cleanunit=~s/[\$,]//g;
foreach my $ans (@fmt_ans) {
$ans.=" $cleanunit";
}
@@ -795,7 +840,16 @@ sub end_numericalresponse {
$tag,$parstack,
$safeeval,1);
$error=&mt("Computer's answer is incorrect ([_1]).",'"'.join(', ',@$response).'"').' ';
- if ($sigline ne '') {
+ if (($ad eq 'NO_UNIT') && $needsdollar) {
+ $error.=&mt('The unit attribute includes [_1] but the answer format does not.','$').' '.
+ &mt('Either remove the [_1] from the unit or prepend [_1] to the answer format.','$');
+ } elsif (($ad eq 'COMMA_FAIL') && $needscomma) {
+ $error.=&mt('The unit attribute includes [_1] but the answer format does not.',',').' '.
+ &mt('Either remove the [_1] from the unit or prepend [_1] to the answer format.',',');
+ } elsif ($ad eq 'UNIT_INVALID_STUDENT') {
+ $error.=&mt('Unable to interpret units. Computer reads units as "[_1]".',$msg).' '.
+ &mt('The unit attribute in the numericalresponse item needs to be a supported physical unit.');
+ } elsif ($sigline ne '') {
$error.=&mt('It is likely that the tolerance range [_1] or significant figures [_2] need to be adjusted.',$tolline,$sigline);
} else {
$error.=&mt('It is likely that the tolerance range [_1] needs to be adjusted.',$tolline);
@@ -823,7 +877,6 @@ sub end_numericalresponse {
}
}
if ($tag eq 'formularesponse' && $target eq 'answer') {
- my $samples=&Apache::lonxml::get_param('samples',$parstack,$safeeval);
$result.=&Apache::response::answer_part($tag,$samples);
}
$result.=&Apache::response::next_answer($tag,$name);
@@ -866,8 +919,8 @@ sub format_prior_response_numerical {
}
sub check_for_answer_errors {
- my ($parstack,$safeeval) = @_;
- &add_in_tag_answer($parstack,$safeeval);
+ my ($parstack,$safeeval,$stringify) = @_;
+ &add_in_tag_answer($parstack,$safeeval,$stringify);
my %counts;
foreach my $name (keys(%answer)) {
push(@{$counts{scalar(@{$answer{$name}{'answers'}})}},$name);
@@ -894,10 +947,9 @@ sub get_table_sizes {
my ($number_of_bubbles,$rbubble_values)=@_;
my $scale=2; #mm for one digit
my $cell_width=0;
- &Apache::lonnet::logthis("textwidth envvar: " . $env{'form.textwidth'});
foreach my $member (@$rbubble_values) {
my $cell_width_real=0;
- if ($member=~/(\+|-)?(\d*)\.?(\d*)\s*\$?\\times\s*10\^{(\+|-)?(\d+)}\$?/) {
+ if ($member=~/(\+|-)?(\d*)\.?(\d*)\s*\$?\\times\s*10\^\{(\+|-)?(\d+)}\$?/) {
$cell_width_real=(length($2)+length($3)+length($5)+7)*$scale;
} elsif ($member=~/(\d*)\.?(\d*)(E|e)(\+|-)?(\d*)/) {
$cell_width_real=(length($1)+length($2)+length($5)+9)*$scale;
@@ -970,6 +1022,15 @@ sub make_numerical_bubbles {
my $number_of_bubbles =
&Apache::response::get_response_param($part.'_'.$id,'numbubbles',8);
+ #
+ # Fixes for BZ 6519 - number of bubbles <= 0 or non-integer.
+ #
+ $number_of_bubbles = int($number_of_bubbles + 0.5);
+ if ($number_of_bubbles <= 0) {
+ $number_of_bubbles = 8;
+ }
+
+
my ($format)=&Apache::lonxml::get_param_var('format',$parstack,$safeeval);
my $name = (exists($answer{$tag_internal_answer_name})
? $tag_internal_answer_name
@@ -1042,7 +1103,23 @@ sub make_numerical_bubbles {
&Math::Random::random_uniform_integer(1,1,10);
}
for ($ind=0;$ind<$number_of_bubbles;$ind++) {
- $bubble_values[$ind] = $answerfactor*($factor**($power-$powers[$#powers-$ind]));
+ my $exponent = $power-$powers[$#powers-$ind];
+ $bubble_values[$ind] = $answerfactor*($factor**$exponent);
+
+ # If bubble is for correct answer (i.e., exponent = 0), and value
+ # of $answerfactor * factor**$exponent is an integer with more than
+ # 15 digits, assign $answerfactor itself as bubble value.
+ # This prevents a "use fewer digits" issue on 64bit servers
+ # when correct answer is >= 1e+16, and when correct bubble is A.
+
+ if ($exponent == 0) {
+ if ($bubble_values[$ind] =~ /^-?(\d+)$/) {
+ if (length($1) > 15) {
+ $bubble_values[$ind] = $answerfactor;
+ }
+ }
+ }
+
$bubble_display[$ind] = &format_number($bubble_values[$ind],
$format,$target,$safeeval);
}
@@ -1058,18 +1135,22 @@ sub make_numerical_bubbles {
}
##
-# Produce LaTeX bubbles given a set of bubble values:
+# Produce LaTeX bubbles laid out horizontally given a set of bubble values:
#
# @param bubble_values - reference to an array of bubble 'values'
# @param bubble_display - reference to the array of texts to display to the user
# for each bubble_value (this is mostly for numerical response
# when the displayed value may not be an exact
# representation of the bubble value.
+# @param bubble_fragment- The LaTeX fragment that will be plugged in to make
+# the bubble itself. Note that the code will autonomously
+# label each bubble with a lable...and that it's perfectly
+# acceptable to use "" for the bubble_fragment.
#
# @return string - the LaTeX fragment that produces the bubbles.
#
-sub make_latex_bubbles {
- my ($bubble_values, $bubble_display) = @_;
+sub make_horizontal_latex_bubbles {
+ my ($bubble_values, $bubble_display, $bubble_fragment) = @_;
my $result;
my $number_of_bubbles = scalar(@{$bubble_values});
@@ -1083,7 +1164,9 @@ sub make_latex_bubbles {
my $j=0;
my $cou=0;
$result.='\vskip 2mm \noindent ';
- $result .= '\textbf{'.$Apache::lonxml::counter.'.} \vskip -3mm ';
+ if ($Apache::lonhomework::type eq 'exam') {
+ $result .= '\textbf{'.$Apache::lonxml::counter.'.} \vskip -3mm ';
+ }
for (my $i=0;$i<$number_of_tables;$i++) {
if ($i == 0) {
@@ -1093,12 +1176,16 @@ sub make_latex_bubbles {
}
$result.='\noindent \setlength{\tabcolsep}{2 mm}\hskip 2pc\begin{tabular}{';
for (my $ind=0;$ind<$table_range[$j];$ind++) {
- $result.='p{3 mm}p{'.$celllength.' mm}';
+ $result.='p{4 mm}p{'.$celllength.' mm}';
}
$result.='}';
for (my $ind=$cou;$ind<$cou+$table_range[$j];$ind++) {
- $result.='\hskip -4 mm {\small \textbf{'.$alphabet[$ind].'}}$\bigcirc$ & \hskip -3 mm {\small '.$bubble_display->[$ind].'} ';
- if ($ind != $cou+$table_range[$j]-1) {$result.=' & ';}
+ $result.='\hskip -4 mm {\small \textbf{ '.$alphabet[$ind].'}}'
+ . $bubble_fragment
+ . '& \hskip -3 mm {\small '.$bubble_display->[$ind].'} ';
+ if ($ind != $cou+$table_range[$j]-1) {
+ $result.=' & ';
+ }
}
$cou += $table_range[$j];
$j++;
@@ -1219,6 +1306,8 @@ sub end_stringresponse {
if (!$Apache::lonxml::default_homework_loaded) {
&Apache::lonxml::default_homework_load($safeeval);
}
+ my $tag;
+ if (scalar(@$tagstack)) { $tag=$$tagstack[-1]; }
if ( $target eq 'grade' && &Apache::response::submitted() ) {
&Apache::response::setup_params('stringresponse',$safeeval);
$safeeval->share_from('capa',['&caparesponse_capa_check_answer']);
@@ -1261,7 +1350,8 @@ sub end_stringresponse {
if ($$args_ref{'type'} eq '') {
$$args_ref{'type'} = 'ci';
}
- &add_in_tag_answer($parstack,$safeeval);
+ my $stringify = 1;
+ &add_in_tag_answer($parstack,$safeeval,$stringify);
my (@final_awards,@final_msgs,@names,%ansstring);
foreach my $name (keys(%answer)) {
&Apache::lonxml::debug(" doing $name with ".join(':',@{ $answer{$name}{'answers'} }));
@@ -1352,7 +1442,11 @@ sub end_stringresponse {
}
}
} elsif ($target eq 'answer' || $target eq 'analyze') {
- &add_in_tag_answer($parstack,$safeeval);
+ my $stringify;
+ if ($type ne 're') {
+ $stringify = 1;
+ }
+ &add_in_tag_answer($parstack,$safeeval,$stringify);
if ($target eq 'analyze') {
push (@{ $Apache::lonhomework::analyze{"parts"} },"$part.$id");
$Apache::lonhomework::analyze{"$part.$id.type"} = 'stringresponse';