diff options
author | Yorhel <git@yorhel.nl> | 2008-11-11 19:35:06 +0100 |
---|---|---|
committer | Yorhel <git@yorhel.nl> | 2008-11-11 19:35:06 +0100 |
commit | 2f8fe55772047d729439c33a38b14b825afc0e3a (patch) | |
tree | e74f4105b56348406ff2ff67395bdadf55a83094 | |
parent | 80d64fd1a4b2b1ca11dc5050b61883bd41863244 (diff) |
Userlist + generic browsing style added
VNDB::Handler::Users::list will be split up in smaller reusable browse
functions later on, the current code simply serves as a means to determine
what those helper functions are supposed to do.
-rw-r--r-- | lib/VNDB/DB/Users.pm | 31 | ||||
-rw-r--r-- | lib/VNDB/Handler/Users.pm | 103 | ||||
-rw-r--r-- | lib/VNDB/Util/CommonHTML.pm | 2 | ||||
-rw-r--r-- | static/f/style.css | 62 | ||||
m--------- | yawf | 0 |
5 files changed, 194 insertions, 4 deletions
diff --git a/lib/VNDB/DB/Users.pm b/lib/VNDB/DB/Users.pm index 140b8861..4910b564 100644 --- a/lib/VNDB/DB/Users.pm +++ b/lib/VNDB/DB/Users.pm @@ -8,7 +8,7 @@ use Exporter 'import'; our @EXPORT = qw|dbUserGet dbUserEdit dbUserAdd dbUserDel|; -# %options->{ username passwd mail order uid results page } +# %options->{ username passwd mail order uid what results page } sub dbUserGet { my $s = shift; my %o = ( @@ -24,6 +24,10 @@ sub dbUserGet { 'username = ?' => $o{username} ) : (), $o{passwd} ? ( 'passwd = decode(?, \'hex\')' => $o{passwd} ) : (), + $o{firstchar} ? ( + 'SUBSTRING(username from 1 for 1) = ?' => $o{firstchar} ) : (), + !$o{firstchar} && defined $o{firstchar} ? ( + 'ASCII(username) < 97 OR ASCII(username) > 122' => 1 ) : (), $o{mail} ? ( 'mail = ?' => $o{mail} ) : (), $o{uid} ? ( @@ -41,6 +45,31 @@ sub dbUserGet { $o{order} ); + # XXX: cache please... + if($o{what} =~ /list/ && $#$r >= 0) { + my %r = map { + $r->[$_]{votes} = 0; + $r->[$_]{changes} = 0; + ($r->[$_]{id}, $_) + } 0..$#$r; + + $r->[$r{$_->{uid}}]{votes} = $_->{cnt} for (@{$s->dbAll(q| + SELECT uid, COUNT(vid) AS cnt + FROM votes + WHERE uid IN(!l) + GROUP BY uid|, + [ keys %r ] + )}); + + $r->[$r{$_->{requester}}]{changes} = $_->{cnt} for (@{$s->dbAll(q| + SELECT requester, COUNT(id) AS cnt + FROM changes + WHERE requester IN(!l) + GROUP BY requester|, + [ keys %r ] + )}); + } + return wantarray ? ($r, $np) : $r; } diff --git a/lib/VNDB/Handler/Users.pm b/lib/VNDB/Handler/Users.pm index 11e88126..aa61b0a7 100644 --- a/lib/VNDB/Handler/Users.pm +++ b/lib/VNDB/Handler/Users.pm @@ -5,6 +5,7 @@ use strict; use warnings; use YAWF ':html'; use Digest::MD5 'md5_hex'; +use POSIX 'strftime'; YAWF::register( @@ -16,6 +17,7 @@ YAWF::register( qr{u/register} => \®ister, qr{u([1-9]\d*)/edit} => \&edit, qr{u([1-9]\d*)/del(/[od])?} => \&delete, + qr{u/list/(all|[0a-z])} => \&list, ); @@ -308,6 +310,107 @@ sub delete { } +sub list { + my($self, $char) = @_; + + my $f = $self->formValidate( + { name => 's', required => 0, default => 'username', enum => [ qw|username registered| ] }, + { name => 'o', required => 0, default => 'a', enum => [ 'a','d' ] }, + { name => 'p', required => 0, default => 1, template => 'int' }, + ); + return 404 if $f->{_err}; + + $self->htmlHeader(title => 'Browse users'); + + div class => 'mainbox'; + h1 'Browse users'; + p class => 'browseopts'; + for ('all', 'a'..'z', 0) { + a href => "/u/list/$_", $_ eq $char ? (class => 'optselected') : (), $_ ? uc $_ : '#'; + } + end; + end; + + my($list, $np) = $self->dbUserGet( + order => $f->{s}.($f->{o} eq 'a' ? ' ASC' : ' DESC'), + $char ne 'all' ? ( + firstchar => $char ) : (), + results => 50, + page => $f->{p}, + what => 'list', + ); + + if($f->{p} > 1 || $np) { + ul class => 'maintabs notfirst'; + if($f->{p} > 1) { + li class => 'left'; + a href => "/u/list/$char?o=$f->{o}&s=$f->{s}&p=".($f->{p}-1), '<- previous'; + end; + } + if($np) { + li; + a href => "/u/list/$char?o=$f->{o}&s=$f->{s}&p=".($f->{p}+1), 'next ->'; + end; + } + end; + } + + div class => 'mainbox browse'; + table; + thead; + Tr; + td class => 'tc1'; + txt 'Username '; + lit $f->{s} eq 'username' && $f->{o} eq 'a' ? "\x{25B4}" : qq|<a href="/u/list/$char?o=a&s=username">\x{25B4}</a>|; + lit $f->{s} eq 'username' && $f->{o} eq 'd' ? "\x{25BE}" : qq|<a href="/u/list/$char?o=d&s=username">\x{25BE}</a>|; + end; + td class => 'tc2'; + txt 'Registered '; + lit $f->{s} eq 'registered' && $f->{o} eq 'a' ? "\x{25B4}" : qq|<a href="/u/list/$char?o=a&s=registered">\x{25B4}</a>|; + lit $f->{s} eq 'registered' && $f->{o} eq 'd' ? "\x{25BE}" : qq|<a href="/u/list/$char?o=d&s=registered">\x{25BE}</a>|; + end; + td class => 'tc3', 'Votes'; + td class => 'tc4', 'Edits'; + end; + end; + for(0..$#$list) { + my $l = $list->[$_]; + Tr $_ % 2 ? (class => 'odd') : (); + td class => 'tc1'; + a href => '/u'.$l->{id}, $l->{username}; + end; + td class => 'tc2', strftime '%Y-%m-%d', gmtime $l->{registered}; + td class => 'tc3'; + lit !($l->{flags} & $self->{user_flags}{list}) ? '-' : !$l->{votes} ? 0 : + qq|<a href="/u$l->{id}/list">$l->{votes}</a>|; + end; + td class => 'tc4'; + lit !$l->{changes} ? 0 : qq|<a href="/u$l->{id}/hist">$l->{changes}</a>|; + end; + end; + } + end; + end; + + if($f->{p} > 1 || $np) { + ul class => 'maintabs bottom'; + if($f->{p} > 1) { + li class => 'left'; + a href => "/u/list/$char?o=$f->{o}&s=$f->{s}&p=".($f->{p}-1), '<- previous'; + end; + } + if($np) { + li; + a href => "/u/list/$char?o=$f->{o}&s=$f->{s}&p=".($f->{p}+1), 'next ->'; + end; + } + end; + } + + $self->htmlFooter; +} + + 1; diff --git a/lib/VNDB/Util/CommonHTML.pm b/lib/VNDB/Util/CommonHTML.pm index 735a55cd..1f0c3edb 100644 --- a/lib/VNDB/Util/CommonHTML.pm +++ b/lib/VNDB/Util/CommonHTML.pm @@ -50,7 +50,7 @@ sub _menu { [ '/' => 'Home' ], [ '#' => 'Visual Novels' ], [ '#' => 'Producers' ], - [ '#' => 'Users' ], + [ '/u/list/all' => 'Users' ], [ '#' => 'Recent Changes' ], [ '#' => 'Discussion Board' ], [ '#' => 'FAQ' ]) { diff --git a/static/f/style.css b/static/f/style.css index cbeca1f4..d492a4a2 100644 --- a/static/f/style.css +++ b/static/f/style.css @@ -27,7 +27,7 @@ table td { padding: 3px; } table tr.odd { - background-color: #112337; + background: url(/f/boxbg.png) repeat; } #bgright { @@ -124,6 +124,7 @@ td.field label { left: 190px; right: 30px; margin: 0; + padding-bottom: 50px!important; } #maincontent h1, #maincontent h2 { font-family: "Futura", "Century New Gothic", "Arial", Serif; @@ -141,7 +142,7 @@ td.field label { } #maincontent div.mainbox { border: 1px solid #258; - margin: 21px 0 10px 0; + margin: 21px 0 -10px 0; padding: 5px; background: url(/f/boxbg.png) repeat; } @@ -223,6 +224,10 @@ p.center { display: inline; margin: 0; } +#maincontent ul.maintabs.notfirst { + display: block; + height: 20px; +} #maincontent ul.maintabs li { display: inline; list-style-type: none; @@ -237,11 +242,64 @@ p.center { margin: 0 0 0 10px; background-color: #012; } +#maincontent ul.maintabs.notfirst li a { + margin-top: 20px; +} +#maincontent ul.maintabs.bottom li a { + margin-top: 10px; + border-bottom: 1px solid #258; + border-top: none; + padding: 4px 7px 2px 7px; +} +#maincontent ul.maintabs li.left a { + float: left; + margin-left: 0; + margin-right: 10px; +} #maincontent ul.maintabs li.tabselected a, #maincontent ul.maintabs li a:hover { background-color: #0c1925; padding-bottom: 6px; } +#maincontent ul.maintabs.bottom li.tabselected a, +#maincontent ul.maintabs.bottom li a:hover { + padding-bottom: 2px; + padding-top: 5px; + margin-top: 9px; +} + + + + +/***** Browsing ******/ + +p.browseopts { + text-align: center; +} +p.browseopts a { + padding: 1px 3px; + color: #fff!important; + border: 1px solid #258; + margin: 0 2px; +} +p.browseopts a.optselected, p.browseopts a:hover { + border: 0; + padding: 2px 4px; +} +#maincontent div.mainbox.browse { + padding: 0; +} +div.mainbox.browse table { + width: 100%; +} +div.mainbox.browse table td.tc1 { + padding-left: 25px; +} +table thead td { + font-weight: bold; + background-color: #135; + /*background-color: #112337;*/ +} diff --git a/yawf b/yawf -Subproject 5a71f64b9b030235275e8ce574221ec074b040c +Subproject 947a4d87107d77f7e5e15d03e1cebbd294acc93 |