# !$Id: nicklisthoriz.pl,v 1.8 2008/03/24 22:07:23 cbellot Exp $
# 
# (C)2007 Cyril Bellot
# Some ideas/code from Wouter Coekaerts nicklist plugin.
#
# Outputs nicklist of current window in an irssi window named "nicklist".
#
# Howto ?
# - first create a window in a split view:
#     /window new split
# - name it "nicklist":
#     /window name nicklist
# - You can also resize, stick it:
#     /window size 5
#     /window stick
# - load this plugin:
#     /script load nicklisthoriz
# - and then you are...
#
# Commands:
#     /nicklist update
#     	redraw the nicklist.
#

use Irssi 20020121.2020 ();
use strict;

my $VERSION = "0.1";
my %IRSSI = (
          authors     => 'Cyril Bellot',
          contact     => 'jcpp\@users.sourceforge.net',
          name        => 'nicklisthoriz',
          description => 'Display nicklist in an horizontal frame',
          license     => 'GPL',
          changed     => '$Date: 2008/03/24 22:07:23 $ ',
);

Irssi::command_bind 'nicklist' => sub {
    my ( $data, $server, $item ) = @_;
    $data =~ s/\s+$//g;
    Irssi::command_runsub ('nicklist', $data, $server, $item ) ;
};

Irssi::command_bind('nicklist update',\&refresh_nicklist);

Irssi::signal_add_last('window item changed', \&refresh_nicklist);
Irssi::signal_add_last('window changed', \&refresh_nicklist);
Irssi::signal_add_last('channel wholist', \&refresh_nicklist);
Irssi::signal_add_first('message join', \&refresh_nicklist);
Irssi::signal_add_first('message part', \&refresh_nicklist);
Irssi::signal_add_first('message kick', \&refresh_nicklist);
Irssi::signal_add_first('message quit', \&refresh_nicklist);
Irssi::signal_add_first('message nick', \&refresh_nicklist);
Irssi::signal_add_first('message own_nick', \&refresh_nicklist);
Irssi::signal_add_first('nick mode changed', \&refresh_nicklist);

my ($MODE_OP, $MODE_HALFOP, $MODE_VOICE, $MODE_NORMAL) = (0,1,2,3);
my ($STATUS_NORMAL, $STATUS_JOINING, $STATUS_PARTING, $STATUS_QUITING, 
	$STATUS_KICKED, $STATUS_SPLIT) = (0,1,2,3,4,5);
my @prefix_mode = ('3@', '2%', '7+', '15.');
my @color_mode = ('5', '3', '2', '');


##################################################
sub calc_text {
    my ($nick) = @_; 
    my $tmp = 15;

    (my $text = $nick->{'nick'}) =~ s/^(.{$tmp})..+$/$1~/;
#    $nick->{'text'} = $prefix_mode[$nick->{'mode'}].$text.
#			(' ' x ($tmp-length($nick->{'nick'})-1));
#    $nick->{'text'} = $prefix_mode[$nick->{'mode'}] . $text;
    $nick->{'text'} = $color_mode[$nick->{'mode'}].$text.
			(' ' x ($tmp-length($nick->{'nick'})-1)).'';
    $nick->{'text'} = $color_mode[$nick->{'mode'}] . $text.'';
    $nick->{'cmp'} = $nick->{'mode'}.lc($nick->{'nick'});
}

##################################################
sub refresh_nicklist {
    my @nicklist = ();
    my $nickprint;
    my $channel = Irssi::active_win->{active};
    if (!$channel || (ref($channel) ne 'Irssi::Irc::Channel' 
	    && ref($channel) ne 'Irssi::Silc::Channel') 
	    || $channel->{'type'} ne 'CHANNEL' 
	    || ($channel->{chat_type} ne 'SILC' 
	    && !$channel->{'names_got'}) ) {
	# no nicklist
    } else {
	### make nicklist ###
	foreach my $nick (sort {(($a->{'op'}?'1':$a->{'halfop'}?'2':$a->{'voice'}?'3':'4').lc($a->{'nick'})) cmp (($b->{'op'}?'1':$b->{'halfop'}?'2':$b->{'voice'}?'3':'4').lc($b->{'nick'}))} $channel->nicks()) {
	    my $thisnick = {'nick' => $nick->{'nick'}, 'mode' => ($nick->{'op'}?$MODE_OP:$nick->{'halfop'}?$MODE_HALFOP:$nick->{'voice'}?$MODE_VOICE:$MODE_NORMAL)};
	    calc_text($thisnick);
	    push @nicklist, $thisnick;
	}
    }
    for(my $i=0; $i<=$#nicklist; $i++) {
	$nickprint.= "[".$nicklist[$i]->{'text'}."] ";
    }

    my $nicklistwin = Irssi::window_find_name('nicklist');
    if ($nicklistwin) {
	$nicklistwin->print("");
	$nicklistwin->command("/clear");
	$nicklistwin->print($nickprint);
    }
}

