--- loncom/interface/lonfeedback.pm 2012/01/07 20:01:16 1.328 +++ loncom/interface/lonfeedback.pm 2012/03/16 18:32:47 1.347 @@ -1,7 +1,7 @@ # The LearningOnline Network # Feedback # -# $Id: lonfeedback.pm,v 1.328 2012/01/07 20:01:16 www Exp $ +# $Id: lonfeedback.pm,v 1.347 2012/03/16 18:32:47 raeburn Exp $ # # Copyright Michigan State University Board of Trustees # @@ -82,6 +82,26 @@ sub discussion_visible { return 1; } +sub discussion_vote_available { + my ($status,$symb)=@_; + my $canvote=&Apache::lonnet::EXT('resource.0.discussvote',$symb); + if ((lc($canvote) eq 'yes') || + ((lc($canvote) eq 'notended') && (&discussion_open($status,$symb)))) { + return 1; + } +} + +sub get_realsymb { + my ($symb) = @_; + my $realsymb = $symb; + if ($symb=~/^bulletin___/) { + my $filename=(&Apache::lonnet::decode_symb($symb))[2]; + $filename=~s{^adm/wrapper/}{}; + $realsymb=&Apache::lonnet::symbread($filename); + } + return $realsymb; +} + sub list_discussion { my ($mode,$status,$ressymb,$imsextras,$group)=@_; unless ($ressymb) { $ressymb=&Apache::lonnet::symbread(); } @@ -257,14 +277,15 @@ sub list_discussion { $visit ++; my $seeid; - if (($group ne '') && ($mode eq 'board') && - ($ressymb =~ m|^bulletin___\d+___adm/wrapper/adm/\Q$cdom\E/\Q$cnum\E/\d+/bulletinboard$|)) { - if (&check_group_priv($group,'dgp') eq 'ok') { - $seeid = 1; - } - } else { - $seeid=&Apache::lonnet::allowed('rin',$crs); + if (&Apache::lonnet::allowed('rin',$env{'request.course.id'}.($env{'request.course.sec'}?'/'.$env{'request.course.sec'}:''))) { + $seeid = 1; } + my $seehidden = &can_see_hidden($mode,$ressymb,undef,$group,$cdom,$cnum,$crs); + +# Is voting on discussions available + my $realsymb = &get_realsymb($ressymb); + my $canvote = &discussion_vote_available($status,$realsymb); + my @discussionitems=(); my %shown = (); my @posteridentity=(); @@ -286,7 +307,7 @@ sub list_discussion { $discinfo{$visitkey} = $visit; &Apache::lonnet::put('nohist_'.$cid.'_discuss',\%discinfo,$env{'user.domain'},$env{'user.name'}); - &build_posting_display(\%usernamesort,\%subjectsort,\%namesort,\%notshown,\%newitem,\%dischash,\%shown,\%alldiscussion,\%imsitems,\%imsfiles,\%roleinfo,\@discussionitems,\@replies,\@depth,\@posters,\$maxdepth,\$visible,\$newpostsflag,\$current,$status,$viewgrades,$seeid,$prevread,$sortposts,$encsymb,$readkey,$showunmark,$showonlyunread,$totposters,\@rolefilter,\@sectionpick,\@grouppick,$classgroups,$statusfilter,$toggkey,$outputtarget,\%anonhash,$anoncnt,$group); + &build_posting_display(\%usernamesort,\%subjectsort,\%namesort,\%notshown,\%newitem,\%dischash,\%shown,\%alldiscussion,\%imsitems,\%imsfiles,\%roleinfo,\@discussionitems,\@replies,\@depth,\@posters,\$maxdepth,\$visible,\$newpostsflag,\$current,$status,$viewgrades,$seeid,$seehidden,$canvote,$prevread,$sortposts,$encsymb,$readkey,$showunmark,$showonlyunread,$totposters,\@rolefilter,\@sectionpick,\@grouppick,$classgroups,$statusfilter,$toggkey,$outputtarget,\%anonhash,$anoncnt,$group); my $discussion=''; my $manifestfile; @@ -442,7 +463,7 @@ imscp_v1p1.xsd http://www.imsglobal.org/ "\n".'
';
@@ -830,7 +890,7 @@ sub action_links_bar {
}
$discussion .= &group_args($group);
$discussion .= '">'.&mt('Export').'';
- if (&Apache::lonnet::allowed('rin',$env{'request.course.id'})) {
+ if ($seehidden) {
$discussion .= ' ';
$discussion .='
- + $lt{'note'} -$lt{'title'}: +$lt{'title'}: ENDDISCUSS if ($env{'form.origpage'}) { @@ -937,7 +997,7 @@ ENDDISCUSS } sub build_posting_display { - my ($usernamesort,$subjectsort,$namesort,$notshown,$newitem,$dischash,$shown,$alldiscussion,$imsitems,$imsfiles,$roleinfo,$discussionitems,$replies,$depth,$posters,$maxdepth,$visible,$newpostsflag,$current,$status,$viewgrades,$seeid,$prevread,$sortposts,$ressymb,$readkey,$showunmark,$showonlyunread,$totposters,$rolefilter,$sectionpick,$grouppick,$classgroups,$statusfilter,$toggkey,$outputtarget,$anonhash,$anoncnt,$group) = @_; + my ($usernamesort,$subjectsort,$namesort,$notshown,$newitem,$dischash,$shown,$alldiscussion,$imsitems,$imsfiles,$roleinfo,$discussionitems,$replies,$depth,$posters,$maxdepth,$visible,$newpostsflag,$current,$status,$viewgrades,$seeid,$seehidden,$canvote,$prevread,$sortposts,$ressymb,$readkey,$showunmark,$showonlyunread,$totposters,$rolefilter,$sectionpick,$grouppick,$classgroups,$statusfilter,$toggkey,$outputtarget,$anonhash,$anoncnt,$group) = @_; my @original=(); my @index=(); my $skip_group_check = 0; @@ -947,14 +1007,20 @@ sub build_posting_display { my %contrib=&Apache::lonnet::restore($symb,$env{'request.course.id'}, $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); + my (%likes,%userlikes,%userunlikes,@theselikes,$oneplus,$twoplus,$oneminus,$twominus); + my $thisuser=$env{'user.name'}.':'.$env{'user.domain'}; + if ($seeid || $canvote) { # And these are the likes/unlikes - my %likes=&Apache::lonnet::dump('disclikes', + %likes=&Apache::lonnet::dump('disclikes', $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}, '^'.$symb.':'); - my $thisuser=$env{'user.name'}.':'.$env{'user.domain'}; # Array with likes to figure out averages, etc. - my @theselikes=(); + @theselikes=(); +# Hashes containing likes and unlikes for this user. + %userlikes=(); + %userunlikes=(); + } # Is the user allowed to see the real name behind anonymous postings? my $see_anonymous = &Apache::lonnet::allowed('rin',$env{'request.course.id'}.($env{'request.course.sec'}?'/'.$env{'request.course.sec'}:'')); @@ -988,41 +1054,55 @@ sub build_posting_display { &filter_regexp($rolefilter,$sectionpick,$statusfilter); $rolematch = $roleregexp.':'.$secregexp.':'.$statusregexp; } + if ($seeid || $canvote) { # We need to go through this twice, first to get the likes/dislikes, then to actually build the display - for (my $id=1;$id<=$contrib{'version'};$id++) { - my $idx=$id; - next if ($contrib{$idx.':deleted'}); - next if ($contrib{$idx.':hidden'}); - unless ((($hiddens{$idx}) && (!$seeid)) || ($deletions{$idx}) || (!$contrib{$idx.':message'})) { - push(@theselikes,$likes{$symb.':'.$idx.':likes'}); + for (my $id=1;$id<=$contrib{'version'};$id++) { + my $idx=$id; + next if ($contrib{$idx.':deleted'}); + next if ($contrib{$idx.':hidden'}); + unless ((($hiddens{$idx}) && (!$seehidden)) || ($deletions{$idx}) || (!$contrib{$idx.':message'})) { + if ($likes{$symb.':'.$idx.':likes'} ne '') { + push(@theselikes,$likes{$symb.':'.$idx.':likes'}); + if (ref($likes{$symb.':'.$idx.':likers'}) eq 'HASH') { + if (exists($likes{$symb.':'.$idx.':likers'}{$thisuser})) { + $userlikes{$idx} = 1; + } + } + if (ref($likes{$symb.':'.$idx.':unlikers'}) eq 'HASH') { + if (exists($likes{$symb.':'.$idx.':unlikers'}{$thisuser})) { + $userunlikes{$idx} = 1; + } + } + } + } } - } -# Figure out average likes and standard deviation if there are enough discussions to warrant that - my $ave=0; - my $stddev=10000; - if ($#theselikes>1) { - my $sum=0; - my $num=$#theselikes+1; - foreach my $thislike (@theselikes) { - $sum+=$thislike; - } - $ave=$sum/$num; - my $sumsq=0; - foreach my $thislike (@theselikes) { - $sumsq+=($thislike-$ave)*($thislike-$ave); +# Figure out average likes and standard deviation if there are enough +# discussions to warrant that + my $ave=0; + my $stddev=10000; + if ($#theselikes>1) { + my $sum=0; + my $num=$#theselikes+1; + foreach my $thislike (@theselikes) { + $sum+=$thislike; + } + $ave=$sum/$num; + my $sumsq=0; + foreach my $thislike (@theselikes) { + $sumsq+=($thislike-$ave)*($thislike-$ave); + } + $stddev=sqrt($sumsq/$num); } - $stddev=sqrt($sumsq/$num); - } # Now we know the average likes $ave and the standard deviation $stddev # Get the boundaries for markup - my $oneplus=$ave+$stddev; - my $twoplus=$ave+2.*$stddev; - my $oneminus=$ave-$stddev; - my $twominus=$ave-2.*$stddev; -# &Apache::lonnet::logthis(join(',',@theselikes)." Ave $ave StdDev $stddev $twominus $oneminus $oneplus $twoplus"); + $oneplus=$ave+$stddev; + $twoplus=$ave+2.*$stddev; + $oneminus=$ave-$stddev; + $twominus=$ave-2.*$stddev; + } # # This is now the real loop. Go through all entries, pick up what we need -# +# for (my $id=1;$id<=$contrib{'version'};$id++) { my $idx=$id; next if ($contrib{$idx.':deleted'}); @@ -1057,7 +1137,7 @@ sub build_posting_display { } else { $$replies[$$depth[$idx]]=1; } - unless ((($hiddens{$idx}) && (!$seeid)) || ($deletions{$idx})) { + unless ((($hiddens{$idx}) && (!$seehidden)) || ($deletions{$idx})) { $$visible++; if ($contrib{$idx.':history'}) { if ($contrib{$idx.':history'} =~ /:/) { @@ -1072,7 +1152,7 @@ sub build_posting_display { my %subjects = (); my %attachtxt = (); my %allattachments = (); - my ($screenname,$plainname); + my ($screenname,$plainname,$showaboutme); my $sender = &mt('Anonymous'); # Anonymous users getting number within a discussion # Since idx is in static order, this should give the same sequence every time. @@ -1082,7 +1162,7 @@ sub build_posting_display { $$anonhash{$key}=&mt('Anonymous').' '.$anoncnt; } my ($message,$subject,$vgrlink,$ctlink); - &get_post_contents(\%contrib,$idx,$seeid,$outputtarget,\%messages,\%subjects,\%allattachments,\%attachtxt,$imsfiles,\$screenname,\$plainname,$numoldver); + &get_post_contents(\%contrib,$idx,$seeid,$seehidden,$outputtarget,\%messages,\%subjects,\%allattachments,\%attachtxt,$imsfiles,\$screenname,\$plainname,\$showaboutme,$numoldver); # Set up for sorting by subject @@ -1112,12 +1192,18 @@ sub build_posting_display { } } if (!$contrib{$idx.':anonymous'} || $see_anonymous) { - $sender=&Apache::loncommon::aboutmewrapper( - $plainname, - $contrib{$idx.':sendername'}, - $contrib{$idx.':senderdomain'}).' ('. - $contrib{$idx.':sendername'}.':'. - $contrib{$idx.':senderdomain'}.')'; + if ($showaboutme) { + $sender = &Apache::loncommon::aboutmewrapper( + $plainname, + $contrib{$idx.':sendername'}, + $contrib{$idx.':senderdomain'}); + } else { + $sender = $plainname; + } + if ($see_anonymous) { + $sender .= ' ('.$contrib{$idx.':sendername'}.':'. + $contrib{$idx.':senderdomain'}.')'; + } $sender = ''.$sender.''; if ($contrib{$idx.':anonymous'}) { $sender.=' ['.$$anonhash{$key}.'] '. @@ -1156,30 +1242,24 @@ sub build_posting_display { @{$$namesort{$lastname}{$firstname}} = ("$idx"); } if ($outputtarget ne 'tex') { - unless ($likes{$symb.':'.$idx.':likers'}=~/\,\Q$thisuser\E\,/) { - $sender.=' '.&discussion_link($symb,&mt('Like'),'like',$idx,$$newpostsflag,$prevread,&group_args($group)); - } - unless ($likes{$symb.':'.$idx.':unlikers'}=~/\,\Q$thisuser\E\,/) { - $sender.=' '.&discussion_link($symb,&mt('Unlike'),'unlike',$idx,$$newpostsflag,$prevread,&group_args($group)); - } - my $thislikes=$likes{$symb.':'.$idx.':likes'}; - if ($thislikes>0) { - $sender.=' ('.&mt("[_1] likes",$thislikes).')'; - } elsif ($thislikes<0) { - $sender.=' ('.&mt("[_1] unlikes",abs($thislikes)).')'; +# Add karma stars + my $karma=&userkarma($contrib{$idx.':sendername'},$contrib{$idx.':senderdomain'}); + for (my $i=1;$i<=$karma;$i++) { + $sender.=' ![]() '. "'; + if ($canvote) { +# Put in the like and unlike buttons + if (($uname eq $env{'user.name'}) && ($udom eq $env{'user.domain'})) { + my $novote = &mt('No voting for your own posts'); + $$discussionitems[$idx].= + ''. + ' ![]() ![]() ![]() ![]() ![]() ![]() |