--- loncom/interface/courseprefs.pm	2025/01/16 16:15:14	1.49.2.28.2.21
+++ loncom/interface/courseprefs.pm	2025/03/15 01:24:03	1.49.2.28.2.22
@@ -1,7 +1,7 @@
 # The LearningOnline Network with CAPA
 # Handler to set configuration settings for a course
 #
-# $Id: courseprefs.pm,v 1.49.2.28.2.21 2025/01/16 16:15:14 raeburn Exp $
+# $Id: courseprefs.pm,v 1.49.2.28.2.22 2025/03/15 01:24:03 raeburn Exp $
 #
 # Copyright Michigan State University Board of Trustees
 #
@@ -1975,10 +1975,14 @@ sub process_ltitools {
             } else {
                 $ltitools{$newid}{'display'}{'target'} = 'iframe';
             }
-            foreach my $item ('passback','roster') {
+            foreach my $item ('passback','roster','returnurl') {
                 if ($env{'form.ltitools_'.$item.'_add'}) {
                     $ltitools{$newid}{$item} = 1;
-                    if ($env{'form.ltitools_'.$item.'valid_add'} ne '') {
+                    if ($item eq 'returnurl') {
+                        if ($env{'form.ltitools_crs'.$item.'_add'}) {
+                            $ltitools{$newid}{'crsconf'}{$item} = 1;
+                        }
+                    } elsif ($env{'form.ltitools_'.$item.'valid_add'} ne '') {
                         my $lifetime = $env{'form.ltitools_'.$item.'valid_add'};
                         $lifetime =~ s/^\s+|\s+$//g;
                         if ($lifetime =~ /^\d+\.?\d*$/) {
@@ -2162,10 +2166,21 @@ sub process_ltitools {
                     } else {
                         $haschanges{$itemid} = 1;
                     }
-                    foreach my $extra ('passback','roster') {
+                    foreach my $extra ('passback','roster','returnurl') {
                         if ($env{'form.ltitools_'.$extra.'_'.$i}) {
                             $ltitools{$itemid}{$extra} = 1;
-                            if ($env{'form.ltitools_'.$extra.'valid_'.$i} ne '') {
+                            if ($extra eq 'returnurl') {
+                                if ($env{'form.ltitools_crs'.$extra.'_'.$i}) {
+                                    $ltitools{$itemid}{'crsconf'}{$extra} = 1;
+                                    if (ref($values->{$itemid}{'crsconf'}) eq 'HASH') {
+                                        if (!$values->{$itemid}{'crsconf'}{$extra}) {
+                                            $haschanges{$itemid} = 1;
+                                        }
+                                    } else {
+                                        $haschanges{$itemid} = 1;
+                                    }
+                                }
+                            } elsif ($env{'form.ltitools_'.$extra.'valid_'.$i} ne '') {
                                 my $lifetime = $env{'form.ltitools_'.$extra.'valid_'.$i};
                                 $lifetime =~ s/^\s+|\s+$//g;
                                 if ($lifetime =~ /^\d+\.?\d*$/) {
@@ -3238,7 +3253,7 @@ sub store_ltitools {
                             }
                         }
                     }
-                    $output .= '<li>'.&mt('Configurable in course:');
+                    $output .= '<li>'.&mt('Configurable in course').':';
                     my @possconfig = ('label','title','target','linktext','explanation','append');
                     my $numconfig = 0;
                     if (ref($changes->{$itemid}{'crsconf'}) eq 'HASH') {
@@ -3253,11 +3268,21 @@ sub store_ltitools {
                         $output .= '&nbsp;'.&mt('None');
                     }
                     $output .= '</li>';
-                    foreach my $item ('passback','roster') {
+                    foreach my $item ('passback','roster','returnurl') {
                         $output .= '<li>'.$lt{$item}.'&nbsp;';
                         if ($changes->{$itemid}{$item}) {
                             $output .= &mt('Yes');
-                            if ($changes->{$itemid}{$item.'valid'}) {
+                            if ($item eq 'returnurl') {
+                                if (ref($changes->{$itemid}{'crsconf'}) eq 'HASH') {
+                                    $output .= ' ['.&mt('Configurable in course').': ';
+                                    if ($changes->{$itemid}{'crsconf'}{$item}) {
+                                        $output .= &mt('Yes'); 
+                                    } else {
+                                        $output .= &mt('No');
+                                    }
+                                    $output .= ']'; 
+                                }
+                            } elsif ($changes->{$itemid}{$item.'valid'}) {
                                 if ($item eq 'passback') {
                                     $output .= ' '.&mt('valid for at least [quant,_1,day] after launch',
                                                        $changes->{$itemid}{$item.'valid'});
@@ -6375,22 +6400,35 @@ sub print_ltitools {
                           '<div class="LC_left_float">'.$lt{'linktext'}.'<br />'.
                           '<input type="text" name="ltitools_linktext_'.$i.'" size="25" value="'.$currdisp{'linktext'}.'" /></div>'.
                           '<div class="LC_left_float">'.$lt{'explanation'}.'<br />'.
-                          '<textarea name="ltitools_explanation_'.$i.'" rows="5" cols="40">'.$currdisp{'explanation'}.
+                          '<textarea name="ltitools_explanation_'.$i.'" rows="5" cols="30">'.$currdisp{'explanation'}.
                           '</textarea></div><div style=""></div><br />';
             my %units = (
                           'passback' => 'days',
                           'roster'   => 'seconds',
                         );
-            foreach my $extra ('passback','roster') {
+            my %courseconfig;
+            if (ref($settings->{$item}) eq 'HASH') {
+                if (ref($settings->{$item}->{'crsconf'}) eq 'HASH') {
+                    %courseconfig = %{$settings->{$item}->{'crsconf'}};
+                }
+            }
+            foreach my $extra ('passback','roster','returnurl') {
                 my $validsty = 'none';
                 my $currvalid;
                 my $checkedon = '';
                 my $checkedoff = ' checked="checked"';
+                my $crscheckedon = '';
+                my $crscheckedoff = ' checked="checked"';
                 if ($settings->{$item}->{$extra}) {
                     $checkedon = $checkedoff;
                     $checkedoff = '';
                     $validsty = 'inline-block';
-                    if ($settings->{$item}->{$extra.'valid'} =~ /^\d+\.?\d*$/) {
+                    if ($extra eq 'returnurl') {
+                        if ($courseconfig{$extra}) {
+                            $crscheckedon = ' checked="checked"';
+                            $crscheckedoff = ''; 
+                        }
+                    } elsif ($settings->{$item}->{$extra.'valid'} =~ /^\d+\.?\d*$/) {
                         $currvalid = $settings->{$item}->{$extra.'valid'};
                     }
                 }
@@ -6399,12 +6437,21 @@ sub print_ltitools {
                               '<label><input type="radio" name="ltitools_'.$extra.'_'.$i.'" value="0"'.$checkedoff.$onclick.' />'.
                               &mt('No').'</label>'.('&nbsp;'x2).
                               '<label><input type="radio" name="ltitools_'.$extra.'_'.$i.'" value="1"'.$checkedon.$onclick.' />'.
-                              &mt('Yes').'</label></span></div>'.
-                              '<div class="LC_floatleft" style="display:'.$validsty.';" id="ltitools_'.$extra.'time_'.$i.'">'.
-                              '<span class="LC_nobreak">'.
-                              &mt("until at least [_1] $units{$extra} after launch",
-                                  '<input type="text" name="ltitools_'.$extra.'valid_'.$i.'" value="'.$currvalid.'" />').
-                              '</span></div><div style="padding:0;clear:both;margin:0;border:0"></div>';
+                              &mt('Yes').'</label></span></div>';
+                if ($extra eq 'returnurl') {
+                    $datatable .= '<div class="LC_floatleft" style="display:'.$validsty.';" id="ltitools_course'.$extra.'_'.$i.'">'.
+                                  '<span class="LC_nobreak"> -- '.&mt('configurable in course').':&nbsp;'.
+                                  '<label><input type="radio" name="ltitools_crs'.$extra.'_'.$i.'" value="0"'.$crscheckedoff.' />'.
+                                  &mt('No').'</label>'.('&nbsp;'x2).
+                                  '<label><input type="radio" name="ltitools_crs'.$extra.'_'.$i.'" value="1"'.$crscheckedon.' />'.
+                                  &mt('Yes').'</label>';
+                } else {
+                    $datatable .= '<div class="LC_floatleft" style="display:'.$validsty.';" id="ltitools_'.$extra.'time_'.$i.'">'.
+                                  '<span class="LC_nobreak">'.
+                                  &mt("until at least [_1] $units{$extra} after launch",
+                                      '<input type="text" name="ltitools_'.$extra.'valid_'.$i.'" value="'.$currvalid.'" />');
+                }
+                $datatable .= '</span></div><div style="padding:0;clear:both;margin:0;border:0"></div>';
             }
             $datatable .= '<span class="LC_nobreak">'.$lt{'icon'}.':&nbsp;';
             if ($imgsrc) {
@@ -6490,14 +6537,8 @@ sub print_ltitools {
                 }
                 $datatable .= '</select></td>';
             }
-            $datatable .= '</tr></table></fieldset>';
-            my %courseconfig;
-            if (ref($settings->{$item}) eq 'HASH') {
-                if (ref($settings->{$item}->{'crsconf'}) eq 'HASH') {
-                    %courseconfig = %{$settings->{$item}->{'crsconf'}};
-                }
-            }
-            $datatable .= '<fieldset><legend>'.&mt('Configurable in course').'</legend><span class="LC_nobreak">';
+            $datatable .= '</tr></table></fieldset>'."\n".
+                          '<fieldset><legend>'.&mt('Configurable in course').'</legend><span class="LC_nobreak">';
             foreach my $item ('label','title','target','linktext','explanation','append') {
                 my $checked;
                 if ($courseconfig{$item}) {
@@ -6518,14 +6559,14 @@ sub print_ltitools {
                                       '<label><input type="checkbox" name="ltitools_customdel_'.$i.'" value="'.
                                       $key.'" />'.&mt('Delete').'</label></span></td><td>'.$key.'</td>'.
                                       '<td><input type="text" name="ltitools_customval_'.$key.'_'.$i.'"'.
-                                      ' value="'.$custom{$key}.'" /></td></tr>';
+                                      ' value="'.$custom{$key}.'" size="35" /></td></tr>';
                     }
                 }
             }
             $datatable .= '<tr><td><span class="LC_nobreak">'.
                           '<label><input type="checkbox" name="ltitools_customadd" value="'.$i.'" />'.
                           &mt('Add').'</label></span></td><td><input type="text" name="ltitools_custom_name_'.$i.'" />'.
-                          '</td><td><input type="text" name="ltitools_custom_value_'.$i.'" /></td></tr>';
+                          '</td><td><input type="text" name="ltitools_custom_value_'.$i.'" size="35" /></td></tr>';
             $datatable .= '</table></fieldset></td></tr>'."\n";
             $itemcount ++;
         }
@@ -6599,18 +6640,27 @@ sub print_ltitools {
                      'passback' => '7',
                      'roster'   => '300',
                    );
-    foreach my $extra ('passback','roster') {
+    foreach my $extra ('passback','roster','returnurl') {
         my $onclick = ' onclick="toggleLTITools(this.form,'."'$extra','add'".');"';
         $datatable .= '<div class="LC_floatleft"><span class="LC_nobreak">'.$lt{$extra}.'&nbsp;'.
                       '<label><input type="radio" name="ltitools_'.$extra.'_add" value="0" checked="checked"'.$onclick.' />'.
                       &mt('No').'</label></span>'.('&nbsp;'x2).'<span class="LC_nobreak">'.
                       '<label><input type="radio" name="ltitools_'.$extra.'_add" value="1"'.$onclick.' />'.
-                      &mt('Yes').'</label></span></div>'.
-                      '<div class="LC_floatleft" style="display:none;" id="ltitools_'.$extra.'time_add">'.
-                      '<span class="LC_nobreak">'.
-                      &mt("until at least [_1] $units{$extra} after launch",
-                          '<input type="text" name="ltitools_'.$extra.'valid_add" value="'.$defaulttimes{$extra}.'" />').
-                      '</span></div><div style="padding:0;clear:both;margin:0;border:0"></div>';
+                      &mt('Yes').'</label></span></div>';
+        if ($extra eq 'returnurl') {
+            $datatable .= '<div class="LC_floatleft" style="display:none;" id="ltitools_course'.$extra.'_add">'.
+                          '<span class="LC_nobreak"> -- '.&mt('configurable in course').':&nbsp;'.
+                          '<label><input type="radio" name="ltitools_crs'.$extra.'_add" value="0" checked="checked" />'.
+                          &mt('No').'</label>'.('&nbsp;'x2).
+                          '<label><input type="radio" name="ltitools_crs'.$extra.'_add" value="1" />'.
+                          &mt('Yes').'</label>';
+        } else {
+            $datatable .= '<div class="LC_floatleft" style="display:none;" id="ltitools_'.$extra.'time_add">'.
+                          '<span class="LC_nobreak">'.
+                          &mt("until at least [_1] $units{$extra} after launch",
+                              '<input type="text" name="ltitools_'.$extra.'valid_add" value="'.$defaulttimes{$extra}.'" />');
+        }
+        $datatable .= '</span></div><div style="padding:0;clear:both;margin:0;border:0"></div>';
     }
     $datatable .= '<span class="LC_nobreak">'.$lt{'icon'}.':&nbsp;'.
                   '('.&mt('if larger than 21x21 pixels, image will be scaled').')&nbsp;';
@@ -6701,6 +6751,7 @@ sub ltitools_names {
                                           'explanation'    => 'Default Explanation',
                                           'passback'       => 'Tool can return grades:',
                                           'roster'         => 'Tool can retrieve roster:',
+                                          'returnurl'      => 'Return URL sent on launch:',
                                           'crstarget'      => 'Display target',
                                           'crslabel'       => 'Course label',
                                           'crstitle'       => 'Course title',