--- loncom/interface/lonhelper.pm 2003/09/29 16:33:09 1.48 +++ loncom/interface/lonhelper.pm 2005/07/12 16:11:19 1.112 @@ -1,7 +1,7 @@ # The LearningOnline Network with CAPA # .helper XML handler to implement the LON-CAPA helper # -# $Id: lonhelper.pm,v 1.48 2003/09/29 16:33:09 bowersj2 Exp $ +# $Id: lonhelper.pm,v 1.112 2005/07/12 16:11:19 albertel Exp $ # # Copyright Michigan State University Board of Trustees # @@ -25,10 +25,6 @@ # # http://www.lon-capa.org/ # -# (Page Handler -# -# (.helper handler -# =pod @@ -172,12 +168,21 @@ before parsing XML fragments and B<Apach when you are done. See lonprintout.pm for examples of this usage in the printHelper subroutine. +=head2 Localization + +The helper framework tries to handle as much localization as +possible. The text is always run through +Apache::lonlocal::normalize_string, so be sure to run the keys through +that function for maximum usefulness and robustness. + =cut package Apache::lonhelper; use Apache::Constants qw(:common); use Apache::File; use Apache::lonxml; +use Apache::lonlocal; +use Apache::lonnet; # Register all the tags with the helper, so the helper can # push and pop them @@ -222,7 +227,7 @@ my $paramHash; # In the debugger, this means that breakpoints are ignored until you step into # a function and get out of what must be a "faked up scope" in the Apache-> # mod_perl connection. In this code, it was manifesting itself in the existence -# of two seperate file-scoped $helper variables, one set to the value of the +# of two separate file-scoped $helper variables, one set to the value of the # helper in the helper constructor, and one referenced by the handler on the # "$helper->process()" line. Using the debugger, one could actually # see the two different $helper variables, as hashes at completely @@ -247,7 +252,7 @@ sub real_handler { my $r = shift; my $uri = shift; if (!defined($uri)) { $uri = $r->uri(); } - $ENV{'request.uri'} = $uri; + $env{'request.uri'} = $uri; my $filename = '/home/httpd/html' . $uri; my $fh = Apache::File->new($filename); my $file; @@ -255,21 +260,13 @@ sub real_handler { # Send header, don't cache this page - if ($r->header_only) { - if ($ENV{'browser.mathml'}) { - $r->content_type('text/xml'); - } else { - $r->content_type('text/html'); - } - $r->send_http_header; - return OK; - } - if ($ENV{'browser.mathml'}) { - $r->content_type('text/xml'); + if ($env{'browser.mathml'}) { + &Apache::loncommon::content_type($r,'text/xml'); } else { - $r->content_type('text/html'); + &Apache::loncommon::content_type($r,'text/html'); } $r->send_http_header; + return OK if $r->header_only; $r->rflush(); # Discard result, we just want the objects that get created by the @@ -278,7 +275,7 @@ sub real_handler { my $allowed = $helper->allowedCheck(); if (!$allowed) { - $ENV{'user.error.msg'} = $ENV{'request.uri'}.':'.$helper->{REQUIRED_PRIV}. + $env{'user.error.msg'} = $env{'request.uri'}.':'.$helper->{REQUIRED_PRIV}. ":0:0:Permission denied to access this helper."; return HTTP_NOT_ACCEPTABLE; } @@ -359,9 +356,11 @@ sub end_state { package Apache::lonhelper::helper; use Digest::MD5 qw(md5_hex); -use HTML::Entities; +use HTML::Entities(); use Apache::loncommon; use Apache::File; +use Apache::lonlocal; +use Apache::lonnet; sub new { my $proto = shift; @@ -373,16 +372,16 @@ sub new { # If there is a state from the previous form, use that. If there is no # state, use the start state parameter. - if (defined $ENV{"form.CURRENT_STATE"}) + if (defined $env{"form.CURRENT_STATE"}) { - $self->{STATE} = $ENV{"form.CURRENT_STATE"}; + $self->{STATE} = $env{"form.CURRENT_STATE"}; } else { $self->{STATE} = "START"; } - $self->{TOKEN} = $ENV{'form.TOKEN'}; + $self->{TOKEN} = $env{'form.TOKEN'}; # If a token was passed, we load that in. Otherwise, we need to create a # new storage file # Tried to use standard Tie'd hashes, but you can't seem to take a @@ -415,16 +414,16 @@ sub new { return undef; } # Must create the storage - $self->{TOKEN} = md5_hex($ENV{'user.name'} . $ENV{'user.domain'} . + $self->{TOKEN} = md5_hex($env{'user.name'} . $env{'user.domain'} . time() . rand()); $self->{FILENAME} = $Apache::lonnet::tmpdir . md5_hex($self->{TOKEN}); } # OK, we now have our persistent storage. - if (defined $ENV{"form.RETURN_PAGE"}) + if (defined $env{"form.RETURN_PAGE"}) { - $self->{RETURN_PAGE} = $ENV{"form.RETURN_PAGE"}; + $self->{RETURN_PAGE} = $env{"form.RETURN_PAGE"}; } else { @@ -453,11 +452,11 @@ sub _saveVars { my $self = shift; my $result = ""; $result .= '<input type="hidden" name="CURRENT_STATE" value="' . - HTML::Entities::encode($self->{STATE}) . "\" />\n"; + HTML::Entities::encode($self->{STATE},'<>&"') . "\" />\n"; $result .= '<input type="hidden" name="TOKEN" value="' . $self->{TOKEN} . "\" />\n"; $result .= '<input type="hidden" name="RETURN_PAGE" value="' . - HTML::Entities::encode($self->{RETURN_PAGE}) . "\" />\n"; + HTML::Entities::encode($self->{RETURN_PAGE},'<>&"') . "\" />\n"; return $result; } @@ -485,11 +484,11 @@ sub declareVar { } my $envname = 'form.' . $var . '.forminput'; - if (defined($ENV{$envname})) { - if (ref($ENV{$envname})) { - $self->{VARS}->{$var} = join('|||', @{$ENV{$envname}}); + if (defined($env{$envname})) { + if (ref($env{$envname})) { + $self->{VARS}->{$var} = join('|||', @{$env{$envname}}); } else { - $self->{VARS}->{$var} = $ENV{$envname}; + $self->{VARS}->{$var} = $env{$envname}; } } } @@ -501,7 +500,7 @@ sub allowedCheck { return 1; } - return Apache::lonnet::allowed($self->{REQUIRED_PRIV}, $ENV{'request.course.id'}); + return Apache::lonnet::allowed($self->{REQUIRED_PRIV}, $env{'request.course.id'}); } sub changeState { @@ -523,7 +522,7 @@ sub process { # Phase 1: Post processing for state of previous screen (which is actually # the "current state" in terms of the helper variables), if it wasn't the # beginning state. - if ($self->{STATE} ne "START" || $ENV{"form.SUBMIT"} eq "Next ->") { + if ($self->{STATE} ne "START" || $env{"form.SUBMIT"} eq &mt("Next ->")) { my $prevState = $self->{STATES}{$self->{STATE}}; $prevState->postprocess(); } @@ -574,13 +573,19 @@ sub display { } # Phase 4: Display. - my $stateTitle = $state->title(); - my $bodytag = &Apache::loncommon::bodytag("$self->{TITLE}",'',''); + my $html=&Apache::lonxml::xmlbegin(); + my $stateTitle=&mt($state->title()); + my $helperTitle = &mt($self->{TITLE}); + my $bodytag = &Apache::loncommon::bodytag($helperTitle,'',''); + my $previous = HTML::Entities::encode(&mt("<- Previous"), '<>&"'); + my $next = HTML::Entities::encode(&mt("Next ->"), '<>&"'); + # FIXME: This should be parameterized, not concatenated - Jeremy + my $loncapaHelper = &mt("LON-CAPA Helper:"); $result .= <<HEADER; -<html> +$html <head> - <title>LON-CAPA Helper: $self->{TITLE}</title> + <title>$loncapaHelper: $helperTitle</title> </head> $bodytag HEADER @@ -607,12 +612,12 @@ HEADER } if ($self->{DONE}) { my $returnPage = $self->{RETURN_PAGE}; - $result .= "<a href=\"$returnPage\">End Helper</a>"; + $result .= "<a href=\"$returnPage\">" . &mt("End Helper") . "</a>"; } else { $result .= '<nobr><input name="back" type="button" '; - $result .= 'value="<- Previous" onclick="history.go(-1)" /> '; - $result .= '<input name="SUBMIT" type="submit" value="Next ->" /></nobr>'; + $result .= 'value="' . $previous . '" onclick="history.go(-1)" /> '; + $result .= '<input name="SUBMIT" type="submit" value="' . $next . '" /></nobr>'; } } @@ -626,12 +631,12 @@ HEADER } if ($self->{DONE}) { my $returnPage = $self->{RETURN_PAGE}; - $result .= "<a href=\"$returnPage\">End Helper</a>"; + $result .= "<a href=\"$returnPage\">" . &mt('End Helper') . "</a>"; } else { $result .= '<nobr><input name="back" type="button" '; - $result .= 'value="<- Previous" onclick="history.go(-1)" /> '; - $result .= '<input name="SUBMIT" type="submit" value="Next ->" /></nobr>'; + $result .= 'value="' . $previous . '" onclick="history.go(-1)" /> '; + $result .= '<input name="SUBMIT" type="submit" value="' . $next . '" /></nobr>'; } } @@ -883,6 +888,7 @@ sub start_defaultvalue { sub end_defaultvalue { return ''; } +# Validators may need to take language specifications sub start_validator { my ($target,$token,$tagstack,$parstack,$parser,$safeeval,$style)=@_; @@ -952,11 +958,17 @@ within each other.) This is also a good template for creating your own new states, as it has very little code beyond the state template. +=head3 Localization + +The contents of the message tag will be run through the +normalize_string function and that will be used as a call to &mt. + =cut no strict; @ISA = ("Apache::lonhelper::element"); use strict; +use Apache::lonlocal; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::message', @@ -976,8 +988,8 @@ sub start_message { return ''; } - $paramHash->{MESSAGE_TEXT} = &Apache::lonxml::get_all_text('/message', - $parser); + $paramHash->{MESSAGE_TEXT} = &mtn(&Apache::lonxml::get_all_text('/message', + $parser)); if (defined($token->[2]{'nextstate'})) { $paramHash->{NEXTSTATE} = $token->[2]{'nextstate'}; @@ -998,7 +1010,7 @@ sub end_message { sub render { my $self = shift; - return $self->{MESSAGE_TEXT}; + return &mtn($self->{MESSAGE_TEXT}); } # If a NEXTSTATE was given, switch to it sub postprocess { @@ -1100,6 +1112,8 @@ tag is stored in the {VARS} hash. no strict; @ISA = ("Apache::lonhelper::element"); use strict; +use Apache::lonlocal; +use Apache::lonnet; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::choices', @@ -1146,11 +1160,11 @@ sub start_choice { } my $computer = $token->[2]{'computer'}; - my $human = &Apache::lonxml::get_all_text('/choice', - $parser); + my $human = &mt(&Apache::lonxml::get_all_text('/choice', + $parser)); my $nextstate = $token->[2]{'nextstate'}; my $evalFlag = $token->[2]{'eval'}; - push @{$paramHash->{CHOICES}}, [$human, $computer, $nextstate, + push @{$paramHash->{CHOICES}}, [&mtn($human), $computer, $nextstate, $evalFlag]; return ''; } @@ -1159,6 +1173,13 @@ sub end_choice { return ''; } +{ + # used to generate unique id attributes for <input> tags. + # internal use only. + my $id = 0; + sub new_id { return $id++; } +} + sub render { my $self = shift; my $var = $self->{'variable'}; @@ -1167,7 +1188,8 @@ sub render { if ($self->{'multichoice'}) { $result .= <<SCRIPT; -<script> +<script type="text/javascript"> +// <!-- function checkall(value, checkName) { for (i=0; i<document.forms.helpform.elements.length; i++) { ele = document.forms.helpform.elements[i]; @@ -1176,6 +1198,7 @@ sub render { } } } +// --> </script> SCRIPT } @@ -1183,10 +1206,13 @@ SCRIPT # Only print "select all" and "unselect all" if there are five or # more choices; fewer then that and it looks silly. if ($self->{'multichoice'} && scalar(@{$self->{CHOICES}}) > 4) { + my %lt=&Apache::lonlocal::texthash( + 'sa' => "Select All", + 'ua' => "Unselect All"); $buttons = <<BUTTONS; <br /> -<input type="button" onclick="checkall(true, '$var')" value="Select All" /> -<input type="button" onclick="checkall(false, '$var')" value="Unselect All" /> +<input type="button" onclick="checkall(true, '$var')" value="$lt{'sa'}" /> +<input type="button" onclick="checkall(false, '$var')" value="$lt{'ua'}" /> <br /> BUTTONS } @@ -1238,14 +1264,16 @@ BUTTONS my $type = "radio"; if ($self->{'multichoice'}) { $type = 'checkbox'; } foreach my $choice (@{$self->{CHOICES}}) { + my $id = &new_id(); $result .= "<tr>\n<td width='20'> </td>\n"; $result .= "<td valign='top'><input type='$type' name='$var.forminput'" - . "' value='" . - HTML::Entities::encode($choice->[1]) + . " value='" . + HTML::Entities::encode($choice->[1],"<>&\"'") . "'"; if ($checkedChoices{$choice->[1]}) { - $result .= " checked "; + $result .= " checked='checked' "; } + $result .= qq{id="id$id"}; my $choiceLabel = $choice->[0]; if ($choice->[4]) { # if we need to evaluate this choice $choiceLabel = "sub { my $helper = shift; my $state = shift;" . @@ -1253,7 +1281,8 @@ BUTTONS $choiceLabel = eval($choiceLabel); $choiceLabel = &$choiceLabel($helper, $self); } - $result .= "/></td><td> " . $choiceLabel . "</td></tr>\n"; + $result .= "/></td><td> ".qq{<label for="id$id">}. + $choiceLabel. "</label></td></tr>\n"; } $result .= "</table>\n\n\n"; $result .= $buttons; @@ -1265,11 +1294,11 @@ BUTTONS # given, switch to it sub postprocess { my $self = shift; - my $chosenValue = $ENV{'form.' . $self->{'variable'} . '.forminput'}; + my $chosenValue = $env{'form.' . $self->{'variable'} . '.forminput'}; if (!defined($chosenValue) && !$self->{'allowempty'}) { - $self->{ERROR_MSG} = "You must choose one or more choices to" . - " continue."; + $self->{ERROR_MSG} = + &mt("You must choose one or more choices to continue."); return 0; } @@ -1312,9 +1341,14 @@ the result is stored in. =cut +# This really ought to be a sibling class to "choice" which is itself +# a child of some abstract class.... *shrug* + no strict; @ISA = ("Apache::lonhelper::element"); use strict; +use Apache::lonlocal; +use Apache::lonnet; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::dropdown', @@ -1392,10 +1426,10 @@ sub render { $result .= "<select name='${var}.forminput'>\n"; foreach my $choice (@{$self->{CHOICES}}) { $result .= "<option value='" . - HTML::Entities::encode($choice->[1]) + HTML::Entities::encode($choice->[1],"<>&\"'") . "'"; if ($checkedChoices{$choice->[1]}) { - $result .= " selected"; + $result .= " selected='selected' "; } my $choiceLabel = $choice->[0]; if ($choice->[4]) { # if we need to evaluate this choice @@ -1404,7 +1438,7 @@ sub render { $choiceLabel = eval($choiceLabel); $choiceLabel = &$choiceLabel($helper, $self); } - $result .= ">" . $choiceLabel . "\n"; + $result .= ">" . &mtn($choiceLabel) . "</option>\n"; } $result .= "</select>\n"; @@ -1415,7 +1449,7 @@ sub render { # given, switch to it sub postprocess { my $self = shift; - my $chosenValue = $ENV{'form.' . $self->{'variable'} . '.forminput'}; + my $chosenValue = $env{'form.' . $self->{'variable'} . '.forminput'}; if (!defined($chosenValue) && !$self->{'allowempty'}) { $self->{ERROR_MSG} = "You must choose one or more choices to" . @@ -1473,7 +1507,8 @@ Example: no strict; @ISA = ("Apache::lonhelper::element"); use strict; - +use Apache::lonlocal; # A localization nightmare +use Apache::lonnet; use Time::localtime; BEGIN { @@ -1533,11 +1568,11 @@ sub render { $result .= "<select name='${var}month'>\n"; for ($i = 0; $i < 12; $i++) { if ($i == $date->mon) { - $result .= "<option value='$i' selected>"; + $result .= "<option value='$i' selected='selected'>"; } else { $result .= "<option value='$i'>"; } - $result .= $months[$i] . "</option>\n"; + $result .= &mt($months[$i]) . "</option>\n"; } $result .= "</select>\n"; @@ -1545,7 +1580,7 @@ sub render { $result .= "<select name='${var}day'>\n"; for ($i = 1; $i < 32; $i++) { if ($i == $date->mday) { - $result .= '<option selected>'; + $result .= '<option selected="selected">'; } else { $result .= '<option>'; } @@ -1557,7 +1592,7 @@ sub render { $result .= "<select name='${var}year'>\n"; for ($i = 2000; $i < 2030; $i++) { # update this after 64-bit dates if ($date->year + 1900 == $i) { - $result .= "<option selected>"; + $result .= "<option selected='selected'>"; } else { $result .= "<option>"; } @@ -1567,25 +1602,28 @@ sub render { # Display Hours and Minutes if they are called for if ($self->{'hoursminutes'}) { + # This needs parameterization for times. + my $am = &mt('a.m.'); + my $pm = &mt('p.m.'); # Build hour $result .= "<select name='${var}hour'>\n"; - $result .= "<option " . ($date->hour == 0 ? 'selected ':'') . - " value='0'>midnight</option>\n"; + $result .= "<option " . ($date->hour == 0 ? 'selected="selected" ':'') . + " value='0'>" . &mt('midnight') . "</option>\n"; for ($i = 1; $i < 12; $i++) { if ($date->hour == $i) { - $result .= "<option selected value='$i'>$i a.m.</option>\n"; + $result .= "<option selected='selected' value='$i'>$i $am</option>\n"; } else { - $result .= "<option value='$i'>$i a.m</option>\n"; + $result .= "<option value='$i'>$i $am</option>\n"; } } - $result .= "<option " . ($date->hour == 12 ? 'selected ':'') . - " value='12'>noon</option>\n"; + $result .= "<option " . ($date->hour == 12 ? 'selected="selected" ':'') . + " value='12'>" . &mt('noon') . "</option>\n"; for ($i = 13; $i < 24; $i++) { my $printedHour = $i - 12; if ($date->hour == $i) { - $result .= "<option selected value='$i'>$printedHour p.m.</option>\n"; + $result .= "<option selected='selected' value='$i'>$printedHour $pm</option>\n"; } else { - $result .= "<option value='$i'>$printedHour p.m.</option>\n"; + $result .= "<option value='$i'>$printedHour $pm</option>\n"; } } @@ -1598,7 +1636,7 @@ sub render { $printedMinute = "0" . $printedMinute; } if ($date->min == $i) { - $result .= "<option selected>"; + $result .= "<option selected='selected'>"; } else { $result .= "<option>"; } @@ -1614,27 +1652,36 @@ sub render { sub postprocess { my $self = shift; my $var = $self->{'variable'}; - my $month = $ENV{'form.' . $var . 'month'}; - my $day = $ENV{'form.' . $var . 'day'}; - my $year = $ENV{'form.' . $var . 'year'}; + my $month = $env{'form.' . $var . 'month'}; + my $day = $env{'form.' . $var . 'day'}; + my $year = $env{'form.' . $var . 'year'}; my $min = 0; my $hour = 0; if ($self->{'hoursminutes'}) { - $min = $ENV{'form.' . $var . 'minute'}; - $hour = $ENV{'form.' . $var . 'hour'}; + $min = $env{'form.' . $var . 'minute'}; + $hour = $env{'form.' . $var . 'hour'}; } - my $chosenDate = Time::Local::timelocal(0, $min, $hour, $day, $month, $year); + my $chosenDate; + eval {$chosenDate = Time::Local::timelocal(0, $min, $hour, $day, $month, $year);}; + my $error = $@; + # Check to make sure that the date was not automatically co-erced into a # valid date, as we want to flag that as an error # This happens for "Feb. 31", for instance, which is coerced to March 2 or - # 3, depending on if it's a leapyear + # 3, depending on if it's a leap year my $checkDate = localtime($chosenDate); - if ($checkDate->mon != $month || $checkDate->mday != $day || + if ($error || $checkDate->mon != $month || $checkDate->mday != $day || $checkDate->year + 1900 != $year) { + unless (Apache::lonlocal::current_language()== ~/^en/) { + $self->{ERROR_MSG} = &mt("Invalid date entry"); + return 0; + } + # LOCALIZATION FIXME: Needs to be parameterized $self->{ERROR_MSG} = "Can't use " . $months[$month] . " $day, $year as a " . "date because it doesn't exist. Please enter a valid date."; + return 0; } @@ -1670,7 +1717,9 @@ to false. The "suppressEmptySequences" a suppressEmptySequences argument to the render routine, which will cause folders that have all of their contained resources filtered out to also be filtered out. The 'addstatus' attribute, if true, will add the icon -and long status display columns to the display. +and long status display columns to the display. The 'addparts' +attribute will add in a part selector beside problems that have more +than 1 part. =head3 SUB-TAGS @@ -1710,12 +1759,13 @@ and long status display columns to the d no strict; @ISA = ("Apache::lonhelper::element"); use strict; +use Apache::lonnet; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::resource', ('resource', 'filterfunc', 'choicefunc', 'valuefunc', - 'mapurl')); + 'mapurl','option')); } sub new { @@ -1737,6 +1787,11 @@ sub start_resource { $paramHash->{'suppressEmptySequences'} = $token->[2]{'suppressEmptySequences'}; $paramHash->{'toponly'} = $token->[2]{'toponly'}; $paramHash->{'addstatus'} = $token->[2]{'addstatus'}; + $paramHash->{'addparts'} = $token->[2]{'addparts'}; + if ($paramHash->{'addparts'}) { + $helper->declareVar($paramHash->{'variable'}.'_part'); + } + $paramHash->{'closeallpages'} = $token->[2]{'closeallpages'}; return ''; } @@ -1819,6 +1874,42 @@ sub start_mapurl { sub end_mapurl { return ''; } + +sub start_option { + my ($target,$token,$tagstack,$parstack,$parser,$safeeval,$style)=@_; + if (!defined($paramHash->{OPTION_TEXTS})) { + $paramHash->{OPTION_TEXTS} = [ ]; + $paramHash->{OPTION_VARS} = [ ]; + + } + # OPTION_TEXTS is a list of the text attribute + # values used to create column headings. + # OPTION_VARS is a list of the variable names, used to create the checkbox + # inputs. + # We're ok with empty elements. as place holders + # Although the 'variable' element should really exist. + # + + my $option_texts = $paramHash->{OPTION_TEXTS}; + my $option_vars = $paramHash->{OPTION_VARS}; + push(@$option_texts, $token->[2]{'text'}); + push(@$option_vars, $token->[2]{'variable'}); + + # Need to create and declare the option variables as well to make them + # persistent. + # + my $varname = $token->[2]{'variable'}; + $helper->declareVar($varname); + + + return ''; +} + +sub end_option { + my ($target,$token,$tagstack,$parstack,$parser,$safeeval,$style)=@_; + return ''; +} + # A note, in case I don't get to this before I leave. # If someone complains about the "Back" button returning them # to the previous folder state, instead of returning them to @@ -1841,7 +1932,8 @@ sub render { if ($self->{'multichoice'}) { $result = <<SCRIPT; -<script> +<script type="text/javascript"> +// <!-- function checkall(value, checkName) { for (i=0; i<document.forms.helpform.elements.length; i++) { ele = document.forms.helpform.elements[i]; @@ -1850,12 +1942,17 @@ sub render { } } } +// --> </script> SCRIPT + my %lt=&Apache::lonlocal::texthash( + 'sar' => "Select All Resources", + 'uar' => "Unselect All Resources"); + $buttons = <<BUTTONS; <br /> -<input type="button" onclick="checkall(true, '$var')" value="Select All Resources" /> -<input type="button" onclick="checkall(false, '$var')" value="Unselect All Resources" /> +<input type="button" onclick="checkall(true, '$var')" value="$lt{'sar'}" /> +<input type="button" onclick="checkall(false, '$var')" value="$lt{'uar'}" /> <br /> BUTTONS } @@ -1866,14 +1963,18 @@ BUTTONS $result .= $buttons; - my $filterFunc = $self->{FILTER_FUNC}; - my $choiceFunc = $self->{CHOICE_FUNC}; - my $valueFunc = $self->{VALUE_FUNC}; - my $multichoice = $self->{'multichoice'}; + my $filterFunc = $self->{FILTER_FUNC}; + my $choiceFunc = $self->{CHOICE_FUNC}; + my $valueFunc = $self->{VALUE_FUNC}; + my $multichoice = $self->{'multichoice'}; + my $option_vars = $self->{OPTION_VARS}; + my $option_texts = $self->{OPTION_TEXTS}; + my $addparts = $self->{'addparts'}; + my $headings_done = 0; # Evaluate the map url as needed my $mapUrl; - if ($self->{EVALUATE_MAP_URL}) { + if ($self->{EVAL_MAP_URL}) { my $mapUrlFunc = eval('sub { my $helper = shift; my $state = shift; ' . $self->{MAP_URL} . '}'); $mapUrl = &$mapUrlFunc($helper, $self); @@ -1881,38 +1982,110 @@ BUTTONS $mapUrl = $self->{MAP_URL}; } + # Create the composite function that renders the column on the nav map # have to admit any language that lets me do this can't be all bad # - Jeremy (Pythonista) ;-) my $checked = 0; my $renderColFunc = sub { my ($resource, $part, $params) = @_; + my $result = ""; + + if(!$headings_done) { + if ($option_texts) { + foreach my $text (@$option_texts) { + $result .= "<th>$text</th>"; + } + } + $result .= "<th>Select</th>"; + $result .= "</tr><tr>"; # Close off the extra row and start a new one. + $headings_done = 1; + } my $inputType; if ($multichoice) { $inputType = 'checkbox'; } else {$inputType = 'radio'; } if (!&$choiceFunc($resource)) { - return '<td> </td>'; + $result .= '<td> </td>'; + return $result; } else { - my $col = "<td><input type='$inputType' name='${var}.forminput' "; + my $col = ""; + my $raw_name = &$valueFunc($resource); + my $resource_name = + HTML::Entities::encode($raw_name,"<>&\"'"); + if($option_vars) { + foreach my $option_var (@$option_vars) { + my $var_value = "\|\|\|" . $helper->{VARS}->{$option_var} . + "\|\|\|"; + my $checked =""; + if($var_value =~ /\Q|||$raw_name|||\E/) { + $checked = "checked='checked'"; + } + $col .= + "<td align='center'><input type='checkbox' name ='$option_var". + ".forminput' value='". + $resource_name . "' $checked /> </td>"; + } + } + + $col .= "<td align='center'><input type='$inputType' name='${var}.forminput' "; if (!$checked && !$multichoice) { - $col .= "checked "; + $col .= "checked='checked' "; $checked = 1; } if ($multichoice) { # all resources start checked; see bug 1174 - $col .= "checked "; + $col .= "checked='checked' "; $checked = 1; } - $col .= "value='" . - HTML::Entities::encode(&$valueFunc($resource)) - . "' /></td>"; - return $col; + $col .= "value='" . $resource_name . "' /></td>"; + + return $result.$col; } }; + my $renderPartsFunc = sub { + my ($resource, $part, $params) = @_; + my $col= "<td>"; + my $id=$resource->{ID}; + my $resource_name = + &HTML::Entities::encode(&$valueFunc($resource),"<>&\"'"); + if ($addparts && (scalar(@{$resource->parts}) > 1)) { + $col .= "<select onclick=\"javascript:updateRadio(this.form,'${var}.forminput','$resource_name');updateHidden(this.form,'$id','${var}');\" name='part_$id.forminput'>\n"; + $col .= "<option value=\"$part\">All Parts</option>\n"; + foreach my $part (@{$resource->parts}) { + $col .= "<option value=\"$part\">Part: $part</option>\n"; + } + $col .= "</select>"; + } + $col .= "</td>"; + }; + $result.=(<<RADIO); +<script type="text/javascript"> +// <!-- + function updateRadio(form,name,value) { + var radiobutton=form[name]; + for (var i=0; i<radiobutton.length; i++) { + if (radiobutton[i].value == value) { + radiobutton[i].checked = true; + break; + } + } + } + function updateHidden(form,id,name) { + var select=form['part_'+id+'.forminput']; + var hidden=form[name+'_part.forminput']; + var which=select.selectedIndex; + hidden.value=select.options[which].value; + } +// --> +</script> +<input type="hidden" name="${var}_part.forminput" /> - $ENV{'form.condition'} = !$self->{'toponly'}; - my $cols = [$renderColFunc, Apache::lonnavmaps::resource()]; +RADIO + $env{'form.condition'} = !$self->{'toponly'}; + my $cols = [$renderColFunc]; + if ($self->{'addparts'}) { push(@$cols, $renderPartsFunc); } + push(@$cols, Apache::lonnavmaps::resource()); if ($self->{'addstatus'}) { push @$cols, (Apache::lonnavmaps::part_status_summary()); @@ -1922,6 +2095,7 @@ BUTTONS 'showParts' => 0, 'filterFunc' => $filterFunc, 'resource_no_folder_link' => 1, + 'closeAllPages' => $self->{'closeallpages'}, 'suppressEmptySequences' => $self->{'suppressEmptySequences'}, 'iterator_map' => $mapUrl } ); @@ -1987,8 +2161,8 @@ shown. Defaults to false. no strict; @ISA = ("Apache::lonhelper::element"); use strict; - - +use Apache::lonlocal; +use Apache::lonnet; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::student', @@ -2011,7 +2185,7 @@ sub start_student { $helper->declareVar($paramHash->{'variable'}); $paramHash->{'multichoice'} = $token->[2]{'multichoice'}; $paramHash->{'coursepersonnel'} = $token->[2]{'coursepersonnel'}; - $paramHash->{'sctiveonly'} = $token->[2]{'activeonly'}; + $paramHash->{'activeonly'} = $token->[2]{'activeonly'}; if (defined($token->[2]{'nextstate'})) { $paramHash->{NEXTSTATE} = $token->[2]{'nextstate'}; } @@ -2035,7 +2209,8 @@ sub render { if ($self->{'multichoice'}) { $result = <<SCRIPT; -<script> +<script type="text/javascript"> +// <!-- function checkall(value, checkName) { for (i=0; i<document.forms.helpform.elements.length; i++) { ele = document.forms.helpform.elements[i]; @@ -2044,12 +2219,63 @@ sub render { } } } + function checksec(value) { + for (i=0; i<document.forms.helpform.elements.length; i++) { + comp = document.forms.helpform.elements.chksec.value; + if (document.forms.helpform.elements[i].value.indexOf(':'+comp+':') != -1) { + if (document.forms.helpform.elements[i].value.indexOf(':Active') != -1) { + document.forms.helpform.elements[i].checked=value; + } + } + } + } + function checkactive() { + for (i=0; i<document.forms.helpform.elements.length; i++) { + if (document.forms.helpform.elements[i].value.indexOf(':Active') != -1) { + document.forms.helpform.elements[i].checked=true; + } + } + } + function uncheckexpired() { + for (i=0; i<document.forms.helpform.elements.length; i++) { + if (document.forms.helpform.elements[i].value.indexOf(':Expired') != -1) { + document.forms.helpform.elements[i].checked=false; + } + } + } +// --> </script> SCRIPT + + my %lt=&Apache::lonlocal::texthash( + 'ocs' => "Select Only Current Students", + 'ues' => "Unselect Expired Students", + 'sas' => "Select All Students", + 'uas' => "Unselect All Students", + 'sfsg' => "Select Current Students for Section/Group", + 'ufsg' => "Unselect for Section/Group"); + $buttons = <<BUTTONS; <br /> -<input type="button" onclick="checkall(true, '$var')" value="Select All Students" /> -<input type="button" onclick="checkall(false, '$var')" value="Unselect All Students" /> +<table> + <tr> + + <td><input type="button" onclick="checkactive()" value="$lt{'ocs'}" /></td> + <td><input type="button" onclick="uncheckexpired()" value="$lt{'ues'}" /><br /></td> + </tr> + <tr> + <td><input type="button" onclick="checkall(true, '$var')" value="$lt{'sas'}" /></td> + <td> <input type="button" onclick="checkall(false, '$var')" value="$lt{'uas'}" /><br /></td> + </tr> + <tr> + <td><input type="button" onclick="checksec(true)" value="$lt{'sfsg'}"></td> + <td><input type="text" size="5" name="chksec"> </td> + </tr> + <tr> + <td><input type="button" onclick="checksec(false)" value="$lt{'ufsg'}"></td> + <td></td> + </tr> +</table> <br /> BUTTONS } @@ -2103,17 +2329,20 @@ BUTTONS if (!$self->{'activeonly'} || $classlist->{$_}->[$status] eq 'Active') { push @$choices, [$_, $classlist->{$_}->[$fullname], - $classlist->{$_}->[$section], 'Student']; + $classlist->{$_}->[$section], + $classlist->{$_}->[$status], 'Student']; } } - my $name = $self->{'coursepersonnel'} ? 'Name' : 'Student Name'; + my $name = $self->{'coursepersonnel'} ? &mt('Name') : &mt('Student Name'); my $type = 'radio'; if ($self->{'multichoice'}) { $type = 'checkbox'; } $result .= "<table cellspacing='2' cellpadding='2' border='0'>\n"; $result .= "<tr><td></td><td align='center'><b>$name</b></td>". - "<td align='center'><b>Section</b></td>" . - "<td align='center'><b>Role</b></td></tr>"; + "<td align='center'><b>" . &mt('Section') . "</b></td>" . + "<td align='center'><b>".&mt('Status')."</b></td>" . + "<td align='center'><b>" . &mt("Role") . "</b></td>" . + "<td align='center'><b>".&mt('Username').":".&mt('Domain')."</b></td></tr>"; my $checked = 0; for my $choice (@$choices) { @@ -2121,17 +2350,25 @@ BUTTONS $self->{'variable'} . '.forminput' . "'"; if (!$self->{'multichoice'} && !$checked) { - $result .= " checked "; + $result .= " checked='checked' "; $checked = 1; } $result .= - " value='" . HTML::Entities::encode($choice->[0] . ':' . $choice->[2]) + " value='" . HTML::Entities::encode($choice->[0] . ':' + .$choice->[2] . ':' + .$choice->[1] . ':' + .$choice->[3], "<>&\"'") . "' /></td><td>" - . HTML::Entities::encode($choice->[1]) + . HTML::Entities::encode($choice->[1],'<>&"') . "</td><td align='center'>" - . HTML::Entities::encode($choice->[2]) + . HTML::Entities::encode($choice->[2],'<>&"') + . "</td>\n<td>" + . HTML::Entities::encode($choice->[3],'<>&"') + . "</td>\n<td>" + . HTML::Entities::encode($choice->[4],'<>&"') . "</td>\n<td>" - . HTML::Entities::encode($choice->[3]) . "</td></tr>\n"; + . HTML::Entities::encode($choice->[0],'<>&"') + . "</td></tr>\n"; } $result .= "</table>\n\n"; @@ -2143,10 +2380,10 @@ BUTTONS sub postprocess { my $self = shift; - my $result = $ENV{'form.' . $self->{'variable'} . '.forminput'}; + my $result = $env{'form.' . $self->{'variable'} . '.forminput'}; if (!$result) { - $self->{ERROR_MSG} = 'You must choose at least one student '. - 'to continue.'; + $self->{ERROR_MSG} = + &mt('You must choose at least one student to continue.'); return 0; } @@ -2212,7 +2449,8 @@ viewing the files. no strict; @ISA = ("Apache::lonhelper::element"); use strict; - +use Apache::lonlocal; +use Apache::lonnet; use Apache::lonpubdir; # for getTitleString BEGIN { @@ -2287,6 +2525,13 @@ sub start_filefilter { sub end_filefilter { return ''; } +{ + # used to generate unique id attributes for <input> tags. + # internal use only. + my $id=0; + sub new_id { return $id++;} +} + sub render { my $self = shift; my $result = ''; @@ -2310,7 +2555,8 @@ sub render { if ($self->{'multichoice'}) { $result = <<SCRIPT; -<script> +<script type="text/javascript"> +// <!-- function checkall(value, checkName) { for (i=0; i<document.forms.helpform.elements.length; i++) { ele = document.forms.helpform.elements[i]; @@ -2328,18 +2574,25 @@ sub render { } } } +// --> </script> SCRIPT - $buttons = <<BUTTONS; + my %lt=&Apache::lonlocal::texthash( + 'saf' => "Select All Files", + 'uaf' => "Unselect All Files"); + $buttons = <<BUTTONS; <br /> -<input type="button" onclick="checkall(true, '$var')" value="Select All Files" /> -<input type="button" onclick="checkall(false, '$var')" value="Unselect All Files" /> +<input type="button" onclick="checkall(true, '$var')" value="$lt{'saf'}" /> +<input type="button" onclick="checkall(false, '$var')" value="$lt{'uaf'}" /> BUTTONS + %lt=&Apache::lonlocal::texthash( + 'sap' => "Select All Published", + 'uap' => "Unselect All Published"); if ($helper->{VARS}->{'construction'}) { - $buttons .= <<BUTTONS; -<input type="button" onclick="checkallclass(true, 'Published')" value="Select All Published" /> -<input type="button" onclick="checkallclass(false, 'Published')" value="Unselect All Published" /> + $buttons .= <<BUTTONS; +<input type="button" onclick="checkallclass(true, 'Published')" value="$lt{'sap'}" /> +<input type="button" onclick="checkallclass(false, 'Published')" value="$lt{'uap'}" /> <br /> BUTTONS } @@ -2351,23 +2604,25 @@ BUTTONS # If the subdirectory is in local CSTR space my $metadir; if ($subdir =~ m|/home/([^/]+)/public_html/(.*)|) { - my $user = $1; - my $domain = $Apache::lonnet::perlvar{'lonDefDomain'}; + my ($user,$domain)= + &Apache::loncacc::constructaccess($subdir, + $Apache::lonnet::perlvar{'lonDefDomain'}); $metadir='/res/'.$domain.'/'.$user.'/'.$2; @fileList = &Apache::lonnet::dirlist($subdir, $domain, $user, ''); } elsif ($subdir =~ m|^~([^/]+)/(.*)$|) { $subdir='/home/'.$1.'/public_html/'.$2; - my $user = $1; - my $domain = $Apache::lonnet::perlvar{'lonDefDomain'}; + my ($user,$domain)= + &Apache::loncacc::constructaccess($subdir, + $Apache::lonnet::perlvar{'lonDefDomain'}); $metadir='/res/'.$domain.'/'.$user.'/'.$2; @fileList = &Apache::lonnet::dirlist($subdir, $domain, $user, ''); } else { # local library server resource space - @fileList = &Apache::lonnet::dirlist($subdir, $ENV{'user.domain'}, $ENV{'user.name'}, ''); + @fileList = &Apache::lonnet::dirlist($subdir, $env{'user.domain'}, $env{'user.name'}, ''); } # Sort the fileList into order - @fileList = sort @fileList; + @fileList = sort {lc($a) cmp lc($b)} @fileList; $result .= $buttons; @@ -2419,14 +2674,16 @@ BUTTONS if ($status eq 'Published' && $helper->{VARS}->{'construction'}) { $onclick = 'onclick="a=1" '; } + my $id = &new_id(); $result .= '<tr><td align="right"' . " bgcolor='$color'>" . "<input $onclick type='$type' name='" . $var - . ".forminput' value='" . HTML::Entities::encode($fileName) . + . ".forminput' ".qq{id="$id"}." value='" . HTML::Entities::encode($fileName,"<>&\"'"). "'"; if (!$self->{'multichoice'} && $choices == 0) { - $result .= ' checked'; + $result .= ' checked="checked"'; } - $result .= "/></td><td bgcolor='$color'>" . $file . "</td>" . + $result .= "/></td><td bgcolor='$color'>". + qq{<label for="$id">}. $file . "</label></td>" . "<td bgcolor='$color'>$title</td>" . "<td bgcolor='$color'>$status</td>" . "</tr>\n"; $choices++; @@ -2454,10 +2711,14 @@ sub fileState { my $constructionSpaceDir = shift; my $file = shift; + my ($uname,$udom)=($env{'user.name'},$env{'user.domain'}); + if ($env{'request.role'}=~/^ca\./) { + (undef,$udom,$uname)=split(/\//,$env{'request.role'}); + } my $docroot = $Apache::lonnet::perlvar{'lonDocRoot'}; my $subdirpart = $constructionSpaceDir; - $subdirpart =~ s/^\/home\/$ENV{'user.name'}\/public_html//; - my $resdir = $docroot . '/res/' . $ENV{'user.domain'} . '/' . $ENV{'user.name'} . + $subdirpart =~ s/^\/home\/$uname\/public_html//; + my $resdir = $docroot . '/res/' . $udom . '/' . $uname . $subdirpart; my @constructionSpaceFileStat = stat($constructionSpaceDir . '/' . $file); @@ -2477,7 +2738,7 @@ sub fileState { sub postprocess { my $self = shift; - my $result = $ENV{'form.' . $self->{'variable'} . '.forminput'}; + my $result = $env{'form.' . $self->{'variable'} . '.forminput'}; if (!$result) { $self->{ERROR_MSG} = 'You must choose at least one file '. 'to continue.'; @@ -2586,6 +2847,7 @@ string honors the validation function, i no strict; @ISA = ("Apache::lonhelper::element"); use strict; +use Apache::lonlocal; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::string', @@ -2629,7 +2891,7 @@ sub render { my $result = ''; if (defined $self->{ERROR_MSG}) { - $result .= '<br /><font color="#FF0000">' . $self->{ERROR_MSG} . '</font><br /><br />'; + $result .= '<p><font color="#FF0000">' . $self->{ERROR_MSG} . '</font></p>'; } $result .= '<input type="string" name="' . $self->{'variable'} . '.forminput"'; @@ -2683,7 +2945,7 @@ package Apache::lonhelper::general; =head2 General-purpose tag: <exec>X<exec, helper tag> The contents of the exec tag are executed as Perl code, B<not> inside a -safe space, so the full range of $ENV and such is available. The code +safe space, so the full range of $env and such is available. The code will be executed as a subroutine wrapped with the following code: "sub { my $helper = shift; my $state = shift;" and @@ -2704,6 +2966,9 @@ be able to call methods on it. =cut +use Apache::lonlocal; +use Apache::lonnet; + BEGIN { &Apache::lonhelper::register('Apache::lonhelper::general', 'exec', 'condition', 'clause', @@ -2825,12 +3090,16 @@ will make a "Finish Helper" button that which is useful for the Course Initialization helper so the users never see the old values taking effect. +If the parameter "restartCourse" is not true a 'Finish' Button will be +presented that takes the user back to whatever was defined as <exitpage> + =cut no strict; @ISA = ("Apache::lonhelper::element"); use strict; - +use Apache::lonlocal; +use Apache::lonnet; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::final', ('final', 'exitpage')); @@ -2915,33 +3184,45 @@ sub render { } if (!@results) { - $result .= ' <li>No changes were made to current settings.</li>'; + $result .= ' <li>' . + &mt('No changes were made to current settings.') . '</li>'; } $result .= '</ul>'; } + my $actionURL = $self->{EXIT_PAGE}; + my $targetURL = ''; + my $finish=&mt('Finish'); if ($self->{'restartCourse'}) { - my $targetURL = '/adm/menu'; - if ($ENV{'course.'.$ENV{'request.course.id'}.'.clonedfrom'}) { + $actionURL = '/adm/roles'; + $targetURL = '/adm/menu'; + if ($env{'course.'.$env{'request.course.id'}.'.url'}=~/^uploaded/) { + $targetURL = '/adm/coursedocs'; + } else { + $targetURL = '/adm/navmaps'; + } + if ($env{'course.'.$env{'request.course.id'}.'.clonedfrom'}) { $targetURL = '/adm/parmset?overview=1'; } - $result .= "<center>\n" . - "<form action='/adm/roles' method='post' target='loncapaclient'>\n" . - "<input type='button' onclick='history.go(-1)' value='<- Previous' />" . - "<input type='hidden' name='orgurl' value='$targetURL' />" . - "<input type='hidden' name='selectrole' value='1' />\n" . - "<input type='hidden' name='" . $ENV{'request.role'} . - "' value='1' />\n<input type='submit' value='Finish Course Initialization' />\n" . - "</form></center>"; + my $finish=&mt('Finish Course Initialization'); } + my $previous = HTML::Entities::encode(&mt("<- Previous"), '<>&"'); + my $next = HTML::Entities::encode(&mt("Next ->"), '<>&"'); + $result .= "<center>\n" . + "<form action='".$actionURL."' method='post' target='loncapaclient'>\n" . + "<input type='button' onclick='history.go(-1)' value='$previous' />" . + "<input type='hidden' name='orgurl' value='$targetURL' />" . + "<input type='hidden' name='selectrole' value='1' />\n" . + "<input type='hidden' name='" . $env{'request.role'} . + "' value='1' />\n<input type='submit' value='" . $finish . "' />\n" . + "</form></center>"; return $result; } sub overrideForm { - my $self = shift; - return $self->{'restartCourse'}; + return 1; } 1; @@ -2956,6 +3237,8 @@ package Apache::lonhelper::parmwizfinal; no strict; @ISA = ('Apache::lonhelper::element'); use strict; +use Apache::lonlocal; +use Apache::lonnet; BEGIN { &Apache::lonhelper::register('Apache::lonhelper::parmwizfinal', @@ -2997,6 +3280,11 @@ sub render { 'answer_date' => "0_answerdate", 'tries' => '0_maxtries', 'weight' => '0_weight' ); + my %realParmName = ('open_date' => "opendate", + 'due_date' => "duedate", + 'answer_date' => "answerdate", + 'tries' => 'maxtries', + 'weight' => 'weight' ); my $affectedResourceId = ""; my $parm_name = $parmTypeHash{$vars->{ACTION_TYPE}}; @@ -3004,11 +3292,17 @@ sub render { my $resourceString; my $symb; my $paramlevel; - + # Print the granularity, depending on the action if ($vars->{GRANULARITY} eq 'whole_course') { - $resourceString .= '<li>for <b>all resources in the course</b></li>'; - $level = 9; # general course, see lonparmset.pm perldoc + $resourceString .= '<li>'.&mt('for <b>all resources in the course</b>').'</li>'; + if ($vars->{TARGETS} eq 'course') { + $level = 11; # general course, see lonparmset.pm perldoc + } elsif ($vars->{TARGETS} eq 'section') { + $level = 6; + } else { + $level = 3; + } $affectedResourceId = "0.0"; $symb = 'a'; $paramlevel = 'general'; @@ -3017,33 +3311,68 @@ sub render { my $res = $navmap->getByMapPc($vars->{RESOURCE_ID}); my $title = $res->compTitle(); $symb = $res->symb(); - $navmap->untieHashes(); - $resourceString .= "<li>for the map named <b>$title</b></li>"; - $level = 8; + $resourceString .= '<li>'.&mt('for the map named [_1]',"<b>$title</b>").'</li>'; + if ($vars->{TARGETS} eq 'course') { + $level = 10; # general course, see lonparmset.pm perldoc + } elsif ($vars->{TARGETS} eq 'section') { + $level = 5; + } else { + $level = 2; + } $affectedResourceId = $vars->{RESOURCE_ID}; $paramlevel = 'map'; } else { my $navmap = Apache::lonnavmaps::navmap->new(); my $res = $navmap->getById($vars->{RESOURCE_ID}); + my $part = $vars->{RESOURCE_ID_part}; + if ($part ne 'All Parts' && $part) { $parm_name=~s/^0/$part/; } else { $part=&mt('All Parts'); } $symb = $res->symb(); my $title = $res->compTitle(); - $navmap->untieHashes(); - $resourceString .= "<li>for the resource named <b>$title</b></li>"; - $level = 7; + $resourceString .= '<li>'.&mt('for the resource named [_1] part [_2]',"<b>$title</b>","<b>$part</b>").'</li>'; + if ($vars->{TARGETS} eq 'course') { + $level = 7; # general course, see lonparmset.pm perldoc + } elsif ($vars->{TARGETS} eq 'section') { + $level = 4; + } else { + $level = 1; + } $affectedResourceId = $vars->{RESOURCE_ID}; $paramlevel = 'full'; } - my $result = "<form name='helpform' method='get' action='/adm/parmset#$affectedResourceId&$parm_name&$level'>\n"; - $result .= '<p>Confirm that this information is correct, then click "Finish Wizard" to complete setting the parameter.<ul>'; + my $result = "<form name='helpform' method='POST' action='/adm/parmset#$affectedResourceId&$parm_name&$level'>\n"; + $result .= "<input type='hidden' name='action' value='settable' />\n"; + $result .= "<input type='hidden' name='dis' value='helper' />\n"; + $result .= "<input type='hidden' name='pscat' value='". + $realParmName{$vars->{ACTION_TYPE}}."' />\n"; + if ($vars->{GRANULARITY} eq 'resource') { + $result .= "<input type='hidden' name='symb' value='". + HTML::Entities::encode($symb,"'<>&\"") . "' />\n"; + } elsif ($vars->{GRANULARITY} eq 'map') { + $result .= "<input type='hidden' name='pschp' value='". + $affectedResourceId."' />\n"; + } + my $part = $vars->{RESOURCE_ID_part}; + if ($part eq 'All Parts' || !$part) { $part=0; } + $result .= "<input type='hidden' name='psprt' value='". + HTML::Entities::encode($part,"'<>&\"") . "' />\n"; + + $result .= '<p>'.&mt('Confirm that this information is correct, then click "Finish Helper" to complete setting the parameter.').'<ul>'; # Print the type of manipulation: - $result .= '<li>Setting the <b>' . $dateTypeHash{$vars->{ACTION_TYPE}} . '</b>'; + my $extra; if ($vars->{ACTION_TYPE} eq 'tries') { - $result .= ' to <b>' . $vars->{TRIES} . '</b>'; + $extra = $vars->{TRIES}; } if ($vars->{ACTION_TYPE} eq 'weight') { - $result .= ' to <b>' . $vars->{WEIGHT} . '</b>'; + $extra = $vars->{WEIGHT}; + } + $result .= "<li>"; + my $what = &mt($dateTypeHash{$vars->{ACTION_TYPE}}); + if ($extra) { + $result .= &mt('Setting the [_1] to [_2]',"<b>$what</b>",$extra); + } else { + $result .= &mt('Setting the [_1]',"<b>$what</b>"); } $result .= "</li>\n"; if ($vars->{ACTION_TYPE} eq 'due_date' || @@ -3065,6 +3394,8 @@ sub render { } elsif ($vars->{ACTION_TYPE} eq 'tries') { $result .= "<input type='hidden' name='pres_value' " . "value='" . $vars->{TRIES} . "' />\n"; + $result .= "<input type='hidden' name='pres_type' " . + "value='int_pos' />\n"; } elsif ($vars->{ACTION_TYPE} eq 'weight') { $result .= "<input type='hidden' name='pres_value' " . "value='" . $vars->{WEIGHT} . "' />\n"; @@ -3074,34 +3405,27 @@ sub render { # Print targets if ($vars->{TARGETS} eq 'course') { - $result .= '<li>for <b>all students in course</b></li>'; + $result .= '<li>'.&mt('for <b>all students in course</b>').'</li>'; } elsif ($vars->{TARGETS} eq 'section') { my $section = $vars->{SECTION_NAME}; - $result .= "<li>for section <b>$section</b></li>"; - $level -= 3; - $result .= "<input type='hidden' name='csec' value='" . - HTML::Entities::encode($section) . "' />\n"; + $result .= '<li>'.&mt('for section [_1]',"<b>$section</b>").'</li>'; + $result .= "<input type='hidden' name='csec' value='" . + HTML::Entities::encode($section,"'<>&\"") . "' />\n"; } else { # FIXME: This is probably wasteful! Store the name! my $classlist = Apache::loncoursedata::get_classlist(); - my $username = $vars->{USER_NAME}; - # Chop off everything after the last colon (section) - $username = substr($username, 0, rindex($username, ':')); - my $name = $classlist->{$username}->[6]; - $result .= "<li>for <b>$name</b></li>"; - $level -= 6; - my ($uname, $udom) = split /:/, $vars->{USER_NAME}; + my ($uname,$udom)=split(':',$vars->{USER_NAME}); + my $name = $classlist->{$uname.':'.$udom}->[6]; + $result .= '<li>'.&mt('for [_1]',"<b>$name</b>").'</li>'; $result .= "<input type='hidden' name='uname' value='". - HTML::Entities::encode($uname) . "' />\n"; + HTML::Entities::encode($uname,"'<>&\"") . "' />\n"; $result .= "<input type='hidden' name='udom' value='". - HTML::Entities::encode($udom) . "' />\n"; + HTML::Entities::encode($udom,"'<>&\"") . "' />\n"; } # Print value if ($vars->{ACTION_TYPE} ne 'tries' && $vars->{ACTION_TYPE} ne 'weight') { - $result .= "<li>to <b>" . ctime($vars->{PARM_DATE}) . "</b> (" . - Apache::lonnavmaps::timeToHumanString($vars->{PARM_DATE}) - . ")</li>\n"; + $result .= '<li>'.&mt('to [_1] ([_2])',"<b>".ctime($vars->{PARM_DATE})."</b>",Apache::lonnavmaps::timeToHumanString($vars->{PARM_DATE}))."</li>\n"; } # print pres_marker @@ -3110,11 +3434,10 @@ sub render { # Make the table appear $result .= "\n<input type='hidden' value='true' name='prevvisit' />"; - $result .= "\n<input type='hidden' value='all' name='pschp' />"; $result .= "\n<input type='hidden' value='$symb' name='pssymb' />"; $result .= "\n<input type='hidden' value='$paramlevel' name='parmlev' />"; - $result .= "<br /><br /><center><input type='submit' value='Finish Helper' /></center></form>\n"; + $result .= "<br /><br /><center><input type='submit' value='".&mt('Finish Helper')."' /></center></form>\n"; return $result; }