menu
[MyWeb.git] / Project.pm
1 # $Id$
2 # Common functions for HTML/XHTML output generation
3 # Copyright (C) 2003 Jan Kratochvil <project-www.jankratochvil.net@jankratochvil.net>
4
5 # This program is free software; you can redistribute it and/or modify
6 # it under the terms of the GNU General Public License as published by
7 # the Free Software Foundation; exactly version 2 of June 1991 is required
8
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 # GNU General Public License for more details.
13
14 # You should have received a copy of the GNU General Public License
15 # along with this program; if not, write to the Free Software
16 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17
18
19 package My::Project;
20 require 5.6.0;  # at least 'use warnings;' but we need some 5.6.0+ modules anyway
21 our $VERSION=do { my @r=(q$Revision$=~/\d+/g); sprintf "%d.".("%03d"x$#r),@r; };
22 our $CVS_ID=q$Id$;
23 use strict;
24 use warnings;
25
26 use My::Web;
27
28 use Exporter;
29 our @EXPORT=qw();
30 our @ISA=qw(My::Web Exporter);
31
32
33 sub ENTRIES     { return top_dir_disk()."/project/CVS/Entries"; }
34 sub ENTRIES_LOG { return top_dir_disk()."/project/CVS/Entries.Log"; }
35
36
37 sub print_project ($)
38 {
39 my($class,$ListItem)=@_;
40
41         print "<h1>".$W->{"title"}."</h1>\n";
42         print $ListItem->{"description"};
43         print "<hr />\n";
44         my @table=(
45                 {"key"=>"summary","text"=>"Summary"},
46                 {"key"=>"license","text"=>"License","format"=>sub ($) {
47                                 my %known=(
48                                                 "PD"=>"Public Domain",
49                                                 "GPL"=>a_href("http://www.gnu.org/licenses/gpl.html","GNU General Public License"),
50                                                 "LGPL"=>a_href("http://www.gnu.org/licenses/lgpl.html","GNU Lesser General Public License"),
51                                                 "com"=>"Commercial"
52                                                 );
53                                 return $known{$_[0]};
54                                 }},
55                 {"key"=>"maintenance","text"=>"State","format"=>sub ($) {
56                                 my %known=(
57                                                 "active"=>"Ready to use. Project is now actively developed.",
58                                                 "ready"=>"Ready to use. Maintained.",
59                                                 "pending"=>"Patch is ready to be applied to the mainstream.",
60                                                 "dead"=>"Dead code, no longer supported.",
61                                                 "merge"=>"Functions belong to existing other project.",
62                                                 "obsolete"=>"Obsoleted.",
63                                                 "update"=>"Package needs updating to recent software.",
64                                                 "accepted"=>"This patch got already integrated by the original package maintainer.",
65                                                 ""=>"",
66                                                 );
67                                 my @r;
68                                 for ($known{($_[0]=~/^([^-]*)-?/)[0] || ""}) {
69                                         push @r,$_ if $_;
70                                         push @r," $'" if $';
71                                         }
72                                 return join(" ",@r);
73                                 }},
74                 {"key"=>"aminet","text"=>a_href('http://www.aminet.net/','Aminet'),"format"=>sub ($) {
75                                 return join(" ",
76                                                 a_href('http://www.aminet.net/'.$_[0].".lha",$_[0].".lha"),
77                                                 "(".a_href('http://www.aminet.net/'.$_[0].".readme","readme").")");
78                                 }},
79                 {"key"=>qr(^download\b),"text"=>sub ($) {
80                                                 $_[0]=~s/^download//;
81                                                 $_[0]=~s/^-/ /;
82                                                 return "Download".$_[0];
83                                                 },
84                                 "format"=>sub ($) {
85                                                 return a_href($_[0],CGI::escapeHTML(File::Basename::basename($_[0])));
86                                                 }},
87                 {"key"=>qr(^link\b),"text"=>sub ($) {
88                                                 $_[0]=~s/^link-//;
89                                                 return $_[0];
90                                                 },
91                                 "format"=>sub ($) {
92                                                 return($_[0]=~/^<a\b/ ? $_[0] : a_href($_[0],CGI::escapeHTML($_[0])));
93                                                 }},
94                 {"key"=>qr(^cvs\b),"text"=>sub ($) {
95                                                 $_[0]=~s/^cvs//;
96                                                 $_[0]=~s/^-/ /;
97                                                 return "CVS".$_[0];
98                                                 },
99                                 "format"=>sub ($$) {
100                                                 my($val,$key)=@_;
101                                                 $key=~s/^cvs//;
102                                                 $key=~s/^-/ /;
103                                                 my $branch="";
104                                                 $branch=$1 if $val=~s/:(.*)//;
105                                                 return join("<br />\n\t\t",
106                                                                 CGI::escapeHTML("cvs -d ".$W->{"pserver"}.":".$W->{"pserver_path"}." -z3"
107                                                                                 ." checkout".(!$branch ? "" : " -r $branch -kk")
108                                                                                 .($val!~m#/# ? "" : " -d ".File::Basename::basename($val))
109                                                                                 ." $val"),
110                                                                 join(" | \n\t\t",
111                                                                                 map({ a_href($_->[1],$_->[0]); }
112                                                                                                 ["ViewCVS CVS repository",$W->{"project_viewcvs"}.$val."/".(!$branch ? "" : '?only_with_tag='.$branch)],
113                                                                                                 ["Download CVS snapshot" ,
114                                                                                                                 $W->{"project_viewcvs"}.$val."/".File::Basename::basename($val).".tar.gz?tarball=1"
115                                                                                                                                 .(!$branch ? "" : '&only_with_tag='.$branch)],
116                                                                                                 ["CVS ChangeLog"         ,top_dir()."/project/ChangeLog.txt.pl?cvs=$val"])));
117                                                 }},
118                 {"key"=>"ownership","text"=>"Ownership"},
119                 {"key"=>"sponsorship","text"=>"Sponsorship"},
120                 {"key"=>"language","text"=>"Programming language","format"=>sub ($) {
121                                 return a_href("http://java.sun.com/",CGI::escapeHTML($_[0]))
122                                                 if $_[0]=~/^Java\b/;
123                                 return a_href("http://www.php.net/",CGI::escapeHTML($_[0]))
124                                                 if $_[0]=~/^PHP\b/;
125                                 return undef();
126                                 }},
127                 );
128
129 sub tableit_func
130 {
131 my($tableit,$val,$key,$ListItem)=@_;
132
133         delete $ListItem->{$key};
134         my $r="";
135         $r.="<tr>";
136                 if ($tableit->{"text"}) {
137                         $r.="<td>";
138                                 $r.=(!ref $_ ? $_ : &{$_}($key)) for ($tableit->{"text"});
139                         $r.="</td>";
140                         }
141                 if ($tableit->{"format"}) {
142                         do { $val=$_ if defined $_; } for (&{$tableit->{"format"}}($val,$key));
143                         }
144                 return join("",map("<tr><td>".$_->[0]."</td><td>".$_->[1]."</td></tr>\n",@$val))
145                                 if ref $val;
146                 $r.="<td>$val</td>";
147         $r.="</tr>\n";
148 }
149
150         print '<table border="0" class="print_project">'."\n";
151                 for my $tableit (@table) {
152                         if (!ref $tableit->{"key"}) {
153                                 print tableit_func($tableit,$ListItem->{$tableit->{"key"}},$tableit->{"key"},$ListItem)
154                                                 if $ListItem->{$tableit->{"key"}};
155                                 }
156                         else {
157                                 for my $key (@{$ListItem->{"keys_array"}}) {
158                                         my $keyregex=$tableit->{"key"};
159                                         next if $key!~/$keyregex/;
160                                         print tableit_func($tableit,$ListItem->{$key},$key,$ListItem);
161                                         }
162                                 }
163                         }
164         print "</table>\n";
165         print vskip;
166 }
167
168 sub project_arr_to_hash (@)
169 {
170 my(@arr)=@_;
171
172         return (
173                         @arr,
174                         "keys_array"=>[ My::Web::arr_keys(@arr) ],
175                         );
176 }
177
178 # $args{"ListItem"}=\%...;
179 sub init_project ($%)
180 {
181 my($class,%args)=@_;
182
183         my $ListItem={ project_arr_to_hash(@{$args{"ListItem"}}) };
184         my $W=$class->init(
185                         "title"=>$ListItem->{"name"}.": ".$ListItem->{"summary"},
186                         %args,
187                         "head_css"=>($args{"head_css"} || "")."
188 table.print_project td { vertical-align: top; }
189 ",
190                         "WebConfig::heading_novskip"=>1,
191                         );
192         $class->heading();
193         print $class->platforms($ListItem->{"platform"});
194         $class->print_project({ %$ListItem });
195         return $W;
196 }
197
198 sub item_hash_read ()
199 {
200         my %dirs;
201         for my $ENTRIES (ENTRIES(),ENTRIES_LOG()) {
202                 local *E;
203                 next if !open E,$ENTRIES;
204                 while (<E>) {
205                         chomp;
206                         do { $dirs{$1}=1; next; } if m#^(?:A )?D/([^/]*)/#;
207                         next if m#^/([^/]*)/# ;
208                         next if /^D$/;
209                         warn "File $ENTRIES contains invalid line \"$_\": $!";
210                         }
211                 close E;
212                 }
213
214         my %item;
215         for my $dir (keys(%dirs)) {
216                 Wrequire "project::${dir}::ListItem";
217                 my $item=eval('\@project::'.$dir.'::ListItem::ListItem');
218                 do { warn "Broken project/$dir/ListItem.pm"; next; } if !defined $item;
219                 $item{$dir}={ My::Project::project_arr_to_hash(@$item) };
220                 }
221         return %item;
222 }
223
224 our @platforms=(
225                 "unixuser"=>"GNU/Linux",
226                 "unixdevel"=>"GNU/Linux Development",
227                 "web"=>"Web",
228                 "amiga"=>"Amiga",
229                 "w32"=>"MS-Windows",
230                 "dos"=>"MS-DOS",
231                 "patch"=>"Patches",
232                 );
233
234 sub views ($$)
235 {
236 my($class,$view_selected)=@_;
237
238         my $view=sub ($$)
239                 {
240                 my($current,$href,$content)=@_;
241
242                         return a_href($href,$content) if $current ne $view_selected;
243                         return "<b>".$content."</b> (current)";
244                 };
245
246         return <<"HERE";
247 <h1>Project List of @{[ a_href 'http://www.jankratochvil.net/','Jan Kratochvil' ]}</h1>
248
249 <ul>
250         <li>@{[ &{$view}('Detailed'     ,top_dir().'/project/','Detailed project listing per platform') ]}</li>
251         <li>@{[ &{$view}('BriefPlatform',top_dir().'/project/List.html.pl?platform=platform',
252                         'Brief project listing per platform') ]}</li>
253         <li>@{[ &{$view}('BriefUnified' ,top_dir().'/project/List.html.pl',
254                         'Unified brief project listing') ]}</li>
255 </ul>
256 @{[ vskip "1ex" ]}
257 HERE
258 }
259
260 sub platforms ($;$)
261 {
262 my($class,$platform_selected)=@_;
263
264         my $r="";
265         $r.='<table border="0" align="center"><tr>'."\n";
266                 $r.='<td>Projects:&nbsp;&nbsp;</td>';
267                 $r.='<td>';
268                         $r.='<table border="1" align="center" style="border-collapse: collapse; border-style: solid;">'."\n";
269                                 $r.='<tr>'."\n";
270                                         my @platforms=@platforms;
271                                         while (@platforms) {
272                                                 my $platform_sym =shift @platforms;
273                                                 my $platform_name=shift @platforms;
274                                                 my $chosen=($platform_selected && $platform_selected eq $platform_sym);
275                                                 $r.='<td style="padding: 5px;">';
276                                                         $r.=a_href((!$platform_selected ? "" : top_dir()."/project/").'#'.$platform_sym,$platform_name,
277                                                                         "attr"=>($chosen
278                                                                                         ? 'style="text-decoration: underline; font-weight: bold;"'
279                                                                                         : 'style="text-decoration: inherit; /* revoke underline */"'));
280                                                 $r.="</td>\n";
281                                                 }
282                                 $r.='</tr>'."\n";
283                         $r.='</table>'."\n";
284                 $r.='</td>'."\n";
285         $r.='</tr></table>'."\n";
286         $r.=vskip "1ex";
287         $r;
288 }
289
290 1;