Annotation of loncom/interface/statistics/loncorrectproblemplot.pm, revision 1.1
1.1 ! matthew 1: # The LearningOnline Network with CAPA
! 2: #
! 3: # $Id$
! 4: #
! 5: # Copyright Michigan State University Board of Trustees
! 6: #
! 7: # This file is part of the LearningOnline Network with CAPA (LON-CAPA).
! 8: #
! 9: # LON-CAPA is free software; you can redistribute it and/or modify
! 10: # it under the terms of the GNU General Public License as published by
! 11: # the Free Software Foundation; either version 2 of the License, or
! 12: # (at your option) any later version.
! 13: #
! 14: # LON-CAPA is distributed in the hope that it will be useful,
! 15: # but WITHOUT ANY WARRANTY; without even the implied warranty of
! 16: # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
! 17: # GNU General Public License for more details.
! 18: #
! 19: # You should have received a copy of the GNU General Public License
! 20: # along with LON-CAPA; if not, write to the Free Software
! 21: # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
! 22: #
! 23: # /home/httpd/html/adm/gpl.txt
! 24: #
! 25: # http://www.lon-capa.org/
! 26: #
! 27:
! 28: package Apache::loncorrectproblemplot;
! 29:
! 30: use strict;
! 31: use Apache::lonnet();
! 32: use Apache::loncommon();
! 33: use Apache::lonhtmlcommon();
! 34: use Apache::loncoursedata();
! 35: use Apache::lonstatistics;
! 36: use Apache::lonstathelpers;
! 37: use Apache::lonlocal;
! 38: use HTML::Entities();
! 39: use Time::Local();
! 40: use Spreadsheet::WriteExcel();
! 41:
! 42: my $plotcolors = ['#33ff00',
! 43: '#ff33cc', '#990000', '#aaaa66', '#663399', '#ff9933',
! 44: '#66ccff', '#ff9999', '#cccc33', '#660000', '#33cc66',
! 45: ];
! 46:
! 47: my @SubmitButtons = (
! 48: { name => 'CreatePlot',
! 49: text => 'Create Plot' },
! 50: { name => 'ClearCache',
! 51: text => 'Clear Caches' },
! 52: { name => 'updatecaches',
! 53: text => 'Update Student Data' },
! 54: );
! 55:
! 56: sub BuildCorrectProblemsPage {
! 57: my ($r,$c)=@_;
! 58: #
! 59: my %Saveable_Parameters = ('Status' => 'scalar',
! 60: 'Section' => 'array');
! 61: &Apache::loncommon::store_course_settings('correct_problems_plot',
! 62: \%Saveable_Parameters);
! 63: &Apache::loncommon::restore_course_settings('correct_problems_plot',
! 64: \%Saveable_Parameters);
! 65: #
! 66: &Apache::lonstatistics::PrepareClasslist();
! 67: #
! 68: $r->print('<h2>'.&mt('Number of Correct Problems Plot').'</h2>');
! 69: $r->print(&CreateInterface());
! 70: #
! 71: my @Students = @Apache::lonstatistics::Students;
! 72: #
! 73: if (@Students < 1) {
! 74: $r->print('<h2>'.
! 75: &mt('There are no students in the sections selected').
! 76: '</h2>');
! 77: }
! 78: #
! 79: &Apache::loncoursedata::clear_internal_caches();
! 80: if (exists($ENV{'form.ClearCache'}) ||
! 81: exists($ENV{'form.updatecaches'}) ||
! 82: (exists($ENV{'form.firstanalysis'}) &&
! 83: $ENV{'form.firstanalysis'} ne 'no')) {
! 84: &Apache::lonstatistics::Gather_Full_Student_Data($r);
! 85: }
! 86: if (! exists($ENV{'form.firstanalysis'})) {
! 87: $r->print('<input type="hidden" name="firstanalysis" value="yes" />');
! 88: } else {
! 89: $r->print('<input type="hidden" name="firstanalysis" value="no" />');
! 90: }
! 91: foreach my $button (@SubmitButtons) {
! 92: $r->print('<input type="submit" name="'.$button->{'name'}.'" '.
! 93: 'value="'.&mt($button->{'text'}).'" />');
! 94: $r->print(' 'x5);
! 95: }
! 96: $r->rflush();
! 97: #
! 98: # Determine which problem symbs we are to sum over
! 99: if (exists($ENV{'form.CreatePlot'})) {
! 100: my @ProblemSymbs;
! 101: if ($Apache::lonstatistics::SelectedMaps[0] ne 'all') {
! 102: foreach my $seq (&Apache::lonstatistics::Sequences_with_Assess()){
! 103: foreach my $res (@{$seq->{'contents'}}) {
! 104: next if ($res->{'type'} ne 'assessment');
! 105: foreach my $part (@{$res->{'parts'}}) {
! 106: push(@ProblemSymbs,{symb=>$res->{'symb'},
! 107: part=>$part});
! 108: }
! 109: }
! 110: }
! 111: }
! 112: my $score_data = &Apache::loncoursedata::get_student_scores
! 113: (\@Apache::lonstatistics::SelectedSections,
! 114: \@ProblemSymbs,
! 115: $Apache::lonstatistics::enrollment_status);
! 116: $r->print(&AnalyzeScoreData($score_data));
! 117: }
! 118: return;
! 119: }
! 120:
! 121: #########################################################
! 122: #########################################################
! 123:
! 124: =pod
! 125:
! 126: =item
! 127:
! 128: =cut
! 129:
! 130: #########################################################
! 131: #########################################################
! 132: sub AnalyzeScoreData {
! 133: my ($score_data) = @_;
! 134: #
! 135: # Basic check first
! 136: if (@$score_data < 1) {
! 137: return '<h2>There is no data to plot</h2>';
! 138: }
! 139: #
! 140: # Determine which bins to use
! 141: my $lowest = $score_data->[0]->[0];
! 142: $lowest = 0;
! 143: my $highest = $score_data->[-1]->[0];
! 144: my $binsize = 1;
! 145: if ($highest > 50) { $binsize = 2; }
! 146: if ($highest > 100) { $binsize = 5; }
! 147: if ($highest > 200) { $binsize = 10; }
! 148: if ($highest > 500) { $binsize = 20; }
! 149: if ($highest > 1000) { $binsize = 50; }
! 150: if ($highest > 2000) { $binsize = 100; }
! 151: #
! 152: # Get the data into the bins (destroying $score_data in the process)
! 153: my @Bins = &bin_data($score_data,$binsize,$lowest,$highest);
! 154: my @Xdata; my @Ydata; my $max;
! 155: my $Str = '<table border="1">'."\n".'<tr><th>Range</th><th>Count</th></tr>'."\n";
! 156: while (my $bin = shift(@Bins)) {
! 157: push (@Xdata,$bin->{'start'});
! 158: push (@Ydata,$bin->{'count'});
! 159: if ($bin->{'count'} > $max) {
! 160: $max = $bin->{'count'};
! 161: }
! 162: $Str.= '<tr><td>'.$bin->{'start'}.' - '.$bin->{'end'}.'</td>'.
! 163: '<td>'.$bin->{'count'}.'</td></tr>'."\n";
! 164: }
! 165: my $title = '';
! 166: $Str .= "</table><br />\n";
! 167: $Str = "<br />\n".&Apache::loncommon::DrawBarGraph($title,
! 168: 'Num Correct Problems',
! 169: 'Number of students',
! 170: $max,
! 171: undef, # colors
! 172: \@Xdata,
! 173: \@Ydata).
! 174: "\n<br />\n".$Str;
! 175: return $Str;
! 176: }
! 177:
! 178:
! 179: #########################################################
! 180: #########################################################
! 181:
! 182: =pod
! 183:
! 184: =item &bin_data($data,$binsize,$startbin,$endbin)
! 185:
! 186: Note: This routine destroys the array of data passed to it.
! 187:
! 188: Inputs: $data: array reference - the contents of @$data must
! 189: be arrays with x and y data. $data = [ [x1,y1],[x2,y2],...];
! 190: $binsize: Width of bins to put data in
! 191: $startbin: the starting bin.
! 192: $endbin: the ending bin.
! 193: Returns: Array of Bins. Each bin is a hash reference with the following
! 194: keys: 'start', 'count', and 'end'.
! 195:
! 196: =cut
! 197:
! 198: #########################################################
! 199: #########################################################
! 200: sub bin_data {
! 201: my ($data,$binsize,$startbin,$endbin)=@_;
! 202: return () if (! defined($data) || ref($data) ne 'ARRAY');
! 203: #
! 204: # Determine bin geometry
! 205: my $binstart = $startbin;
! 206: my $binend = $startbin+$binsize;
! 207: # put the data into bins
! 208: my @Bins;
! 209: my $count=0;
! 210: my $idx=0;
! 211: while ($idx < scalar(@$data) && ($binend-$endbin)<$binsize) {
! 212: my $dataset = $data->[$idx++];
! 213: my ($x,$y) = @{$dataset};
! 214: while ($x > $binend) {
! 215: # store the old data
! 216: push (@Bins,{ start => $binstart,
! 217: count => $count,
! 218: end => $binend });
! 219: # start counting again
! 220: $binstart += $binsize;
! 221: $binend += $binsize;
! 222: $count = 0;
! 223: }
! 224: $count+=$y;
! 225: }
! 226: return @Bins;
! 227: }
! 228:
! 229: #########################################################
! 230: #########################################################
! 231:
! 232: =pod
! 233:
! 234: =item
! 235:
! 236: =cut
! 237:
! 238: #########################################################
! 239: #########################################################
! 240: sub CreateInterface {
! 241: ##
! 242: ## Environment variable initialization
! 243: my $Str;
! 244: $Str .= '<table cellspacing="5">'."\n";
! 245: $Str .= '<tr>';
! 246: $Str .= '<td align="center"><b>'.&mt('Sections').'</b></td>';
! 247: $Str .= '<td align="center"><b>'.&mt('Enrollment Status').'</b></td>';
! 248: $Str .= '<td align="center"><b>'.&mt('Sequences and Folders').'</b></td>';
! 249: $Str .= '</tr>'."\n";
! 250: ##
! 251: ##
! 252: $Str .= '<tr><td align="center">'."\n";
! 253: $Str .= &Apache::lonstatistics::SectionSelect('Section','multiple',5);
! 254: $Str .= '</td>';
! 255: #
! 256: $Str .= '<td align="center">';
! 257: $Str .= &Apache::lonhtmlcommon::StatusOptions(undef,undef,5);
! 258: $Str .= '</td><td>'."\n";
! 259: #
! 260: my $only_seq_with_assessments = sub {
! 261: my $s=shift;
! 262: if ($s->{'num_assess'} < 1) {
! 263: return 0;
! 264: } else {
! 265: return 1;
! 266: }
! 267: };
! 268: $Str .= &Apache::lonstatistics::MapSelect('Maps','multiple,all',5,
! 269: $only_seq_with_assessments);
! 270: $Str .= '</td><td>'."\n";
! 271: ##
! 272: $Str .= '</tr>'."\n";
! 273: $Str .= '</table>'."\n";
! 274: return $Str;
! 275: }
! 276:
! 277: 1;
! 278:
! 279: __END__
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>