All pastes #1224532 Raw Edit

nickcolor-xchat.pl

public text v1 · immutable
#1224532 ·published 2008-10-10 13:46 UTC
rendered paste body
use strict;
use Irssi 20020101.0250 ();
use vars qw($VERSION %IRSSI); 
$VERSION = "1";
%IRSSI = (
    authors     => "Timo Sirainen, Ian Peters",
    contact     => "tss\@iki.fi", 
    name        => "Nick Color",
    description => "assign a different color for each nick",
    license     => "Public Domain",
    url         => "http://irssi.org/",
    changed     => "2002-03-04T22:47+0100"
);

# hm.. i should make it possible to use the existing one..
Irssi::theme_register([
  'pubmsg_hilight', '{pubmsghinick $0 $3 $1}$2',
  'action_public', '{pubaction $0-}'
]);

my %saved_colors;
my %session_colors = {};
my @colors = qw/ 3 4 6 5 9 10 11 12 13 /;

sub load_colors {
  open COLORS, "$ENV{HOME}/.irssi/saved_colors";

  while (<COLORS>) {
    # I don't know why this is necessary only inside of irssi
    my @lines = split "\n";
    foreach my $line (@lines) {
      my($nick, $color) = split ":", $line;
      $saved_colors{$nick} = $color;
    }
  }

  close COLORS;
}

sub save_colors {
  open COLORS, ">$ENV{HOME}/.irssi/saved_colors";

  foreach my $nick (keys %saved_colors) {
    print COLORS "$nick:$saved_colors{$nick}\n";
  }

  close COLORS;
}

# This gave reasonable distribution values when run across
# /usr/share/dict/words

sub simple_hash {
  my ($string) = @_;
  chomp $string;
  my @chars = split //, $string;
  my $counter = 0;

  foreach my $char (@chars) {
    $counter += ord $char;
  }

  $counter = $colors[$counter % 9];

  return $counter;
}

sub get_color {
  my ($nick) = @_;

  # Has the user assigned this nick a color?
  my $color = $saved_colors{$nick};

  # Have -we- already assigned this nick a color?
  if (!$color) {
    $color = $session_colors{$nick};
  }

  # Let's assign this nick a color
  if (!$color) {
    $color = simple_hash $nick;
    $session_colors{$nick} = $color;
  }

  $color = "0".$color if ($color < 10);
  return $color;
}

# FIXME: breaks /HILIGHT etc.
sub sig_public {
  my ($server, $msg, $nick, $address, $target) = @_;
  my $chanrec = $server->channel_find($target);
  return if not $chanrec;
  my $nickrec = $chanrec->nick_find($nick);
  return if not $nickrec;

  my $color = get_color($nick);

  $server->command('/^format pubmsg {pubmsgnick $2 {pubnick '.chr(3).$color.'$0}}$1');
}

sub sig_own_public {
  my ($server, $msg, $target) = @_;
  my $nick = $server->{nick};
  return if not $nick;
  my $chanrec = $server->channel_find($target);
  return if not $chanrec;
  my $nickrec = $chanrec->nick_find($nick);
  return if not $nickrec;

  my $color = get_color($nick);

  $server->command('/^format own_msg {ownmsgnick $2 {ownnick '.chr(3).$color.'$0}}$1');
}

sub sig_action {
  my ($server, $msg, $nick, $address, $target) = @_;
  my $chanrec = $server->channel_find($target);
  return if not $chanrec;
  my $nickrec = $chanrec->nick_find($nick);
  return if not $nickrec;

  my $color = get_color($nick);

  $server->command('/^format action_public {pubaction '.chr(3).$color.'$0-}');
}

sub sig_own_action {
  my ($server, $msg, $target) = @_;
  my $nick = $server->{nick};
  return if not $nick;
  my $chanrec = $server->channel_find($target);
  return if not $chanrec;
  my $nickrec = $chanrec->nick_find($nick);
  return if not $nickrec;

  my $color = get_color($nick);

  $server->command('/^format own_action {ownaction '.chr(3).$color.'$0}'.chr(3).$color.'$1');
}

sub cmd_color {
  my ($data, $server, $witem) = @_;
  my ($op, $nick, $color) = split " ", $data;

  $op = lc $op;

  if (!$op) {
    Irssi::print ("No operation given");
  } elsif ($op eq "save") {
    save_colors;
  } elsif ($op eq "set") {
    if (!$nick) {
      Irssi::print ("Nick not given");
    } elsif (!$color) {
      Irssi::print ("Color not given");
    } elsif ($color < 2 || $color > 14) {
      Irssi::print ("Color must be between 2 and 14 inclusive");
    } else {
      $saved_colors{$nick} = $color;
    }
  } elsif ($op eq "clear") {
    if (!$nick) {
      Irssi::print ("Nick not given");
    } else {
      delete ($saved_colors{$nick});
    }
  } elsif ($op eq "list") {
    Irssi::print ("\nSaved Colors:");
    foreach my $nick (keys %saved_colors) {
      Irssi::print (chr (3) . "$saved_colors{$nick}$nick" .
                    chr (3) . "1 ($saved_colors{$nick})");
    }
  } elsif ($op eq "preview") {
    Irssi::print ("\nAvailable colors:");
    foreach my $i (2..14) {
      Irssi::print (chr (3) . "$i" . "Color #$i");
    }
  }
}

load_colors;

Irssi::command_bind('color', 'cmd_color');

Irssi::signal_add('message public', 'sig_public');
Irssi::signal_add('message own_public', 'sig_own_public');
Irssi::signal_add('message irc action', 'sig_action');
Irssi::signal_add('message irc own_action', 'sig_own_action');