1#!/usr/local/bin/perl -w 2# 3# Copyright (c) 2002 Victor Ivanov <v0rbiz@yahoo.com> 4# All rights reserved. 5# 6# Redistribution and use in source and binary forms, with or without 7# modification, are permitted provided that the following conditions 8# are met: 9# 1. Redistributions of source code must retain the above copyright 10# notice, this list of conditions and the following disclaimer. 11# 2. Redistributions in binary form must reproduce the above copyright 12# notice, this list of conditions and the following disclaimer in the 13# documentation and/or other materials provided with the distribution. 14# 15# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25# SUCH DAMAGE. 26# 27 28use strict; 29use vars qw($VERSION %IRSSI); 30 31$VERSION = '1.0b3'; 32%IRSSI = ( 33 authors => 'Victor Ivanov', 34 contact => 'v0rbiz@yahoo.com', 35 name => 'romaji', 36 description => 'translates romaji to hiragana or katakana in text enclosed in ^R', 37 license => 'BSD 2-clause', 38 url => 'http://irssi.org/scripts/' 39); 40 41 42my(%hira) = ( 43 "a" => "あ", "i" => "い", "u" => "う", "e" => "え", "o" => "お", 44 "ka" => "か", "ki" => "き", "ku" => "く", "ke" => "け", "ko" => "こ", 45 "sa" => "さ", "shi" => "し", "su" => "す", "se" => "せ", "so" => "そ", 46 "ta" => "た", "chi" => "ち", "tsu" => "つ", "te" => "て", "to" => "と", 47 "na" => "な", "ni" => "に", "nu" => "ぬ", "ne" => "ね", "no" => "の", 48 "ha" => "は", "hi" => "ひ", "hu" => "ふ", "he" => "へ", "ho" => "ほ", "fu" => "ふ", 49 "ma" => "ま", "mi" => "み", "mu" => "む", "me" => "め", "mo" => "も", 50 "ya" => "や", "yu" => "ゆ", "yo" => "よ", 51 "ra" => "ら", "ri" => "り", "ru" => "る", "re" => "れ", "ro" => "ろ", 52 "wa" => "わ", "wi" => "ゐ", "we" => "ゑ", "wo" => "を", 53 "n" => "ん", 54 "m" => "ん", 55 56 "ga" => "が", "gi" => "ぎ", "gu" => "ぐ", "ge" => "げ", "go" => "ご", 57 "za" => "ざ", "ji" => "じ", "zu" => "ず", "ze" => "ぜ", "zo" => "ぞ", 58 "da" => "だ", "dzi" => "ぢ", "dzu" => "づ", "de" => "で", "do" => "ど", 59 "ba" => "ば", "bi" => "び", "bu" => "ぶ", "be" => "べ", "bo" => "ぼ", 60 "pa" => "ぱ", "pi" => "ぴ", "pu" => "ぷ", "pe" => "ぺ", "po" => "ぽ", 61 62 "fa" => "ふぁ", "fi" => "ふぃ", "fe" => "ふぇ", "fo" => "ふぉ", 63 "di" => "でぃ", 64 65 "kya" => "きゃ", "kyu" => "きゅ", "kyo" => "きょ", 66 "sha" => "しゃ", "shu" => "しゅ", "sho" => "しょ", 67 "cha" => "ちゃ", "chu" => "ちゅ", "cho" => "ちょ", 68 "nya" => "にゃ", "nyu" => "にゅ", "nyo" => "にょ", 69 "hya" => "ひゃ", "hyu" => "ひゅ", "hyo" => "ひょ", 70 "mya" => "みゃ", "myu" => "みゅ", "myo" => "みょ", 71 "rya" => "りゃ", "ryu" => "りゅ", "ryo" => "りょ", 72 "gya" => "ぎゃ", "gyu" => "ぎゅ", "gyo" => "ぎょ", 73 "ja" => "じゃ", "ju" => "じゅ", "jo" => "じょ", 74 "jya" => "じゃ", "jyu" => "じゅ", "jyo" => "じょ", 75 "dza" => "ぢゃ", "dju" => "ぢゅ", "dzo" => "ぢょ", 76 "dja" => "ぢゃ", "djo" => "ぢょ", 77 "bya" => "びゃ", "byu" => "びゅ", "byo" => "びょ", 78 "pya" => "ぴゃ", "pyu" => "ぴゅ", "pyo" => "ぴょ", 79 80 "TSU" => "っ" 81); 82 83my(%kata) = ( 84 "a" => "ア", "i" => "イ", "u" => "ウ", "e" => "エ", "o" => "オ", 85 "ka" => "カ", "ki" => "キ", "ku" => "ク", "ke" => "ケ", "ko" => "コ", 86 "sa" => "サ", "shi" => "シ", "su" => "ス", "se" => "セ", "so" => "ソ", 87 "ta" => "タ", "chi" => "チ", "tsu" => "ツ", "te" => "テ", "to" => "ト", 88 "na" => "ナ", "ni" => "ニ", "nu" => "ヌ", "ne" => "ネ", "no" => "ノ", 89 "ha" => "ハ", "hi" => "ヒ", "hu" => "フ", "he" => "ヘ", "ho" => "ホ", "fu" => "フ", 90 "ma" => "マ", "mi" => "ミ", "mu" => "ム", "me" => "メ", "mo" => "モ", 91 "ya" => "ヤ", "yu" => "ユ", "yo" => "ヨ", "ye" => "エ", 92 "ra" => "ラ", "ri" => "リ", "ru" => "ル", "re" => "レ", "ro" => "ロ", 93 "wa" => "ワ", "wi" => "ヰ", "we" => "ヱ", "wo" => "ヲ", 94 "n" => "ン", 95 "m" => "ン", 96 97 "ga" => "ガ", "gi" => "ギ", "gu" => "グ", "ge" => "ゲ", "go" => "ゴ", 98 "za" => "ザ", "ji" => "ジ", "zu" => "ズ", "ze" => "ゼ", "zo" => "ゾ", 99 "da" => "ダ", "dzi" => "ヂ", "dzu" => "ヅ", "de" => "デ", "do" => "ド", 100 "ba" => "バ", "bi" => "ビ", "bu" => "ブ", "be" => "ベ", "bo" => "ボ", 101 "pa" => "パ", "pi" => "ピ", "pu" => "プ", "pe" => "ペ", "po" => "ポ", 102 103 "va" => "ヴァ", "vi" => "ヴィ", "vu" => "ヴ", "ve" => "ヴェ", "vo" => "ヴォ", 104 "fa" => "ファ", "fi" => "フィ", "fe" => "フェ", "fo" => "フォ", 105 "di" => "ディ", 106 107 "dje" => "ヂェ", "dze" => "ヂェ", 108 109 "kya" => "キャ", "kyu" => "キュ", "kyo" => "キョ", 110 "sha" => "シャ", "shu" => "シュ", "sho" => "ショ", 111 "cha" => "チャ", "chu" => "チュ", "cho" => "チョ", 112 "nya" => "ニャ", "nyu" => "ニュ", "nyo" => "ニョ", 113 "hya" => "ヒャ", "hyu" => "ヒュ", "hyo" => "ヒョ", 114 "mya" => "ミャ", "myu" => "ミュ", "myo" => "ミョ", 115 "rya" => "リャ", "ryu" => "リュ", "ryo" => "リョ", 116 "gya" => "ギャ", "gyu" => "ギュ", "gyo" => "ギョ", 117 "ja" => "ジャ", "ju" => "ジュ", "jo" => "ジョ", 118 "jya" => "ジャ", "jyu" => "ジュ", "jyo" => "ジョ", 119 "dza" => "ヂャ", "dju" => "ヂュ", "dzo" => "ヂョ", 120 "dja" => "ヂャ", "djo" => "ヂョ", 121 "bya" => "ビャ", "byu" => "ビュ", "byo" => "ビョ", 122 "pya" => "ピャ", "pyu" => "ピュ", "pyo" => "ピョ", 123 124 "TSU" => "ッ" 125); 126 127my(%comn) = ( 128 "-" => "ー", 129 "." => "。", 130 "," => "、", 131 "!" => "!", 132 "?" => "?", 133 "~" => "〜", 134 " " => " ", 135 "[" => "〔", "]" => "〕", 136 "{" => "【", "}" => "】", 137 "(" => "(", ")" => ")", 138 "0" => "0", "1" => "1", "2" => "2", "3" => "3", "4" => "4", 139 "5" => "5", "6" => "6", "7" => "7", "8" => "8", "9" => "9", 140 "*" => "★", # ☆ is uglier :P 141 # where to put ♪ ? 142); 143 144my(@squot) = ( "「", "」" ); 145my($squoti) = 0; 146my(@dquot) = ( "『", "』" ); 147my($dquoti) = 0; 148 149sub r2hk ($$) { 150 my($str) = ""; 151 my($pos) = 0; 152 my($inlen) = length($_[0]); 153 my($last) = ""; 154 my($href) = $_[1]; 155 my($inp) = lc($_[0]); 156 157 while ($pos < $inlen) { 158 my($len); 159 my($p) = substr($inp, $pos, 3); 160 my($h) = ${$href}{$p}; 161 162 # this could be done with another cycle, but this way's faster i guess 163 if ($h) { 164 $len = 3; 165 } else { 166 $p = substr($inp, $pos, 2); 167 $h = ${$href}{$p}; 168 if ($h) { 169 $len = 2; 170 } else { 171 $p = substr($inp, $pos, 1); 172 $h = ${$href}{$p}; 173 if (!$h) { 174 if ($p eq "'") { 175 $h = $squot[$squoti]; 176 $squoti = 1 - $squoti; 177 } elsif ($p eq "\"") { 178 $h = $dquot[$dquoti]; 179 $dquoti = 1 - $dquoti; 180 } else { 181 $h = $p; 182 } 183 } 184 $len = 1; 185 } 186 } 187 188 if ($h ne $p) { 189 if ($last) { 190 if ($last eq substr($p, 0, 1)) { 191 $str .= ${$href}{"TSU"}; 192 } else { 193 $str .= $last; 194 } 195 $last = ""; 196 } 197 } else { 198 $str .= $last; 199 $last = $p; 200 $h = ""; 201 } 202 203 $str .= $h; 204 205 $pos += $len; 206 } 207 208 $str .= $last; 209 210 return $str; 211} 212 213my($lock_ev) = 0; 214 215sub event1 { 216 my ($line, $server, $witem) = @_; 217 218 return unless ref $witem; 219 if ($lock_ev) { return }; 220 $squoti = 0; 221 $dquoti = 0; 222 223 my ($str) = ""; 224 my (@p) = split(//, $line); 225 my ($i); 226 my ($inside) = 0; 227 my ($empty) = 0; 228 229 for ($i = 0; $i <= $#p; $i++) { 230 if ($inside) { 231 if (!$p[$i]) { 232 $empty++; 233 } else { 234 if ($empty == 0) { 235 $str .= r2hk($p[$i], \%hira); 236 } else { 237 $str .= r2hk($p[$i], \%kata); 238 } 239 $empty = 0; 240 $inside = 0; 241 } 242 } else { 243 $str .= $p[$i]; 244 $inside = 1; 245 } 246 } 247 248 $lock_ev = 1; 249 Irssi::signal_emit('send command', $str, $server, $witem); 250 Irssi::signal_stop(); 251 $lock_ev = 0; 252} 253 254sub cmd_romaji { 255 Irssi::print('%BRomaji (with ひらがな and カタカナ support) version '.$VERSION); 256 Irssi::print('(this is amateur product and comes with %Wno warranty%n, see the source)'); 257 Irssi::print('Text enclosed in Ctrl-Rs (like this) will be converted to hiragana.'); 258 Irssi::print('If the opening ^R is doubled, it will be converted to katakana.'); 259 Irssi::print('Example: genki -> げんき and genki -> ゲンキ'); 260} 261 262Irssi::signal_add('send command', "event1"); 263Irssi::command_bind('romaji', \&cmd_romaji); 264 265Irssi::print('%B'.$IRSSI{name}.' '.$VERSION.'%n loaded; type /romaji for more info'); 266 267# Add the common hash to hiragana and kitakana hashes 268my($k, $v); 269 270while (($k, $v) = each %comn) { 271 $hira{$k} = $v; 272 $kata{$k} = $v; 273} 274