--- loncom/homework/caparesponse/caparesponse.pm 2007/02/18 02:03:18 1.208
+++ loncom/homework/caparesponse/caparesponse.pm 2012/02/01 17:35:24 1.250
@@ -1,7 +1,7 @@
# The LearningOnline Network with CAPA
# caparesponse definition
#
-# $Id: caparesponse.pm,v 1.208 2007/02/18 02:03:18 albertel Exp $
+# $Id: caparesponse.pm,v 1.250 2012/02/01 17:35:24 www Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -33,6 +33,7 @@ use Safe::Hole;
use Apache::lonmaxima();
use Apache::lonlocal;
use Apache::lonnet;
+use Apache::lonmsg();
use Apache::response();
use Storable qw(dclone);
@@ -279,6 +280,8 @@ sub start_numericalresponse {
$token,40).
&Apache::loncommon::help_open_topic('Formula_Response_Sampling');
}
+ $result.=&Apache::edit::text_arg('Pre-Processor Subroutine:','preprocess',
+ $token,10);
$result.=&Apache::edit::end_row().&Apache::edit::start_spanning_row();
} elsif ($target eq 'modified') {
my $constructtag;
@@ -286,11 +289,11 @@ sub start_numericalresponse {
$constructtag=&Apache::edit::get_new_args($token,$parstack,
$safeeval,'answer',
'incorrect','unit',
- 'format');
+ 'format','preprocess');
} elsif ($token->[1] eq 'formularesponse') {
$constructtag=&Apache::edit::get_new_args($token,$parstack,
$safeeval,'answer',
- 'samples');
+ 'samples','preprocess');
}
if ($constructtag) {
$result = &Apache::edit::rebuild_tag($token);
@@ -305,7 +308,7 @@ sub start_numericalresponse {
my $hideunit=&Apache::lonnet::EXT('resource.'.$partid.'_'.$id.'.turnoffunit');
&Apache::lonxml::debug("Got unit $hideunit for $partid $id");
#no way to enter units, with radio buttons
- if (lc($hideunit) eq "yes") {
+ if ((lc($hideunit) eq "yes") && ($Apache::lonhomework::type ne 'exam')) {
my $unit=&Apache::lonxml::get_param_var('unit',$parstack,
$safeeval);
if ($unit =~ /\S/) { $result.=" (in $unit) "; }
@@ -392,9 +395,6 @@ sub setup_capa_args {
sub setup_capa_response {
my ($args_ref,$response) = @_;
- use Data::Dumper;
- &Apache::lonxml::debug("response dump is ".&Dumper($response));
-
if (ref($response)) {
$$args_ref{'response'}=dclone($response);
} else {
@@ -404,7 +404,7 @@ sub setup_capa_response {
sub check_submission {
my ($response,$partid,$id,$tag,$parstack,$safeeval,$ignore_sig)=@_;
- my @args = ('type','tol','sig','format','unit','calc','samples');
+ my @args = ('type','tol','sig','format','unit','calc','samples','preprocess');
my $args_ref = &setup_capa_args($safeeval,$parstack,\@args,$response);
my $hideunit=
@@ -430,10 +430,18 @@ sub check_submission {
}
} elsif ($tag eq 'numericalresponse') {
$$args_ref{'type'}='float';
+ } elsif ($tag eq 'stringresponse') {
+ if ($$args_ref{'type'} eq '') {
+ $$args_ref{'type'} = 'ci';
+ }
}
-
+
&add_in_tag_answer($parstack,$safeeval);
+ if (!%answer) {
+ &Apache::lonxml::error("No answers are defined");
+ }
+
my (@final_awards,@final_msgs,@names);
foreach my $name (keys(%answer)) {
&Apache::lonxml::debug(" doing $name with ".join(':',@{ $answer{$name}{'answers'} }));
@@ -445,6 +453,7 @@ sub check_submission {
my ($result,@msgs) =
&Apache::run::run("&caparesponse_check_list()",$safeeval);
&Apache::lonxml::debug("checking $name $result with $response took ".&Time::HiRes::tv_interval($t0));
+
&Apache::lonxml::debug('msgs are '.join(':',@msgs));
my ($awards)=split(/:/,$result);
my @awards= split(/,/,$awards);
@@ -460,12 +469,54 @@ sub check_submission {
return($ad,$msg, $name);
}
+sub stringresponse_gradechange {
+ my ($part,$id,$previous,$caller,$response,$ad,$type) = @_;
+ return unless (ref($previous) eq 'HASH');
+ my ($prevarray,$prevaward);
+ my %typenames = (
+ cs => 'Case sensitive',
+ ci => 'Case insensitive',
+ );
+ if ($caller eq 'cs') {
+ return unless (ref($previous->{'version'}) eq 'ARRAY');
+ $prevarray = $previous->{'version'};
+ $prevaward = $previous->{'award'};
+ } elsif ($caller eq 'ci') {
+ return unless (ref($previous->{'versionci'}) eq 'ARRAY');
+ $prevarray = $previous->{'versionci'};
+ $prevaward = $previous->{'awardci'};
+ } else {
+ return;
+ }
+ my $count=0;
+ my %count_lookup;
+ foreach my $i (1..$Apache::lonhomework::history{'version'}) {
+ my $prefix = $i.":resource.$part";
+ next if (!exists($Apache::lonhomework::history{"$prefix.award"}));
+ $count++;
+ $count_lookup{$i} = $count;
+ }
+ my ($symb,$courseid,$domain,$name) = &Apache::lonnet::whichuser();
+ my %coursedesc = &Apache::lonnet::coursedescription($courseid);
+ my $cdom = $coursedesc{'domain'};
+ my $versions = ' (submissions: '.join(', ',map {$count_lookup{$_} } @{$prevarray}).')';
+ my $warning = "String Response ($typenames{$type}) grading discrepancy: award for response of $response changed from $prevaward".$versions." to $ad; user: $name:$domain in course: $courseid for part: $part response: $id for symb: $symb";
+ &Apache::lonnet::logthis($warning);
+ my $origmail = $Apache::lonnet::perlvar{'lonAdmEMail'};
+ my $recipients = &Apache::loncommon::build_recipient_list(undef,'errormail',
+ $cdom,$origmail);
+ if ($recipients ne '') {
+ &Apache::lonmsg::sendemail($recipients,'Stringresponse Grading Discrepancy',$warning);
+ }
+ return;
+}
+
sub add_in_tag_answer {
my ($parstack,$safeeval,$response_level) = @_;
my @answer=&Apache::lonxml::get_param_var('answer',$parstack,$safeeval,
$response_level);
&Apache::lonxml::debug('answer is'.join(':',@answer));
- if (@answer && defined($answer[0])) {
+ if (@answer && $answer[0] =~ /\S/) {
$answer{$tag_internal_answer_name}= {'type' => 'ordered',
'answers' => [\@answer] };
}
@@ -509,12 +560,12 @@ sub end_numericalresponse {
&Apache::lonxml::debug($$parstack[-1] . "\n
");
if ( &Apache::response::submitted('scantron')) {
- &add_in_tag_answer($parstack,$safeeval);
- my ($values,$display)=&make_numerical_bubbles($partid,$id,
- $target,$parstack,$safeeval);
- $response=$values->[$response];
- }
- $Apache::lonhomework::results{"resource.$partid.$id.submission"}=$response;
+ &add_in_tag_answer($parstack,$safeeval);
+ my ($values,$display)=&make_numerical_bubbles($partid,$id,
+ $target,$parstack,$safeeval);
+ $response=$values->[$response];
+ }
+ $Apache::lonhomework::results{"resource.$partid.$id.submission"}=$response;
my ($ad,$msg,$name)=&check_submission($response,$partid,$id,
$tag,$parstack,
$safeeval);
@@ -528,11 +579,18 @@ sub end_numericalresponse {
$Apache::inputtags::params{'sig'});
}
&Apache::lonxml::debug("\n
result:$result:$Apache::lonxml::curdepth
\n");
- if ($Apache::lonhomework::type eq 'survey' &&
- ($ad eq 'INCORRECT' || $ad eq 'APPROX_ANS' ||
- $ad eq 'EXACT_ANS')) {
- $ad='SUBMITTED';
- }
+ if (($ad eq 'INCORRECT' || $ad eq 'APPROX_ANS' ||
+ $ad eq 'EXACT_ANS')) {
+ if ($Apache::lonhomework::type eq 'survey') {
+ $ad='SUBMITTED';
+ } elsif ($Apache::lonhomework::type eq 'surveycred') {
+ $ad='SUBMITTED_CREDIT';
+ } elsif ($Apache::lonhomework::type eq 'anonsurvey') {
+ $ad='ANONYMOUS';
+ } elsif ($Apache::lonhomework::type eq 'anonsurveycred') {
+ $ad='ANONYMOUS_CREDIT';
+ }
+ }
&Apache::response::handle_previous(\%previous,$ad);
$Apache::lonhomework::results{"resource.$partid.$id.awarddetail"}=$ad;
$Apache::lonhomework::results{"resource.$partid.$id.awardmsg"}=$msg;
@@ -580,9 +638,16 @@ sub end_numericalresponse {
&get_table_sizes($number_of_bubbles,$bubble_display);
my $j=0;
my $cou=0;
- $result.='\vskip -1 mm \noindent \begin{enumerate}\item[\textbf{'.$Apache::lonxml::counter.'}.]';
+ $result.='\vskip 2mm \noindent ';
+ $result .= '\textbf{'.$Apache::lonxml::counter.'.} \vskip -3mm ';
+
for (my $i=0;$i<$number_of_tables;$i++) {
- $result.='\vskip -1 mm \noindent \setlength{\tabcolsep}{2 mm}\begin{tabular}{';
+ if ($i == 0) {
+ $result .= '\vskip -1mm ';
+ } else {
+ $result .= '\vskip 1mm ';
+ }
+ $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}';
}
@@ -595,12 +660,18 @@ sub end_numericalresponse {
$j++;
$result.='\\\\\end{tabular}\vskip 0 mm ';
}
- $result.='\end{enumerate}';
} 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') {
@@ -676,12 +747,12 @@ sub end_numericalresponse {
#}
}
if ($high && $tag eq 'numericalresponse') {
- $element.=' ['.$low.','.$high.']';
+ $element.='; ['.$low.'; '.$high.']';
$tolline .= "[$low, $high]";
}
if (defined($sighigh) && $tag eq 'numericalresponse') {
if ($env{'form.answer_output_mode'} eq 'tex') {
- $element.= " Sig $siglow - $sighigh";
+ $element.= "; Sig $siglow - $sighigh";
} else {
$element.= " Sig $siglow - $sighigh";
$sigline .= "[$siglow, $sighigh]";
@@ -701,7 +772,7 @@ sub end_numericalresponse {
}
}
if ($target eq 'answer') {
- $result.= &Apache::response::answer_part($tag,join(', ',@all_answer_info));
+ $result.= &Apache::response::answer_part($tag,join('; ',@all_answer_info));
}
}
@@ -740,16 +811,17 @@ sub end_numericalresponse {
if ($ad ne 'EXACT_ANS' && $ad ne 'APPROX_ANS') {
my $error;
if ($tag eq 'formularesponse') {
- $error=&mt('Computer\'s answer is incorrect ("[_1]").',join(', ',@$response));
+ $error=&mt("Computer's answer is incorrect ([_1]).",'"'.join(', ',@$response).'"');
} else {
# answer failed check if it is sig figs that is failing
my ($ad,$msg)=&check_submission($response,$partid,$id,
$tag,$parstack,
$safeeval,1);
+ $error=&mt("Computer's answer is incorrect ([_1]).",'"'.join(', ',@$response).'"').' ';
if ($sigline ne '') {
- $error=&mt('Computer\'s answer is incorrect ("[_1]"). It is likely that the tolerance range [_2] or significant figures [_3] need to be adjusted.',join(', ',@$response),$tolline,$sigline);
+ $error.=&mt('It is likely that the tolerance range [_1] or significant figures [_2] need to be adjusted.',$tolline,$sigline);
} else {
- $error=&mt('Computer\'s answer is incorrect ("[_1]"). It is likely that the tolerance range [_2] needs to be adjusted.',join(', ',@$response),$tolline);
+ $error.=&mt('It is likely that the tolerance range [_1] needs to be adjusted.',$tolline);
}
}
if ($ad ne 'EXACT_ANS' && $ad ne 'APPROX_ANS') {
@@ -785,12 +857,37 @@ sub end_numericalresponse {
}
if ($target eq 'grade' || $target eq 'web' || $target eq 'answer' ||
$target eq 'tex' || $target eq 'analyze') {
- &Apache::lonxml::increment_counter($increment);
+ if (($tag eq 'formularesponse') && ($target eq 'analyze')) {
+ my $type = &Apache::lonnet::EXT('resource.'.$partid.'_'.$id.'.type');
+ if ($type eq 'exam') {
+ $increment = &Apache::response::repetition();
+ }
+ }
+ &Apache::lonxml::increment_counter($increment,"$partid.$id");
+ if ($target eq 'analyze') {
+ &Apache::lonhomework::set_bubble_lines();
+ }
}
&Apache::response::end_response();
return $result;
}
+sub format_prior_response_numerical {
+ my ($mode,$answer) = @_;
+ if (ref($answer)) {
+ my $result = '
'. + &HTML::Entities::encode($element,'"<>&').' | '; + } + $result.='